diff options
author | Konstantin Porotchkin <kostap@marvell.com> | 2017-11-22 18:37:51 +0200 |
---|---|---|
committer | Kostya Porotchkin <kostap@marvell.com> | 2017-11-27 13:37:31 +0200 |
commit | 266d129e653030beca02c043bc3afc9f343fc94e (patch) | |
tree | 6767c49db424ff52878e5545cca4ce83bf255095 | |
parent | d35484402b56e572d67a6158c10edeb252869893 (diff) |
marvell: svc: Update the SVC algorithm to v0.8
Add parity check for WP efuse values according to SVC
definition version 0.8
Change-Id: I5221975bbc2ec02cf07b2ca68b5a4f36aa6087a9
Signed-off-by: Konstantin Porotchkin <kostap@marvell.com>
Reviewed-on: http://vgitil04.il.marvell.com:8080/46753
Tested-by: iSoC Platform CI <ykjenk@marvell.com>
Reviewed-by: Ilan Dahan <iland@marvell.com>
Reviewed-by: Neta Zur Hershkovits <neta@marvell.com>
-rw-r--r-- | plat/marvell/a8k/common/plat_ble_setup.c | 35 |
1 files changed, 29 insertions, 6 deletions
diff --git a/plat/marvell/a8k/common/plat_ble_setup.c b/plat/marvell/a8k/common/plat_ble_setup.c index 0511b7b6..cae821c0 100644 --- a/plat/marvell/a8k/common/plat_ble_setup.c +++ b/plat/marvell/a8k/common/plat_ble_setup.c @@ -314,7 +314,7 @@ static void ble_plat_avs_config(void) } /****************************************************************************** - * SVC flow - v0.6 + * SVC flow - v0.8 * The feature is inteded to configure AVS value according to eFuse values * that are burned individually for each SoC during the test process. * Primary AVS value is stored in HD efuse and processed on power on by the HW engine @@ -328,7 +328,7 @@ static void ble_plat_svc_config(void) uint32_t reg_val, avs_workpoint, freq_pidi_mode; uint64_t efuse; uint32_t device_id, single_cluster; - uint8_t svc[4]; + uint8_t svc[4], i, sw_ver; /* Set access to LD0 */ reg_val = mmio_read_32(MVEBU_AP_EFUSE_SRV_CTRL_REG); @@ -345,9 +345,9 @@ static void ble_plat_svc_config(void) * SW version 0 (efuse not programmed) should follow the * regular AVS update flow. */ - reg_val = (efuse >> EFUSE_AP_LD0_SWREV_OFFS) & EFUSE_AP_LD0_SWREV_MASK; - if (reg_val < 1) { - NOTICE("SVC: SW Revision 0x%x. SVC is not supported\n", reg_val); + sw_ver = (efuse >> EFUSE_AP_LD0_SWREV_OFFS) & EFUSE_AP_LD0_SWREV_MASK; + if (sw_ver < 1) { + NOTICE("SVC: SW Revision 0x%x. SVC is not supported\n", sw_ver); ble_plat_avs_config(); return; } @@ -364,7 +364,26 @@ static void ble_plat_svc_config(void) svc[2] = (efuse >> EFUSE_AP_LD0_SVC3_OFFS) & EFUSE_AP_LD0_WP_MASK; svc[3] = (efuse >> EFUSE_AP_LD0_SVC4_OFFS) & EFUSE_AP_LD0_WP_MASK; INFO("SVC: Efuse WP: [0]=0x%x, [1]=0x%x, [2]=0x%x, [3]=0x%x\n", - svc[0], svc[1], svc[2], svc[3]); + svc[0], svc[1], svc[2], svc[3]); + + /* Validate parity of SVC workpoint values */ + for (i = 0; i < 4; i++) { + uint8_t parity, bit; + + for (bit = 1, parity = svc[i] & 1; bit < 7; bit++) + parity ^= (svc[i] >> bit) & 1; + + if (parity != ((svc[i] >> 7) & 1)) { + /* Starting from SW version 2, + * the parity check is mandatory + */ + if (sw_ver > 1) { + ERROR("Failed SVC WP[%d] parity check!\n", i); + ERROR("Ignoring the WP values\n"); + return; + } + } + } single_cluster = mmio_read_32(MVEBU_AP_LD0_220_189_EFUSE_OFFS); single_cluster = (single_cluster >> EFUSE_AP_LD0_CLUSTER_DOWN_OFFS) & 1; @@ -444,6 +463,10 @@ static void ble_plat_svc_config(void) return; } + /* Remove parity bit */ + if (sw_ver > 1) + avs_workpoint &= 0x7F; + reg_val = mmio_read_32(AVS_EN_CTRL_REG); NOTICE("SVC: AVS work point changed from 0x%x to 0x%x\n", (reg_val & AVS_VDD_LOW_LIMIT_MASK) >> AVS_LOW_VDD_LIMIT_OFFSET, |