1*0181937fSRuchika Gupta /* 2*0181937fSRuchika Gupta * Copyright 2014 Freescale Semiconductor, Inc. 3*0181937fSRuchika Gupta * 4*0181937fSRuchika Gupta * SPDX-License-Identifier: GPL-2.0+ 5*0181937fSRuchika Gupta */ 6*0181937fSRuchika Gupta 7*0181937fSRuchika Gupta #include <common.h> 8*0181937fSRuchika Gupta #include <libfdt.h> 9*0181937fSRuchika Gupta #include <fdt_support.h> 10*0181937fSRuchika Gupta #if CONFIG_SYS_FSL_SEC_COMPAT == 2 || CONFIG_SYS_FSL_SEC_COMPAT >= 4 11*0181937fSRuchika Gupta #include <fsl_sec.h> 12*0181937fSRuchika Gupta #endif 13*0181937fSRuchika Gupta 14*0181937fSRuchika Gupta /* 15*0181937fSRuchika Gupta * update crypto node properties to a specified revision of the SEC 16*0181937fSRuchika Gupta * called with sec_rev == 0 if not on an E processor 17*0181937fSRuchika Gupta */ 18*0181937fSRuchika Gupta #if CONFIG_SYS_FSL_SEC_COMPAT == 2 /* SEC 2.x/3.x */ 19*0181937fSRuchika Gupta void fdt_fixup_crypto_node(void *blob, int sec_rev) 20*0181937fSRuchika Gupta { 21*0181937fSRuchika Gupta static const struct sec_rev_prop { 22*0181937fSRuchika Gupta u32 sec_rev; 23*0181937fSRuchika Gupta u32 num_channels; 24*0181937fSRuchika Gupta u32 channel_fifo_len; 25*0181937fSRuchika Gupta u32 exec_units_mask; 26*0181937fSRuchika Gupta u32 descriptor_types_mask; 27*0181937fSRuchika Gupta } sec_rev_prop_list[] = { 28*0181937fSRuchika Gupta { 0x0200, 4, 24, 0x07e, 0x01010ebf }, /* SEC 2.0 */ 29*0181937fSRuchika Gupta { 0x0201, 4, 24, 0x0fe, 0x012b0ebf }, /* SEC 2.1 */ 30*0181937fSRuchika Gupta { 0x0202, 1, 24, 0x04c, 0x0122003f }, /* SEC 2.2 */ 31*0181937fSRuchika Gupta { 0x0204, 4, 24, 0x07e, 0x012b0ebf }, /* SEC 2.4 */ 32*0181937fSRuchika Gupta { 0x0300, 4, 24, 0x9fe, 0x03ab0ebf }, /* SEC 3.0 */ 33*0181937fSRuchika Gupta { 0x0301, 4, 24, 0xbfe, 0x03ab0ebf }, /* SEC 3.1 */ 34*0181937fSRuchika Gupta { 0x0303, 4, 24, 0x97c, 0x03a30abf }, /* SEC 3.3 */ 35*0181937fSRuchika Gupta }; 36*0181937fSRuchika Gupta static char compat_strlist[ARRAY_SIZE(sec_rev_prop_list) * 37*0181937fSRuchika Gupta sizeof("fsl,secX.Y")]; 38*0181937fSRuchika Gupta int crypto_node, sec_idx, err; 39*0181937fSRuchika Gupta char *p; 40*0181937fSRuchika Gupta u32 val; 41*0181937fSRuchika Gupta 42*0181937fSRuchika Gupta /* locate crypto node based on lowest common compatible */ 43*0181937fSRuchika Gupta crypto_node = fdt_node_offset_by_compatible(blob, -1, "fsl,sec2.0"); 44*0181937fSRuchika Gupta if (crypto_node == -FDT_ERR_NOTFOUND) 45*0181937fSRuchika Gupta return; 46*0181937fSRuchika Gupta 47*0181937fSRuchika Gupta /* delete it if not on an E-processor */ 48*0181937fSRuchika Gupta if (crypto_node > 0 && !sec_rev) { 49*0181937fSRuchika Gupta fdt_del_node(blob, crypto_node); 50*0181937fSRuchika Gupta return; 51*0181937fSRuchika Gupta } 52*0181937fSRuchika Gupta 53*0181937fSRuchika Gupta /* else we got called for possible uprev */ 54*0181937fSRuchika Gupta for (sec_idx = 0; sec_idx < ARRAY_SIZE(sec_rev_prop_list); sec_idx++) 55*0181937fSRuchika Gupta if (sec_rev_prop_list[sec_idx].sec_rev == sec_rev) 56*0181937fSRuchika Gupta break; 57*0181937fSRuchika Gupta 58*0181937fSRuchika Gupta if (sec_idx == ARRAY_SIZE(sec_rev_prop_list)) { 59*0181937fSRuchika Gupta puts("warning: unknown SEC revision number\n"); 60*0181937fSRuchika Gupta return; 61*0181937fSRuchika Gupta } 62*0181937fSRuchika Gupta 63*0181937fSRuchika Gupta val = cpu_to_fdt32(sec_rev_prop_list[sec_idx].num_channels); 64*0181937fSRuchika Gupta err = fdt_setprop(blob, crypto_node, "fsl,num-channels", &val, 4); 65*0181937fSRuchika Gupta if (err < 0) 66*0181937fSRuchika Gupta printf("WARNING: could not set crypto property: %s\n", 67*0181937fSRuchika Gupta fdt_strerror(err)); 68*0181937fSRuchika Gupta 69*0181937fSRuchika Gupta val = cpu_to_fdt32(sec_rev_prop_list[sec_idx].descriptor_types_mask); 70*0181937fSRuchika Gupta err = fdt_setprop(blob, crypto_node, "fsl,descriptor-types-mask", 71*0181937fSRuchika Gupta &val, 4); 72*0181937fSRuchika Gupta if (err < 0) 73*0181937fSRuchika Gupta printf("WARNING: could not set crypto property: %s\n", 74*0181937fSRuchika Gupta fdt_strerror(err)); 75*0181937fSRuchika Gupta 76*0181937fSRuchika Gupta val = cpu_to_fdt32(sec_rev_prop_list[sec_idx].exec_units_mask); 77*0181937fSRuchika Gupta err = fdt_setprop(blob, crypto_node, "fsl,exec-units-mask", &val, 4); 78*0181937fSRuchika Gupta if (err < 0) 79*0181937fSRuchika Gupta printf("WARNING: could not set crypto property: %s\n", 80*0181937fSRuchika Gupta fdt_strerror(err)); 81*0181937fSRuchika Gupta 82*0181937fSRuchika Gupta val = cpu_to_fdt32(sec_rev_prop_list[sec_idx].channel_fifo_len); 83*0181937fSRuchika Gupta err = fdt_setprop(blob, crypto_node, "fsl,channel-fifo-len", &val, 4); 84*0181937fSRuchika Gupta if (err < 0) 85*0181937fSRuchika Gupta printf("WARNING: could not set crypto property: %s\n", 86*0181937fSRuchika Gupta fdt_strerror(err)); 87*0181937fSRuchika Gupta 88*0181937fSRuchika Gupta val = 0; 89*0181937fSRuchika Gupta while (sec_idx >= 0) { 90*0181937fSRuchika Gupta p = compat_strlist + val; 91*0181937fSRuchika Gupta val += sprintf(p, "fsl,sec%d.%d", 92*0181937fSRuchika Gupta (sec_rev_prop_list[sec_idx].sec_rev & 0xff00) >> 8, 93*0181937fSRuchika Gupta sec_rev_prop_list[sec_idx].sec_rev & 0x00ff) + 1; 94*0181937fSRuchika Gupta sec_idx--; 95*0181937fSRuchika Gupta } 96*0181937fSRuchika Gupta err = fdt_setprop(blob, crypto_node, "compatible", &compat_strlist, 97*0181937fSRuchika Gupta val); 98*0181937fSRuchika Gupta if (err < 0) 99*0181937fSRuchika Gupta printf("WARNING: could not set crypto property: %s\n", 100*0181937fSRuchika Gupta fdt_strerror(err)); 101*0181937fSRuchika Gupta } 102*0181937fSRuchika Gupta #elif CONFIG_SYS_FSL_SEC_COMPAT >= 4 /* SEC4 */ 103*0181937fSRuchika Gupta static u8 caam_get_era(void) 104*0181937fSRuchika Gupta { 105*0181937fSRuchika Gupta static const struct { 106*0181937fSRuchika Gupta u16 ip_id; 107*0181937fSRuchika Gupta u8 maj_rev; 108*0181937fSRuchika Gupta u8 era; 109*0181937fSRuchika Gupta } caam_eras[] = { 110*0181937fSRuchika Gupta {0x0A10, 1, 1}, 111*0181937fSRuchika Gupta {0x0A10, 2, 2}, 112*0181937fSRuchika Gupta {0x0A12, 1, 3}, 113*0181937fSRuchika Gupta {0x0A14, 1, 3}, 114*0181937fSRuchika Gupta {0x0A14, 2, 4}, 115*0181937fSRuchika Gupta {0x0A16, 1, 4}, 116*0181937fSRuchika Gupta {0x0A10, 3, 4}, 117*0181937fSRuchika Gupta {0x0A11, 1, 4}, 118*0181937fSRuchika Gupta {0x0A18, 1, 4}, 119*0181937fSRuchika Gupta {0x0A11, 2, 5}, 120*0181937fSRuchika Gupta {0x0A12, 2, 5}, 121*0181937fSRuchika Gupta {0x0A13, 1, 5}, 122*0181937fSRuchika Gupta {0x0A1C, 1, 5} 123*0181937fSRuchika Gupta }; 124*0181937fSRuchika Gupta 125*0181937fSRuchika Gupta ccsr_sec_t __iomem *sec = (void __iomem *)CONFIG_SYS_FSL_SEC_ADDR; 126*0181937fSRuchika Gupta u32 secvid_ms = sec_in32(&sec->secvid_ms); 127*0181937fSRuchika Gupta u32 ccbvid = sec_in32(&sec->ccbvid); 128*0181937fSRuchika Gupta u16 ip_id = (secvid_ms & SEC_SECVID_MS_IPID_MASK) >> 129*0181937fSRuchika Gupta SEC_SECVID_MS_IPID_SHIFT; 130*0181937fSRuchika Gupta u8 maj_rev = (secvid_ms & SEC_SECVID_MS_MAJ_REV_MASK) >> 131*0181937fSRuchika Gupta SEC_SECVID_MS_MAJ_REV_SHIFT; 132*0181937fSRuchika Gupta u8 era = (ccbvid & SEC_CCBVID_ERA_MASK) >> SEC_CCBVID_ERA_SHIFT; 133*0181937fSRuchika Gupta 134*0181937fSRuchika Gupta int i; 135*0181937fSRuchika Gupta 136*0181937fSRuchika Gupta if (era) /* This is '0' prior to CAAM ERA-6 */ 137*0181937fSRuchika Gupta return era; 138*0181937fSRuchika Gupta 139*0181937fSRuchika Gupta for (i = 0; i < ARRAY_SIZE(caam_eras); i++) 140*0181937fSRuchika Gupta if (caam_eras[i].ip_id == ip_id && 141*0181937fSRuchika Gupta caam_eras[i].maj_rev == maj_rev) 142*0181937fSRuchika Gupta return caam_eras[i].era; 143*0181937fSRuchika Gupta 144*0181937fSRuchika Gupta return 0; 145*0181937fSRuchika Gupta } 146*0181937fSRuchika Gupta 147*0181937fSRuchika Gupta static void fdt_fixup_crypto_era(void *blob, u32 era) 148*0181937fSRuchika Gupta { 149*0181937fSRuchika Gupta int err; 150*0181937fSRuchika Gupta int crypto_node; 151*0181937fSRuchika Gupta 152*0181937fSRuchika Gupta crypto_node = fdt_path_offset(blob, "crypto"); 153*0181937fSRuchika Gupta if (crypto_node < 0) { 154*0181937fSRuchika Gupta printf("WARNING: Missing crypto node\n"); 155*0181937fSRuchika Gupta return; 156*0181937fSRuchika Gupta } 157*0181937fSRuchika Gupta 158*0181937fSRuchika Gupta err = fdt_setprop(blob, crypto_node, "fsl,sec-era", &era, 159*0181937fSRuchika Gupta sizeof(era)); 160*0181937fSRuchika Gupta if (err < 0) { 161*0181937fSRuchika Gupta printf("ERROR: could not set fsl,sec-era property: %s\n", 162*0181937fSRuchika Gupta fdt_strerror(err)); 163*0181937fSRuchika Gupta } 164*0181937fSRuchika Gupta } 165*0181937fSRuchika Gupta 166*0181937fSRuchika Gupta void fdt_fixup_crypto_node(void *blob, int sec_rev) 167*0181937fSRuchika Gupta { 168*0181937fSRuchika Gupta u8 era; 169*0181937fSRuchika Gupta 170*0181937fSRuchika Gupta if (!sec_rev) { 171*0181937fSRuchika Gupta fdt_del_node_and_alias(blob, "crypto"); 172*0181937fSRuchika Gupta return; 173*0181937fSRuchika Gupta } 174*0181937fSRuchika Gupta 175*0181937fSRuchika Gupta /* Add SEC ERA information in compatible */ 176*0181937fSRuchika Gupta era = caam_get_era(); 177*0181937fSRuchika Gupta if (era) { 178*0181937fSRuchika Gupta fdt_fixup_crypto_era(blob, era); 179*0181937fSRuchika Gupta } else { 180*0181937fSRuchika Gupta printf("WARNING: Unable to get ERA for CAAM rev: %d\n", 181*0181937fSRuchika Gupta sec_rev); 182*0181937fSRuchika Gupta } 183*0181937fSRuchika Gupta } 184*0181937fSRuchika Gupta #endif 185