Message ID | 73355b6d611c32de640d59acc712e5cf3a203e36.1596626630.git.michal.simek@xilinx.com |
---|---|
State | Deferred |
Delegated to: | Tom Rini |
Headers | show |
Series | xilinx: zynqmp: Silicon name cleanup | expand |
Hi, st 5. 8. 2020 v 13:24 odesÃlatel Michal Simek <michal.simek@xilinx.com> napsal: > > From: Ibai Erkiaga <ibai.erkiaga-elorza@xilinx.com> > > Current algorithm used to get the silicon name is bit complicated and > hard to follow. Updated to use more straightforward mechanism based on > the Device ID code table (Table 1-2). The full IDCODE register is used > (except device revision bits [31:28]) to get the device name and IDCODE2 > value is used for identifying the variant. > > Additionally to make the algorithm bit more clear it also save some space > as the devices table is slightly bit smaller. > > Signed-off-by: Ibai Erkiaga <ibai.erkiaga-elorza@xilinx.com> > Signed-off-by: Michal Simek <michal.simek@xilinx.com> > --- > > board/xilinx/zynqmp/zynqmp.c | 299 +++++++++++++++-------------------- > 1 file changed, 126 insertions(+), 173 deletions(-) > > diff --git a/board/xilinx/zynqmp/zynqmp.c b/board/xilinx/zynqmp/zynqmp.c > index 2a430a9e4638..383125087255 100644 > --- a/board/xilinx/zynqmp/zynqmp.c > +++ b/board/xilinx/zynqmp/zynqmp.c > @@ -38,180 +38,123 @@ > > #include "pm_cfg_obj.h" > > +#define ZYNQMP_VERSION_SIZE 7 > +#define EFUSE_VCU_DIS_MASK 0x100 > +#define EFUSE_VCU_DIS_SHIFT 8 > +#define EFUSE_GPU_DIS_MASK 0x20 > +#define EFUSE_GPU_DIS_SHIFT 5 > +#define IDCODE2_PL_INIT_MASK 0x200 > +#define IDCODE2_PL_INIT_SHIFT 9 > + > DECLARE_GLOBAL_DATA_PTR; > > #if defined(CONFIG_FPGA) && defined(CONFIG_FPGA_ZYNQMPPL) && \ > - !defined(CONFIG_SPL_BUILD) > + !defined(CONFIG_SPL_BUILD) || (defined(CONFIG_SPL_FPGA_SUPPORT) && \ > + defined(CONFIG_SPL_BUILD)) > + > static xilinx_desc zynqmppl = XILINX_ZYNQMP_DESC; > > +enum { > + ZYNQMP_VARIANT_EG = BIT(0U), > + ZYNQMP_VARIANT_EV = BIT(1U), > + ZYNQMP_VARIANT_CG = BIT(2U), > + ZYNQMP_VARIANT_DR = BIT(3U), > +}; > + > static const struct { > u32 id; > - u32 ver; > - char *name; > - bool evexists; > + u8 device; > + u8 variants; > } zynqmp_devices[] = { > { > - .id = 0x10, > - .name = "3eg", > - }, > - { > - .id = 0x10, > - .ver = 0x2c, > - .name = "3cg", > - }, > - { > - .id = 0x11, > - .name = "2eg", > - }, > - { > - .id = 0x11, > - .ver = 0x2c, > - .name = "2cg", > - }, > - { > - .id = 0x20, > - .name = "5ev", > - .evexists = 1, > - }, > - { > - .id = 0x20, > - .ver = 0x100, > - .name = "5eg", > - .evexists = 1, > - }, > - { > - .id = 0x20, > - .ver = 0x12c, > - .name = "5cg", > - .evexists = 1, > - }, > - { > - .id = 0x21, > - .name = "4ev", > - .evexists = 1, > - }, > - { > - .id = 0x21, > - .ver = 0x100, > - .name = "4eg", > - .evexists = 1, > - }, > - { > - .id = 0x21, > - .ver = 0x12c, > - .name = "4cg", > - .evexists = 1, > - }, > - { > - .id = 0x30, > - .name = "7ev", > - .evexists = 1, > - }, > - { > - .id = 0x30, > - .ver = 0x100, > - .name = "7eg", > - .evexists = 1, > - }, > - { > - .id = 0x30, > - .ver = 0x12c, > - .name = "7cg", > - .evexists = 1, > - }, > - { > - .id = 0x38, > - .name = "9eg", > - }, > - { > - .id = 0x38, > - .ver = 0x2c, > - .name = "9cg", > + .id = 0x04711093, > + .device = 2, > + .variants = ZYNQMP_VARIANT_EG | ZYNQMP_VARIANT_CG, > }, > { > - .id = 0x39, > - .name = "6eg", > + .id = 0x04710093, > + .device = 3, > + .variants = ZYNQMP_VARIANT_EG | ZYNQMP_VARIANT_CG, > }, > { > - .id = 0x39, > - .ver = 0x2c, > - .name = "6cg", > + .id = 0x04721093, > + .device = 4, > + .variants = ZYNQMP_VARIANT_EG | ZYNQMP_VARIANT_CG | > + ZYNQMP_VARIANT_EV, > }, > { > - .id = 0x40, > - .name = "11eg", > - }, > - { /* For testing purpose only */ > - .id = 0x50, > - .ver = 0x2c, > - .name = "15cg", > + .id = 0x04720093, > + .device = 5, > + .variants = ZYNQMP_VARIANT_EG | ZYNQMP_VARIANT_CG | > + ZYNQMP_VARIANT_EV, > }, > { > - .id = 0x50, > - .name = "15eg", > + .id = 0x04739093, > + .device = 6, > + .variants = ZYNQMP_VARIANT_EG | ZYNQMP_VARIANT_CG, > }, > { > - .id = 0x58, > - .name = "19eg", > + .id = 0x04730093, > + .device = 7, > + .variants = ZYNQMP_VARIANT_EG | ZYNQMP_VARIANT_CG | > + ZYNQMP_VARIANT_EV, > }, > { > - .id = 0x59, > - .name = "17eg", > + .id = 0x04738093, > + .device = 9, > + .variants = ZYNQMP_VARIANT_EG, > }, > { > - .id = 0x61, > - .name = "21dr", > + .id = 0x04740093, > + .device = 11, > + .variants = ZYNQMP_VARIANT_EG, > }, > { > - .id = 0x63, > - .name = "23dr", > + .id = 0x04750093, > + .device = 15, > + .variants = ZYNQMP_VARIANT_EG, > }, > { > - .id = 0x65, > - .name = "25dr", > + .id = 0x04759093, > + .device = 17, > + .variants = ZYNQMP_VARIANT_EG, > }, > { > - .id = 0x64, > - .name = "27dr", > + .id = 0x04758093, > + .device = 19, > + .variants = ZYNQMP_VARIANT_EG, > }, > { > - .id = 0x60, > - .name = "28dr", > + .id = 0x047E1093, > + .device = 21, > + .variants = ZYNQMP_VARIANT_DR, > }, > { > - .id = 0x62, > - .name = "29dr", > + .id = 0x047E5093, > + .device = 25, > + .variants = ZYNQMP_VARIANT_DR, > }, > { > - .id = 0x66, > - .name = "39dr", > + .id = 0x047E4093, > + .device = 27, > + .variants = ZYNQMP_VARIANT_DR, > }, > { > - .id = 0x7b, > - .name = "48dr", > + .id = 0x047E0093, > + .device = 28, > + .variants = ZYNQMP_VARIANT_DR, > }, > { > - .id = 0x7e, > - .name = "49dr", > + .id = 0x047E2093, > + .device = 29, > + .variants = ZYNQMP_VARIANT_DR, > }, > }; > -#endif > - > -#define ZYNQMP_VERSION_SIZE 9 > -#define ZYNQMP_PL_STATUS_BIT 9 > -#define ZYNQMP_IPDIS_VCU_BIT 8 > -#define ZYNQMP_PL_STATUS_MASK BIT(ZYNQMP_PL_STATUS_BIT) > -#define ZYNQMP_CSU_VERSION_MASK ~(ZYNQMP_PL_STATUS_MASK) > -#define ZYNQMP_CSU_VCUDIS_VER_MASK ZYNQMP_CSU_VERSION_MASK & \ > - ~BIT(ZYNQMP_IPDIS_VCU_BIT) > -#define MAX_VARIANTS_EV 3 > > -#if defined(CONFIG_FPGA) && defined(CONFIG_FPGA_ZYNQMPPL) && \ > - !defined(CONFIG_SPL_BUILD) > static char *zynqmp_get_silicon_idcode_name(void) > { > - u32 i, id, ver, j; > - char *buf; > + u32 i; > + u32 idcode, idcode2; > static char name[ZYNQMP_VERSION_SIZE]; > u32 ret_payload[PAYLOAD_ARG_CNT]; > > @@ -226,58 +169,68 @@ static char *zynqmp_get_silicon_idcode_name(void) > * payload[2][29] = PL_INIT > */ > > - /* Get IDCODE field */ > - id = ret_payload[1]; > - id &= ZYNQMP_CSU_IDCODE_DEVICE_CODE_MASK | ZYNQMP_CSU_IDCODE_SVD_MASK; > - id >>= ZYNQMP_CSU_IDCODE_SVD_SHIFT; > - > - /* Shift silicon version info */ > - ver = ret_payload[2] >> ZYNQMP_CSU_VERSION_EMPTY_SHIFT; > - > - debug("%s, ID: 0x%0X, Ver: 0x%0X\r\n", __func__, id, ver); > + idcode = ret_payload[1]; > + idcode2 = ret_payload[2] >> ZYNQMP_CSU_VERSION_EMPTY_SHIFT; > + debug("%s, IDCODE: 0x%0X, IDCODE2: 0x%0X\r\n", __func__, idcode, > + idcode2); > > for (i = 0; i < ARRAY_SIZE(zynqmp_devices); i++) { > - if (zynqmp_devices[i].id == id) { > - if (zynqmp_devices[i].evexists && > - !(ver & ZYNQMP_PL_STATUS_MASK)) > - break; > - if (zynqmp_devices[i].ver == (ver & > - ZYNQMP_CSU_VERSION_MASK)) > - break; > - } > + if (zynqmp_devices[i].id == (idcode & 0x0FFFFFFF)) > + break; > } > > if (i >= ARRAY_SIZE(zynqmp_devices)) > return "unknown"; > > + /* Add device prefix to the name */ > strncat(name, "zu", 2); > - if (!zynqmp_devices[i].evexists || > - (ver & ZYNQMP_PL_STATUS_MASK)) { > - strncat(name, zynqmp_devices[i].name, > - ZYNQMP_VERSION_SIZE - 3); > - return name; > - } > - > - /* > - * Here we are means, PL not powered up and ev variant > - * exists. So, we need to ignore VCU disable bit(8) in > - * version and findout if its CG or EG/EV variant. > - */ > - for (j = 0; j < MAX_VARIANTS_EV; j++, i++) { > - if ((zynqmp_devices[i].ver & ~BIT(ZYNQMP_IPDIS_VCU_BIT)) == > - (ver & ZYNQMP_CSU_VCUDIS_VER_MASK)) { > - strncat(name, zynqmp_devices[i].name, > - ZYNQMP_VERSION_SIZE - 3); > - break; > + strncat(&name[2], simple_itoa(zynqmp_devices[i].device), 2); > + > + if (zynqmp_devices[i].variants & ZYNQMP_VARIANT_EV) { > + /* Devices with EV variant might be EG/CG/EV family */ > + if (idcode2 & IDCODE2_PL_INIT_MASK) { > + u32 family = ((idcode2 & EFUSE_VCU_DIS_MASK) >> > + EFUSE_VCU_DIS_SHIFT) << 1 | > + ((idcode2 & EFUSE_GPU_DIS_MASK) >> > + EFUSE_GPU_DIS_SHIFT); > + > + /* > + * Get family name based on extended idcode values as > + * determined on UG1087, EXTENDED_IDCODE register > + * description > + */ > + switch (family) { > + case 0x00: > + strncat(name, "ev", 2); > + break; > + case 0x10: > + strncat(name, "eg", 2); > + break; > + case 0x11: > + strncat(name, "cg", 2); > + break; > + default: > + /* Do not append family name*/ > + break; > + } > + } else { > + /* > + * When PL powered down the VCU Disable efuse cannot be > + * read. So, ignore the bit and just findout if it is CG > + * or EG/EV variant. > + */ > + strncat(name, (idcode2 & EFUSE_GPU_DIS_MASK) ? "cg" : > + "e", 2); > } > - } > - > - if (j >= MAX_VARIANTS_EV) > - return "unknown"; > - > - if (strstr(name, "eg") || strstr(name, "ev")) { > - buf = strstr(name, "e"); > - *buf = '\0'; > + } else if (zynqmp_devices[i].variants & ZYNQMP_VARIANT_CG) { > + /* Devices with CG variant might be EG or CG family */ > + strncat(name, (idcode2 & EFUSE_GPU_DIS_MASK) ? "cg" : "eg", 2); > + } else if (zynqmp_devices[i].variants & ZYNQMP_VARIANT_EG) { > + strncat(name, "eg", 2); > + } else if (zynqmp_devices[i].variants & ZYNQMP_VARIANT_DR) { > + strncat(name, "dr", 2); > + } else { > + debug("Variant not identified\n"); > } > > return name; > -- > 2.27.0 > Please ignore this patch because it removes support for several DR devices. Thanks, Michal
diff --git a/board/xilinx/zynqmp/zynqmp.c b/board/xilinx/zynqmp/zynqmp.c index 2a430a9e4638..383125087255 100644 --- a/board/xilinx/zynqmp/zynqmp.c +++ b/board/xilinx/zynqmp/zynqmp.c @@ -38,180 +38,123 @@ #include "pm_cfg_obj.h" +#define ZYNQMP_VERSION_SIZE 7 +#define EFUSE_VCU_DIS_MASK 0x100 +#define EFUSE_VCU_DIS_SHIFT 8 +#define EFUSE_GPU_DIS_MASK 0x20 +#define EFUSE_GPU_DIS_SHIFT 5 +#define IDCODE2_PL_INIT_MASK 0x200 +#define IDCODE2_PL_INIT_SHIFT 9 + DECLARE_GLOBAL_DATA_PTR; #if defined(CONFIG_FPGA) && defined(CONFIG_FPGA_ZYNQMPPL) && \ - !defined(CONFIG_SPL_BUILD) + !defined(CONFIG_SPL_BUILD) || (defined(CONFIG_SPL_FPGA_SUPPORT) && \ + defined(CONFIG_SPL_BUILD)) + static xilinx_desc zynqmppl = XILINX_ZYNQMP_DESC; +enum { + ZYNQMP_VARIANT_EG = BIT(0U), + ZYNQMP_VARIANT_EV = BIT(1U), + ZYNQMP_VARIANT_CG = BIT(2U), + ZYNQMP_VARIANT_DR = BIT(3U), +}; + static const struct { u32 id; - u32 ver; - char *name; - bool evexists; + u8 device; + u8 variants; } zynqmp_devices[] = { { - .id = 0x10, - .name = "3eg", - }, - { - .id = 0x10, - .ver = 0x2c, - .name = "3cg", - }, - { - .id = 0x11, - .name = "2eg", - }, - { - .id = 0x11, - .ver = 0x2c, - .name = "2cg", - }, - { - .id = 0x20, - .name = "5ev", - .evexists = 1, - }, - { - .id = 0x20, - .ver = 0x100, - .name = "5eg", - .evexists = 1, - }, - { - .id = 0x20, - .ver = 0x12c, - .name = "5cg", - .evexists = 1, - }, - { - .id = 0x21, - .name = "4ev", - .evexists = 1, - }, - { - .id = 0x21, - .ver = 0x100, - .name = "4eg", - .evexists = 1, - }, - { - .id = 0x21, - .ver = 0x12c, - .name = "4cg", - .evexists = 1, - }, - { - .id = 0x30, - .name = "7ev", - .evexists = 1, - }, - { - .id = 0x30, - .ver = 0x100, - .name = "7eg", - .evexists = 1, - }, - { - .id = 0x30, - .ver = 0x12c, - .name = "7cg", - .evexists = 1, - }, - { - .id = 0x38, - .name = "9eg", - }, - { - .id = 0x38, - .ver = 0x2c, - .name = "9cg", + .id = 0x04711093, + .device = 2, + .variants = ZYNQMP_VARIANT_EG | ZYNQMP_VARIANT_CG, }, { - .id = 0x39, - .name = "6eg", + .id = 0x04710093, + .device = 3, + .variants = ZYNQMP_VARIANT_EG | ZYNQMP_VARIANT_CG, }, { - .id = 0x39, - .ver = 0x2c, - .name = "6cg", + .id = 0x04721093, + .device = 4, + .variants = ZYNQMP_VARIANT_EG | ZYNQMP_VARIANT_CG | + ZYNQMP_VARIANT_EV, }, { - .id = 0x40, - .name = "11eg", - }, - { /* For testing purpose only */ - .id = 0x50, - .ver = 0x2c, - .name = "15cg", + .id = 0x04720093, + .device = 5, + .variants = ZYNQMP_VARIANT_EG | ZYNQMP_VARIANT_CG | + ZYNQMP_VARIANT_EV, }, { - .id = 0x50, - .name = "15eg", + .id = 0x04739093, + .device = 6, + .variants = ZYNQMP_VARIANT_EG | ZYNQMP_VARIANT_CG, }, { - .id = 0x58, - .name = "19eg", + .id = 0x04730093, + .device = 7, + .variants = ZYNQMP_VARIANT_EG | ZYNQMP_VARIANT_CG | + ZYNQMP_VARIANT_EV, }, { - .id = 0x59, - .name = "17eg", + .id = 0x04738093, + .device = 9, + .variants = ZYNQMP_VARIANT_EG, }, { - .id = 0x61, - .name = "21dr", + .id = 0x04740093, + .device = 11, + .variants = ZYNQMP_VARIANT_EG, }, { - .id = 0x63, - .name = "23dr", + .id = 0x04750093, + .device = 15, + .variants = ZYNQMP_VARIANT_EG, }, { - .id = 0x65, - .name = "25dr", + .id = 0x04759093, + .device = 17, + .variants = ZYNQMP_VARIANT_EG, }, { - .id = 0x64, - .name = "27dr", + .id = 0x04758093, + .device = 19, + .variants = ZYNQMP_VARIANT_EG, }, { - .id = 0x60, - .name = "28dr", + .id = 0x047E1093, + .device = 21, + .variants = ZYNQMP_VARIANT_DR, }, { - .id = 0x62, - .name = "29dr", + .id = 0x047E5093, + .device = 25, + .variants = ZYNQMP_VARIANT_DR, }, { - .id = 0x66, - .name = "39dr", + .id = 0x047E4093, + .device = 27, + .variants = ZYNQMP_VARIANT_DR, }, { - .id = 0x7b, - .name = "48dr", + .id = 0x047E0093, + .device = 28, + .variants = ZYNQMP_VARIANT_DR, }, { - .id = 0x7e, - .name = "49dr", + .id = 0x047E2093, + .device = 29, + .variants = ZYNQMP_VARIANT_DR, }, }; -#endif - -#define ZYNQMP_VERSION_SIZE 9 -#define ZYNQMP_PL_STATUS_BIT 9 -#define ZYNQMP_IPDIS_VCU_BIT 8 -#define ZYNQMP_PL_STATUS_MASK BIT(ZYNQMP_PL_STATUS_BIT) -#define ZYNQMP_CSU_VERSION_MASK ~(ZYNQMP_PL_STATUS_MASK) -#define ZYNQMP_CSU_VCUDIS_VER_MASK ZYNQMP_CSU_VERSION_MASK & \ - ~BIT(ZYNQMP_IPDIS_VCU_BIT) -#define MAX_VARIANTS_EV 3 -#if defined(CONFIG_FPGA) && defined(CONFIG_FPGA_ZYNQMPPL) && \ - !defined(CONFIG_SPL_BUILD) static char *zynqmp_get_silicon_idcode_name(void) { - u32 i, id, ver, j; - char *buf; + u32 i; + u32 idcode, idcode2; static char name[ZYNQMP_VERSION_SIZE]; u32 ret_payload[PAYLOAD_ARG_CNT]; @@ -226,58 +169,68 @@ static char *zynqmp_get_silicon_idcode_name(void) * payload[2][29] = PL_INIT */ - /* Get IDCODE field */ - id = ret_payload[1]; - id &= ZYNQMP_CSU_IDCODE_DEVICE_CODE_MASK | ZYNQMP_CSU_IDCODE_SVD_MASK; - id >>= ZYNQMP_CSU_IDCODE_SVD_SHIFT; - - /* Shift silicon version info */ - ver = ret_payload[2] >> ZYNQMP_CSU_VERSION_EMPTY_SHIFT; - - debug("%s, ID: 0x%0X, Ver: 0x%0X\r\n", __func__, id, ver); + idcode = ret_payload[1]; + idcode2 = ret_payload[2] >> ZYNQMP_CSU_VERSION_EMPTY_SHIFT; + debug("%s, IDCODE: 0x%0X, IDCODE2: 0x%0X\r\n", __func__, idcode, + idcode2); for (i = 0; i < ARRAY_SIZE(zynqmp_devices); i++) { - if (zynqmp_devices[i].id == id) { - if (zynqmp_devices[i].evexists && - !(ver & ZYNQMP_PL_STATUS_MASK)) - break; - if (zynqmp_devices[i].ver == (ver & - ZYNQMP_CSU_VERSION_MASK)) - break; - } + if (zynqmp_devices[i].id == (idcode & 0x0FFFFFFF)) + break; } if (i >= ARRAY_SIZE(zynqmp_devices)) return "unknown"; + /* Add device prefix to the name */ strncat(name, "zu", 2); - if (!zynqmp_devices[i].evexists || - (ver & ZYNQMP_PL_STATUS_MASK)) { - strncat(name, zynqmp_devices[i].name, - ZYNQMP_VERSION_SIZE - 3); - return name; - } - - /* - * Here we are means, PL not powered up and ev variant - * exists. So, we need to ignore VCU disable bit(8) in - * version and findout if its CG or EG/EV variant. - */ - for (j = 0; j < MAX_VARIANTS_EV; j++, i++) { - if ((zynqmp_devices[i].ver & ~BIT(ZYNQMP_IPDIS_VCU_BIT)) == - (ver & ZYNQMP_CSU_VCUDIS_VER_MASK)) { - strncat(name, zynqmp_devices[i].name, - ZYNQMP_VERSION_SIZE - 3); - break; + strncat(&name[2], simple_itoa(zynqmp_devices[i].device), 2); + + if (zynqmp_devices[i].variants & ZYNQMP_VARIANT_EV) { + /* Devices with EV variant might be EG/CG/EV family */ + if (idcode2 & IDCODE2_PL_INIT_MASK) { + u32 family = ((idcode2 & EFUSE_VCU_DIS_MASK) >> + EFUSE_VCU_DIS_SHIFT) << 1 | + ((idcode2 & EFUSE_GPU_DIS_MASK) >> + EFUSE_GPU_DIS_SHIFT); + + /* + * Get family name based on extended idcode values as + * determined on UG1087, EXTENDED_IDCODE register + * description + */ + switch (family) { + case 0x00: + strncat(name, "ev", 2); + break; + case 0x10: + strncat(name, "eg", 2); + break; + case 0x11: + strncat(name, "cg", 2); + break; + default: + /* Do not append family name*/ + break; + } + } else { + /* + * When PL powered down the VCU Disable efuse cannot be + * read. So, ignore the bit and just findout if it is CG + * or EG/EV variant. + */ + strncat(name, (idcode2 & EFUSE_GPU_DIS_MASK) ? "cg" : + "e", 2); } - } - - if (j >= MAX_VARIANTS_EV) - return "unknown"; - - if (strstr(name, "eg") || strstr(name, "ev")) { - buf = strstr(name, "e"); - *buf = '\0'; + } else if (zynqmp_devices[i].variants & ZYNQMP_VARIANT_CG) { + /* Devices with CG variant might be EG or CG family */ + strncat(name, (idcode2 & EFUSE_GPU_DIS_MASK) ? "cg" : "eg", 2); + } else if (zynqmp_devices[i].variants & ZYNQMP_VARIANT_EG) { + strncat(name, "eg", 2); + } else if (zynqmp_devices[i].variants & ZYNQMP_VARIANT_DR) { + strncat(name, "dr", 2); + } else { + debug("Variant not identified\n"); } return name;