mirror of
https://github.com/AsahiLinux/u-boot
synced 2025-02-16 14:08:45 +00:00
Merge branch 'master' of git://git.denx.de/u-boot-mpc85xx
This commit is contained in:
commit
1c6f6a6ef9
27 changed files with 2008 additions and 68 deletions
|
@ -27,6 +27,8 @@
|
|||
#define CONFIG_SYS_FSL_SCFG_ADDR (CONFIG_SYS_IMMR + 0x00570000)
|
||||
#define CONFIG_SYS_FSL_SEC_ADDR (CONFIG_SYS_IMMR + 0x700000)
|
||||
#define CONFIG_SYS_FSL_JR0_ADDR (CONFIG_SYS_IMMR + 0x710000)
|
||||
#define CONFIG_SYS_SEC_MON_ADDR (CONFIG_SYS_IMMR + 0x00e90000)
|
||||
#define CONFIG_SYS_SFP_ADDR (CONFIG_SYS_IMMR + 0x00e80200)
|
||||
#define CONFIG_SYS_FSL_SERDES_ADDR (CONFIG_SYS_IMMR + 0x00ea0000)
|
||||
#define CONFIG_SYS_FSL_GUTS_ADDR (CONFIG_SYS_IMMR + 0x00ee0000)
|
||||
#define CONFIG_SYS_FSL_LS1_CLK_ADDR (CONFIG_SYS_IMMR + 0x00ee1000)
|
||||
|
@ -95,7 +97,25 @@
|
|||
#define CONFIG_SYS_FSL_DSPI_BE
|
||||
#define CONFIG_SYS_FSL_QSPI_BE
|
||||
#define CONFIG_SYS_FSL_DCU_BE
|
||||
#define CONFIG_SYS_FSL_SEC_MON_LE
|
||||
#define CONFIG_SYS_FSL_SEC_LE
|
||||
#define CONFIG_SYS_FSL_SFP_VER_3_2
|
||||
#define CONFIG_SYS_FSL_SFP_BE
|
||||
#define CONFIG_SYS_FSL_SRK_LE
|
||||
#define CONFIG_KEY_REVOCATION
|
||||
#define CONFIG_FSL_ISBC_KEY_EXT
|
||||
|
||||
#ifdef CONFIG_SECURE_BOOT
|
||||
#define CONFIG_CMD_ESBC_VALIDATE
|
||||
#define CONFIG_FSL_SEC_MON
|
||||
#define CONFIG_SHA_PROG_HW_ACCEL
|
||||
#define CONFIG_DM
|
||||
#define CONFIG_RSA
|
||||
#define CONFIG_RSA_FREESCALE_EXP
|
||||
#ifndef CONFIG_FSL_CAAM
|
||||
#define CONFIG_FSL_CAAM
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#define DCU_LAYER_MAX_NUM 16
|
||||
|
||||
|
|
|
@ -73,6 +73,11 @@ int checkcpu (void)
|
|||
unsigned int i, core, nr_cores = cpu_numcores();
|
||||
u32 mask = cpu_mask();
|
||||
|
||||
#ifdef CONFIG_HETROGENOUS_CLUSTERS
|
||||
unsigned int j, dsp_core, dsp_numcores = cpu_num_dspcores();
|
||||
u32 dsp_mask = cpu_dsp_mask();
|
||||
#endif
|
||||
|
||||
svr = get_svr();
|
||||
major = SVR_MAJ(svr);
|
||||
minor = SVR_MIN(svr);
|
||||
|
@ -166,6 +171,16 @@ int checkcpu (void)
|
|||
printf("CPU%d:%-4s MHz, ", core,
|
||||
strmhz(buf1, sysinfo.freq_processor[core]));
|
||||
}
|
||||
|
||||
#ifdef CONFIG_HETROGENOUS_CLUSTERS
|
||||
for_each_cpu(j, dsp_core, dsp_numcores, dsp_mask) {
|
||||
if (!(j & 3))
|
||||
printf("\n ");
|
||||
printf("DSP CPU%d:%-4s MHz, ", j,
|
||||
strmhz(buf1, sysinfo.freq_processor_dsp[dsp_core]));
|
||||
}
|
||||
#endif
|
||||
|
||||
printf("\n CCB:%-4s MHz,", strmhz(buf1, sysinfo.freq_systembus));
|
||||
printf("\n");
|
||||
|
||||
|
@ -224,6 +239,19 @@ int checkcpu (void)
|
|||
printf(" QE:%-4s MHz\n", strmhz(buf1, sysinfo.freq_qe));
|
||||
#endif
|
||||
|
||||
#if defined(CONFIG_SYS_CPRI)
|
||||
printf(" ");
|
||||
printf("CPRI:%-4s MHz", strmhz(buf1, sysinfo.freq_cpri));
|
||||
#endif
|
||||
|
||||
#if defined(CONFIG_SYS_MAPLE)
|
||||
printf("\n ");
|
||||
printf("MAPLE:%-4s MHz, ", strmhz(buf1, sysinfo.freq_maple));
|
||||
printf("MAPLE-ULB:%-4s MHz, ", strmhz(buf1, sysinfo.freq_maple_ulb));
|
||||
printf("MAPLE-eTVPE:%-4s MHz\n",
|
||||
strmhz(buf1, sysinfo.freq_maple_etvpe));
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_SYS_DPAA_FMAN
|
||||
for (i = 0; i < CONFIG_SYS_NUM_FMAN; i++) {
|
||||
printf(" FMAN%d: %s MHz\n", i + 1,
|
||||
|
|
|
@ -34,6 +34,10 @@ void get_sys_info(sys_info_t *sys_info)
|
|||
#ifdef CONFIG_FSL_CORENET
|
||||
volatile ccsr_clk_t *clk = (void *)(CONFIG_SYS_FSL_CORENET_CLK_ADDR);
|
||||
unsigned int cpu;
|
||||
#ifdef CONFIG_HETROGENOUS_CLUSTERS
|
||||
unsigned int dsp_cpu;
|
||||
uint rcw_tmp1, rcw_tmp2;
|
||||
#endif
|
||||
#ifdef CONFIG_SYS_FSL_QORIQ_CHASSIS2
|
||||
int cc_group[12] = CONFIG_SYS_FSL_CLUSTER_CLOCKS;
|
||||
#endif
|
||||
|
@ -157,6 +161,7 @@ void get_sys_info(sys_info_t *sys_info)
|
|||
else
|
||||
freq_c_pll[i] = sys_info->freq_systembus * ratio[i];
|
||||
}
|
||||
|
||||
#ifdef CONFIG_SYS_FSL_QORIQ_CHASSIS2
|
||||
/*
|
||||
* As per CHASSIS2 architeture total 12 clusters are posible and
|
||||
|
@ -181,6 +186,20 @@ void get_sys_info(sys_info_t *sys_info)
|
|||
sys_info->freq_processor[cpu] =
|
||||
freq_c_pll[cplx_pll] / core_cplx_pll_div[c_pll_sel];
|
||||
}
|
||||
|
||||
#ifdef CONFIG_HETROGENOUS_CLUSTERS
|
||||
for_each_cpu(i, dsp_cpu, cpu_num_dspcores(), cpu_dsp_mask()) {
|
||||
int dsp_cluster = fsl_qoriq_dsp_core_to_cluster(dsp_cpu);
|
||||
u32 c_pll_sel = (in_be32
|
||||
(&clk->clkcsr[dsp_cluster].clkcncsr) >> 27)
|
||||
& 0xf;
|
||||
u32 cplx_pll = core_cplx_PLL[c_pll_sel];
|
||||
cplx_pll += cc_group[dsp_cluster] - 1;
|
||||
sys_info->freq_processor_dsp[dsp_cpu] =
|
||||
freq_c_pll[cplx_pll] / core_cplx_pll_div[c_pll_sel];
|
||||
}
|
||||
#endif
|
||||
|
||||
#if defined(CONFIG_PPC_B4860) || defined(CONFIG_PPC_B4420) || \
|
||||
defined(CONFIG_PPC_T2080) || defined(CONFIG_PPC_T2081)
|
||||
#define FM1_CLK_SEL 0xe0000000
|
||||
|
@ -243,6 +262,127 @@ void get_sys_info(sys_info_t *sys_info)
|
|||
sys_info->freq_qman = sys_info->freq_systembus / CONFIG_QBMAN_CLK_DIV;
|
||||
#endif
|
||||
|
||||
#if defined(CONFIG_SYS_MAPLE)
|
||||
#define CPRI_CLK_SEL 0x1C000000
|
||||
#define CPRI_CLK_SHIFT 26
|
||||
#define CPRI_ALT_CLK_SEL 0x00007000
|
||||
#define CPRI_ALT_CLK_SHIFT 12
|
||||
|
||||
rcw_tmp1 = in_be32(&gur->rcwsr[7]); /* Reading RCW bits: 224-255*/
|
||||
rcw_tmp2 = in_be32(&gur->rcwsr[15]); /* Reading RCW bits: 480-511*/
|
||||
/* For MAPLE and CPRI frequency */
|
||||
switch ((rcw_tmp1 & CPRI_CLK_SEL) >> CPRI_CLK_SHIFT) {
|
||||
case 1:
|
||||
sys_info->freq_maple = freq_c_pll[CONFIG_SYS_CPRI_CLK];
|
||||
sys_info->freq_cpri = freq_c_pll[CONFIG_SYS_CPRI_CLK];
|
||||
break;
|
||||
case 2:
|
||||
sys_info->freq_maple = freq_c_pll[CONFIG_SYS_CPRI_CLK] / 2;
|
||||
sys_info->freq_cpri = freq_c_pll[CONFIG_SYS_CPRI_CLK] / 2;
|
||||
break;
|
||||
case 3:
|
||||
sys_info->freq_maple = freq_c_pll[CONFIG_SYS_CPRI_CLK] / 3;
|
||||
sys_info->freq_cpri = freq_c_pll[CONFIG_SYS_CPRI_CLK] / 3;
|
||||
break;
|
||||
case 4:
|
||||
sys_info->freq_maple = freq_c_pll[CONFIG_SYS_CPRI_CLK] / 4;
|
||||
sys_info->freq_cpri = freq_c_pll[CONFIG_SYS_CPRI_CLK] / 4;
|
||||
break;
|
||||
case 5:
|
||||
if (((rcw_tmp2 & CPRI_ALT_CLK_SEL)
|
||||
>> CPRI_ALT_CLK_SHIFT) == 6) {
|
||||
sys_info->freq_maple =
|
||||
freq_c_pll[CONFIG_SYS_CPRI_CLK - 2] / 2;
|
||||
sys_info->freq_cpri =
|
||||
freq_c_pll[CONFIG_SYS_CPRI_CLK - 2] / 2;
|
||||
}
|
||||
if (((rcw_tmp2 & CPRI_ALT_CLK_SEL)
|
||||
>> CPRI_ALT_CLK_SHIFT) == 7) {
|
||||
sys_info->freq_maple =
|
||||
freq_c_pll[CONFIG_SYS_CPRI_CLK - 2] / 3;
|
||||
sys_info->freq_cpri =
|
||||
freq_c_pll[CONFIG_SYS_CPRI_CLK - 2] / 3;
|
||||
}
|
||||
break;
|
||||
case 6:
|
||||
sys_info->freq_maple = freq_c_pll[CONFIG_SYS_CPRI_CLK + 1] / 2;
|
||||
sys_info->freq_cpri = freq_c_pll[CONFIG_SYS_CPRI_CLK + 1] / 2;
|
||||
break;
|
||||
case 7:
|
||||
sys_info->freq_maple = freq_c_pll[CONFIG_SYS_CPRI_CLK + 1] / 3;
|
||||
sys_info->freq_cpri = freq_c_pll[CONFIG_SYS_CPRI_CLK + 1] / 3;
|
||||
break;
|
||||
default:
|
||||
printf("Error: Unknown MAPLE/CPRI clock select!\n");
|
||||
}
|
||||
|
||||
/* For MAPLE ULB and eTVPE frequencies */
|
||||
#define ULB_CLK_SEL 0x00000038
|
||||
#define ULB_CLK_SHIFT 3
|
||||
#define ETVPE_CLK_SEL 0x00000007
|
||||
#define ETVPE_CLK_SHIFT 0
|
||||
|
||||
switch ((rcw_tmp2 & ULB_CLK_SEL) >> ULB_CLK_SHIFT) {
|
||||
case 1:
|
||||
sys_info->freq_maple_ulb = freq_c_pll[CONFIG_SYS_ULB_CLK];
|
||||
break;
|
||||
case 2:
|
||||
sys_info->freq_maple_ulb = freq_c_pll[CONFIG_SYS_ULB_CLK] / 2;
|
||||
break;
|
||||
case 3:
|
||||
sys_info->freq_maple_ulb = freq_c_pll[CONFIG_SYS_ULB_CLK] / 3;
|
||||
break;
|
||||
case 4:
|
||||
sys_info->freq_maple_ulb = freq_c_pll[CONFIG_SYS_ULB_CLK] / 4;
|
||||
break;
|
||||
case 5:
|
||||
sys_info->freq_maple_ulb = sys_info->freq_systembus;
|
||||
break;
|
||||
case 6:
|
||||
sys_info->freq_maple_ulb =
|
||||
freq_c_pll[CONFIG_SYS_ULB_CLK - 1] / 2;
|
||||
break;
|
||||
case 7:
|
||||
sys_info->freq_maple_ulb =
|
||||
freq_c_pll[CONFIG_SYS_ULB_CLK - 1] / 3;
|
||||
break;
|
||||
default:
|
||||
printf("Error: Unknown MAPLE ULB clock select!\n");
|
||||
}
|
||||
|
||||
switch ((rcw_tmp2 & ETVPE_CLK_SEL) >> ETVPE_CLK_SHIFT) {
|
||||
case 1:
|
||||
sys_info->freq_maple_etvpe = freq_c_pll[CONFIG_SYS_ETVPE_CLK];
|
||||
break;
|
||||
case 2:
|
||||
sys_info->freq_maple_etvpe =
|
||||
freq_c_pll[CONFIG_SYS_ETVPE_CLK] / 2;
|
||||
break;
|
||||
case 3:
|
||||
sys_info->freq_maple_etvpe =
|
||||
freq_c_pll[CONFIG_SYS_ETVPE_CLK] / 3;
|
||||
break;
|
||||
case 4:
|
||||
sys_info->freq_maple_etvpe =
|
||||
freq_c_pll[CONFIG_SYS_ETVPE_CLK] / 4;
|
||||
break;
|
||||
case 5:
|
||||
sys_info->freq_maple_etvpe = sys_info->freq_systembus;
|
||||
break;
|
||||
case 6:
|
||||
sys_info->freq_maple_etvpe =
|
||||
freq_c_pll[CONFIG_SYS_ETVPE_CLK - 1] / 2;
|
||||
break;
|
||||
case 7:
|
||||
sys_info->freq_maple_etvpe =
|
||||
freq_c_pll[CONFIG_SYS_ETVPE_CLK - 1] / 3;
|
||||
break;
|
||||
default:
|
||||
printf("Error: Unknown MAPLE eTVPE clock select!\n");
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_SYS_DPAA_FMAN
|
||||
#ifndef CONFIG_FM_PLAT_CLK_DIV
|
||||
switch ((rcw_tmp & FM1_CLK_SEL) >> FM1_CLK_SHIFT) {
|
||||
|
|
|
@ -133,6 +133,53 @@ u32 compute_ppc_cpumask(void)
|
|||
return mask;
|
||||
}
|
||||
|
||||
#ifdef CONFIG_HETROGENOUS_CLUSTERS
|
||||
u32 compute_dsp_cpumask(void)
|
||||
{
|
||||
ccsr_gur_t *gur = (void __iomem *)(CONFIG_SYS_MPC85xx_GUTS_ADDR);
|
||||
int i = CONFIG_DSP_CLUSTER_START, count = 0;
|
||||
u32 cluster, type, dsp_mask = 0;
|
||||
|
||||
do {
|
||||
int j;
|
||||
cluster = in_be32(&gur->tp_cluster[i].lower);
|
||||
for (j = 0; j < TP_INIT_PER_CLUSTER; j++) {
|
||||
type = init_type(cluster, j);
|
||||
if (type) {
|
||||
if (TP_ITYP_TYPE(type) == TP_ITYP_TYPE_SC)
|
||||
dsp_mask |= 1 << count;
|
||||
count++;
|
||||
}
|
||||
}
|
||||
i++;
|
||||
} while ((cluster & TP_CLUSTER_EOC) != TP_CLUSTER_EOC);
|
||||
|
||||
return dsp_mask;
|
||||
}
|
||||
|
||||
int fsl_qoriq_dsp_core_to_cluster(unsigned int core)
|
||||
{
|
||||
ccsr_gur_t *gur = (void __iomem *)(CONFIG_SYS_MPC85xx_GUTS_ADDR);
|
||||
int count = 0, i = CONFIG_DSP_CLUSTER_START;
|
||||
u32 cluster;
|
||||
|
||||
do {
|
||||
int j;
|
||||
cluster = in_be32(&gur->tp_cluster[i].lower);
|
||||
for (j = 0; j < TP_INIT_PER_CLUSTER; j++) {
|
||||
if (init_type(cluster, j)) {
|
||||
if (count == core)
|
||||
return i;
|
||||
count++;
|
||||
}
|
||||
}
|
||||
i++;
|
||||
} while ((cluster & TP_CLUSTER_EOC) != TP_CLUSTER_EOC);
|
||||
|
||||
return -1; /* cannot identify the cluster */
|
||||
}
|
||||
#endif
|
||||
|
||||
int fsl_qoriq_core_to_cluster(unsigned int core)
|
||||
{
|
||||
ccsr_gur_t *gur = (void __iomem *)(CONFIG_SYS_MPC85xx_GUTS_ADDR);
|
||||
|
@ -198,8 +245,43 @@ __weak u32 cpu_mask(void)
|
|||
return cpu->mask;
|
||||
}
|
||||
|
||||
#ifdef CONFIG_HETROGENOUS_CLUSTERS
|
||||
__weak u32 cpu_dsp_mask(void)
|
||||
{
|
||||
ccsr_pic_t __iomem *pic = (void *)CONFIG_SYS_MPC8xxx_PIC_ADDR;
|
||||
struct cpu_type *cpu = gd->arch.cpu;
|
||||
|
||||
/* better to query feature reporting register than just assume 1 */
|
||||
if (cpu == &cpu_type_unknown)
|
||||
return ((in_be32(&pic->frr) & MPC8xxx_PICFRR_NCPU_MASK) >>
|
||||
MPC8xxx_PICFRR_NCPU_SHIFT) + 1;
|
||||
|
||||
if (cpu->dsp_num_cores == 0)
|
||||
return compute_dsp_cpumask();
|
||||
|
||||
return cpu->dsp_mask;
|
||||
}
|
||||
|
||||
/*
|
||||
* Return the number of cores on this SOC.
|
||||
* Return the number of SC/DSP cores on this SOC.
|
||||
*/
|
||||
__weak int cpu_num_dspcores(void)
|
||||
{
|
||||
struct cpu_type *cpu = gd->arch.cpu;
|
||||
|
||||
/*
|
||||
* Report # of cores in terms of the cpu_mask if we haven't
|
||||
* figured out how many there are yet
|
||||
*/
|
||||
if (cpu->dsp_num_cores == 0)
|
||||
return hweight32(cpu_dsp_mask());
|
||||
|
||||
return cpu->dsp_num_cores;
|
||||
}
|
||||
#endif
|
||||
|
||||
/*
|
||||
* Return the number of PPC cores on this SOC.
|
||||
*/
|
||||
__weak int cpu_numcores(void)
|
||||
{
|
||||
|
@ -215,6 +297,7 @@ __weak int cpu_numcores(void)
|
|||
return cpu->num_cores;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* Check if the given core ID is valid
|
||||
*
|
||||
|
@ -248,6 +331,12 @@ int fixup_cpu(void)
|
|||
cpu->num_cores = cpu_numcores();
|
||||
}
|
||||
|
||||
#ifdef CONFIG_HETROGENOUS_CLUSTERS
|
||||
if (cpu->dsp_num_cores == 0) {
|
||||
cpu->dsp_mask = cpu_dsp_mask();
|
||||
cpu->dsp_num_cores = cpu_num_dspcores();
|
||||
}
|
||||
#endif
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
|
@ -25,6 +25,8 @@
|
|||
/* IP endianness */
|
||||
#define CONFIG_SYS_FSL_IFC_BE
|
||||
#define CONFIG_SYS_FSL_SEC_BE
|
||||
#define CONFIG_SYS_FSL_SFP_BE
|
||||
#define CONFIG_SYS_FSL_SEC_MON_BE
|
||||
|
||||
/* Number of TLB CAM entries we have on FSL Book-E chips */
|
||||
#if defined(CONFIG_E500MC)
|
||||
|
@ -201,7 +203,7 @@
|
|||
#elif defined(CONFIG_P1013)
|
||||
#define CONFIG_MAX_CPUS 1
|
||||
#define CONFIG_SYS_FSL_NUM_LAWS 12
|
||||
#define CONFIG_USB_MAX_CONTROLLER_COUNT 2
|
||||
#define CONFIG_USB_MAX_CONTROLLER_COUNT 1
|
||||
#define CONFIG_SYS_PPC_E500_DEBUG_TLB 2
|
||||
#define CONFIG_TSECV2
|
||||
#define CONFIG_SYS_FSL_SEC_COMPAT 2
|
||||
|
@ -285,7 +287,7 @@
|
|||
#define CONFIG_SYS_PPC_E500_DEBUG_TLB 2
|
||||
#define CONFIG_TSECV2
|
||||
#define CONFIG_SYS_FSL_SEC_COMPAT 2
|
||||
#define CONFIG_USB_MAX_CONTROLLER_COUNT 2
|
||||
#define CONFIG_USB_MAX_CONTROLLER_COUNT 1
|
||||
#define CONFIG_SYS_CCSRBAR_DEFAULT 0xff700000
|
||||
#define CONFIG_SYS_FSL_ERRATUM_ELBC_A001
|
||||
#define CONFIG_SYS_FSL_ERRATUM_ESDHC111
|
||||
|
@ -689,13 +691,22 @@
|
|||
#define CONFIG_FSL_CORENET /* Freescale CoreNet platform */
|
||||
#define CONFIG_SYS_FSL_QORIQ_CHASSIS2 /* Freescale Chassis generation 2 */
|
||||
#define CONFIG_SYS_FSL_QMAN_V3 /* QMAN version 3 */
|
||||
#define CONFIG_HETROGENOUS_CLUSTERS /* DSP/SC3900 core clusters */
|
||||
#define CONFIG_PPC_CLUSTER_START 0 /*Start index of ppc clusters*/
|
||||
#define CONFIG_DSP_CLUSTER_START 1 /*Start index of dsp clusters*/
|
||||
#define CONFIG_SYS_FSL_NUM_LAWS 32
|
||||
#define CONFIG_SYS_FSL_SRDS_1
|
||||
#define CONFIG_SYS_FSL_SRDS_2
|
||||
#define CONFIG_SYS_MAPLE
|
||||
#define CONFIG_SYS_CPRI
|
||||
#define CONFIG_SYS_FSL_NUM_CC_PLLS 5
|
||||
#define CONFIG_SYS_FSL_SEC_COMPAT 4
|
||||
#define CONFIG_SYS_NUM_FMAN 1
|
||||
#define CONFIG_USB_MAX_CONTROLLER_COUNT 1
|
||||
#define CONFIG_SYS_FM1_CLK 0
|
||||
#define CONFIG_SYS_CPRI_CLK 3
|
||||
#define CONFIG_SYS_ULB_CLK 4
|
||||
#define CONFIG_SYS_ETVPE_CLK 1
|
||||
#define CONFIG_SYS_FSL_DDR_VER FSL_DDR_VER_4_7
|
||||
#define CONFIG_SYS_FSL_IFC_BANK_COUNT 4
|
||||
#define CONFIG_SYS_FMAN_V3
|
||||
|
@ -718,8 +729,9 @@
|
|||
#ifdef CONFIG_PPC_B4860
|
||||
#define CONFIG_SYS_FSL_CORES_PER_CLUSTER 4
|
||||
#define CONFIG_MAX_CPUS 4
|
||||
#define CONFIG_MAX_DSP_CPUS 12
|
||||
#define CONFIG_NUM_DSP_CPUS 6
|
||||
#define CONFIG_SYS_FSL_SRDS_NUM_PLLS 2
|
||||
#define CONFIG_SYS_FSL_NUM_CC_PLLS 4
|
||||
#define CONFIG_SYS_FSL_CLUSTER_CLOCKS { 1, 4, 4, 4 }
|
||||
#define CONFIG_SYS_NUM_FM1_DTSEC 6
|
||||
#define CONFIG_SYS_NUM_FM1_10GEC 2
|
||||
|
@ -731,9 +743,9 @@
|
|||
#define CONFIG_SYS_FSL_SRIO_LIODN
|
||||
#else
|
||||
#define CONFIG_MAX_CPUS 2
|
||||
#define CONFIG_MAX_DSP_CPUS 2
|
||||
#define CONFIG_SYS_FSL_SRDS_NUM_PLLS 1
|
||||
#define CONFIG_SYS_FSL_CORES_PER_CLUSTER 2
|
||||
#define CONFIG_SYS_FSL_NUM_CC_PLLS 4
|
||||
#define CONFIG_SYS_FSL_CLUSTER_CLOCKS { 1, 4 }
|
||||
#define CONFIG_SYS_NUM_FM1_DTSEC 4
|
||||
#define CONFIG_SYS_NUM_FM1_10GEC 0
|
||||
|
|
|
@ -6,6 +6,19 @@
|
|||
|
||||
#ifndef __FSL_SECURE_BOOT_H
|
||||
#define __FSL_SECURE_BOOT_H
|
||||
#include <asm/config_mpc85xx.h>
|
||||
|
||||
#ifdef CONFIG_SECURE_BOOT
|
||||
#define CONFIG_CMD_ESBC_VALIDATE
|
||||
#define CONFIG_FSL_SEC_MON
|
||||
#define CONFIG_SHA_PROG_HW_ACCEL
|
||||
#define CONFIG_DM
|
||||
#define CONFIG_RSA
|
||||
#define CONFIG_RSA_FREESCALE_EXP
|
||||
#ifndef CONFIG_FSL_CAAM
|
||||
#define CONFIG_FSL_CAAM
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_SECURE_BOOT
|
||||
#if defined(CONFIG_FSL_CORENET)
|
||||
|
@ -28,9 +41,31 @@
|
|||
defined(CONFIG_PPC_T1023) || \
|
||||
defined(CONFIG_PPC_T1024)
|
||||
#define CONFIG_SYS_CPC_REINIT_F
|
||||
#define CONFIG_KEY_REVOCATION
|
||||
#undef CONFIG_SYS_INIT_L3_ADDR
|
||||
#define CONFIG_SYS_INIT_L3_ADDR 0xbff00000
|
||||
#endif
|
||||
|
||||
#if defined(CONFIG_C29XPCIE)
|
||||
#define CONFIG_KEY_REVOCATION
|
||||
#endif
|
||||
|
||||
#if defined(CONFIG_PPC_P3041) || \
|
||||
defined(CONFIG_PPC_P4080) || \
|
||||
defined(CONFIG_PPC_P5020) || \
|
||||
defined(CONFIG_PPC_P5040) || \
|
||||
defined(CONFIG_PPC_P2041)
|
||||
#define CONFIG_FSL_TRUST_ARCH_v1
|
||||
#endif
|
||||
|
||||
#if defined(CONFIG_FSL_CORENET)
|
||||
/* The key used for verification of next level images
|
||||
* is picked up from an Extension Table which has
|
||||
* been verified by the ISBC (Internal Secure boot Code)
|
||||
* in boot ROM of the SoC
|
||||
*/
|
||||
#define CONFIG_FSL_ISBC_KEY_EXT
|
||||
#endif
|
||||
|
||||
#endif
|
||||
#endif
|
||||
|
|
|
@ -17,6 +17,7 @@
|
|||
#include <asm/fsl_i2c.h>
|
||||
#include <fsl_ifc.h>
|
||||
#include <fsl_sec.h>
|
||||
#include <fsl_sfp.h>
|
||||
#include <asm/fsl_lbc.h>
|
||||
#include <asm/fsl_fman.h>
|
||||
#include <fsl_immap.h>
|
||||
|
@ -2823,21 +2824,6 @@ struct ccsr_pman {
|
|||
u8 res_f4[0xf0c];
|
||||
};
|
||||
#endif
|
||||
#ifdef CONFIG_SYS_FSL_SFP_VER_3_0
|
||||
struct ccsr_sfp_regs {
|
||||
u32 ospr; /* 0x200 */
|
||||
u32 reserved0[14];
|
||||
u32 srk_hash[8]; /* 0x23c Super Root Key Hash */
|
||||
u32 oem_uid; /* 0x9c OEM Unique ID */
|
||||
u8 reserved2[0x04];
|
||||
u32 ovpr; /* 0xA4 Intent To Secure */
|
||||
u8 reserved4[0x08];
|
||||
u32 fsl_uid; /* 0xB0 FSL Unique ID */
|
||||
u8 reserved5[0x04];
|
||||
u32 fsl_spfr0; /* Scratch Pad Fuse Register 0 */
|
||||
u32 fsl_spfr1; /* Scratch Pad Fuse Register 1 */
|
||||
};
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_FSL_CORENET
|
||||
#define CONFIG_SYS_FSL_CORENET_CCM_OFFSET 0x0000
|
||||
|
@ -2897,6 +2883,7 @@ struct ccsr_sfp_regs {
|
|||
#define CONFIG_SYS_MPC85xx_SATA2_OFFSET 0x221000
|
||||
#define CONFIG_SYS_FSL_SEC_OFFSET 0x300000
|
||||
#define CONFIG_SYS_FSL_JR0_OFFSET 0x301000
|
||||
#define CONFIG_SYS_SEC_MON_OFFSET 0x314000
|
||||
#define CONFIG_SYS_FSL_CORENET_PME_OFFSET 0x316000
|
||||
#define CONFIG_SYS_FSL_QMAN_OFFSET 0x318000
|
||||
#define CONFIG_SYS_FSL_BMAN_OFFSET 0x31a000
|
||||
|
@ -2964,7 +2951,7 @@ struct ccsr_sfp_regs {
|
|||
#endif
|
||||
#define CONFIG_SYS_MPC85xx_SERDES2_OFFSET 0xE3100
|
||||
#define CONFIG_SYS_MPC85xx_SERDES1_OFFSET 0xE3000
|
||||
#define CONFIG_SYS_SNVS_OFFSET 0xE6000
|
||||
#define CONFIG_SYS_SEC_MON_OFFSET 0xE6000
|
||||
#define CONFIG_SYS_SFP_OFFSET 0xE7000
|
||||
#define CONFIG_SYS_MPC85xx_CPM_OFFSET 0x80000
|
||||
#define CONFIG_SYS_FSL_QMAN_OFFSET 0x88000
|
||||
|
@ -3094,6 +3081,9 @@ struct ccsr_sfp_regs {
|
|||
#define CONFIG_SYS_SFP_ADDR \
|
||||
(CONFIG_SYS_IMMR + CONFIG_SYS_SFP_OFFSET)
|
||||
|
||||
#define CONFIG_SYS_SEC_MON_ADDR \
|
||||
(CONFIG_SYS_IMMR + CONFIG_SYS_SEC_MON_OFFSET)
|
||||
|
||||
#define TSEC_BASE_ADDR (CONFIG_SYS_IMMR + CONFIG_SYS_TSEC1_OFFSET)
|
||||
#define MDIO_BASE_ADDR (CONFIG_SYS_IMMR + CONFIG_SYS_MDIO1_OFFSET)
|
||||
|
||||
|
|
|
@ -1202,12 +1202,17 @@ struct cpu_type {
|
|||
u32 soc_ver;
|
||||
u32 num_cores;
|
||||
u32 mask; /* which cpu(s) actually exist */
|
||||
#ifdef CONFIG_HETROGENOUS_CLUSTERS
|
||||
u32 dsp_num_cores;
|
||||
u32 dsp_mask; /* which DSP cpu(s) actually exist */
|
||||
#endif
|
||||
};
|
||||
|
||||
struct cpu_type *identify_cpu(u32 ver);
|
||||
int fixup_cpu(void);
|
||||
|
||||
int fsl_qoriq_core_to_cluster(unsigned int core);
|
||||
int fsl_qoriq_dsp_core_to_cluster(unsigned int core);
|
||||
|
||||
#if defined(CONFIG_MPC85xx) || defined(CONFIG_MPC86xx)
|
||||
#define CPU_TYPE_ENTRY(n, v, nc) \
|
||||
|
|
|
@ -72,4 +72,10 @@ obj-$(CONFIG_P5020DS) += p_corenet/
|
|||
obj-$(CONFIG_P5040DS) += p_corenet/
|
||||
|
||||
obj-$(CONFIG_LS102XA_NS_ACCESS) += ns_access.o
|
||||
|
||||
ifdef CONFIG_SECURE_BOOT
|
||||
obj-y += fsl_validate.o
|
||||
obj-$(CONFIG_CMD_ESBC_VALIDATE) += cmd_esbc_validate.o
|
||||
endif
|
||||
|
||||
endif
|
||||
|
|
34
board/freescale/common/cmd_esbc_validate.c
Normal file
34
board/freescale/common/cmd_esbc_validate.c
Normal file
|
@ -0,0 +1,34 @@
|
|||
/*
|
||||
* Copyright 2015 Freescale Semiconductor, Inc.
|
||||
*
|
||||
* SPDX-License-Identifier: GPL-2.0+
|
||||
*/
|
||||
|
||||
#include <common.h>
|
||||
#include <command.h>
|
||||
#include <fsl_validate.h>
|
||||
|
||||
static int do_esbc_validate(cmd_tbl_t *cmdtp, int flag, int argc,
|
||||
char * const argv[])
|
||||
{
|
||||
if (argc < 2)
|
||||
return cmd_usage(cmdtp);
|
||||
|
||||
return fsl_secboot_validate(cmdtp, flag, argc, argv);
|
||||
}
|
||||
|
||||
/***************************************************/
|
||||
static char esbc_validate_help_text[] =
|
||||
"esbc_validate hdr_addr <hash_val> - Validates signature using\n"
|
||||
" RSA verification\n"
|
||||
" $hdr_addr Address of header of the image\n"
|
||||
" to be validated.\n"
|
||||
" $hash_val -Optional\n"
|
||||
" It provides Hash of public/srk key to be\n"
|
||||
" used to verify signature.\n";
|
||||
|
||||
U_BOOT_CMD(
|
||||
esbc_validate, 3, 0, do_esbc_validate,
|
||||
"Validates signature on a given image using RSA verification",
|
||||
esbc_validate_help_text
|
||||
);
|
840
board/freescale/common/fsl_validate.c
Normal file
840
board/freescale/common/fsl_validate.c
Normal file
|
@ -0,0 +1,840 @@
|
|||
/*
|
||||
* Copyright 2015 Freescale Semiconductor, Inc.
|
||||
*
|
||||
* SPDX-License-Identifier: GPL-2.0+
|
||||
*/
|
||||
|
||||
#include <common.h>
|
||||
#include <fsl_validate.h>
|
||||
#include <fsl_secboot_err.h>
|
||||
#include <fsl_sfp.h>
|
||||
#include <fsl_sec.h>
|
||||
#include <command.h>
|
||||
#include <malloc.h>
|
||||
#include <dm/uclass.h>
|
||||
#include <u-boot/rsa-mod-exp.h>
|
||||
#include <hash.h>
|
||||
#include <fsl_secboot_err.h>
|
||||
#ifndef CONFIG_MPC85xx
|
||||
#include <asm/arch/immap_ls102xa.h>
|
||||
#endif
|
||||
|
||||
#define SHA256_BITS 256
|
||||
#define SHA256_BYTES (256/8)
|
||||
#define SHA256_NIBBLES (256/4)
|
||||
#define NUM_HEX_CHARS (sizeof(ulong) * 2)
|
||||
|
||||
/* This array contains DER value for SHA-256 */
|
||||
static const u8 hash_identifier[] = { 0x30, 0x31, 0x30, 0x0d, 0x06, 0x09, 0x60,
|
||||
0x86, 0x48, 0x01, 0x65, 0x03, 0x04, 0x02, 0x01, 0x05, 0x00,
|
||||
0x04, 0x20
|
||||
};
|
||||
|
||||
static u8 hash_val[SHA256_BYTES];
|
||||
static const u8 barker_code[ESBC_BARKER_LEN] = { 0x68, 0x39, 0x27, 0x81 };
|
||||
|
||||
void branch_to_self(void) __attribute__ ((noreturn));
|
||||
|
||||
/*
|
||||
* This function will put core in infinite loop.
|
||||
* This will be called when the ESBC can not proceed further due
|
||||
* to some unknown errors.
|
||||
*/
|
||||
void branch_to_self(void)
|
||||
{
|
||||
printf("Core is in infinite loop due to errors.\n");
|
||||
self:
|
||||
goto self;
|
||||
}
|
||||
|
||||
#if defined(CONFIG_FSL_ISBC_KEY_EXT)
|
||||
static u32 check_ie(struct fsl_secboot_img_priv *img)
|
||||
{
|
||||
if (img->hdr.ie_flag)
|
||||
return 1;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* This function returns the CSF Header Address of uboot
|
||||
* For MPC85xx based platforms, the LAW mapping for NOR
|
||||
* flash changes in uboot code. Hence the offset needs
|
||||
* to be calculated and added to the new NOR flash base
|
||||
* address
|
||||
*/
|
||||
#if defined(CONFIG_MPC85xx)
|
||||
int get_csf_base_addr(ulong *csf_addr, ulong *flash_base_addr)
|
||||
{
|
||||
struct ccsr_gur __iomem *gur = (void *)(CONFIG_SYS_MPC85xx_GUTS_ADDR);
|
||||
u32 csf_hdr_addr = in_be32(&gur->scratchrw[0]);
|
||||
u32 csf_flash_offset = csf_hdr_addr & ~(CONFIG_SYS_PBI_FLASH_BASE);
|
||||
ulong flash_addr, addr;
|
||||
int found = 0;
|
||||
int i = 0;
|
||||
|
||||
for (i = 0; i < CONFIG_SYS_MAX_FLASH_BANKS; i++) {
|
||||
flash_addr = flash_info[i].start[0];
|
||||
addr = flash_info[i].start[0] + csf_flash_offset;
|
||||
if (memcmp((u8 *)addr, barker_code, ESBC_BARKER_LEN) == 0) {
|
||||
debug("Barker found on addr %lx\n", addr);
|
||||
found = 1;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (!found)
|
||||
return -1;
|
||||
|
||||
*csf_addr = addr;
|
||||
*flash_base_addr = flash_addr;
|
||||
|
||||
return 0;
|
||||
}
|
||||
#else
|
||||
/* For platforms like LS1020, correct flash address is present in
|
||||
* the header. So the function reqturns flash base address as 0
|
||||
*/
|
||||
int get_csf_base_addr(ulong *csf_addr, ulong *flash_base_addr)
|
||||
{
|
||||
struct ccsr_gur __iomem *gur = (void *)(CONFIG_SYS_FSL_GUTS_ADDR);
|
||||
u32 csf_hdr_addr = in_be32(&gur->scratchrw[0]);
|
||||
|
||||
if (memcmp((u8 *)csf_hdr_addr, barker_code, ESBC_BARKER_LEN))
|
||||
return -1;
|
||||
|
||||
*csf_addr = csf_hdr_addr;
|
||||
*flash_base_addr = 0;
|
||||
return 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
static int get_ie_info_addr(ulong *ie_addr)
|
||||
{
|
||||
struct fsl_secboot_img_hdr *hdr;
|
||||
struct fsl_secboot_sg_table *sg_tbl;
|
||||
ulong flash_base_addr, csf_addr;
|
||||
|
||||
if (get_csf_base_addr(&csf_addr, &flash_base_addr))
|
||||
return -1;
|
||||
|
||||
hdr = (struct fsl_secboot_img_hdr *)csf_addr;
|
||||
|
||||
/* For SoC's with Trust Architecture v1 with corenet bus
|
||||
* the sg table field in CSF header has absolute address
|
||||
* for sg table in memory. In other Trust Architecture,
|
||||
* this field specifies the offset of sg table from the
|
||||
* base address of CSF Header
|
||||
*/
|
||||
#if defined(CONFIG_FSL_TRUST_ARCH_v1) && defined(CONFIG_FSL_CORENET)
|
||||
sg_tbl = (struct fsl_secboot_sg_table *)
|
||||
(((ulong)hdr->psgtable & ~(CONFIG_SYS_PBI_FLASH_BASE)) +
|
||||
flash_base_addr);
|
||||
#else
|
||||
sg_tbl = (struct fsl_secboot_sg_table *)(csf_addr +
|
||||
(ulong)hdr->psgtable);
|
||||
#endif
|
||||
|
||||
/* IE Key Table is the first entry in the SG Table */
|
||||
#if defined(CONFIG_MPC85xx)
|
||||
*ie_addr = (sg_tbl->src_addr & ~(CONFIG_SYS_PBI_FLASH_BASE)) +
|
||||
flash_base_addr;
|
||||
#else
|
||||
*ie_addr = sg_tbl->src_addr;
|
||||
#endif
|
||||
|
||||
debug("IE Table address is %lx\n", *ie_addr);
|
||||
return 0;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_KEY_REVOCATION
|
||||
/* This function checks srk_table_flag in header and set/reset srk_flag.*/
|
||||
static u32 check_srk(struct fsl_secboot_img_priv *img)
|
||||
{
|
||||
if (img->hdr.len_kr.srk_table_flag & SRK_FLAG)
|
||||
return 1;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* This function returns ospr's key_revoc values.*/
|
||||
static u32 get_key_revoc(void)
|
||||
{
|
||||
struct ccsr_sfp_regs *sfp_regs = (void *)(CONFIG_SYS_SFP_ADDR);
|
||||
return (sfp_in32(&sfp_regs->ospr) & OSPR_KEY_REVOC_MASK) >>
|
||||
OSPR_KEY_REVOC_SHIFT;
|
||||
}
|
||||
|
||||
/* This function checks if selected key is revoked or not.*/
|
||||
static u32 is_key_revoked(u32 keynum, u32 rev_flag)
|
||||
{
|
||||
if (keynum == UNREVOCABLE_KEY)
|
||||
return 0;
|
||||
|
||||
if ((u32)(1 << (ALIGN_REVOC_KEY - keynum)) & rev_flag)
|
||||
return 1;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* It validates srk_table key lengths.*/
|
||||
static u32 validate_srk_tbl(struct srk_table *tbl, u32 num_entries)
|
||||
{
|
||||
int i = 0;
|
||||
for (i = 0; i < num_entries; i++) {
|
||||
if (!((tbl[i].key_len == 2 * KEY_SIZE_BYTES/4) ||
|
||||
(tbl[i].key_len == 2 * KEY_SIZE_BYTES/2) ||
|
||||
(tbl[i].key_len == 2 * KEY_SIZE_BYTES)))
|
||||
return ERROR_ESBC_CLIENT_HEADER_INV_SRK_ENTRY_KEYLEN;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
/* This function return length of public key.*/
|
||||
static inline u32 get_key_len(struct fsl_secboot_img_priv *img)
|
||||
{
|
||||
return img->key_len;
|
||||
}
|
||||
|
||||
/*
|
||||
* Handles the ESBC uboot client header verification failure.
|
||||
* This function handles all the errors which might occur in the
|
||||
* parsing and checking of ESBC uboot client header. It will also
|
||||
* set the error bits in the SEC_MON.
|
||||
*/
|
||||
static void fsl_secboot_header_verification_failure(void)
|
||||
{
|
||||
struct ccsr_sec_mon_regs *sec_mon_regs = (void *)
|
||||
(CONFIG_SYS_SEC_MON_ADDR);
|
||||
struct ccsr_sfp_regs *sfp_regs = (void *)(CONFIG_SYS_SFP_ADDR);
|
||||
u32 sts = sec_mon_in32(&sec_mon_regs->hp_stat);
|
||||
|
||||
/* 29th bit of OSPR is ITS */
|
||||
u32 its = sfp_in32(&sfp_regs->ospr) >> 2;
|
||||
|
||||
/*
|
||||
* Read the SEC_MON status register
|
||||
* Read SSM_ST field
|
||||
*/
|
||||
sts = sec_mon_in32(&sec_mon_regs->hp_stat);
|
||||
if ((sts & HPSR_SSM_ST_MASK) == HPSR_SSM_ST_TRUST) {
|
||||
if (its == 1)
|
||||
change_sec_mon_state(HPSR_SSM_ST_TRUST,
|
||||
HPSR_SSM_ST_SOFT_FAIL);
|
||||
else
|
||||
change_sec_mon_state(HPSR_SSM_ST_TRUST,
|
||||
HPSR_SSM_ST_NON_SECURE);
|
||||
}
|
||||
|
||||
printf("Generating reset request\n");
|
||||
do_reset(NULL, 0, 0, NULL);
|
||||
}
|
||||
|
||||
/*
|
||||
* Handles the ESBC uboot client image verification failure.
|
||||
* This function handles all the errors which might occur in the
|
||||
* public key hash comparison and signature verification of
|
||||
* ESBC uboot client image. It will also
|
||||
* set the error bits in the SEC_MON.
|
||||
*/
|
||||
static void fsl_secboot_image_verification_failure(void)
|
||||
{
|
||||
struct ccsr_sec_mon_regs *sec_mon_regs = (void *)
|
||||
(CONFIG_SYS_SEC_MON_ADDR);
|
||||
struct ccsr_sfp_regs *sfp_regs = (void *)(CONFIG_SYS_SFP_ADDR);
|
||||
u32 sts = sec_mon_in32(&sec_mon_regs->hp_stat);
|
||||
|
||||
u32 its = sfp_in32(&sfp_regs->ospr) & ITS_MASK >> ITS_BIT;
|
||||
|
||||
/*
|
||||
* Read the SEC_MON status register
|
||||
* Read SSM_ST field
|
||||
*/
|
||||
sts = sec_mon_in32(&sec_mon_regs->hp_stat);
|
||||
if ((sts & HPSR_SSM_ST_MASK) == HPSR_SSM_ST_TRUST) {
|
||||
if (its == 1) {
|
||||
change_sec_mon_state(HPSR_SSM_ST_TRUST,
|
||||
HPSR_SSM_ST_SOFT_FAIL);
|
||||
|
||||
printf("Generating reset request\n");
|
||||
do_reset(NULL, 0, 0, NULL);
|
||||
} else {
|
||||
change_sec_mon_state(HPSR_SSM_ST_TRUST,
|
||||
HPSR_SSM_ST_NON_SECURE);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void fsl_secboot_bootscript_parse_failure(void)
|
||||
{
|
||||
fsl_secboot_header_verification_failure();
|
||||
}
|
||||
|
||||
/*
|
||||
* Handles the errors in esbc boot.
|
||||
* This function handles all the errors which might occur in the
|
||||
* esbc boot phase. It will call the appropriate api to log the
|
||||
* errors and set the error bits in the SEC_MON.
|
||||
*/
|
||||
void fsl_secboot_handle_error(int error)
|
||||
{
|
||||
const struct fsl_secboot_errcode *e;
|
||||
|
||||
for (e = fsl_secboot_errcodes; e->errcode != ERROR_ESBC_CLIENT_MAX;
|
||||
e++) {
|
||||
if (e->errcode == error)
|
||||
printf("ERROR :: %x :: %s\n", error, e->name);
|
||||
}
|
||||
|
||||
switch (error) {
|
||||
case ERROR_ESBC_CLIENT_HEADER_BARKER:
|
||||
case ERROR_ESBC_CLIENT_HEADER_IMG_SIZE:
|
||||
case ERROR_ESBC_CLIENT_HEADER_KEY_LEN:
|
||||
case ERROR_ESBC_CLIENT_HEADER_SIG_LEN:
|
||||
case ERROR_ESBC_CLIENT_HEADER_KEY_LEN_NOT_TWICE_SIG_LEN:
|
||||
case ERROR_ESBC_CLIENT_HEADER_KEY_MOD_1:
|
||||
case ERROR_ESBC_CLIENT_HEADER_KEY_MOD_2:
|
||||
case ERROR_ESBC_CLIENT_HEADER_SIG_KEY_MOD:
|
||||
case ERROR_ESBC_CLIENT_HEADER_SG_ESBC_EP:
|
||||
case ERROR_ESBC_CLIENT_HEADER_SG_ENTIRES_BAD:
|
||||
#ifdef CONFIG_KEY_REVOCATION
|
||||
case ERROR_ESBC_CLIENT_HEADER_KEY_REVOKED:
|
||||
case ERROR_ESBC_CLIENT_HEADER_INVALID_SRK_NUM_ENTRY:
|
||||
case ERROR_ESBC_CLIENT_HEADER_INVALID_KEY_NUM:
|
||||
case ERROR_ESBC_CLIENT_HEADER_INV_SRK_ENTRY_KEYLEN:
|
||||
#endif
|
||||
#if defined(CONFIG_FSL_ISBC_KEY_EXT)
|
||||
/*@fallthrough@*/
|
||||
case ERROR_ESBC_CLIENT_HEADER_IE_KEY_REVOKED:
|
||||
case ERROR_ESBC_CLIENT_HEADER_INVALID_IE_NUM_ENTRY:
|
||||
case ERROR_ESBC_CLIENT_HEADER_INVALID_IE_KEY_NUM:
|
||||
case ERROR_ESBC_CLIENT_HEADER_INV_IE_ENTRY_KEYLEN:
|
||||
case ERROR_IE_TABLE_NOT_FOUND:
|
||||
#endif
|
||||
fsl_secboot_header_verification_failure();
|
||||
break;
|
||||
case ERROR_ESBC_SEC_RESET:
|
||||
case ERROR_ESBC_SEC_DEQ:
|
||||
case ERROR_ESBC_SEC_ENQ:
|
||||
case ERROR_ESBC_SEC_DEQ_TO:
|
||||
case ERROR_ESBC_SEC_JOBQ_STATUS:
|
||||
case ERROR_ESBC_CLIENT_HASH_COMPARE_KEY:
|
||||
case ERROR_ESBC_CLIENT_HASH_COMPARE_EM:
|
||||
fsl_secboot_image_verification_failure();
|
||||
break;
|
||||
case ERROR_ESBC_MISSING_BOOTM:
|
||||
fsl_secboot_bootscript_parse_failure();
|
||||
break;
|
||||
case ERROR_ESBC_WRONG_CMD:
|
||||
default:
|
||||
branch_to_self();
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
static void fsl_secblk_handle_error(int error)
|
||||
{
|
||||
switch (error) {
|
||||
case ERROR_ESBC_SEC_ENQ:
|
||||
fsl_secboot_handle_error(ERROR_ESBC_SEC_ENQ);
|
||||
break;
|
||||
case ERROR_ESBC_SEC_DEQ:
|
||||
fsl_secboot_handle_error(ERROR_ESBC_SEC_DEQ);
|
||||
break;
|
||||
case ERROR_ESBC_SEC_DEQ_TO:
|
||||
fsl_secboot_handle_error(ERROR_ESBC_SEC_DEQ_TO);
|
||||
break;
|
||||
default:
|
||||
printf("Job Queue Output status %x\n", error);
|
||||
fsl_secboot_handle_error(ERROR_ESBC_SEC_JOBQ_STATUS);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Calculate hash of key obtained via offset present in ESBC uboot
|
||||
* client hdr. This function calculates the hash of key which is obtained
|
||||
* through offset present in ESBC uboot client header.
|
||||
*/
|
||||
static int calc_img_key_hash(struct fsl_secboot_img_priv *img)
|
||||
{
|
||||
struct hash_algo *algo;
|
||||
void *ctx;
|
||||
int i, srk = 0;
|
||||
int ret = 0;
|
||||
const char *algo_name = "sha256";
|
||||
|
||||
/* Calculate hash of the esbc key */
|
||||
ret = hash_progressive_lookup_algo(algo_name, &algo);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
ret = algo->hash_init(algo, &ctx);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
/* Update hash for ESBC key */
|
||||
#ifdef CONFIG_KEY_REVOCATION
|
||||
if (check_srk(img)) {
|
||||
ret = algo->hash_update(algo, ctx,
|
||||
(u8 *)(img->ehdrloc + img->hdr.srk_tbl_off),
|
||||
img->hdr.len_kr.num_srk * sizeof(struct srk_table), 1);
|
||||
srk = 1;
|
||||
}
|
||||
#endif
|
||||
if (!srk)
|
||||
ret = algo->hash_update(algo, ctx,
|
||||
img->img_key, img->key_len, 1);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
/* Copy hash at destination buffer */
|
||||
ret = algo->hash_finish(algo, ctx, hash_val, algo->digest_size);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
for (i = 0; i < SHA256_BYTES; i++)
|
||||
img->img_key_hash[i] = hash_val[i];
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*
|
||||
* Calculate hash of ESBC hdr and ESBC. This function calculates the
|
||||
* single hash of ESBC header and ESBC image. If SG flag is on, all
|
||||
* SG entries are also hashed alongwith the complete SG table.
|
||||
*/
|
||||
static int calc_esbchdr_esbc_hash(struct fsl_secboot_img_priv *img)
|
||||
{
|
||||
struct hash_algo *algo;
|
||||
void *ctx;
|
||||
int ret = 0;
|
||||
int key_hash = 0;
|
||||
const char *algo_name = "sha256";
|
||||
|
||||
/* Calculate the hash of the ESBC */
|
||||
ret = hash_progressive_lookup_algo(algo_name, &algo);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
ret = algo->hash_init(algo, &ctx);
|
||||
/* Copy hash at destination buffer */
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
/* Update hash for CSF Header */
|
||||
ret = algo->hash_update(algo, ctx,
|
||||
(u8 *)&img->hdr, sizeof(struct fsl_secboot_img_hdr), 0);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
/* Update the hash with that of srk table if srk flag is 1
|
||||
* If IE Table is selected, key is not added in the hash
|
||||
* If neither srk table nor IE key table available, add key
|
||||
* from header in the hash calculation
|
||||
*/
|
||||
#ifdef CONFIG_KEY_REVOCATION
|
||||
if (check_srk(img)) {
|
||||
ret = algo->hash_update(algo, ctx,
|
||||
(u8 *)(img->ehdrloc + img->hdr.srk_tbl_off),
|
||||
img->hdr.len_kr.num_srk * sizeof(struct srk_table), 0);
|
||||
key_hash = 1;
|
||||
}
|
||||
#endif
|
||||
#if defined(CONFIG_FSL_ISBC_KEY_EXT)
|
||||
if (!key_hash && check_ie(img))
|
||||
key_hash = 1;
|
||||
#endif
|
||||
if (!key_hash)
|
||||
ret = algo->hash_update(algo, ctx,
|
||||
img->img_key, img->hdr.key_len, 0);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
/* Update hash for actual Image */
|
||||
ret = algo->hash_update(algo, ctx,
|
||||
(u8 *)img->hdr.pimg, img->hdr.img_size, 1);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
/* Copy hash at destination buffer */
|
||||
ret = algo->hash_finish(algo, ctx, hash_val, algo->digest_size);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*
|
||||
* Construct encoded hash EM' wrt PKCSv1.5. This function calculates the
|
||||
* pointers for padding, DER value and hash. And finally, constructs EM'
|
||||
* which includes hash of complete CSF header and ESBC image. If SG flag
|
||||
* is on, hash of SG table and entries is also included.
|
||||
*/
|
||||
static void construct_img_encoded_hash_second(struct fsl_secboot_img_priv *img)
|
||||
{
|
||||
/*
|
||||
* RSA PKCSv1.5 encoding format for encoded message is below
|
||||
* EM = 0x0 || 0x1 || PS || 0x0 || DER || Hash
|
||||
* PS is Padding String
|
||||
* DER is DER value for SHA-256
|
||||
* Hash is SHA-256 hash
|
||||
* *********************************************************
|
||||
* representative points to first byte of EM initially and is
|
||||
* filled with 0x0
|
||||
* representative is incremented by 1 and second byte is filled
|
||||
* with 0x1
|
||||
* padding points to third byte of EM
|
||||
* digest points to full length of EM - 32 bytes
|
||||
* hash_id (DER value) points to 19 bytes before pDigest
|
||||
* separator is one byte which separates padding and DER
|
||||
*/
|
||||
|
||||
size_t len;
|
||||
u8 *representative;
|
||||
u8 *padding, *digest;
|
||||
u8 *hash_id, *separator;
|
||||
int i;
|
||||
|
||||
len = (get_key_len(img) / 2) - 1;
|
||||
representative = img->img_encoded_hash_second;
|
||||
representative[0] = 0;
|
||||
representative[1] = 1; /* block type 1 */
|
||||
|
||||
padding = &representative[2];
|
||||
digest = &representative[1] + len - 32;
|
||||
hash_id = digest - sizeof(hash_identifier);
|
||||
separator = hash_id - 1;
|
||||
|
||||
/* fill padding area pointed by padding with 0xff */
|
||||
memset(padding, 0xff, separator - padding);
|
||||
|
||||
/* fill byte pointed by separator */
|
||||
*separator = 0;
|
||||
|
||||
/* fill SHA-256 DER value pointed by HashId */
|
||||
memcpy(hash_id, hash_identifier, sizeof(hash_identifier));
|
||||
|
||||
/* fill hash pointed by Digest */
|
||||
for (i = 0; i < SHA256_BYTES; i++)
|
||||
digest[i] = hash_val[i];
|
||||
}
|
||||
|
||||
/*
|
||||
* Reads and validates the ESBC client header.
|
||||
* This function reads key and signature from the ESBC client header.
|
||||
* If Scatter/Gather flag is on, lengths and offsets of images
|
||||
* present as SG entries are also read. This function also checks
|
||||
* whether the header is valid or not.
|
||||
*/
|
||||
static int read_validate_esbc_client_header(struct fsl_secboot_img_priv *img)
|
||||
{
|
||||
char buf[20];
|
||||
struct fsl_secboot_img_hdr *hdr = &img->hdr;
|
||||
void *esbc = (u8 *)img->ehdrloc;
|
||||
u8 *k, *s;
|
||||
#ifdef CONFIG_KEY_REVOCATION
|
||||
u32 ret;
|
||||
u32 key_num, key_revoc_flag, size;
|
||||
#endif
|
||||
#if defined(CONFIG_FSL_ISBC_KEY_EXT)
|
||||
struct ie_key_info *ie_info;
|
||||
u32 ie_num, ie_revoc_flag, ie_key_len;
|
||||
#endif
|
||||
int key_found = 0;
|
||||
|
||||
/* check barker code */
|
||||
if (memcmp(hdr->barker, barker_code, ESBC_BARKER_LEN))
|
||||
return ERROR_ESBC_CLIENT_HEADER_BARKER;
|
||||
|
||||
sprintf(buf, "%p", hdr->pimg);
|
||||
setenv("img_addr", buf);
|
||||
|
||||
if (!hdr->img_size)
|
||||
return ERROR_ESBC_CLIENT_HEADER_IMG_SIZE;
|
||||
|
||||
/* Key checking*/
|
||||
#ifdef CONFIG_KEY_REVOCATION
|
||||
if (check_srk(img)) {
|
||||
if ((hdr->len_kr.num_srk == 0) ||
|
||||
(hdr->len_kr.num_srk > MAX_KEY_ENTRIES))
|
||||
return ERROR_ESBC_CLIENT_HEADER_INVALID_SRK_NUM_ENTRY;
|
||||
|
||||
key_num = hdr->len_kr.srk_sel;
|
||||
if (key_num == 0 || key_num > hdr->len_kr.num_srk)
|
||||
return ERROR_ESBC_CLIENT_HEADER_INVALID_KEY_NUM;
|
||||
|
||||
/* Get revoc key from sfp */
|
||||
key_revoc_flag = get_key_revoc();
|
||||
ret = is_key_revoked(key_num, key_revoc_flag);
|
||||
if (ret)
|
||||
return ERROR_ESBC_CLIENT_HEADER_KEY_REVOKED;
|
||||
|
||||
size = hdr->len_kr.num_srk * sizeof(struct srk_table);
|
||||
|
||||
memcpy(&img->srk_tbl, esbc + hdr->srk_tbl_off, size);
|
||||
|
||||
ret = validate_srk_tbl(img->srk_tbl, hdr->len_kr.num_srk);
|
||||
|
||||
if (ret != 0)
|
||||
return ret;
|
||||
|
||||
img->key_len = img->srk_tbl[key_num - 1].key_len;
|
||||
|
||||
memcpy(&img->img_key, &(img->srk_tbl[key_num - 1].pkey),
|
||||
img->key_len);
|
||||
|
||||
key_found = 1;
|
||||
}
|
||||
#endif
|
||||
|
||||
#if defined(CONFIG_FSL_ISBC_KEY_EXT)
|
||||
if (!key_found && check_ie(img)) {
|
||||
if (get_ie_info_addr(&img->ie_addr))
|
||||
return ERROR_IE_TABLE_NOT_FOUND;
|
||||
ie_info = (struct ie_key_info *)img->ie_addr;
|
||||
if (ie_info->num_keys == 0 || ie_info->num_keys > 32)
|
||||
return ERROR_ESBC_CLIENT_HEADER_INVALID_IE_NUM_ENTRY;
|
||||
|
||||
ie_num = hdr->ie_key_sel;
|
||||
if (ie_num == 0 || ie_num > ie_info->num_keys)
|
||||
return ERROR_ESBC_CLIENT_HEADER_INVALID_IE_KEY_NUM;
|
||||
|
||||
ie_revoc_flag = ie_info->key_revok;
|
||||
if ((u32)(1 << (ie_num - 1)) & ie_revoc_flag)
|
||||
return ERROR_ESBC_CLIENT_HEADER_IE_KEY_REVOKED;
|
||||
|
||||
ie_key_len = ie_info->ie_key_tbl[ie_num - 1].key_len;
|
||||
|
||||
if (!((ie_key_len == 2 * KEY_SIZE_BYTES / 4) ||
|
||||
(ie_key_len == 2 * KEY_SIZE_BYTES / 2) ||
|
||||
(ie_key_len == 2 * KEY_SIZE_BYTES)))
|
||||
return ERROR_ESBC_CLIENT_HEADER_INV_IE_ENTRY_KEYLEN;
|
||||
|
||||
memcpy(&img->img_key, &(ie_info->ie_key_tbl[ie_num - 1].pkey),
|
||||
ie_key_len);
|
||||
|
||||
img->key_len = ie_key_len;
|
||||
key_found = 1;
|
||||
}
|
||||
#endif
|
||||
|
||||
if (key_found == 0) {
|
||||
/* check key length */
|
||||
if (!((hdr->key_len == 2 * KEY_SIZE_BYTES / 4) ||
|
||||
(hdr->key_len == 2 * KEY_SIZE_BYTES / 2) ||
|
||||
(hdr->key_len == 2 * KEY_SIZE_BYTES)))
|
||||
return ERROR_ESBC_CLIENT_HEADER_KEY_LEN;
|
||||
|
||||
memcpy(&img->img_key, esbc + hdr->pkey, hdr->key_len);
|
||||
|
||||
img->key_len = hdr->key_len;
|
||||
|
||||
key_found = 1;
|
||||
}
|
||||
|
||||
/* check signaure */
|
||||
if (get_key_len(img) == 2 * hdr->sign_len) {
|
||||
/* check signature length */
|
||||
if (!((hdr->sign_len == KEY_SIZE_BYTES / 4) ||
|
||||
(hdr->sign_len == KEY_SIZE_BYTES / 2) ||
|
||||
(hdr->sign_len == KEY_SIZE_BYTES)))
|
||||
return ERROR_ESBC_CLIENT_HEADER_SIG_LEN;
|
||||
} else {
|
||||
return ERROR_ESBC_CLIENT_HEADER_KEY_LEN_NOT_TWICE_SIG_LEN;
|
||||
}
|
||||
|
||||
memcpy(&img->img_sign, esbc + hdr->psign, hdr->sign_len);
|
||||
|
||||
/* No SG support */
|
||||
if (hdr->sg_flag)
|
||||
return ERROR_ESBC_CLIENT_HEADER_SG;
|
||||
|
||||
/* modulus most significant bit should be set */
|
||||
k = (u8 *)&img->img_key;
|
||||
|
||||
if ((k[0] & 0x80) == 0)
|
||||
return ERROR_ESBC_CLIENT_HEADER_KEY_MOD_1;
|
||||
|
||||
/* modulus value should be odd */
|
||||
if ((k[get_key_len(img) / 2 - 1] & 0x1) == 0)
|
||||
return ERROR_ESBC_CLIENT_HEADER_KEY_MOD_2;
|
||||
|
||||
/* Check signature value < modulus value */
|
||||
s = (u8 *)&img->img_sign;
|
||||
|
||||
if (!(memcmp(s, k, hdr->sign_len) < 0))
|
||||
return ERROR_ESBC_CLIENT_HEADER_SIG_KEY_MOD;
|
||||
|
||||
return ESBC_VALID_HDR;
|
||||
}
|
||||
|
||||
static inline int str2longbe(const char *p, ulong *num)
|
||||
{
|
||||
char *endptr;
|
||||
ulong tmp;
|
||||
|
||||
if (!p) {
|
||||
return 0;
|
||||
} else {
|
||||
tmp = simple_strtoul(p, &endptr, 16);
|
||||
if (sizeof(ulong) == 4)
|
||||
*num = cpu_to_be32(tmp);
|
||||
else
|
||||
*num = cpu_to_be64(tmp);
|
||||
}
|
||||
|
||||
return *p != '\0' && *endptr == '\0';
|
||||
}
|
||||
|
||||
int fsl_secboot_validate(cmd_tbl_t *cmdtp, int flag, int argc,
|
||||
char * const argv[])
|
||||
{
|
||||
struct ccsr_sfp_regs *sfp_regs = (void *)(CONFIG_SYS_SFP_ADDR);
|
||||
ulong hash[SHA256_BYTES/sizeof(ulong)];
|
||||
char hash_str[NUM_HEX_CHARS + 1];
|
||||
ulong addr = simple_strtoul(argv[1], NULL, 16);
|
||||
struct fsl_secboot_img_priv *img;
|
||||
struct fsl_secboot_img_hdr *hdr;
|
||||
void *esbc;
|
||||
int ret, i, hash_cmd = 0;
|
||||
u32 srk_hash[8];
|
||||
uint32_t key_len;
|
||||
struct key_prop prop;
|
||||
#if !defined(USE_HOSTCC)
|
||||
struct udevice *mod_exp_dev;
|
||||
#endif
|
||||
|
||||
if (argc == 3) {
|
||||
char *cp = argv[2];
|
||||
int i = 0;
|
||||
|
||||
if (*cp == '0' && *(cp + 1) == 'x')
|
||||
cp += 2;
|
||||
|
||||
/* The input string expected is in hex, where
|
||||
* each 4 bits would be represented by a hex
|
||||
* sha256 hash is 256 bits long, which would mean
|
||||
* num of characters = 256 / 4
|
||||
*/
|
||||
if (strlen(cp) != SHA256_NIBBLES) {
|
||||
printf("%s is not a 256 bits hex string as expected\n",
|
||||
argv[2]);
|
||||
return -1;
|
||||
}
|
||||
|
||||
for (i = 0; i < sizeof(hash)/sizeof(ulong); i++) {
|
||||
strncpy(hash_str, cp + (i * NUM_HEX_CHARS),
|
||||
NUM_HEX_CHARS);
|
||||
hash_str[NUM_HEX_CHARS] = '\0';
|
||||
if (!str2longbe(hash_str, &hash[i])) {
|
||||
printf("%s is not a 256 bits hex string ",
|
||||
argv[2]);
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
hash_cmd = 1;
|
||||
}
|
||||
|
||||
img = malloc(sizeof(struct fsl_secboot_img_priv));
|
||||
|
||||
if (!img)
|
||||
return -1;
|
||||
|
||||
memset(img, 0, sizeof(struct fsl_secboot_img_priv));
|
||||
|
||||
hdr = &img->hdr;
|
||||
img->ehdrloc = addr;
|
||||
esbc = (u8 *)img->ehdrloc;
|
||||
|
||||
memcpy(hdr, esbc, sizeof(struct fsl_secboot_img_hdr));
|
||||
|
||||
/* read and validate esbc header */
|
||||
ret = read_validate_esbc_client_header(img);
|
||||
|
||||
if (ret != ESBC_VALID_HDR) {
|
||||
fsl_secboot_handle_error(ret);
|
||||
goto exit;
|
||||
}
|
||||
|
||||
/* SRKH present in SFP */
|
||||
for (i = 0; i < NUM_SRKH_REGS; i++)
|
||||
srk_hash[i] = srk_in32(&sfp_regs->srk_hash[i]);
|
||||
|
||||
/*
|
||||
* Calculate hash of key obtained via offset present in
|
||||
* ESBC uboot client hdr
|
||||
*/
|
||||
ret = calc_img_key_hash(img);
|
||||
if (ret) {
|
||||
fsl_secblk_handle_error(ret);
|
||||
goto exit;
|
||||
}
|
||||
|
||||
/* Compare hash obtained above with SRK hash present in SFP */
|
||||
if (hash_cmd)
|
||||
ret = memcmp(&hash, &img->img_key_hash, SHA256_BYTES);
|
||||
else
|
||||
ret = memcmp(srk_hash, img->img_key_hash, SHA256_BYTES);
|
||||
|
||||
#if defined(CONFIG_FSL_ISBC_KEY_EXT)
|
||||
if (!hash_cmd && check_ie(img))
|
||||
ret = 0;
|
||||
#endif
|
||||
|
||||
if (ret != 0) {
|
||||
fsl_secboot_handle_error(ERROR_ESBC_CLIENT_HASH_COMPARE_KEY);
|
||||
goto exit;
|
||||
}
|
||||
|
||||
ret = calc_esbchdr_esbc_hash(img);
|
||||
if (ret) {
|
||||
fsl_secblk_handle_error(ret);
|
||||
goto exit;
|
||||
}
|
||||
|
||||
/* Construct encoded hash EM' wrt PKCSv1.5 */
|
||||
construct_img_encoded_hash_second(img);
|
||||
|
||||
/* Fill prop structure for public key */
|
||||
memset(&prop, 0, sizeof(struct key_prop));
|
||||
key_len = get_key_len(img) / 2;
|
||||
prop.modulus = img->img_key;
|
||||
prop.public_exponent = img->img_key + key_len;
|
||||
prop.num_bits = key_len * 8;
|
||||
prop.exp_len = key_len;
|
||||
|
||||
ret = uclass_get_device(UCLASS_MOD_EXP, 0, &mod_exp_dev);
|
||||
if (ret) {
|
||||
printf("RSA: Can't find Modular Exp implementation\n");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
ret = rsa_mod_exp(mod_exp_dev, img->img_sign, img->hdr.sign_len,
|
||||
&prop, img->img_encoded_hash);
|
||||
if (ret) {
|
||||
fsl_secblk_handle_error(ret);
|
||||
goto exit;
|
||||
}
|
||||
|
||||
/*
|
||||
* compare the encoded messages EM' and EM wrt RSA PKCSv1.5
|
||||
* memcmp returns zero on success
|
||||
* memcmp returns non-zero on failure
|
||||
*/
|
||||
ret = memcmp(&img->img_encoded_hash_second, &img->img_encoded_hash,
|
||||
img->hdr.sign_len);
|
||||
|
||||
if (ret) {
|
||||
fsl_secboot_handle_error(ERROR_ESBC_CLIENT_HASH_COMPARE_EM);
|
||||
goto exit;
|
||||
}
|
||||
|
||||
printf("esbc_validate command successful\n");
|
||||
|
||||
exit:
|
||||
return 0;
|
||||
}
|
|
@ -16,21 +16,6 @@
|
|||
|
||||
DECLARE_GLOBAL_DATA_PTR;
|
||||
|
||||
int fsl_ddr_get_dimm_params(dimm_params_t *pdimm,
|
||||
unsigned int controller_number,
|
||||
unsigned int dimm_number)
|
||||
{
|
||||
const char dimm_model[] = "RAW timing DDR";
|
||||
|
||||
if ((controller_number == 0) && (dimm_number == 0)) {
|
||||
memcpy(pdimm, &ddr_raw_timing, sizeof(dimm_params_t));
|
||||
memset(pdimm->mpart, 0, sizeof(pdimm->mpart));
|
||||
memcpy(pdimm->mpart, dimm_model, sizeof(dimm_model) - 1);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
void fsl_ddr_board_options(memctl_options_t *popts,
|
||||
dimm_params_t *pdimm,
|
||||
unsigned int ctrl_num)
|
||||
|
|
|
@ -6,35 +6,6 @@
|
|||
|
||||
#ifndef __DDR_H__
|
||||
#define __DDR_H__
|
||||
dimm_params_t ddr_raw_timing = {
|
||||
.n_ranks = 2,
|
||||
.rank_density = 2147483648u,
|
||||
.capacity = 4294967296u,
|
||||
.primary_sdram_width = 64,
|
||||
.ec_sdram_width = 8,
|
||||
.registered_dimm = 0,
|
||||
.mirrored_dimm = 0,
|
||||
.n_row_addr = 15,
|
||||
.n_col_addr = 10,
|
||||
.n_banks_per_sdram_device = 8,
|
||||
.edc_config = 2, /* ECC */
|
||||
.burst_lengths_bitmask = 0x0c,
|
||||
.tckmin_x_ps = 1071,
|
||||
.caslat_x = 0xfe << 4, /* 5,6,7,8,9,10,11 */
|
||||
.taa_ps = 13125,
|
||||
.twr_ps = 15000,
|
||||
.trcd_ps = 13125,
|
||||
.trrd_ps = 6000,
|
||||
.trp_ps = 13125,
|
||||
.tras_ps = 34000,
|
||||
.trc_ps = 48125,
|
||||
.trfc_ps = 260000,
|
||||
.twtr_ps = 7500,
|
||||
.trtp_ps = 7500,
|
||||
.refresh_rate_ps = 7800000,
|
||||
.tfaw_ps = 35000,
|
||||
};
|
||||
|
||||
struct board_specific_parameters {
|
||||
u32 n_ranks;
|
||||
u32 datarate_mhz_high;
|
||||
|
|
105
doc/README.Heterogeneous-SoCs
Normal file
105
doc/README.Heterogeneous-SoCs
Normal file
|
@ -0,0 +1,105 @@
|
|||
DSP side awareness for Freescale heterogeneous multicore chips based on
|
||||
StarCore and Power Architecture
|
||||
===============================================================
|
||||
powerpc/mpc85xx code ve APIs and function to get the number,
|
||||
configuration and frequencies of all PowerPC cores and devices
|
||||
connected to them, but it didnt have the similar code ofr HEterogeneous
|
||||
SC3900/DSP cores and such devices like CPRI, MAPLE, MAPLE-ULB etc.
|
||||
|
||||
Code for DSP side awareness provides such functionality for Freescale
|
||||
Heterogeneous SoCs which are chasis-2 compliant like B4860 and B4420
|
||||
|
||||
As part of this feature, following changes have been made:
|
||||
==========================================================
|
||||
|
||||
1. Changed files:
|
||||
=================
|
||||
- arch/powerpc/cpu/mpc85xx/cpu.c
|
||||
|
||||
Code added in this file to print the DSP cores and other device's(CPRI,
|
||||
MAPLE etc) frequencies
|
||||
|
||||
- arch/powerpc/cpu/mpc85xx/speed.c
|
||||
|
||||
Added Defines and code to extract the frequncy information for all
|
||||
required cores and devices from RCW and System frequency
|
||||
|
||||
- arch/powerpc/cpu/mpc8xxx/cpu.c
|
||||
|
||||
Added API to get the number of SC cores in running system and Their BIT
|
||||
MASK, similar to the code written for PowerPC
|
||||
|
||||
- arch/powerpc/include/asm/config_mpc85xx.h
|
||||
|
||||
Added top level CONFIG to identify presence of HETEROGENUOUS clusters
|
||||
in the system and CONFIGS for SC3900/DSP components
|
||||
|
||||
- arch/powerpc/include/asm/processor.h
|
||||
- include/common.h
|
||||
|
||||
Added newly added Functions Declaration
|
||||
|
||||
- include/e500.h
|
||||
|
||||
Global structure updated for dsp cores and other components
|
||||
|
||||
2. CONFIGs ADDED
|
||||
================
|
||||
|
||||
CONFIG_HETROGENOUS_CLUSTERS - Define for checking the presence of
|
||||
DSP/SC3900 core clusters
|
||||
|
||||
CONFIG_SYS_FSL_NUM_CC_PLLS - Define for number of PLLs
|
||||
|
||||
Though there are only 4 PLLs in B4, but in sequence of PLLs from PLL1 -
|
||||
PLL5, PLL3 is Reserved(as mentioned in RM), so this define contains the
|
||||
value as 5 not 4, to iterate over all PLLs while coding
|
||||
|
||||
CONFIG_SYS_MAPLE - Define for MAPLE Baseband Accelerator
|
||||
CONFIG_SYS_CPRI - Define for CPRI Interface
|
||||
CONFIG_PPC_CLUSTER_START - Start index of ppc clusters
|
||||
CONFIG_DSP_CLUSTER_START - Start index of dsp clusters
|
||||
|
||||
Following are the defines for PLL's index that provide the Clocking to
|
||||
CPRI, ULB and ETVE components
|
||||
|
||||
CONFIG_SYS_CPRI_CLK - Define PLL index for CPRI clock
|
||||
CONFIG_SYS_ULB_CLK - Define PLL index for ULB clock
|
||||
CONFIG_SYS_ETVPE_CLK - Define PLL index for ETVPE clock
|
||||
|
||||
3. Changes in MPC85xx_SYS_INFO Global structure
|
||||
===============================================
|
||||
|
||||
DSP cores and other device's components have been added in this structure.
|
||||
|
||||
freq_processor_dsp[CONFIG_MAX_DSP_CPUS] - Array to contain the DSP core's frequencies
|
||||
freq_cpri - To store CPRI frequency
|
||||
freq_maple - To store MAPLE frequency
|
||||
freq_maple_ulb - To store MAPLE-ULB frequency
|
||||
freq_maple_etvpe - To store MAPLE-eTVPE frequency
|
||||
|
||||
4. U-BOOT LOGS
|
||||
==============
|
||||
4.1 B4860QDS board
|
||||
Boot from NOR flash
|
||||
|
||||
U-Boot 2014.07-00222-g70587a8-dirty (Aug 07 2014 - 13:15:47)
|
||||
|
||||
CPU0: B4860E, Version: 2.0, (0x86880020)
|
||||
Core: e6500, Version: 2.0, (0x80400020) Clock Configuration:
|
||||
CPU0:1600 MHz, CPU1:1600 MHz, CPU2:1600 MHz, CPU3:1600 MHz,
|
||||
DSP CPU0:1200 MHz, DSP CPU1:1200 MHz, DSP CPU2:1200 MHz, DSP CPU3:1200 MHz,
|
||||
DSP CPU4:1200 MHz, DSP CPU5:1200 MHz,
|
||||
CCB:666.667 MHz,
|
||||
DDR:933.333 MHz (1866.667 MT/s data rate) (Asynchronous), IFC:166.667 MHz
|
||||
CPRI:600 MHz
|
||||
MAPLE:600 MHz, MAPLE-ULB:800 MHz, MAPLE-eTVPE:1000 MHz
|
||||
FMAN1: 666.667 MHz
|
||||
QMAN: 333.333 MHz
|
||||
|
||||
CPUn - PowerPC core
|
||||
DSP CPUn - SC3900 core
|
||||
|
||||
Shaveta Leekha(shaveta@freescale.com)
|
||||
Created August 7, 2014
|
||||
===========================================
|
41
doc/README.esbc_validate
Normal file
41
doc/README.esbc_validate
Normal file
|
@ -0,0 +1,41 @@
|
|||
/*
|
||||
* (C) Copyright 2015
|
||||
*
|
||||
* SPDX-License-Identifier: GPL-2.0+
|
||||
*/
|
||||
|
||||
esbc_validate command
|
||||
========================================
|
||||
|
||||
1. esbc_validate command is meant for validating header and
|
||||
signature of images (Boot Script and ESBC uboot client).
|
||||
SHA-256 and RSA operations are performed using SEC block in HW.
|
||||
This command works on both PBL based and Non PBL based Freescale
|
||||
platforms.
|
||||
Command usage:
|
||||
esbc_validate img_hdr_addr [pub_key_hash]
|
||||
esbc_validate hdr_addr <hash_val>
|
||||
Validates signature using RSA verification.
|
||||
$hdr_addr Address of header of the image to be validated.
|
||||
$hash_val -Optional. It provides Hash of public/srk key to be
|
||||
used to verify signature.
|
||||
|
||||
2. ESBC uboot client can be linux. Additionally, rootfs and device
|
||||
tree blob can also be signed.
|
||||
3. In the event of header or signature failure in validation,
|
||||
ITS and ITF bits determine further course of action.
|
||||
4. In case of soft failure, appropriate error is dumped on console.
|
||||
5. In case of hard failure, SoC is issued RESET REQUEST after
|
||||
dumping error on the console.
|
||||
6. KEY REVOCATION Feature:
|
||||
QorIQ platforms like B4/T4 have support of srk key table and key
|
||||
revocation in ISBC code in Silicon.
|
||||
The srk key table allows the user to have a key table with multiple
|
||||
keys and revoke any key in case of particular key gets compromised.
|
||||
In case the ISBC code uses the key revocation and srk key table to
|
||||
verify the u-boot code, the subsequent chain of trust should also
|
||||
use the same.
|
||||
6. ISBC KEY EXTENSION Feature:
|
||||
This feature allows large number of keys to be used for esbc validation
|
||||
of images. A set of public keys is being signed and validated by ISBC
|
||||
which can be further used for esbc validation of images.
|
|
@ -4,4 +4,5 @@
|
|||
# SPDX-License-Identifier: GPL-2.0+
|
||||
#
|
||||
|
||||
obj-$(CONFIG_RSA) += mod_exp_uclass.o mod_exp_sw.o
|
||||
obj-$(CONFIG_RSA) += mod_exp_uclass.o
|
||||
obj-$(CONFIG_RSA_SOFTWARE_EXP) += mod_exp_sw.o
|
||||
|
|
|
@ -53,3 +53,11 @@ config DM_CROS_EC
|
|||
but otherwise makes few changes. Since cros_ec also supports
|
||||
LPC (which doesn't support driver model yet), a full
|
||||
conversion is not yet possible.
|
||||
|
||||
config CONFIG_FSL_SEC_MON
|
||||
bool "Enable FSL SEC_MON Driver"
|
||||
help
|
||||
Freescale Security Monitor block is responsible for monitoring
|
||||
system states.
|
||||
Security Monitor can be transitioned on any security failures,
|
||||
like software violations or hardware security violations.
|
||||
|
|
|
@ -28,3 +28,4 @@ obj-$(CONFIG_SMSC_LPC47M) += smsc_lpc47m.o
|
|||
obj-$(CONFIG_STATUS_LED) += status_led.o
|
||||
obj-$(CONFIG_TWL4030_LED) += twl4030_led.o
|
||||
obj-$(CONFIG_FSL_IFC) += fsl_ifc.o
|
||||
obj-$(CONFIG_FSL_SEC_MON) += fsl_sec_mon.o
|
||||
|
|
146
drivers/misc/fsl_sec_mon.c
Normal file
146
drivers/misc/fsl_sec_mon.c
Normal file
|
@ -0,0 +1,146 @@
|
|||
/*
|
||||
* Copyright 2015 Freescale Semiconductor, Inc.
|
||||
*
|
||||
* SPDX-License-Identifier: GPL-2.0+
|
||||
*/
|
||||
|
||||
#include <common.h>
|
||||
#include <fsl_sec_mon.h>
|
||||
|
||||
int change_sec_mon_state(u32 initial_state, u32 final_state)
|
||||
{
|
||||
struct ccsr_sec_mon_regs *sec_mon_regs = (void *)
|
||||
(CONFIG_SYS_SEC_MON_ADDR);
|
||||
u32 sts = sec_mon_in32(&sec_mon_regs->hp_stat);
|
||||
int timeout = 10;
|
||||
|
||||
if ((sts & HPSR_SSM_ST_MASK) != initial_state)
|
||||
return -1;
|
||||
|
||||
if (initial_state == HPSR_SSM_ST_TRUST) {
|
||||
switch (final_state) {
|
||||
case HPSR_SSM_ST_NON_SECURE:
|
||||
printf("SEC_MON state transitioning to Soft Fail.\n");
|
||||
sec_mon_setbits32(&sec_mon_regs->hp_com, HPCOMR_SW_SV);
|
||||
|
||||
/*
|
||||
* poll till SEC_MON is in
|
||||
* Soft Fail state
|
||||
*/
|
||||
while (((sts & HPSR_SSM_ST_MASK) !=
|
||||
HPSR_SSM_ST_SOFT_FAIL)) {
|
||||
while (timeout) {
|
||||
sts = sec_mon_in32
|
||||
(&sec_mon_regs->hp_stat);
|
||||
|
||||
if ((sts & HPSR_SSM_ST_MASK) ==
|
||||
HPSR_SSM_ST_SOFT_FAIL)
|
||||
break;
|
||||
|
||||
udelay(10);
|
||||
timeout--;
|
||||
}
|
||||
}
|
||||
|
||||
if (timeout == 0) {
|
||||
printf("SEC_MON state transition timeout.\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
timeout = 10;
|
||||
|
||||
printf("SEC_MON state transitioning to Non Secure.\n");
|
||||
sec_mon_setbits32(&sec_mon_regs->hp_com, HPCOMR_SSM_ST);
|
||||
|
||||
/*
|
||||
* poll till SEC_MON is in
|
||||
* Non Secure state
|
||||
*/
|
||||
while (((sts & HPSR_SSM_ST_MASK) !=
|
||||
HPSR_SSM_ST_NON_SECURE)) {
|
||||
while (timeout) {
|
||||
sts = sec_mon_in32
|
||||
(&sec_mon_regs->hp_stat);
|
||||
|
||||
if ((sts & HPSR_SSM_ST_MASK) ==
|
||||
HPSR_SSM_ST_NON_SECURE)
|
||||
break;
|
||||
|
||||
udelay(10);
|
||||
timeout--;
|
||||
}
|
||||
}
|
||||
|
||||
if (timeout == 0) {
|
||||
printf("SEC_MON state transition timeout.\n");
|
||||
return -1;
|
||||
}
|
||||
break;
|
||||
case HPSR_SSM_ST_SOFT_FAIL:
|
||||
printf("SEC_MON state transitioning to Soft Fail.\n");
|
||||
sec_mon_setbits32(&sec_mon_regs->hp_com, HPCOMR_SW_FSV);
|
||||
|
||||
/*
|
||||
* polling loop till SEC_MON is in
|
||||
* Soft Fail state
|
||||
*/
|
||||
while (((sts & HPSR_SSM_ST_MASK) !=
|
||||
HPSR_SSM_ST_SOFT_FAIL)) {
|
||||
while (timeout) {
|
||||
sts = sec_mon_in32
|
||||
(&sec_mon_regs->hp_stat);
|
||||
|
||||
if ((sts & HPSR_SSM_ST_MASK) ==
|
||||
HPSR_SSM_ST_SOFT_FAIL)
|
||||
break;
|
||||
|
||||
udelay(10);
|
||||
timeout--;
|
||||
}
|
||||
}
|
||||
|
||||
if (timeout == 0) {
|
||||
printf("SEC_MON state transition timeout.\n");
|
||||
return -1;
|
||||
}
|
||||
break;
|
||||
default:
|
||||
return -1;
|
||||
}
|
||||
} else if (initial_state == HPSR_SSM_ST_NON_SECURE) {
|
||||
switch (final_state) {
|
||||
case HPSR_SSM_ST_SOFT_FAIL:
|
||||
printf("SEC_MON state transitioning to Soft Fail.\n");
|
||||
sec_mon_setbits32(&sec_mon_regs->hp_com, HPCOMR_SW_FSV);
|
||||
|
||||
/*
|
||||
* polling loop till SEC_MON is in
|
||||
* Soft Fail state
|
||||
*/
|
||||
while (((sts & HPSR_SSM_ST_MASK) !=
|
||||
HPSR_SSM_ST_SOFT_FAIL)) {
|
||||
while (timeout) {
|
||||
sts = sec_mon_in32
|
||||
(&sec_mon_regs->hp_stat);
|
||||
|
||||
if ((sts & HPSR_SSM_ST_MASK) ==
|
||||
HPSR_SSM_ST_SOFT_FAIL)
|
||||
break;
|
||||
|
||||
udelay(10);
|
||||
timeout--;
|
||||
}
|
||||
}
|
||||
|
||||
if (timeout == 0) {
|
||||
printf("SEC_MON state transition timeout.\n");
|
||||
return -1;
|
||||
}
|
||||
break;
|
||||
default:
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
|
@ -553,7 +553,9 @@ static inline int cpumask_next(int cpu, unsigned int mask)
|
|||
iter++, cpu = cpumask_next(cpu, mask)) \
|
||||
|
||||
int cpu_numcores (void);
|
||||
int cpu_num_dspcores(void);
|
||||
u32 cpu_mask (void);
|
||||
u32 cpu_dsp_mask(void);
|
||||
int is_core_valid (unsigned int);
|
||||
int probecpu (void);
|
||||
int checkcpu (void);
|
||||
|
|
|
@ -220,7 +220,6 @@
|
|||
#define CONFIG_CHIP_SELECTS_PER_CTRL (2 * CONFIG_DIMM_SLOTS_PER_CTLR)
|
||||
|
||||
#define CONFIG_DDR_SPD
|
||||
#define CONFIG_SYS_DDR_RAW_TIMING
|
||||
#define CONFIG_SYS_FSL_DDR3
|
||||
|
||||
#define CONFIG_SYS_SPD_BUS_NUM 0
|
||||
|
|
|
@ -11,6 +11,9 @@
|
|||
typedef struct
|
||||
{
|
||||
unsigned long freq_processor[CONFIG_MAX_CPUS];
|
||||
#ifdef CONFIG_HETROGENOUS_CLUSTERS
|
||||
unsigned long freq_processor_dsp[CONFIG_MAX_DSP_CPUS];
|
||||
#endif
|
||||
unsigned long freq_systembus;
|
||||
unsigned long freq_ddrbus;
|
||||
unsigned long freq_localbus;
|
||||
|
@ -24,6 +27,14 @@ typedef struct
|
|||
#ifdef CONFIG_SYS_DPAA_PME
|
||||
unsigned long freq_pme;
|
||||
#endif
|
||||
#ifdef CONFIG_SYS_CPRI
|
||||
unsigned long freq_cpri;
|
||||
#endif
|
||||
#ifdef CONFIG_SYS_MAPLE
|
||||
unsigned long freq_maple;
|
||||
unsigned long freq_maple_ulb;
|
||||
unsigned long freq_maple_etvpe;
|
||||
#endif
|
||||
#ifdef CONFIG_SYS_FSL_SINGLE_SOURCE_CLK
|
||||
unsigned char diff_sysclk;
|
||||
#endif
|
||||
|
|
58
include/fsl_sec_mon.h
Normal file
58
include/fsl_sec_mon.h
Normal file
|
@ -0,0 +1,58 @@
|
|||
/*
|
||||
* Common internal memory map for some Freescale SoCs
|
||||
*
|
||||
* Copyright 2015 Freescale Semiconductor, Inc.
|
||||
* SPDX-License-Identifier: GPL-2.0+
|
||||
*/
|
||||
|
||||
#ifndef __FSL_SEC_MON_H
|
||||
#define __FSL_SEC_MON_H
|
||||
|
||||
#include <common.h>
|
||||
#include <asm/io.h>
|
||||
|
||||
#ifdef CONFIG_SYS_FSL_SEC_MON_LE
|
||||
#define sec_mon_in32(a) in_le32(a)
|
||||
#define sec_mon_out32(a, v) out_le32(a, v)
|
||||
#define sec_mon_in16(a) in_le16(a)
|
||||
#define sec_mon_clrbits32 clrbits_le32
|
||||
#define sec_mon_setbits32 setbits_le32
|
||||
#elif defined(CONFIG_SYS_FSL_SEC_MON_BE)
|
||||
#define sec_mon_in32(a) in_be32(a)
|
||||
#define sec_mon_out32(a, v) out_be32(a, v)
|
||||
#define sec_mon_in16(a) in_be16(a)
|
||||
#define sec_mon_clrbits32 clrbits_be32
|
||||
#define sec_mon_setbits32 setbits_be32
|
||||
#else
|
||||
#error Neither CONFIG_SYS_FSL_SEC_MON_LE nor CONFIG_SYS_FSL_SEC_MON_BE defined
|
||||
#endif
|
||||
|
||||
struct ccsr_sec_mon_regs {
|
||||
u8 reserved0[0x04];
|
||||
u32 hp_com; /* 0x04 SEC_MON_HP Command Register */
|
||||
u8 reserved2[0x0c];
|
||||
u32 hp_stat; /* 0x08 SEC_MON_HP Status Register */
|
||||
};
|
||||
|
||||
#define HPCOMR_SW_SV 0x100 /* Security Violation bit */
|
||||
#define HPCOMR_SW_FSV 0x200 /* Fatal Security Violation bit */
|
||||
#define HPCOMR_SSM_ST 0x1 /* SSM_ST field in SEC_MON command */
|
||||
#define HPSR_SSM_ST_CHECK 0x900 /* SEC_MON is in check state */
|
||||
#define HPSR_SSM_ST_NON_SECURE 0xb00 /* SEC_MON is in non secure state */
|
||||
#define HPSR_SSM_ST_TRUST 0xd00 /* SEC_MON is in trusted state */
|
||||
#define HPSR_SSM_ST_SOFT_FAIL 0x300 /* SEC_MON is in soft fail state */
|
||||
#define HPSR_SSM_ST_MASK 0xf00 /* Mask for SSM_ST field */
|
||||
|
||||
/*
|
||||
* SEC_MON read. This specifies the possible reads
|
||||
* from the SEC_MON
|
||||
*/
|
||||
enum {
|
||||
SEC_MON_SSM_ST,
|
||||
SEC_MON_SW_FSV,
|
||||
SEC_MON_SW_SV,
|
||||
};
|
||||
|
||||
int change_sec_mon_state(uint32_t initial_state, uint32_t final_state);
|
||||
|
||||
#endif /* __FSL_SEC_MON_H */
|
128
include/fsl_secboot_err.h
Normal file
128
include/fsl_secboot_err.h
Normal file
|
@ -0,0 +1,128 @@
|
|||
/*
|
||||
* Copyright 2015 Freescale Semiconductor, Inc.
|
||||
*
|
||||
* SPDX-License-Identifier: GPL-2.0+
|
||||
*/
|
||||
|
||||
#ifndef _FSL_SECBOOT_ERR_H
|
||||
#define _FSL_SECBOOT_ERR_H
|
||||
|
||||
#define ERROR_ESBC_PAMU_INIT 0x100000
|
||||
#define ERROR_ESBC_SEC_RESET 0x200000
|
||||
#define ERROR_ESBC_SEC_INIT 0x400000
|
||||
#define ERROR_ESBC_SEC_DEQ 0x800000
|
||||
#define ERROR_ESBC_SEC_DEQ_TO 0x1000000
|
||||
#define ERROR_ESBC_SEC_ENQ 0x2000000
|
||||
#define ERROR_ESBC_SEC_JOBQ_STATUS 0x4000000
|
||||
#define ERROR_ESBC_CLIENT_CPUID_NO_MATCH 0x1
|
||||
#define ERROR_ESBC_CLIENT_HDR_LOC 0x2
|
||||
#define ERROR_ESBC_CLIENT_HEADER_BARKER 0x4
|
||||
#define ERROR_ESBC_CLIENT_HEADER_KEY_LEN 0x8
|
||||
#define ERROR_ESBC_CLIENT_HEADER_SIG_LEN 0x10
|
||||
#define ERROR_ESBC_CLIENT_HEADER_KEY_REVOKED 0x11
|
||||
#define ERROR_ESBC_CLIENT_HEADER_INVALID_SRK_NUM_ENTRY 0x12
|
||||
#define ERROR_ESBC_CLIENT_HEADER_INVALID_KEY_NUM 0x13
|
||||
#define ERROR_ESBC_CLIENT_HEADER_INV_SRK_ENTRY_KEYLEN 0x14
|
||||
#define ERROR_ESBC_CLIENT_HEADER_IE_KEY_REVOKED 0x15
|
||||
#define ERROR_ESBC_CLIENT_HEADER_INVALID_IE_NUM_ENTRY 0x16
|
||||
#define ERROR_ESBC_CLIENT_HEADER_INVALID_IE_KEY_NUM 0x17
|
||||
#define ERROR_ESBC_CLIENT_HEADER_INV_IE_ENTRY_KEYLEN 0x18
|
||||
#define ERROR_IE_TABLE_NOT_FOUND 0x19
|
||||
#define ERROR_ESBC_CLIENT_HEADER_KEY_LEN_NOT_TWICE_SIG_LEN 0x20
|
||||
#define ERROR_ESBC_CLIENT_HEADER_KEY_MOD_1 0x40
|
||||
#define ERROR_ESBC_CLIENT_HEADER_KEY_MOD_2 0x80
|
||||
#define ERROR_ESBC_CLIENT_HEADER_SIG_KEY_MOD 0x100
|
||||
#define ERROR_ESBC_CLIENT_HEADER_SG_ESBC_EP 0x200
|
||||
#define ERROR_ESBC_CLIENT_HASH_COMPARE_KEY 0x400
|
||||
#define ERROR_ESBC_CLIENT_HASH_COMPARE_EM 0x800
|
||||
#define ERROR_ESBC_CLIENT_SSM_TRUSTSTS 0x1000
|
||||
#define ERROR_ESBC_CLIENT_BAD_ADDRESS 0x2000
|
||||
#define ERROR_ESBC_CLIENT_MISC 0x4000
|
||||
#define ERROR_ESBC_CLIENT_HEADER_SG_ENTIRES_BAD 0x8000
|
||||
#define ERROR_ESBC_CLIENT_HEADER_SG 0x10000
|
||||
#define ERROR_ESBC_CLIENT_HEADER_IMG_SIZE 0x20000
|
||||
#define ERROR_ESBC_WRONG_CMD 0x40000
|
||||
#define ERROR_ESBC_MISSING_BOOTM 0x80000
|
||||
#define ERROR_ESBC_CLIENT_MAX 0x0
|
||||
|
||||
struct fsl_secboot_errcode {
|
||||
int errcode;
|
||||
const char *name;
|
||||
};
|
||||
|
||||
static const struct fsl_secboot_errcode fsl_secboot_errcodes[] = {
|
||||
{ ERROR_ESBC_PAMU_INIT,
|
||||
"Error in initializing PAMU"},
|
||||
{ ERROR_ESBC_SEC_RESET,
|
||||
"Error in resetting Job ring of SEC"},
|
||||
{ ERROR_ESBC_SEC_INIT,
|
||||
"Error in initializing SEC"},
|
||||
{ ERROR_ESBC_SEC_ENQ,
|
||||
"Error in enqueue operation by SEC"},
|
||||
{ ERROR_ESBC_SEC_DEQ_TO,
|
||||
"Dequeue operation by SEC is timed out"},
|
||||
{ ERROR_ESBC_SEC_DEQ,
|
||||
"Error in dequeue operation by SEC"},
|
||||
{ ERROR_ESBC_SEC_JOBQ_STATUS,
|
||||
"Error in status of the job submitted to SEC"},
|
||||
{ ERROR_ESBC_CLIENT_CPUID_NO_MATCH,
|
||||
"Current core is not boot core i.e core0" },
|
||||
{ ERROR_ESBC_CLIENT_HDR_LOC,
|
||||
"Header address not in allowed memory range" },
|
||||
{ ERROR_ESBC_CLIENT_HEADER_BARKER,
|
||||
"Wrong barker code in header" },
|
||||
{ ERROR_ESBC_CLIENT_HEADER_KEY_LEN,
|
||||
"Wrong public key length in header" },
|
||||
{ ERROR_ESBC_CLIENT_HEADER_SIG_LEN,
|
||||
"Wrong signature length in header" },
|
||||
{ ERROR_ESBC_CLIENT_HEADER_KEY_LEN_NOT_TWICE_SIG_LEN,
|
||||
"Public key length not twice of signature length" },
|
||||
{ ERROR_ESBC_CLIENT_HEADER_KEY_MOD_1,
|
||||
"Public key Modulus most significant bit not set" },
|
||||
{ ERROR_ESBC_CLIENT_HEADER_KEY_MOD_2,
|
||||
"Public key Modulus in header not odd" },
|
||||
{ ERROR_ESBC_CLIENT_HEADER_SIG_KEY_MOD,
|
||||
"Signature not less than modulus" },
|
||||
{ ERROR_ESBC_CLIENT_HEADER_SG_ESBC_EP,
|
||||
"Entry point not in allowed space or one of the SG entries" },
|
||||
{ ERROR_ESBC_CLIENT_HASH_COMPARE_KEY,
|
||||
"Public key hash comparison failed" },
|
||||
{ ERROR_ESBC_CLIENT_HASH_COMPARE_EM,
|
||||
"RSA verification failed" },
|
||||
{ ERROR_ESBC_CLIENT_SSM_TRUSTSTS,
|
||||
"SNVS not in TRUSTED state" },
|
||||
{ ERROR_ESBC_CLIENT_BAD_ADDRESS,
|
||||
"Bad address error" },
|
||||
{ ERROR_ESBC_CLIENT_MISC,
|
||||
"Miscallaneous error" },
|
||||
{ ERROR_ESBC_CLIENT_HEADER_SG,
|
||||
"No SG support" },
|
||||
{ ERROR_ESBC_CLIENT_HEADER_IMG_SIZE,
|
||||
"Invalid Image size" },
|
||||
{ ERROR_ESBC_WRONG_CMD,
|
||||
"Unknown cmd/Wrong arguments. Core in infinite loop"},
|
||||
{ ERROR_ESBC_MISSING_BOOTM,
|
||||
"Bootm command missing from bootscript" },
|
||||
{ ERROR_ESBC_CLIENT_HEADER_KEY_REVOKED,
|
||||
"Selected key is revoked" },
|
||||
{ ERROR_ESBC_CLIENT_HEADER_INVALID_SRK_NUM_ENTRY,
|
||||
"Wrong key entry" },
|
||||
{ ERROR_ESBC_CLIENT_HEADER_INVALID_KEY_NUM,
|
||||
"Wrong key is selected" },
|
||||
{ ERROR_ESBC_CLIENT_HEADER_INV_SRK_ENTRY_KEYLEN,
|
||||
"Wrong srk public key len in header" },
|
||||
{ ERROR_ESBC_CLIENT_HEADER_IE_KEY_REVOKED,
|
||||
"Selected IE key is revoked" },
|
||||
{ ERROR_ESBC_CLIENT_HEADER_INVALID_IE_NUM_ENTRY,
|
||||
"Wrong key entry in IE Table" },
|
||||
{ ERROR_ESBC_CLIENT_HEADER_INVALID_IE_KEY_NUM,
|
||||
"Wrong IE key is selected" },
|
||||
{ ERROR_ESBC_CLIENT_HEADER_INV_IE_ENTRY_KEYLEN,
|
||||
"Wrong IE public key len in header" },
|
||||
{ ERROR_IE_TABLE_NOT_FOUND,
|
||||
"Information about IE Table missing" },
|
||||
{ ERROR_ESBC_CLIENT_MAX, "NULL" }
|
||||
};
|
||||
|
||||
void fsl_secboot_handle_error(int error);
|
||||
#endif
|
85
include/fsl_sfp.h
Normal file
85
include/fsl_sfp.h
Normal file
|
@ -0,0 +1,85 @@
|
|||
/*
|
||||
* Copyright 2015 Freescale Semiconductor, Inc.
|
||||
*
|
||||
* SPDX-License-Identifier: GPL-2.0+
|
||||
*/
|
||||
|
||||
#ifndef _FSL_SFP_SNVS_
|
||||
#define _FSL_SFP_SNVS_
|
||||
|
||||
#include <common.h>
|
||||
#include <config.h>
|
||||
#include <asm/io.h>
|
||||
|
||||
#ifdef CONFIG_SYS_FSL_SRK_LE
|
||||
#define srk_in32(a) in_le32(a)
|
||||
#else
|
||||
#define srk_in32(a) in_be32(a)
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_SYS_FSL_SFP_LE
|
||||
#define sfp_in32(a) in_le32(a)
|
||||
#define sfp_out32(a, v) out_le32(a, v)
|
||||
#define sfp_in16(a) in_le16(a)
|
||||
#elif defined(CONFIG_SYS_FSL_SFP_BE)
|
||||
#define sfp_in32(a) in_be32(a)
|
||||
#define sfp_out32(a, v) out_be32(a, v)
|
||||
#define sfp_in16(a) in_be16(a)
|
||||
#else
|
||||
#error Neither CONFIG_SYS_FSL_SFP_LE nor CONFIG_SYS_FSL_SFP_BE is defined
|
||||
#endif
|
||||
|
||||
/* Number of SRKH registers */
|
||||
#define NUM_SRKH_REGS 8
|
||||
|
||||
#ifdef CONFIG_SYS_FSL_SFP_VER_3_2
|
||||
struct ccsr_sfp_regs {
|
||||
u32 ospr; /* 0x200 */
|
||||
u32 ospr1; /* 0x204 */
|
||||
u32 reserved1[4];
|
||||
u32 fswpr; /* 0x218 FSL Section Write Protect */
|
||||
u32 fsl_uid; /* 0x21c FSL UID 0 */
|
||||
u32 fsl_uid_1; /* 0x220 FSL UID 0 */
|
||||
u32 reserved2[12];
|
||||
u32 srk_hash[8]; /* 0x254 Super Root Key Hash */
|
||||
u32 oem_uid; /* 0x274 OEM UID 0*/
|
||||
u32 oem_uid_1; /* 0x278 OEM UID 1*/
|
||||
u32 oem_uid_2; /* 0x27c OEM UID 2*/
|
||||
u32 oem_uid_3; /* 0x280 OEM UID 3*/
|
||||
u32 oem_uid_4; /* 0x284 OEM UID 4*/
|
||||
u32 reserved3[8];
|
||||
};
|
||||
#elif defined(CONFIG_SYS_FSL_SFP_VER_3_0)
|
||||
struct ccsr_sfp_regs {
|
||||
u32 ospr; /* 0x200 */
|
||||
u32 reserved0[14];
|
||||
u32 srk_hash[NUM_SRKH_REGS]; /* 0x23c Super Root Key Hash */
|
||||
u32 oem_uid; /* 0x9c OEM Unique ID */
|
||||
u8 reserved2[0x04];
|
||||
u32 ovpr; /* 0xA4 Intent To Secure */
|
||||
u8 reserved4[0x08];
|
||||
u32 fsl_uid; /* 0xB0 FSL Unique ID */
|
||||
u8 reserved5[0x04];
|
||||
u32 fsl_spfr0; /* Scratch Pad Fuse Register 0 */
|
||||
u32 fsl_spfr1; /* Scratch Pad Fuse Register 1 */
|
||||
|
||||
};
|
||||
#else
|
||||
struct ccsr_sfp_regs {
|
||||
u8 reserved0[0x40];
|
||||
u32 ospr; /* 0x40 OEM Security Policy Register */
|
||||
u8 reserved2[0x38];
|
||||
u32 srk_hash[8]; /* 0x7c Super Root Key Hash */
|
||||
u32 oem_uid; /* 0x9c OEM Unique ID */
|
||||
u8 reserved4[0x4];
|
||||
u32 ovpr; /* 0xA4 OEM Validation Policy Register */
|
||||
u8 reserved8[0x8];
|
||||
u32 fsl_uid; /* 0xB0 FSL Unique ID */
|
||||
};
|
||||
#endif
|
||||
#define ITS_MASK 0x00000004
|
||||
#define ITS_BIT 2
|
||||
#define OSPR_KEY_REVOC_SHIFT 13
|
||||
#define OSPR_KEY_REVOC_MASK 0x0000e000
|
||||
|
||||
#endif
|
199
include/fsl_validate.h
Normal file
199
include/fsl_validate.h
Normal file
|
@ -0,0 +1,199 @@
|
|||
/*
|
||||
* Copyright 2015 Freescale Semiconductor, Inc.
|
||||
*
|
||||
* SPDX-License-Identifier: GPL-2.0+
|
||||
*/
|
||||
|
||||
#ifndef _FSL_VALIDATE_H_
|
||||
#define _FSL_VALIDATE_H_
|
||||
|
||||
#include <fsl_sec.h>
|
||||
#include <fsl_sec_mon.h>
|
||||
#include <command.h>
|
||||
#include <linux/types.h>
|
||||
|
||||
#define WORD_SIZE 4
|
||||
|
||||
/* Minimum and maximum size of RSA signature length in bits */
|
||||
#define KEY_SIZE 4096
|
||||
#define KEY_SIZE_BYTES (KEY_SIZE/8)
|
||||
#define KEY_SIZE_WORDS (KEY_SIZE_BYTES/(WORD_SIZE))
|
||||
|
||||
extern struct jobring jr;
|
||||
|
||||
#ifdef CONFIG_KEY_REVOCATION
|
||||
/* Srk table and key revocation check */
|
||||
#define SRK_FLAG 0x01
|
||||
#define UNREVOCABLE_KEY 4
|
||||
#define ALIGN_REVOC_KEY 3
|
||||
#define MAX_KEY_ENTRIES 4
|
||||
#endif
|
||||
|
||||
/* Barker code size in bytes */
|
||||
#define ESBC_BARKER_LEN 4 /* barker code length in ESBC uboot client */
|
||||
/* header */
|
||||
|
||||
/* No-error return values */
|
||||
#define ESBC_VALID_HDR 0 /* header is valid */
|
||||
|
||||
/* Maximum number of SG entries allowed */
|
||||
#define MAX_SG_ENTRIES 8
|
||||
|
||||
/*
|
||||
* ESBC uboot client header structure.
|
||||
* The struct contain the following fields
|
||||
* barker code
|
||||
* public key offset
|
||||
* pub key length
|
||||
* signature offset
|
||||
* length of the signature
|
||||
* ptr to SG table
|
||||
* no of entries in SG table
|
||||
* esbc ptr
|
||||
* size of esbc
|
||||
* esbc entry point
|
||||
* Scatter gather flag
|
||||
* UID flag
|
||||
* FSL UID
|
||||
* OEM UID
|
||||
* Here, pub key is modulus concatenated with exponent
|
||||
* of equal length
|
||||
*/
|
||||
struct fsl_secboot_img_hdr {
|
||||
u8 barker[ESBC_BARKER_LEN]; /* barker code */
|
||||
union {
|
||||
u32 pkey; /* public key offset */
|
||||
#ifdef CONFIG_KEY_REVOCATION
|
||||
u32 srk_tbl_off;
|
||||
#endif
|
||||
};
|
||||
|
||||
union {
|
||||
u32 key_len; /* pub key length in bytes */
|
||||
#ifdef CONFIG_KEY_REVOCATION
|
||||
struct {
|
||||
u32 srk_table_flag:8;
|
||||
u32 srk_sel:8;
|
||||
u32 num_srk:16;
|
||||
} len_kr;
|
||||
#endif
|
||||
};
|
||||
|
||||
u32 psign; /* signature offset */
|
||||
u32 sign_len; /* length of the signature in bytes */
|
||||
union {
|
||||
struct fsl_secboot_sg_table *psgtable; /* ptr to SG table */
|
||||
u8 *pimg; /* ptr to ESBC client image */
|
||||
};
|
||||
union {
|
||||
u32 sg_entries; /* no of entries in SG table */
|
||||
u32 img_size; /* ESBC client image size in bytes */
|
||||
};
|
||||
ulong img_start; /* ESBC client entry point */
|
||||
u32 sg_flag; /* Scatter gather flag */
|
||||
u32 uid_flag;
|
||||
u32 fsl_uid_0;
|
||||
u32 oem_uid_0;
|
||||
u32 reserved1[2];
|
||||
u32 fsl_uid_1;
|
||||
u32 oem_uid_1;
|
||||
u32 reserved2[2];
|
||||
u32 ie_flag;
|
||||
u32 ie_key_sel;
|
||||
};
|
||||
|
||||
#if defined(CONFIG_FSL_ISBC_KEY_EXT)
|
||||
struct ie_key_table {
|
||||
u32 key_len;
|
||||
u8 pkey[2 * KEY_SIZE_BYTES];
|
||||
};
|
||||
|
||||
struct ie_key_info {
|
||||
uint32_t key_revok;
|
||||
uint32_t num_keys;
|
||||
struct ie_key_table ie_key_tbl[32];
|
||||
};
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_KEY_REVOCATION
|
||||
struct srk_table {
|
||||
u32 key_len;
|
||||
u8 pkey[2 * KEY_SIZE_BYTES];
|
||||
};
|
||||
#endif
|
||||
|
||||
/*
|
||||
* SG table.
|
||||
*/
|
||||
#if defined(CONFIG_FSL_TRUST_ARCH_v1) && defined(CONFIG_FSL_CORENET)
|
||||
/*
|
||||
* This struct contains the following fields
|
||||
* length of the segment
|
||||
* source address
|
||||
*/
|
||||
struct fsl_secboot_sg_table {
|
||||
u32 len; /* length of the segment in bytes */
|
||||
ulong src_addr; /* ptr to the data segment */
|
||||
};
|
||||
#else
|
||||
/*
|
||||
* This struct contains the following fields
|
||||
* length of the segment
|
||||
* Destination Target ID
|
||||
* source address
|
||||
* destination address
|
||||
*/
|
||||
struct fsl_secboot_sg_table {
|
||||
u32 len;
|
||||
u32 trgt_id;
|
||||
ulong src_addr;
|
||||
ulong dst_addr;
|
||||
};
|
||||
#endif
|
||||
|
||||
/*
|
||||
* ESBC private structure.
|
||||
* Private structure used by ESBC to store following fields
|
||||
* ESBC client key
|
||||
* ESBC client key hash
|
||||
* ESBC client Signature
|
||||
* Encoded hash recovered from signature
|
||||
* Encoded hash of ESBC client header plus ESBC client image
|
||||
*/
|
||||
struct fsl_secboot_img_priv {
|
||||
uint32_t hdr_location;
|
||||
ulong ie_addr;
|
||||
u32 key_len;
|
||||
struct fsl_secboot_img_hdr hdr;
|
||||
|
||||
u8 img_key[2 * KEY_SIZE_BYTES]; /* ESBC client key */
|
||||
u8 img_key_hash[32]; /* ESBC client key hash */
|
||||
|
||||
#ifdef CONFIG_KEY_REVOCATION
|
||||
struct srk_table srk_tbl[MAX_KEY_ENTRIES];
|
||||
#endif
|
||||
u8 img_sign[KEY_SIZE_BYTES]; /* ESBC client signature */
|
||||
|
||||
u8 img_encoded_hash[KEY_SIZE_BYTES]; /* EM wrt RSA PKCSv1.5 */
|
||||
/* Includes hash recovered after
|
||||
* signature verification
|
||||
*/
|
||||
|
||||
u8 img_encoded_hash_second[KEY_SIZE_BYTES];/* EM' wrt RSA PKCSv1.5 */
|
||||
/* Includes hash of
|
||||
* ESBC client header plus
|
||||
* ESBC client image
|
||||
*/
|
||||
|
||||
struct fsl_secboot_sg_table sgtbl[MAX_SG_ENTRIES]; /* SG table */
|
||||
u32 ehdrloc; /* ESBC client location */
|
||||
};
|
||||
|
||||
int fsl_secboot_validate(cmd_tbl_t *cmdtp, int flag, int argc,
|
||||
char * const argv[]);
|
||||
int fsl_secboot_blob_encap(cmd_tbl_t *cmdtp, int flag, int argc,
|
||||
char * const argv[]);
|
||||
int fsl_secboot_blob_decap(cmd_tbl_t *cmdtp, int flag, int argc,
|
||||
char * const argv[]);
|
||||
|
||||
#endif
|
|
@ -7,4 +7,5 @@
|
|||
# SPDX-License-Identifier: GPL-2.0+
|
||||
#
|
||||
|
||||
obj-$(CONFIG_FIT_SIGNATURE) += rsa-verify.o rsa-checksum.o rsa-mod-exp.o
|
||||
obj-$(CONFIG_FIT_SIGNATURE) += rsa-verify.o rsa-checksum.o
|
||||
obj-$(CONFIG_RSA_SOFTWARE_EXP) += rsa-mod-exp.o
|
||||
|
|
Loading…
Add table
Reference in a new issue