diff options
author | Tom Rini <trini@ti.com> | 2014-10-20 22:17:26 (GMT) |
---|---|---|
committer | Tom Rini <trini@ti.com> | 2014-10-20 22:17:26 (GMT) |
commit | a84c8107d9b050fe8a31220d28588abfc2d99aee (patch) | |
tree | 03f380795c62c2af870cc837c901795c3a9e227e | |
parent | 3e780af127282e5e24fa737a5b56d7c4523a72c9 (diff) | |
parent | ba4740205d22d31da289f5b6b2f8db7d27896f40 (diff) | |
download | u-boot-a84c8107d9b050fe8a31220d28588abfc2d99aee.tar.xz |
Merge branch 'master' of git://git.denx.de/u-boot-fsl-qoriq
44 files changed, 2558 insertions, 74 deletions
@@ -544,6 +544,12 @@ The following options need to be configured: CONFIG_SYS_FSL_OTHER_DDR_NUM_CTRLS Number of controllers used for other than main memory. + CONFIG_SYS_FSL_SEC_BE + Defines the SEC controller register space as Big Endian + + CONFIG_SYS_FSL_SEC_LE + Defines the SEC controller register space as Little Endian + - Intel Monahans options: CONFIG_SYS_MONAHANS_RUN_MODE_OSC_RATIO diff --git a/arch/arm/include/asm/arch-ls102xa/config.h b/arch/arm/include/asm/arch-ls102xa/config.h index a500b5b..f2c9687 100644 --- a/arch/arm/include/asm/arch-ls102xa/config.h +++ b/arch/arm/include/asm/arch-ls102xa/config.h @@ -19,6 +19,8 @@ #define CONFIG_SYS_IFC_ADDR (CONFIG_SYS_IMMR + 0x00530000) #define CONFIG_SYS_FSL_ESDHC_ADDR (CONFIG_SYS_IMMR + 0x00560000) #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_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) @@ -66,6 +68,7 @@ #define CONFIG_SYS_FSL_DSPI_BE #define CONFIG_SYS_FSL_QSPI_BE #define CONFIG_SYS_FSL_DCU_BE +#define CONFIG_SYS_FSL_SEC_LE #define DCU_LAYER_MAX_NUM 16 @@ -76,6 +79,7 @@ #define CONFIG_SYS_FSL_IFC_BANK_COUNT 8 #define CONFIG_NUM_DDR_CONTROLLERS 1 #define CONFIG_SYS_FSL_DDR_VER FSL_DDR_VER_5_0 +#define CONFIG_SYS_FSL_SEC_COMPAT 5 #else #error SoC not defined #endif diff --git a/arch/powerpc/cpu/mpc85xx/cpu_init.c b/arch/powerpc/cpu/mpc85xx/cpu_init.c index 5bfab70..85d32fc 100644 --- a/arch/powerpc/cpu/mpc85xx/cpu_init.c +++ b/arch/powerpc/cpu/mpc85xx/cpu_init.c @@ -27,6 +27,9 @@ #include <hwconfig.h> #include <linux/compiler.h> #include "mp.h" +#ifdef CONFIG_FSL_CAAM +#include <fsl_sec.h> +#endif #ifdef CONFIG_SYS_QE_FMAN_FW_IN_NAND #include <nand.h> #include <errno.h> @@ -423,7 +426,8 @@ ulong cpu_init_f(void) { ulong flag = 0; extern void m8560_cpm_reset (void); -#ifdef CONFIG_SYS_DCSRBAR_PHYS +#if defined(CONFIG_SYS_DCSRBAR_PHYS) || \ + (defined(CONFIG_SECURE_BOOT) && defined(CONFIG_FSL_CORENET)) ccsr_gur_t *gur = (void *)(CONFIG_SYS_MPC85xx_GUTS_ADDR); #endif #if defined(CONFIG_SECURE_BOOT) @@ -455,6 +459,12 @@ ulong cpu_init_f(void) #if defined(CONFIG_SYS_CPC_REINIT_F) disable_cpc_sram(); #endif + +#if defined(CONFIG_FSL_CORENET) + /* Put PAMU in bypass mode */ + out_be32(&gur->pamubypenr, FSL_CORENET_PAMU_BYPASS); +#endif + #endif #ifdef CONFIG_CPM2 @@ -803,7 +813,7 @@ int cpu_init_r(void) #ifdef CONFIG_SYS_FSL_ERRATUM_SEC_A003571 #define MCFGR_AXIPIPE 0x000000f0 if (IS_SVR_REV(svr, 1, 0)) - clrbits_be32(&sec->mcfgr, MCFGR_AXIPIPE); + sec_clrbits32(&sec->mcfgr, MCFGR_AXIPIPE); #endif #ifdef CONFIG_SYS_FSL_ERRATUM_A005871 @@ -938,6 +948,10 @@ int cpu_init_r(void) fman_enet_init(); #endif +#ifdef CONFIG_FSL_CAAM + sec_init(); +#endif + #if defined(CONFIG_FSL_SATA_V2) && defined(CONFIG_FSL_SATA_ERRATUM_A001) /* * For P1022/1013 Rev1.0 silicon, after power on SATA host diff --git a/arch/powerpc/cpu/mpc85xx/fdt.c b/arch/powerpc/cpu/mpc85xx/fdt.c index 3222e26..d4c3d9d 100644 --- a/arch/powerpc/cpu/mpc85xx/fdt.c +++ b/arch/powerpc/cpu/mpc85xx/fdt.c @@ -714,7 +714,7 @@ void ft_cpu_setup(void *blob, bd_t *bd) ccsr_sec_t __iomem *sec; sec = (void __iomem *)CONFIG_SYS_FSL_SEC_ADDR; - fdt_fixup_crypto_node(blob, in_be32(&sec->secvid_ms)); + fdt_fixup_crypto_node(blob, sec_in32(&sec->secvid_ms)); } #endif diff --git a/arch/powerpc/cpu/mpc85xx/liodn.c b/arch/powerpc/cpu/mpc85xx/liodn.c index 19e130e..7a2d4be 100644 --- a/arch/powerpc/cpu/mpc85xx/liodn.c +++ b/arch/powerpc/cpu/mpc85xx/liodn.c @@ -66,12 +66,12 @@ static void setup_sec_liodn_base(void) return; /* QILCR[QSLOM] */ - out_be32(&sec->qilcr_ms, 0x3ff<<16); + sec_out32(&sec->qilcr_ms, 0x3ff<<16); base = (liodn_bases[FSL_HW_PORTAL_SEC].id[0] << 16) | liodn_bases[FSL_HW_PORTAL_SEC].id[1]; - out_be32(&sec->qilcr_ls, base); + sec_out32(&sec->qilcr_ls, base); } #ifdef CONFIG_SYS_DPAA_FMAN diff --git a/arch/powerpc/cpu/mpc8xxx/fdt.c b/arch/powerpc/cpu/mpc8xxx/fdt.c index 4cec5e1..c6b4d95 100644 --- a/arch/powerpc/cpu/mpc8xxx/fdt.c +++ b/arch/powerpc/cpu/mpc8xxx/fdt.c @@ -287,8 +287,8 @@ static u8 caam_get_era(void) }; ccsr_sec_t __iomem *sec = (void __iomem *)CONFIG_SYS_FSL_SEC_ADDR; - u32 secvid_ms = in_be32(&sec->secvid_ms); - u32 ccbvid = in_be32(&sec->ccbvid); + u32 secvid_ms = sec_in32(&sec->secvid_ms); + u32 ccbvid = sec_in32(&sec->ccbvid); u16 ip_id = (secvid_ms & SEC_SECVID_MS_IPID_MASK) >> SEC_SECVID_MS_IPID_SHIFT; u8 maj_rev = (secvid_ms & SEC_SECVID_MS_MAJ_REV_MASK) >> diff --git a/arch/powerpc/include/asm/config_mpc85xx.h b/arch/powerpc/include/asm/config_mpc85xx.h index 712f2ef..4c1774f 100644 --- a/arch/powerpc/include/asm/config_mpc85xx.h +++ b/arch/powerpc/include/asm/config_mpc85xx.h @@ -24,6 +24,7 @@ /* IP endianness */ #define CONFIG_SYS_FSL_IFC_BE +#define CONFIG_SYS_FSL_SEC_BE /* Number of TLB CAM entries we have on FSL Book-E chips */ #if defined(CONFIG_E500MC) diff --git a/arch/powerpc/include/asm/immap_85xx.h b/arch/powerpc/include/asm/immap_85xx.h index dfb370e..0264523 100644 --- a/arch/powerpc/include/asm/immap_85xx.h +++ b/arch/powerpc/include/asm/immap_85xx.h @@ -16,6 +16,7 @@ #include <asm/fsl_dma.h> #include <asm/fsl_i2c.h> #include <fsl_ifc.h> +#include <fsl_sec.h> #include <asm/fsl_lbc.h> #include <asm/fsl_fman.h> #include <fsl_immap.h> @@ -1911,6 +1912,7 @@ defined(CONFIG_PPC_T1020) || defined(CONFIG_PPC_T1022) u8 res24[64]; u32 pblsr; /* Preboot loader status */ u32 pamubypenr; /* PAMU bypass enable */ +#define FSL_CORENET_PAMU_BYPASS 0xffff0000 u32 dmacr1; /* DMA control */ u8 res25[4]; u32 gensr1; /* General status */ @@ -2675,72 +2677,6 @@ enum { FSL_SRDS_B3_LANE_D = 23, }; -/* Security Engine Block (MS = Most Sig., LS = Least Sig.) */ -#if CONFIG_SYS_FSL_SEC_COMPAT >= 4 -typedef struct ccsr_sec { - u32 res0; - u32 mcfgr; /* Master CFG Register */ - u8 res1[0x8]; - struct { - u32 ms; /* Job Ring LIODN Register, MS */ - u32 ls; /* Job Ring LIODN Register, LS */ - } jrliodnr[4]; - u8 res2[0x30]; - struct { - u32 ms; /* RTIC LIODN Register, MS */ - u32 ls; /* RTIC LIODN Register, LS */ - } rticliodnr[4]; - u8 res3[0x1c]; - u32 decorr; /* DECO Request Register */ - struct { - u32 ms; /* DECO LIODN Register, MS */ - u32 ls; /* DECO LIODN Register, LS */ - } decoliodnr[8]; - u8 res4[0x40]; - u32 dar; /* DECO Avail Register */ - u32 drr; /* DECO Reset Register */ - u8 res5[0xe78]; - u32 crnr_ms; /* CHA Revision Number Register, MS */ - u32 crnr_ls; /* CHA Revision Number Register, LS */ - u32 ctpr_ms; /* Compile Time Parameters Register, MS */ - u32 ctpr_ls; /* Compile Time Parameters Register, LS */ - u8 res6[0x10]; - u32 far_ms; /* Fault Address Register, MS */ - u32 far_ls; /* Fault Address Register, LS */ - u32 falr; /* Fault Address LIODN Register */ - u32 fadr; /* Fault Address Detail Register */ - u8 res7[0x4]; - u32 csta; /* CAAM Status Register */ - u8 res8[0x8]; - u32 rvid; /* Run Time Integrity Checking Version ID Reg.*/ - u32 ccbvid; /* CHA Cluster Block Version ID Register */ - u32 chavid_ms; /* CHA Version ID Register, MS */ - u32 chavid_ls; /* CHA Version ID Register, LS */ - u32 chanum_ms; /* CHA Number Register, MS */ - u32 chanum_ls; /* CHA Number Register, LS */ - u32 secvid_ms; /* SEC Version ID Register, MS */ - u32 secvid_ls; /* SEC Version ID Register, LS */ - u8 res9[0x6020]; - u32 qilcr_ms; /* Queue Interface LIODN CFG Register, MS */ - u32 qilcr_ls; /* Queue Interface LIODN CFG Register, LS */ - u8 res10[0x8fd8]; -} ccsr_sec_t; - -#define SEC_CTPR_MS_AXI_LIODN 0x08000000 -#define SEC_CTPR_MS_QI 0x02000000 -#define SEC_RVID_MA 0x0f000000 -#define SEC_CHANUM_MS_JRNUM_MASK 0xf0000000 -#define SEC_CHANUM_MS_JRNUM_SHIFT 28 -#define SEC_CHANUM_MS_DECONUM_MASK 0x0f000000 -#define SEC_CHANUM_MS_DECONUM_SHIFT 24 -#define SEC_SECVID_MS_IPID_MASK 0xffff0000 -#define SEC_SECVID_MS_IPID_SHIFT 16 -#define SEC_SECVID_MS_MAJ_REV_MASK 0x0000ff00 -#define SEC_SECVID_MS_MAJ_REV_SHIFT 8 -#define SEC_CCBVID_ERA_MASK 0xff000000 -#define SEC_CCBVID_ERA_SHIFT 24 -#endif - typedef struct ccsr_qman { #ifdef CONFIG_SYS_FSL_QMAN_V3 u8 res0[0x200]; @@ -2940,6 +2876,7 @@ struct ccsr_sfp_regs { #define CONFIG_SYS_MPC85xx_SATA1_OFFSET 0x220000 #define CONFIG_SYS_MPC85xx_SATA2_OFFSET 0x221000 #define CONFIG_SYS_FSL_SEC_OFFSET 0x300000 +#define CONFIG_SYS_FSL_JR0_OFFSET 0x301000 #define CONFIG_SYS_FSL_CORENET_PME_OFFSET 0x316000 #define CONFIG_SYS_FSL_QMAN_OFFSET 0x318000 #define CONFIG_SYS_FSL_BMAN_OFFSET 0x31a000 @@ -3000,8 +2937,10 @@ struct ccsr_sfp_regs { #define CONFIG_SYS_MPC85xx_ESDHC_OFFSET 0x2e000 #if defined(CONFIG_PPC_C29X) #define CONFIG_SYS_FSL_SEC_OFFSET 0x80000 +#define CONFIG_SYS_FSL_JR0_OFFSET 0x81000 #else #define CONFIG_SYS_FSL_SEC_OFFSET 0x30000 +#define CONFIG_SYS_FSL_JR0_OFFSET 0x31000 #endif #define CONFIG_SYS_MPC85xx_SERDES2_OFFSET 0xE3100 #define CONFIG_SYS_MPC85xx_SERDES1_OFFSET 0xE3000 @@ -3106,6 +3045,8 @@ struct ccsr_sfp_regs { (CONFIG_SYS_IMMR + CONFIG_SYS_MPC85xx_USB2_PHY_OFFSET) #define CONFIG_SYS_FSL_SEC_ADDR \ (CONFIG_SYS_IMMR + CONFIG_SYS_FSL_SEC_OFFSET) +#define CONFIG_SYS_FSL_JR0_ADDR \ + (CONFIG_SYS_IMMR + CONFIG_SYS_FSL_JR0_OFFSET) #define CONFIG_SYS_FSL_FM1_ADDR \ (CONFIG_SYS_IMMR + CONFIG_SYS_FSL_FM1_OFFSET) #define CONFIG_SYS_FSL_FM1_DTSEC1_ADDR \ diff --git a/arch/powerpc/include/asm/types.h b/arch/powerpc/include/asm/types.h index b27a6b7..b29ce79 100644 --- a/arch/powerpc/include/asm/types.h +++ b/arch/powerpc/include/asm/types.h @@ -41,8 +41,12 @@ typedef unsigned long long u64; #define BITS_PER_LONG 32 +#ifdef CONFIG_PHYS_64BIT +typedef unsigned long long dma_addr_t; +#else /* DMA addresses are 32-bits wide */ typedef u32 dma_addr_t; +#endif #ifdef CONFIG_PHYS_64BIT typedef unsigned long long phys_addr_t; diff --git a/board/freescale/ls1021aqds/MAINTAINERS b/board/freescale/ls1021aqds/MAINTAINERS index ccf4513..e30e944 100644 --- a/board/freescale/ls1021aqds/MAINTAINERS +++ b/board/freescale/ls1021aqds/MAINTAINERS @@ -5,3 +5,4 @@ F: board/freescale/ls1021aqds/ F: include/configs/ls1021aqds.h F: configs/ls1021aqds_nor_defconfig F: configs/ls1021aqds_ddr4_nor_defconfig +F: configs/ls1021aqds_nor_SECURE_BOOT_defconfig diff --git a/board/freescale/ls1021aqds/ls1021aqds.c b/board/freescale/ls1021aqds/ls1021aqds.c index 12e83f7..5fafc85 100644 --- a/board/freescale/ls1021aqds/ls1021aqds.c +++ b/board/freescale/ls1021aqds/ls1021aqds.c @@ -13,6 +13,7 @@ #include <mmc.h> #include <fsl_esdhc.h> #include <fsl_ifc.h> +#include <fsl_sec.h> #include "../common/qixis.h" #include "ls1021aqds_qixis.h" @@ -213,6 +214,15 @@ int config_serdes_mux(void) return 0; } +#if defined(CONFIG_MISC_INIT_R) +int misc_init_r(void) +{ +#ifdef CONFIG_FSL_CAAM + return sec_init(); +#endif +} +#endif + int board_init(void) { struct ccsr_cci400 *cci = (struct ccsr_cci400 *)CONFIG_SYS_CCI400_ADDR; diff --git a/board/freescale/ls1021atwr/MAINTAINERS b/board/freescale/ls1021atwr/MAINTAINERS index 4e5bc15..8def0e5 100644 --- a/board/freescale/ls1021atwr/MAINTAINERS +++ b/board/freescale/ls1021atwr/MAINTAINERS @@ -4,3 +4,4 @@ S: Maintained F: board/freescale/ls1021atwr/ F: include/configs/ls1021atwr.h F: configs/ls1021atwr_nor_defconfig +F: configs/ls1021atwr_nor_SECURE_BOOT_defconfig diff --git a/board/freescale/ls1021atwr/ls1021atwr.c b/board/freescale/ls1021atwr/ls1021atwr.c index b522ff2..50d5640 100644 --- a/board/freescale/ls1021atwr/ls1021atwr.c +++ b/board/freescale/ls1021atwr/ls1021atwr.c @@ -16,6 +16,7 @@ #include <netdev.h> #include <fsl_mdio.h> #include <tsec.h> +#include <fsl_sec.h> DECLARE_GLOBAL_DATA_PTR; @@ -280,6 +281,15 @@ int board_init(void) return 0; } +#if defined(CONFIG_MISC_INIT_R) +int misc_init_r(void) +{ +#ifdef CONFIG_FSL_CAAM + return sec_init(); +#endif +} +#endif + void ft_board_setup(void *blob, bd_t *bd) { ft_cpu_setup(blob, bd); diff --git a/common/Makefile b/common/Makefile index b19d379..c84b3bc 100644 --- a/common/Makefile +++ b/common/Makefile @@ -265,4 +265,6 @@ obj-y += aboot.o obj-y += fb_mmc.o endif +obj-$(CONFIG_CMD_BLOB) += cmd_blob.o + CFLAGS_env_embedded.o := -Wa,--no-warn -DENV_CRC=$(shell tools/envcrc 2>/dev/null) diff --git a/common/cmd_blob.c b/common/cmd_blob.c new file mode 100644 index 0000000..82ecaf0 --- /dev/null +++ b/common/cmd_blob.c @@ -0,0 +1,109 @@ +/* + * + * Command for encapsulating/decapsulating blob of memory. + * + * SPDX-License-Identifier: GPL-2.0+ + */ + +#include <common.h> +#include <command.h> +#include <environment.h> +#include <malloc.h> +#include <asm/byteorder.h> +#include <linux/compiler.h> + +DECLARE_GLOBAL_DATA_PTR; + +/** + * blob_decap() - Decapsulate the data as a blob + * @key_mod: - Pointer to key modifier/key + * @src: - Address of data to be decapsulated + * @dst: - Address of data to be decapsulated + * @len: - Size of data to be decapsulated + * + * Returns zero on success,and negative on error. + */ +__weak int blob_decap(u8 *key_mod, u8 *src, u8 *dst, u32 len) +{ + return 0; +} + +/** + * blob_encap() - Encapsulate the data as a blob + * @key_mod: - Pointer to key modifier/key + * @src: - Address of data to be encapsulated + * @dst: - Address of data to be encapsulated + * @len: - Size of data to be encapsulated + * + * Returns zero on success,and negative on error. + */ +__weak int blob_encap(u8 *key_mod, u8 *src, u8 *dst, u32 len) +{ + return 0; +} + +/** + * do_blob() - Handle the "blob" command-line command + * @cmdtp: Command data struct pointer + * @flag: Command flag + * @argc: Command-line argument count + * @argv: Array of command-line arguments + * + * Returns zero on success, CMD_RET_USAGE in case of misuse and negative + * on error. + */ +static int do_blob(cmd_tbl_t *cmdtp, int flag, int argc, char *const argv[]) +{ + uint32_t key_addr, src_addr, dst_addr, len; + uint8_t *km_ptr, *src_ptr, *dst_ptr; + int enc, ret = 0; + + if (argc != 6) + return CMD_RET_USAGE; + + if (!strncmp(argv[1], "enc", 3)) + enc = 1; + else if (!strncmp(argv[1], "dec", 3)) + enc = 0; + else + return CMD_RET_USAGE; + + src_addr = simple_strtoul(argv[2], NULL, 16); + dst_addr = simple_strtoul(argv[3], NULL, 16); + len = simple_strtoul(argv[4], NULL, 16); + key_addr = simple_strtoul(argv[5], NULL, 16); + + km_ptr = (uint8_t *)key_addr; + src_ptr = (uint8_t *)src_addr; + dst_ptr = (uint8_t *)dst_addr; + + if (enc) + ret = blob_encap(km_ptr, src_ptr, dst_ptr, len); + else + ret = blob_decap(km_ptr, src_ptr, dst_ptr, len); + + return ret; +} + +/***************************************************/ +static char blob_help_text[] = + "enc src dst len km - Encapsulate and create blob of data\n" + " $len bytes long at address $src and\n" + " store the result at address $dst.\n" + " $km is the 16 byte key modifier\n" + " is also required for generation/use as\n" + " key for cryptographic operation. Key\n" + " modifier should be 16 byte long.\n" + "blob dec src dst len km - Decapsulate the blob of data at address\n" + " $src and store result of $len byte at\n" + " addr $dst.\n" + " $km is the 16 byte key modifier\n" + " is also required for generation/use as\n" + " key for cryptographic operation. Key\n" + " modifier should be 16 byte long.\n"; + +U_BOOT_CMD( + blob, 6, 1, do_blob, + "Blob encapsulation/decryption", + blob_help_text +); diff --git a/configs/ls1021aqds_nor_SECURE_BOOT_defconfig b/configs/ls1021aqds_nor_SECURE_BOOT_defconfig new file mode 100644 index 0000000..2b47995 --- /dev/null +++ b/configs/ls1021aqds_nor_SECURE_BOOT_defconfig @@ -0,0 +1,3 @@ +CONFIG_SYS_EXTRA_OPTIONS="SECURE_BOOT" +CONFIG_ARM=y +CONFIG_TARGET_LS1021AQDS=y diff --git a/configs/ls1021atwr_nor_SECURE_BOOT_defconfig b/configs/ls1021atwr_nor_SECURE_BOOT_defconfig new file mode 100644 index 0000000..eeeb0d5 --- /dev/null +++ b/configs/ls1021atwr_nor_SECURE_BOOT_defconfig @@ -0,0 +1,3 @@ +CONFIG_SYS_EXTRA_OPTIONS="SECURE_BOOT" +CONFIG_ARM=y +CONFIG_TARGET_LS1021ATWR=y diff --git a/drivers/crypto/Makefile b/drivers/crypto/Makefile index b807795..7b79237 100644 --- a/drivers/crypto/Makefile +++ b/drivers/crypto/Makefile @@ -6,3 +6,4 @@ # obj-$(CONFIG_EXYNOS_ACE_SHA) += ace_sha.o +obj-y += fsl/ diff --git a/drivers/crypto/fsl/Makefile b/drivers/crypto/fsl/Makefile new file mode 100644 index 0000000..cb13d2e --- /dev/null +++ b/drivers/crypto/fsl/Makefile @@ -0,0 +1,10 @@ +# +# Copyright 2014 Freescale Semiconductor, Inc. +# +# This program is free software; you can redistribute it and/or +# modify it under the terms of the GNU General Public License +# Version 2 as published by the Free Software Foundation. +# + +obj-$(CONFIG_FSL_CAAM) += jr.o fsl_hash.o jobdesc.o error.o +obj-$(CONFIG_CMD_BLOB) += fsl_blob.o diff --git a/drivers/crypto/fsl/desc.h b/drivers/crypto/fsl/desc.h new file mode 100644 index 0000000..504f2b0 --- /dev/null +++ b/drivers/crypto/fsl/desc.h @@ -0,0 +1,651 @@ +/* + * CAAM descriptor composition header + * Definitions to support CAAM descriptor instruction generation + * + * Copyright 2008-2014 Freescale Semiconductor, Inc. + * + * SPDX-License-Identifier: GPL-2.0+ + * + * Based on desc.h file in linux drivers/crypto/caam + */ + +#ifndef DESC_H +#define DESC_H + +/* Max size of any CAAM descriptor in 32-bit words, inclusive of header */ +#define MAX_CAAM_DESCSIZE 64 + +/* Block size of any entity covered/uncovered with a KEK/TKEK */ +#define KEK_BLOCKSIZE 16 +/* + * Supported descriptor command types as they show up + * inside a descriptor command word. + */ +#define CMD_SHIFT 27 +#define CMD_MASK 0xf8000000 + +#define CMD_KEY (0x00 << CMD_SHIFT) +#define CMD_SEQ_KEY (0x01 << CMD_SHIFT) +#define CMD_LOAD (0x02 << CMD_SHIFT) +#define CMD_SEQ_LOAD (0x03 << CMD_SHIFT) +#define CMD_FIFO_LOAD (0x04 << CMD_SHIFT) +#define CMD_SEQ_FIFO_LOAD (0x05 << CMD_SHIFT) +#define CMD_STORE (0x0a << CMD_SHIFT) +#define CMD_SEQ_STORE (0x0b << CMD_SHIFT) +#define CMD_FIFO_STORE (0x0c << CMD_SHIFT) +#define CMD_SEQ_FIFO_STORE (0x0d << CMD_SHIFT) +#define CMD_MOVE_LEN (0x0e << CMD_SHIFT) +#define CMD_MOVE (0x0f << CMD_SHIFT) +#define CMD_OPERATION (0x10 << CMD_SHIFT) +#define CMD_SIGNATURE (0x12 << CMD_SHIFT) +#define CMD_JUMP (0x14 << CMD_SHIFT) +#define CMD_MATH (0x15 << CMD_SHIFT) +#define CMD_DESC_HDR (0x16 << CMD_SHIFT) +#define CMD_SHARED_DESC_HDR (0x17 << CMD_SHIFT) +#define CMD_SEQ_IN_PTR (0x1e << CMD_SHIFT) +#define CMD_SEQ_OUT_PTR (0x1f << CMD_SHIFT) + +/* General-purpose class selector for all commands */ +#define CLASS_SHIFT 25 +#define CLASS_MASK (0x03 << CLASS_SHIFT) + +#define CLASS_NONE (0x00 << CLASS_SHIFT) +#define CLASS_1 (0x01 << CLASS_SHIFT) +#define CLASS_2 (0x02 << CLASS_SHIFT) +#define CLASS_BOTH (0x03 << CLASS_SHIFT) + +/* + * Descriptor header command constructs + * Covers shared, job, and trusted descriptor headers + */ + +/* + * Do Not Run - marks a descriptor inexecutable if there was + * a preceding error somewhere + */ +#define HDR_DNR 0x01000000 + +/* + * ONE - should always be set. Combination of ONE (always + * set) and ZRO (always clear) forms an endianness sanity check + */ +#define HDR_ONE 0x00800000 +#define HDR_ZRO 0x00008000 + +/* Start Index or SharedDesc Length */ +#define HDR_START_IDX_MASK 0x3f +#define HDR_START_IDX_SHIFT 16 + +/* If shared descriptor header, 6-bit length */ +#define HDR_DESCLEN_SHR_MASK 0x3f + +/* If non-shared header, 7-bit length */ +#define HDR_DESCLEN_MASK 0x7f + +/* This is a TrustedDesc (if not SharedDesc) */ +#define HDR_TRUSTED 0x00004000 + +/* Make into TrustedDesc (if not SharedDesc) */ +#define HDR_MAKE_TRUSTED 0x00002000 + +/* Save context if self-shared (if SharedDesc) */ +#define HDR_SAVECTX 0x00001000 + +/* Next item points to SharedDesc */ +#define HDR_SHARED 0x00001000 + +/* + * Reverse Execution Order - execute JobDesc first, then + * execute SharedDesc (normally SharedDesc goes first). + */ +#define HDR_REVERSE 0x00000800 + +/* Propogate DNR property to SharedDesc */ +#define HDR_PROP_DNR 0x00000800 + +/* JobDesc/SharedDesc share property */ +#define HDR_SD_SHARE_MASK 0x03 +#define HDR_SD_SHARE_SHIFT 8 +#define HDR_JD_SHARE_MASK 0x07 +#define HDR_JD_SHARE_SHIFT 8 + +#define HDR_SHARE_NEVER (0x00 << HDR_SD_SHARE_SHIFT) +#define HDR_SHARE_WAIT (0x01 << HDR_SD_SHARE_SHIFT) +#define HDR_SHARE_SERIAL (0x02 << HDR_SD_SHARE_SHIFT) +#define HDR_SHARE_ALWAYS (0x03 << HDR_SD_SHARE_SHIFT) +#define HDR_SHARE_DEFER (0x04 << HDR_SD_SHARE_SHIFT) + +/* JobDesc/SharedDesc descriptor length */ +#define HDR_JD_LENGTH_MASK 0x7f +#define HDR_SD_LENGTH_MASK 0x3f + +/* + * KEY/SEQ_KEY Command Constructs + */ + +/* Key Destination Class: 01 = Class 1, 02 - Class 2 */ +#define KEY_DEST_CLASS_SHIFT 25 /* use CLASS_1 or CLASS_2 */ +#define KEY_DEST_CLASS_MASK (0x03 << KEY_DEST_CLASS_SHIFT) + +/* Scatter-Gather Table/Variable Length Field */ +#define KEY_SGF 0x01000000 +#define KEY_VLF 0x01000000 + +/* Immediate - Key follows command in the descriptor */ +#define KEY_IMM 0x00800000 + +/* + * Encrypted - Key is encrypted either with the KEK, or + * with the TDKEK if TK is set + */ +#define KEY_ENC 0x00400000 + +/* + * No Write Back - Do not allow key to be FIFO STOREd + */ +#define KEY_NWB 0x00200000 + +/* + * Enhanced Encryption of Key + */ +#define KEY_EKT 0x00100000 + +/* + * Encrypted with Trusted Key + */ +#define KEY_TK 0x00008000 + +/* + * KDEST - Key Destination: 0 - class key register, + * 1 - PKHA 'e', 2 - AFHA Sbox, 3 - MDHA split-key + */ +#define KEY_DEST_SHIFT 16 +#define KEY_DEST_MASK (0x03 << KEY_DEST_SHIFT) + +#define KEY_DEST_CLASS_REG (0x00 << KEY_DEST_SHIFT) +#define KEY_DEST_PKHA_E (0x01 << KEY_DEST_SHIFT) +#define KEY_DEST_AFHA_SBOX (0x02 << KEY_DEST_SHIFT) +#define KEY_DEST_MDHA_SPLIT (0x03 << KEY_DEST_SHIFT) + +/* Length in bytes */ +#define KEY_LENGTH_MASK 0x000003ff + +/* + * LOAD/SEQ_LOAD/STORE/SEQ_STORE Command Constructs + */ + +/* + * Load/Store Destination: 0 = class independent CCB, + * 1 = class 1 CCB, 2 = class 2 CCB, 3 = DECO + */ +#define LDST_CLASS_SHIFT 25 +#define LDST_CLASS_MASK (0x03 << LDST_CLASS_SHIFT) +#define LDST_CLASS_IND_CCB (0x00 << LDST_CLASS_SHIFT) +#define LDST_CLASS_1_CCB (0x01 << LDST_CLASS_SHIFT) +#define LDST_CLASS_2_CCB (0x02 << LDST_CLASS_SHIFT) +#define LDST_CLASS_DECO (0x03 << LDST_CLASS_SHIFT) + +/* Scatter-Gather Table/Variable Length Field */ +#define LDST_SGF 0x01000000 +#define LDST_VLF LDST_SGF + +/* Immediate - Key follows this command in descriptor */ +#define LDST_IMM_MASK 1 +#define LDST_IMM_SHIFT 23 +#define LDST_IMM (LDST_IMM_MASK << LDST_IMM_SHIFT) + +/* SRC/DST - Destination for LOAD, Source for STORE */ +#define LDST_SRCDST_SHIFT 16 +#define LDST_SRCDST_MASK (0x7f << LDST_SRCDST_SHIFT) + +#define LDST_SRCDST_BYTE_CONTEXT (0x20 << LDST_SRCDST_SHIFT) +#define LDST_SRCDST_BYTE_KEY (0x40 << LDST_SRCDST_SHIFT) +#define LDST_SRCDST_BYTE_INFIFO (0x7c << LDST_SRCDST_SHIFT) +#define LDST_SRCDST_BYTE_OUTFIFO (0x7e << LDST_SRCDST_SHIFT) + +#define LDST_SRCDST_WORD_MODE_REG (0x00 << LDST_SRCDST_SHIFT) +#define LDST_SRCDST_WORD_KEYSZ_REG (0x01 << LDST_SRCDST_SHIFT) +#define LDST_SRCDST_WORD_DATASZ_REG (0x02 << LDST_SRCDST_SHIFT) +#define LDST_SRCDST_WORD_ICVSZ_REG (0x03 << LDST_SRCDST_SHIFT) +#define LDST_SRCDST_WORD_CHACTRL (0x06 << LDST_SRCDST_SHIFT) +#define LDST_SRCDST_WORD_DECOCTRL (0x06 << LDST_SRCDST_SHIFT) +#define LDST_SRCDST_WORD_IRQCTRL (0x07 << LDST_SRCDST_SHIFT) +#define LDST_SRCDST_WORD_DECO_PCLOVRD (0x07 << LDST_SRCDST_SHIFT) +#define LDST_SRCDST_WORD_CLRW (0x08 << LDST_SRCDST_SHIFT) +#define LDST_SRCDST_WORD_DECO_MATH0 (0x08 << LDST_SRCDST_SHIFT) +#define LDST_SRCDST_WORD_STAT (0x09 << LDST_SRCDST_SHIFT) +#define LDST_SRCDST_WORD_DECO_MATH1 (0x09 << LDST_SRCDST_SHIFT) +#define LDST_SRCDST_WORD_DECO_MATH2 (0x0a << LDST_SRCDST_SHIFT) +#define LDST_SRCDST_WORD_DECO_AAD_SZ (0x0b << LDST_SRCDST_SHIFT) +#define LDST_SRCDST_WORD_DECO_MATH3 (0x0b << LDST_SRCDST_SHIFT) +#define LDST_SRCDST_WORD_CLASS1_ICV_SZ (0x0c << LDST_SRCDST_SHIFT) +#define LDST_SRCDST_WORD_ALTDS_CLASS1 (0x0f << LDST_SRCDST_SHIFT) +#define LDST_SRCDST_WORD_PKHA_A_SZ (0x10 << LDST_SRCDST_SHIFT) +#define LDST_SRCDST_WORD_PKHA_B_SZ (0x11 << LDST_SRCDST_SHIFT) +#define LDST_SRCDST_WORD_PKHA_N_SZ (0x12 << LDST_SRCDST_SHIFT) +#define LDST_SRCDST_WORD_PKHA_E_SZ (0x13 << LDST_SRCDST_SHIFT) +#define LDST_SRCDST_WORD_CLASS_CTX (0x20 << LDST_SRCDST_SHIFT) +#define LDST_SRCDST_WORD_DESCBUF (0x40 << LDST_SRCDST_SHIFT) +#define LDST_SRCDST_WORD_DESCBUF_JOB (0x41 << LDST_SRCDST_SHIFT) +#define LDST_SRCDST_WORD_DESCBUF_SHARED (0x42 << LDST_SRCDST_SHIFT) +#define LDST_SRCDST_WORD_DESCBUF_JOB_WE (0x45 << LDST_SRCDST_SHIFT) +#define LDST_SRCDST_WORD_DESCBUF_SHARED_WE (0x46 << LDST_SRCDST_SHIFT) +#define LDST_SRCDST_WORD_INFO_FIFO (0x7a << LDST_SRCDST_SHIFT) + +/* Offset in source/destination */ +#define LDST_OFFSET_SHIFT 8 +#define LDST_OFFSET_MASK (0xff << LDST_OFFSET_SHIFT) + +/* LDOFF definitions used when DST = LDST_SRCDST_WORD_DECOCTRL */ +/* These could also be shifted by LDST_OFFSET_SHIFT - this reads better */ +#define LDOFF_CHG_SHARE_SHIFT 0 +#define LDOFF_CHG_SHARE_MASK (0x3 << LDOFF_CHG_SHARE_SHIFT) +#define LDOFF_CHG_SHARE_NEVER (0x1 << LDOFF_CHG_SHARE_SHIFT) +#define LDOFF_CHG_SHARE_OK_PROP (0x2 << LDOFF_CHG_SHARE_SHIFT) +#define LDOFF_CHG_SHARE_OK_NO_PROP (0x3 << LDOFF_CHG_SHARE_SHIFT) + +#define LDOFF_ENABLE_AUTO_NFIFO (1 << 2) +#define LDOFF_DISABLE_AUTO_NFIFO (1 << 3) + +#define LDOFF_CHG_NONSEQLIODN_SHIFT 4 +#define LDOFF_CHG_NONSEQLIODN_MASK (0x3 << LDOFF_CHG_NONSEQLIODN_SHIFT) +#define LDOFF_CHG_NONSEQLIODN_SEQ (0x1 << LDOFF_CHG_NONSEQLIODN_SHIFT) +#define LDOFF_CHG_NONSEQLIODN_NON_SEQ (0x2 << LDOFF_CHG_NONSEQLIODN_SHIFT) +#define LDOFF_CHG_NONSEQLIODN_TRUSTED (0x3 << LDOFF_CHG_NONSEQLIODN_SHIFT) + +#define LDOFF_CHG_SEQLIODN_SHIFT 6 +#define LDOFF_CHG_SEQLIODN_MASK (0x3 << LDOFF_CHG_SEQLIODN_SHIFT) +#define LDOFF_CHG_SEQLIODN_SEQ (0x1 << LDOFF_CHG_SEQLIODN_SHIFT) +#define LDOFF_CHG_SEQLIODN_NON_SEQ (0x2 << LDOFF_CHG_SEQLIODN_SHIFT) +#define LDOFF_CHG_SEQLIODN_TRUSTED (0x3 << LDOFF_CHG_SEQLIODN_SHIFT) + +/* Data length in bytes */ +#define LDST_LEN_SHIFT 0 +#define LDST_LEN_MASK (0xff << LDST_LEN_SHIFT) + +/* Special Length definitions when dst=deco-ctrl */ +#define LDLEN_ENABLE_OSL_COUNT (1 << 7) +#define LDLEN_RST_CHA_OFIFO_PTR (1 << 6) +#define LDLEN_RST_OFIFO (1 << 5) +#define LDLEN_SET_OFIFO_OFF_VALID (1 << 4) +#define LDLEN_SET_OFIFO_OFF_RSVD (1 << 3) +#define LDLEN_SET_OFIFO_OFFSET_SHIFT 0 +#define LDLEN_SET_OFIFO_OFFSET_MASK (3 << LDLEN_SET_OFIFO_OFFSET_SHIFT) + +/* + * FIFO_LOAD/FIFO_STORE/SEQ_FIFO_LOAD/SEQ_FIFO_STORE + * Command Constructs + */ + +/* + * Load Destination: 0 = skip (SEQ_FIFO_LOAD only), + * 1 = Load for Class1, 2 = Load for Class2, 3 = Load both + * Store Source: 0 = normal, 1 = Class1key, 2 = Class2key + */ +#define FIFOLD_CLASS_SHIFT 25 +#define FIFOLD_CLASS_MASK (0x03 << FIFOLD_CLASS_SHIFT) +#define FIFOLD_CLASS_SKIP (0x00 << FIFOLD_CLASS_SHIFT) +#define FIFOLD_CLASS_CLASS1 (0x01 << FIFOLD_CLASS_SHIFT) +#define FIFOLD_CLASS_CLASS2 (0x02 << FIFOLD_CLASS_SHIFT) +#define FIFOLD_CLASS_BOTH (0x03 << FIFOLD_CLASS_SHIFT) + +#define FIFOST_CLASS_SHIFT 25 +#define FIFOST_CLASS_MASK (0x03 << FIFOST_CLASS_SHIFT) +#define FIFOST_CLASS_NORMAL (0x00 << FIFOST_CLASS_SHIFT) +#define FIFOST_CLASS_CLASS1KEY (0x01 << FIFOST_CLASS_SHIFT) +#define FIFOST_CLASS_CLASS2KEY (0x02 << FIFOST_CLASS_SHIFT) + +/* + * Scatter-Gather Table/Variable Length Field + * If set for FIFO_LOAD, refers to a SG table. Within + * SEQ_FIFO_LOAD, is variable input sequence + */ +#define FIFOLDST_SGF_SHIFT 24 +#define FIFOLDST_SGF_MASK (1 << FIFOLDST_SGF_SHIFT) +#define FIFOLDST_VLF_MASK (1 << FIFOLDST_SGF_SHIFT) +#define FIFOLDST_SGF (1 << FIFOLDST_SGF_SHIFT) +#define FIFOLDST_VLF (1 << FIFOLDST_SGF_SHIFT) + +/* Immediate - Data follows command in descriptor */ +#define FIFOLD_IMM_SHIFT 23 +#define FIFOLD_IMM_MASK (1 << FIFOLD_IMM_SHIFT) +#define FIFOLD_IMM (1 << FIFOLD_IMM_SHIFT) + +/* Continue - Not the last FIFO store to come */ +#define FIFOST_CONT_SHIFT 23 +#define FIFOST_CONT_MASK (1 << FIFOST_CONT_SHIFT) + +/* + * Extended Length - use 32-bit extended length that + * follows the pointer field. Illegal with IMM set + */ +#define FIFOLDST_EXT_SHIFT 22 +#define FIFOLDST_EXT_MASK (1 << FIFOLDST_EXT_SHIFT) +#define FIFOLDST_EXT (1 << FIFOLDST_EXT_SHIFT) + +/* Input data type.*/ +#define FIFOLD_TYPE_SHIFT 16 +#define FIFOLD_CONT_TYPE_SHIFT 19 /* shift past last-flush bits */ +#define FIFOLD_TYPE_MASK (0x3f << FIFOLD_TYPE_SHIFT) + +/* PK types */ +#define FIFOLD_TYPE_PK (0x00 << FIFOLD_TYPE_SHIFT) +#define FIFOLD_TYPE_PK_MASK (0x30 << FIFOLD_TYPE_SHIFT) +#define FIFOLD_TYPE_PK_TYPEMASK (0x0f << FIFOLD_TYPE_SHIFT) +#define FIFOLD_TYPE_PK_A0 (0x00 << FIFOLD_TYPE_SHIFT) +#define FIFOLD_TYPE_PK_A1 (0x01 << FIFOLD_TYPE_SHIFT) +#define FIFOLD_TYPE_PK_A2 (0x02 << FIFOLD_TYPE_SHIFT) +#define FIFOLD_TYPE_PK_A3 (0x03 << FIFOLD_TYPE_SHIFT) +#define FIFOLD_TYPE_PK_B0 (0x04 << FIFOLD_TYPE_SHIFT) +#define FIFOLD_TYPE_PK_B1 (0x05 << FIFOLD_TYPE_SHIFT) +#define FIFOLD_TYPE_PK_B2 (0x06 << FIFOLD_TYPE_SHIFT) +#define FIFOLD_TYPE_PK_B3 (0x07 << FIFOLD_TYPE_SHIFT) +#define FIFOLD_TYPE_PK_N (0x08 << FIFOLD_TYPE_SHIFT) +#define FIFOLD_TYPE_PK_A (0x0c << FIFOLD_TYPE_SHIFT) +#define FIFOLD_TYPE_PK_B (0x0d << FIFOLD_TYPE_SHIFT) + +/* Other types. Need to OR in last/flush bits as desired */ +#define FIFOLD_TYPE_MSG_MASK (0x38 << FIFOLD_TYPE_SHIFT) +#define FIFOLD_TYPE_MSG (0x10 << FIFOLD_TYPE_SHIFT) +#define FIFOLD_TYPE_MSG1OUT2 (0x18 << FIFOLD_TYPE_SHIFT) +#define FIFOLD_TYPE_IV (0x20 << FIFOLD_TYPE_SHIFT) +#define FIFOLD_TYPE_BITDATA (0x28 << FIFOLD_TYPE_SHIFT) +#define FIFOLD_TYPE_AAD (0x30 << FIFOLD_TYPE_SHIFT) +#define FIFOLD_TYPE_ICV (0x38 << FIFOLD_TYPE_SHIFT) + +/* Last/Flush bits for use with "other" types above */ +#define FIFOLD_TYPE_ACT_MASK (0x07 << FIFOLD_TYPE_SHIFT) +#define FIFOLD_TYPE_NOACTION (0x00 << FIFOLD_TYPE_SHIFT) +#define FIFOLD_TYPE_FLUSH1 (0x01 << FIFOLD_TYPE_SHIFT) +#define FIFOLD_TYPE_LAST1 (0x02 << FIFOLD_TYPE_SHIFT) +#define FIFOLD_TYPE_LAST2FLUSH (0x03 << FIFOLD_TYPE_SHIFT) +#define FIFOLD_TYPE_LAST2 (0x04 << FIFOLD_TYPE_SHIFT) +#define FIFOLD_TYPE_LAST2FLUSH1 (0x05 << FIFOLD_TYPE_SHIFT) +#define FIFOLD_TYPE_LASTBOTH (0x06 << FIFOLD_TYPE_SHIFT) +#define FIFOLD_TYPE_LASTBOTHFL (0x07 << FIFOLD_TYPE_SHIFT) +#define FIFOLD_TYPE_NOINFOFIFO (0x0F << FIFOLD_TYPE_SHIFT) + +#define FIFOLDST_LEN_MASK 0xffff +#define FIFOLDST_EXT_LEN_MASK 0xffffffff + +/* Output data types */ +#define FIFOST_TYPE_SHIFT 16 +#define FIFOST_TYPE_MASK (0x3f << FIFOST_TYPE_SHIFT) + +#define FIFOST_TYPE_PKHA_A0 (0x00 << FIFOST_TYPE_SHIFT) +#define FIFOST_TYPE_PKHA_A1 (0x01 << FIFOST_TYPE_SHIFT) +#define FIFOST_TYPE_PKHA_A2 (0x02 << FIFOST_TYPE_SHIFT) +#define FIFOST_TYPE_PKHA_A3 (0x03 << FIFOST_TYPE_SHIFT) +#define FIFOST_TYPE_PKHA_B0 (0x04 << FIFOST_TYPE_SHIFT) +#define FIFOST_TYPE_PKHA_B1 (0x05 << FIFOST_TYPE_SHIFT) +#define FIFOST_TYPE_PKHA_B2 (0x06 << FIFOST_TYPE_SHIFT) +#define FIFOST_TYPE_PKHA_B3 (0x07 << FIFOST_TYPE_SHIFT) +#define FIFOST_TYPE_PKHA_N (0x08 << FIFOST_TYPE_SHIFT) +#define FIFOST_TYPE_PKHA_A (0x0c << FIFOST_TYPE_SHIFT) +#define FIFOST_TYPE_PKHA_B (0x0d << FIFOST_TYPE_SHIFT) +#define FIFOST_TYPE_AF_SBOX_JKEK (0x10 << FIFOST_TYPE_SHIFT) +#define FIFOST_TYPE_AF_SBOX_TKEK (0x21 << FIFOST_TYPE_SHIFT) +#define FIFOST_TYPE_PKHA_E_JKEK (0x22 << FIFOST_TYPE_SHIFT) +#define FIFOST_TYPE_PKHA_E_TKEK (0x23 << FIFOST_TYPE_SHIFT) +#define FIFOST_TYPE_KEY_KEK (0x24 << FIFOST_TYPE_SHIFT) +#define FIFOST_TYPE_KEY_TKEK (0x25 << FIFOST_TYPE_SHIFT) +#define FIFOST_TYPE_SPLIT_KEK (0x26 << FIFOST_TYPE_SHIFT) +#define FIFOST_TYPE_SPLIT_TKEK (0x27 << FIFOST_TYPE_SHIFT) +#define FIFOST_TYPE_OUTFIFO_KEK (0x28 << FIFOST_TYPE_SHIFT) +#define FIFOST_TYPE_OUTFIFO_TKEK (0x29 << FIFOST_TYPE_SHIFT) +#define FIFOST_TYPE_MESSAGE_DATA (0x30 << FIFOST_TYPE_SHIFT) +#define FIFOST_TYPE_RNGSTORE (0x34 << FIFOST_TYPE_SHIFT) +#define FIFOST_TYPE_RNGFIFO (0x35 << FIFOST_TYPE_SHIFT) +#define FIFOST_TYPE_SKIP (0x3f << FIFOST_TYPE_SHIFT) + +/* + * OPERATION Command Constructs + */ + +/* Operation type selectors - OP TYPE */ +#define OP_TYPE_SHIFT 24 +#define OP_TYPE_MASK (0x07 << OP_TYPE_SHIFT) + +#define OP_TYPE_UNI_PROTOCOL (0x00 << OP_TYPE_SHIFT) +#define OP_TYPE_PK (0x01 << OP_TYPE_SHIFT) +#define OP_TYPE_CLASS1_ALG (0x02 << OP_TYPE_SHIFT) +#define OP_TYPE_CLASS2_ALG (0x04 << OP_TYPE_SHIFT) +#define OP_TYPE_DECAP_PROTOCOL (0x06 << OP_TYPE_SHIFT) +#define OP_TYPE_ENCAP_PROTOCOL (0x07 << OP_TYPE_SHIFT) + +/* ProtocolID selectors - PROTID */ +#define OP_PCLID_SHIFT 16 +#define OP_PCLID_MASK (0xff << 16) + +/* Assuming OP_TYPE = OP_TYPE_UNI_PROTOCOL */ +#define OP_PCLID_BLOB (0x0d << OP_PCLID_SHIFT) +#define OP_PCLID_SECRETKEY (0x11 << OP_PCLID_SHIFT) +#define OP_PCLID_PUBLICKEYPAIR (0x14 << OP_PCLID_SHIFT) + +/* For non-protocol/alg-only op commands */ +#define OP_ALG_TYPE_SHIFT 24 +#define OP_ALG_TYPE_MASK (0x7 << OP_ALG_TYPE_SHIFT) +#define OP_ALG_TYPE_CLASS1 2 +#define OP_ALG_TYPE_CLASS2 4 + +#define OP_ALG_ALGSEL_SHIFT 16 +#define OP_ALG_ALGSEL_MASK (0xff << OP_ALG_ALGSEL_SHIFT) +#define OP_ALG_ALGSEL_SUBMASK (0x0f << OP_ALG_ALGSEL_SHIFT) +#define OP_ALG_ALGSEL_AES (0x10 << OP_ALG_ALGSEL_SHIFT) +#define OP_ALG_ALGSEL_DES (0x20 << OP_ALG_ALGSEL_SHIFT) +#define OP_ALG_ALGSEL_3DES (0x21 << OP_ALG_ALGSEL_SHIFT) +#define OP_ALG_ALGSEL_ARC4 (0x30 << OP_ALG_ALGSEL_SHIFT) +#define OP_ALG_ALGSEL_MD5 (0x40 << OP_ALG_ALGSEL_SHIFT) +#define OP_ALG_ALGSEL_SHA1 (0x41 << OP_ALG_ALGSEL_SHIFT) +#define OP_ALG_ALGSEL_SHA224 (0x42 << OP_ALG_ALGSEL_SHIFT) +#define OP_ALG_ALGSEL_SHA256 (0x43 << OP_ALG_ALGSEL_SHIFT) +#define OP_ALG_ALGSEL_SHA384 (0x44 << OP_ALG_ALGSEL_SHIFT) +#define OP_ALG_ALGSEL_SHA512 (0x45 << OP_ALG_ALGSEL_SHIFT) +#define OP_ALG_ALGSEL_RNG (0x50 << OP_ALG_ALGSEL_SHIFT) +#define OP_ALG_ALGSEL_SNOW (0x60 << OP_ALG_ALGSEL_SHIFT) +#define OP_ALG_ALGSEL_SNOW_F8 (0x60 << OP_ALG_ALGSEL_SHIFT) +#define OP_ALG_ALGSEL_KASUMI (0x70 << OP_ALG_ALGSEL_SHIFT) +#define OP_ALG_ALGSEL_CRC (0x90 << OP_ALG_ALGSEL_SHIFT) +#define OP_ALG_ALGSEL_SNOW_F9 (0xA0 << OP_ALG_ALGSEL_SHIFT) + +#define OP_ALG_AAI_SHIFT 4 +#define OP_ALG_AAI_MASK (0x1ff << OP_ALG_AAI_SHIFT) + +/* randomizer AAI set */ +#define OP_ALG_AAI_RNG (0x00 << OP_ALG_AAI_SHIFT) +#define OP_ALG_AAI_RNG_NZB (0x10 << OP_ALG_AAI_SHIFT) +#define OP_ALG_AAI_RNG_OBP (0x20 << OP_ALG_AAI_SHIFT) + +/* RNG4 AAI set */ +#define OP_ALG_AAI_RNG4_SH_0 (0x00 << OP_ALG_AAI_SHIFT) +#define OP_ALG_AAI_RNG4_SH_1 (0x01 << OP_ALG_AAI_SHIFT) +#define OP_ALG_AAI_RNG4_PS (0x40 << OP_ALG_AAI_SHIFT) +#define OP_ALG_AAI_RNG4_AI (0x80 << OP_ALG_AAI_SHIFT) +#define OP_ALG_AAI_RNG4_SK (0x100 << OP_ALG_AAI_SHIFT) + +/* hmac/smac AAI set */ +#define OP_ALG_AAI_HASH (0x00 << OP_ALG_AAI_SHIFT) +#define OP_ALG_AAI_HMAC (0x01 << OP_ALG_AAI_SHIFT) +#define OP_ALG_AAI_SMAC (0x02 << OP_ALG_AAI_SHIFT) +#define OP_ALG_AAI_HMAC_PRECOMP (0x04 << OP_ALG_AAI_SHIFT) + +#define OP_ALG_AS_SHIFT 2 +#define OP_ALG_AS_MASK (0x3 << OP_ALG_AS_SHIFT) +#define OP_ALG_AS_UPDATE (0 << OP_ALG_AS_SHIFT) +#define OP_ALG_AS_INIT (1 << OP_ALG_AS_SHIFT) +#define OP_ALG_AS_FINALIZE (2 << OP_ALG_AS_SHIFT) +#define OP_ALG_AS_INITFINAL (3 << OP_ALG_AS_SHIFT) + +#define OP_ALG_ICV_SHIFT 1 +#define OP_ALG_ICV_MASK (1 << OP_ALG_ICV_SHIFT) +#define OP_ALG_ICV_OFF (0 << OP_ALG_ICV_SHIFT) +#define OP_ALG_ICV_ON (1 << OP_ALG_ICV_SHIFT) + +#define OP_ALG_DIR_SHIFT 0 +#define OP_ALG_DIR_MASK 1 +#define OP_ALG_DECRYPT 0 +#define OP_ALG_ENCRYPT 1 + +/* PKHA algorithm type set */ +#define OP_ALG_PK 0x00800000 +#define OP_ALG_PK_FUN_MASK 0x3f /* clrmem, modmath, or cpymem */ + +/* PKHA mode modular-arithmetic functions */ +#define OP_ALG_PKMODE_MOD_EXPO 0x006 + +/* + * SEQ_IN_PTR Command Constructs + */ + +/* Release Buffers */ +#define SQIN_RBS 0x04000000 + +/* Sequence pointer is really a descriptor */ +#define SQIN_INL 0x02000000 + +/* Sequence pointer is a scatter-gather table */ +#define SQIN_SGF 0x01000000 + +/* Appends to a previous pointer */ +#define SQIN_PRE 0x00800000 + +/* Use extended length following pointer */ +#define SQIN_EXT 0x00400000 + +/* Restore sequence with pointer/length */ +#define SQIN_RTO 0x00200000 + +/* Replace job descriptor */ +#define SQIN_RJD 0x00100000 + +#define SQIN_LEN_SHIFT 0 +#define SQIN_LEN_MASK (0xffff << SQIN_LEN_SHIFT) + +/* + * SEQ_OUT_PTR Command Constructs + */ + +/* Sequence pointer is a scatter-gather table */ +#define SQOUT_SGF 0x01000000 + +/* Appends to a previous pointer */ +#define SQOUT_PRE SQIN_PRE + +/* Restore sequence with pointer/length */ +#define SQOUT_RTO SQIN_RTO + +/* Use extended length following pointer */ +#define SQOUT_EXT 0x00400000 + +#define SQOUT_LEN_SHIFT 0 +#define SQOUT_LEN_MASK (0xffff << SQOUT_LEN_SHIFT) + +/* + * MOVE Command Constructs + */ + +#define MOVE_AUX_SHIFT 25 +#define MOVE_AUX_MASK (3 << MOVE_AUX_SHIFT) +#define MOVE_AUX_MS (2 << MOVE_AUX_SHIFT) +#define MOVE_AUX_LS (1 << MOVE_AUX_SHIFT) + +#define MOVE_WAITCOMP_SHIFT 24 +#define MOVE_WAITCOMP_MASK (1 << MOVE_WAITCOMP_SHIFT) +#define MOVE_WAITCOMP (1 << MOVE_WAITCOMP_SHIFT) + +#define MOVE_SRC_SHIFT 20 +#define MOVE_SRC_MASK (0x0f << MOVE_SRC_SHIFT) +#define MOVE_SRC_CLASS1CTX (0x00 << MOVE_SRC_SHIFT) +#define MOVE_SRC_CLASS2CTX (0x01 << MOVE_SRC_SHIFT) +#define MOVE_SRC_OUTFIFO (0x02 << MOVE_SRC_SHIFT) +#define MOVE_SRC_DESCBUF (0x03 << MOVE_SRC_SHIFT) +#define MOVE_SRC_MATH0 (0x04 << MOVE_SRC_SHIFT) +#define MOVE_SRC_MATH1 (0x05 << MOVE_SRC_SHIFT) +#define MOVE_SRC_MATH2 (0x06 << MOVE_SRC_SHIFT) +#define MOVE_SRC_MATH3 (0x07 << MOVE_SRC_SHIFT) +#define MOVE_SRC_INFIFO (0x08 << MOVE_SRC_SHIFT) +#define MOVE_SRC_INFIFO_CL (0x09 << MOVE_SRC_SHIFT) + +#define MOVE_DEST_SHIFT 16 +#define MOVE_DEST_MASK (0x0f << MOVE_DEST_SHIFT) +#define MOVE_DEST_CLASS1CTX (0x00 << MOVE_DEST_SHIFT) +#define MOVE_DEST_CLASS2CTX (0x01 << MOVE_DEST_SHIFT) +#define MOVE_DEST_OUTFIFO (0x02 << MOVE_DEST_SHIFT) +#define MOVE_DEST_DESCBUF (0x03 << MOVE_DEST_SHIFT) +#define MOVE_DEST_MATH0 (0x04 << MOVE_DEST_SHIFT) +#define MOVE_DEST_MATH1 (0x05 << MOVE_DEST_SHIFT) +#define MOVE_DEST_MATH2 (0x06 << MOVE_DEST_SHIFT) +#define MOVE_DEST_MATH3 (0x07 << MOVE_DEST_SHIFT) +#define MOVE_DEST_CLASS1INFIFO (0x08 << MOVE_DEST_SHIFT) +#define MOVE_DEST_CLASS2INFIFO (0x09 << MOVE_DEST_SHIFT) +#define MOVE_DEST_INFIFO_NOINFO (0x0a << MOVE_DEST_SHIFT) +#define MOVE_DEST_PK_A (0x0c << MOVE_DEST_SHIFT) +#define MOVE_DEST_CLASS1KEY (0x0d << MOVE_DEST_SHIFT) +#define MOVE_DEST_CLASS2KEY (0x0e << MOVE_DEST_SHIFT) + +#define MOVE_OFFSET_SHIFT 8 +#define MOVE_OFFSET_MASK (0xff << MOVE_OFFSET_SHIFT) + +#define MOVE_LEN_SHIFT 0 +#define MOVE_LEN_MASK (0xff << MOVE_LEN_SHIFT) + +#define MOVELEN_MRSEL_SHIFT 0 +#define MOVELEN_MRSEL_MASK (0x3 << MOVE_LEN_SHIFT) + +/* + * JUMP Command Constructs + */ + +#define JUMP_CLASS_SHIFT 25 +#define JUMP_CLASS_MASK (3 << JUMP_CLASS_SHIFT) +#define JUMP_CLASS_NONE 0 +#define JUMP_CLASS_CLASS1 (1 << JUMP_CLASS_SHIFT) +#define JUMP_CLASS_CLASS2 (2 << JUMP_CLASS_SHIFT) +#define JUMP_CLASS_BOTH (3 << JUMP_CLASS_SHIFT) + +#define JUMP_JSL_SHIFT 24 +#define JUMP_JSL_MASK (1 << JUMP_JSL_SHIFT) +#define JUMP_JSL (1 << JUMP_JSL_SHIFT) + +#define JUMP_TYPE_SHIFT 22 +#define JUMP_TYPE_MASK (0x03 << JUMP_TYPE_SHIFT) +#define JUMP_TYPE_LOCAL (0x00 << JUMP_TYPE_SHIFT) +#define JUMP_TYPE_NONLOCAL (0x01 << JUMP_TYPE_SHIFT) +#define JUMP_TYPE_HALT (0x02 << JUMP_TYPE_SHIFT) +#define JUMP_TYPE_HALT_USER (0x03 << JUMP_TYPE_SHIFT) + +#define JUMP_TEST_SHIFT 16 +#define JUMP_TEST_MASK (0x03 << JUMP_TEST_SHIFT) +#define JUMP_TEST_ALL (0x00 << JUMP_TEST_SHIFT) +#define JUMP_TEST_INVALL (0x01 << JUMP_TEST_SHIFT) +#define JUMP_TEST_ANY (0x02 << JUMP_TEST_SHIFT) +#define JUMP_TEST_INVANY (0x03 << JUMP_TEST_SHIFT) + +/* Condition codes. JSL bit is factored in */ +#define JUMP_COND_SHIFT 8 +#define JUMP_COND_MASK (0x100ff << JUMP_COND_SHIFT) +#define JUMP_COND_PK_0 (0x80 << JUMP_COND_SHIFT) +#define JUMP_COND_PK_GCD_1 (0x40 << JUMP_COND_SHIFT) +#define JUMP_COND_PK_PRIME (0x20 << JUMP_COND_SHIFT) +#define JUMP_COND_MATH_N (0x08 << JUMP_COND_SHIFT) +#define JUMP_COND_MATH_Z (0x04 << JUMP_COND_SHIFT) +#define JUMP_COND_MATH_C (0x02 << JUMP_COND_SHIFT) +#define JUMP_COND_MATH_NV (0x01 << JUMP_COND_SHIFT) + +#define JUMP_COND_JRP ((0x80 << JUMP_COND_SHIFT) | JUMP_JSL) +#define JUMP_COND_SHRD ((0x40 << JUMP_COND_SHIFT) | JUMP_JSL) +#define JUMP_COND_SELF ((0x20 << JUMP_COND_SHIFT) | JUMP_JSL) +#define JUMP_COND_CALM ((0x10 << JUMP_COND_SHIFT) | JUMP_JSL) +#define JUMP_COND_NIP ((0x08 << JUMP_COND_SHIFT) | JUMP_JSL) +#define JUMP_COND_NIFP ((0x04 << JUMP_COND_SHIFT) | JUMP_JSL) +#define JUMP_COND_NOP ((0x02 << JUMP_COND_SHIFT) | JUMP_JSL) +#define JUMP_COND_NCP ((0x01 << JUMP_COND_SHIFT) | JUMP_JSL) + +#define JUMP_OFFSET_SHIFT 0 +#define JUMP_OFFSET_MASK (0xff << JUMP_OFFSET_SHIFT) + +#define OP_ALG_RNG4_SHIFT 4 +#define OP_ALG_RNG4_MAS (0x1f3 << OP_ALG_RNG4_SHIFT) +#define OP_ALG_RNG4_SK (0x100 << OP_ALG_RNG4_SHIFT) + +#endif /* DESC_H */ diff --git a/drivers/crypto/fsl/desc_constr.h b/drivers/crypto/fsl/desc_constr.h new file mode 100644 index 0000000..f9cae91 --- /dev/null +++ b/drivers/crypto/fsl/desc_constr.h @@ -0,0 +1,280 @@ +/* + * caam descriptor construction helper functions + * + * Copyright 2008-2014 Freescale Semiconductor, Inc. + * + * SPDX-License-Identifier: GPL-2.0+ + * + * Based on desc_constr.h file in linux drivers/crypto/caam + */ + +#include <linux/compat.h> +#include "desc.h" + +#define IMMEDIATE (1 << 23) +#define CAAM_CMD_SZ sizeof(u32) +#define CAAM_PTR_SZ sizeof(dma_addr_t) +#define CAAM_DESC_BYTES_MAX (CAAM_CMD_SZ * MAX_CAAM_DESCSIZE) +#define DESC_JOB_IO_LEN (CAAM_CMD_SZ * 5 + CAAM_PTR_SZ * 3) + +#ifdef DEBUG +#define PRINT_POS do { printf("%02d: %s\n", desc_len(desc),\ + &__func__[sizeof("append")]); \ + } while (0) +#else +#define PRINT_POS +#endif + +#define SET_OK_NO_PROP_ERRORS (IMMEDIATE | LDST_CLASS_DECO | \ + LDST_SRCDST_WORD_DECOCTRL | \ + (LDOFF_CHG_SHARE_OK_NO_PROP << \ + LDST_OFFSET_SHIFT)) +#define DISABLE_AUTO_INFO_FIFO (IMMEDIATE | LDST_CLASS_DECO | \ + LDST_SRCDST_WORD_DECOCTRL | \ + (LDOFF_DISABLE_AUTO_NFIFO << LDST_OFFSET_SHIFT)) +#define ENABLE_AUTO_INFO_FIFO (IMMEDIATE | LDST_CLASS_DECO | \ + LDST_SRCDST_WORD_DECOCTRL | \ + (LDOFF_ENABLE_AUTO_NFIFO << LDST_OFFSET_SHIFT)) + +static inline int desc_len(u32 *desc) +{ + return *desc & HDR_DESCLEN_MASK; +} + +static inline int desc_bytes(void *desc) +{ + return desc_len(desc) * CAAM_CMD_SZ; +} + +static inline u32 *desc_end(u32 *desc) +{ + return desc + desc_len(desc); +} + +static inline void init_desc(u32 *desc, u32 options) +{ + *desc = (options | HDR_ONE) + 1; +} + +static inline void init_job_desc(u32 *desc, u32 options) +{ + init_desc(desc, CMD_DESC_HDR | options); +} + +static inline void append_ptr(u32 *desc, dma_addr_t ptr) +{ + dma_addr_t *offset = (dma_addr_t *)desc_end(desc); + + *offset = ptr; + + (*desc) += CAAM_PTR_SZ / CAAM_CMD_SZ; +} + +static inline void append_data(u32 *desc, void *data, int len) +{ + u32 *offset = desc_end(desc); + + if (len) /* avoid sparse warning: memcpy with byte count of 0 */ + memcpy(offset, data, len); + + (*desc) += (len + CAAM_CMD_SZ - 1) / CAAM_CMD_SZ; +} + +static inline void append_cmd(u32 *desc, u32 command) +{ + u32 *cmd = desc_end(desc); + + *cmd = command; + + (*desc)++; +} + +#define append_u32 append_cmd + +static inline void append_u64(u32 *desc, u64 data) +{ + u32 *offset = desc_end(desc); + + *offset = upper_32_bits(data); + *(++offset) = lower_32_bits(data); + + (*desc) += 2; +} + +/* Write command without affecting header, and return pointer to next word */ +static inline u32 *write_cmd(u32 *desc, u32 command) +{ + *desc = command; + + return desc + 1; +} + +static inline void append_cmd_ptr(u32 *desc, dma_addr_t ptr, int len, + u32 command) +{ + append_cmd(desc, command | len); + append_ptr(desc, ptr); +} + +/* Write length after pointer, rather than inside command */ +static inline void append_cmd_ptr_extlen(u32 *desc, dma_addr_t ptr, + unsigned int len, u32 command) +{ + append_cmd(desc, command); + if (!(command & (SQIN_RTO | SQIN_PRE))) + append_ptr(desc, ptr); + append_cmd(desc, len); +} + +static inline void append_cmd_data(u32 *desc, void *data, int len, + u32 command) +{ + append_cmd(desc, command | IMMEDIATE | len); + append_data(desc, data, len); +} + +#define APPEND_CMD_RET(cmd, op) \ +static inline u32 *append_##cmd(u32 *desc, u32 options) \ +{ \ + u32 *cmd = desc_end(desc); \ + PRINT_POS; \ + append_cmd(desc, CMD_##op | options); \ + return cmd; \ +} +APPEND_CMD_RET(jump, JUMP) +APPEND_CMD_RET(move, MOVE) + +static inline void set_jump_tgt_here(u32 *desc, u32 *jump_cmd) +{ + *jump_cmd = *jump_cmd | (desc_len(desc) - (jump_cmd - desc)); +} + +static inline void set_move_tgt_here(u32 *desc, u32 *move_cmd) +{ + *move_cmd &= ~MOVE_OFFSET_MASK; + *move_cmd = *move_cmd | ((desc_len(desc) << (MOVE_OFFSET_SHIFT + 2)) & + MOVE_OFFSET_MASK); +} + +#define APPEND_CMD(cmd, op) \ +static inline void append_##cmd(u32 *desc, u32 options) \ +{ \ + PRINT_POS; \ + append_cmd(desc, CMD_##op | options); \ +} +APPEND_CMD(operation, OPERATION) + +#define APPEND_CMD_LEN(cmd, op) \ +static inline void append_##cmd(u32 *desc, unsigned int len, u32 options) \ +{ \ + PRINT_POS; \ + append_cmd(desc, CMD_##op | len | options); \ +} +APPEND_CMD_LEN(seq_store, SEQ_STORE) +APPEND_CMD_LEN(seq_fifo_load, SEQ_FIFO_LOAD) +APPEND_CMD_LEN(seq_fifo_store, SEQ_FIFO_STORE) + +#define APPEND_CMD_PTR(cmd, op) \ +static inline void append_##cmd(u32 *desc, dma_addr_t ptr, unsigned int len, \ + u32 options) \ +{ \ + PRINT_POS; \ + append_cmd_ptr(desc, ptr, len, CMD_##op | options); \ +} +APPEND_CMD_PTR(key, KEY) +APPEND_CMD_PTR(load, LOAD) +APPEND_CMD_PTR(fifo_load, FIFO_LOAD) +APPEND_CMD_PTR(fifo_store, FIFO_STORE) + +static inline void append_store(u32 *desc, dma_addr_t ptr, unsigned int len, + u32 options) +{ + u32 cmd_src; + + cmd_src = options & LDST_SRCDST_MASK; + + append_cmd(desc, CMD_STORE | options | len); + + /* The following options do not require pointer */ + if (!(cmd_src == LDST_SRCDST_WORD_DESCBUF_SHARED || + cmd_src == LDST_SRCDST_WORD_DESCBUF_JOB || + cmd_src == LDST_SRCDST_WORD_DESCBUF_JOB_WE || + cmd_src == LDST_SRCDST_WORD_DESCBUF_SHARED_WE)) + append_ptr(desc, ptr); +} + +#define APPEND_SEQ_PTR_INTLEN(cmd, op) \ +static inline void append_seq_##cmd##_ptr_intlen(u32 *desc, dma_addr_t ptr, \ + unsigned int len, \ + u32 options) \ +{ \ + PRINT_POS; \ + if (options & (SQIN_RTO | SQIN_PRE)) \ + append_cmd(desc, CMD_SEQ_##op##_PTR | len | options); \ + else \ + append_cmd_ptr(desc, ptr, len, CMD_SEQ_##op##_PTR | options); \ +} +APPEND_SEQ_PTR_INTLEN(in, IN) +APPEND_SEQ_PTR_INTLEN(out, OUT) + +#define APPEND_CMD_PTR_TO_IMM(cmd, op) \ +static inline void append_##cmd##_as_imm(u32 *desc, void *data, \ + unsigned int len, u32 options) \ +{ \ + PRINT_POS; \ + append_cmd_data(desc, data, len, CMD_##op | options); \ +} +APPEND_CMD_PTR_TO_IMM(load, LOAD); +APPEND_CMD_PTR_TO_IMM(fifo_load, FIFO_LOAD); + +#define APPEND_CMD_PTR_EXTLEN(cmd, op) \ +static inline void append_##cmd##_extlen(u32 *desc, dma_addr_t ptr, \ + unsigned int len, u32 options) \ +{ \ + PRINT_POS; \ + append_cmd_ptr_extlen(desc, ptr, len, CMD_##op | SQIN_EXT | options); \ +} +APPEND_CMD_PTR_EXTLEN(seq_in_ptr, SEQ_IN_PTR) +APPEND_CMD_PTR_EXTLEN(seq_out_ptr, SEQ_OUT_PTR) + +/* + * Determine whether to store length internally or externally depending on + * the size of its type + */ +#define APPEND_CMD_PTR_LEN(cmd, op, type) \ +static inline void append_##cmd(u32 *desc, dma_addr_t ptr, \ + type len, u32 options) \ +{ \ + PRINT_POS; \ + if (sizeof(type) > sizeof(u16)) \ + append_##cmd##_extlen(desc, ptr, len, options); \ + else \ + append_##cmd##_intlen(desc, ptr, len, options); \ +} +APPEND_CMD_PTR_LEN(seq_in_ptr, SEQ_IN_PTR, u32) +APPEND_CMD_PTR_LEN(seq_out_ptr, SEQ_OUT_PTR, u32) + +/* + * 2nd variant for commands whose specified immediate length differs + * from length of immediate data provided, e.g., split keys + */ +#define APPEND_CMD_PTR_TO_IMM2(cmd, op) \ +static inline void append_##cmd##_as_imm(u32 *desc, void *data, \ + unsigned int data_len, \ + unsigned int len, u32 options) \ +{ \ + PRINT_POS; \ + append_cmd(desc, CMD_##op | IMMEDIATE | len | options); \ + append_data(desc, data, data_len); \ +} +APPEND_CMD_PTR_TO_IMM2(key, KEY); + +#define APPEND_CMD_RAW_IMM(cmd, op, type) \ +static inline void append_##cmd##_imm_##type(u32 *desc, type immediate, \ + u32 options) \ +{ \ + PRINT_POS; \ + append_cmd(desc, CMD_##op | IMMEDIATE | options | sizeof(type)); \ + append_cmd(desc, immediate); \ +} +APPEND_CMD_RAW_IMM(load, LOAD, u32); diff --git a/drivers/crypto/fsl/error.c b/drivers/crypto/fsl/error.c new file mode 100644 index 0000000..28cdcdd --- /dev/null +++ b/drivers/crypto/fsl/error.c @@ -0,0 +1,258 @@ +/* + * CAAM Error Reporting + * + * Copyright 2009-2014 Freescale Semiconductor, Inc. + * + * SPDX-License-Identifier: GPL-2.0+ + * + * Derived from error.c file in linux drivers/crypto/caam + */ + +#include <common.h> +#include <malloc.h> +#include "desc.h" +#include "jr.h" + +#define CAAM_ERROR_STR_MAX 302 + +#define JRSTA_SSRC_SHIFT 28 +#define JRSTA_CCBERR_CHAID_MASK 0x00f0 +#define JRSTA_CCBERR_CHAID_SHIFT 4 +#define JRSTA_CCBERR_ERRID_MASK 0x000 +#define JRSTA_CCBERR_CHAID_RNG (0x05 << JRSTA_CCBERR_CHAID_SHIFT) + +#define JRSTA_DECOERR_JUMP 0x08000000 +#define JRSTA_DECOERR_INDEX_SHIFT 8 +#define JRSTA_DECOERR_INDEX_MASK 0xff00 +#define JRSTA_DECOERR_ERROR_MASK 0x00ff + + +static const struct { + u8 value; + const char *error_text; +} desc_error_list[] = { + { 0x00, "No error." }, + { 0x01, "SGT Length Error. The descriptor is trying to read" \ + " more data than is contained in the SGT table." }, + { 0x02, "SGT Null Entry Error." }, + { 0x03, "Job Ring Control Error. Bad value in Job Ring Control reg." }, + { 0x04, "Invalid Descriptor Command." }, + { 0x05, "Reserved." }, + { 0x06, "Invalid KEY Command" }, + { 0x07, "Invalid LOAD Command" }, + { 0x08, "Invalid STORE Command" }, + { 0x09, "Invalid OPERATION Command" }, + { 0x0A, "Invalid FIFO LOAD Command" }, + { 0x0B, "Invalid FIFO STORE Command" }, + { 0x0C, "Invalid MOVE/MOVE_LEN Command" }, + { 0x0D, "Invalid JUMP Command" }, + { 0x0E, "Invalid MATH Command" }, + { 0x0F, "Invalid SIGNATURE Command" }, + { 0x10, "Invalid Sequence Command" }, + { 0x11, "Skip data type invalid. The type must be 0xE or 0xF."}, + { 0x12, "Shared Descriptor Header Error" }, + { 0x13, "Header Error. Invalid length or parity, or other problems." }, + { 0x14, "Burster Error. Burster has gotten to an illegal state" }, + { 0x15, "Context Register Length Error" }, + { 0x16, "DMA Error" }, + { 0x17, "Reserved." }, + { 0x1A, "Job failed due to JR reset" }, + { 0x1B, "Job failed due to Fail Mode" }, + { 0x1C, "DECO Watchdog timer timeout error" }, + { 0x1D, "DECO tried to copy a key from another DECO but" \ + " the other DECO's Key Registers were locked" }, + { 0x1E, "DECO attempted to copy data from a DECO" \ + "that had an unmasked Descriptor error" }, + { 0x1F, "LIODN error" }, + { 0x20, "DECO has completed a reset initiated via the DRR register" }, + { 0x21, "Nonce error" }, + { 0x22, "Meta data is too large (> 511 bytes) for TLS decap" }, + { 0x23, "Read Input Frame error" }, + { 0x24, "JDKEK, TDKEK or TDSK not loaded error" }, + { 0x80, "DNR (do not run) error" }, + { 0x81, "undefined protocol command" }, + { 0x82, "invalid setting in PDB" }, + { 0x83, "Anti-replay LATE error" }, + { 0x84, "Anti-replay REPLAY error" }, + { 0x85, "Sequence number overflow" }, + { 0x86, "Sigver invalid signature" }, + { 0x87, "DSA Sign Illegal test descriptor" }, + { 0x88, "Protocol Format Error" }, + { 0x89, "Protocol Size Error" }, + { 0xC1, "Blob Command error: Undefined mode" }, + { 0xC2, "Blob Command error: Secure Memory Blob mode error" }, + { 0xC4, "Blob Command error: Black Blob key or input size error" }, + { 0xC5, "Blob Command error: Invalid key destination" }, + { 0xC8, "Blob Command error: Trusted/Secure mode error" }, + { 0xF0, "IPsec TTL or hop limit field is 0, or was decremented to 0" }, + { 0xF1, "3GPP HFN matches or exceeds the Threshold" }, +}; + +static const char * const cha_id_list[] = { + "", + "AES", + "DES", + "ARC4", + "MDHA", + "RNG", + "SNOW f8", + "Kasumi f8/9", + "PKHA", + "CRCA", + "SNOW f9", + "ZUCE", + "ZUCA", +}; + +static const char * const err_id_list[] = { + "No error.", + "Mode error.", + "Data size error.", + "Key size error.", + "PKHA A memory size error.", + "PKHA B memory size error.", + "Data arrived out of sequence error.", + "PKHA divide-by-zero error.", + "PKHA modulus even error.", + "DES key parity error.", + "ICV check failed.", + "Hardware error.", + "Unsupported CCM AAD size.", + "Class 1 CHA is not reset", + "Invalid CHA combination was selected", + "Invalid CHA selected.", +}; + +static const char * const rng_err_id_list[] = { + "", + "", + "", + "Instantiate", + "Not instantiated", + "Test instantiate", + "Prediction resistance", + "Prediction resistance and test request", + "Uninstantiate", + "Secure key generation", +}; + +static void report_ccb_status(const u32 status, + const char *error) +{ + u8 cha_id = (status & JRSTA_CCBERR_CHAID_MASK) >> + JRSTA_CCBERR_CHAID_SHIFT; + u8 err_id = status & JRSTA_CCBERR_ERRID_MASK; + u8 idx = (status & JRSTA_DECOERR_INDEX_MASK) >> + JRSTA_DECOERR_INDEX_SHIFT; + char *idx_str; + const char *cha_str = "unidentified cha_id value 0x"; + char cha_err_code[3] = { 0 }; + const char *err_str = "unidentified err_id value 0x"; + char err_err_code[3] = { 0 }; + + if (status & JRSTA_DECOERR_JUMP) + idx_str = "jump tgt desc idx"; + else + idx_str = "desc idx"; + + if (cha_id < ARRAY_SIZE(cha_id_list)) + cha_str = cha_id_list[cha_id]; + else + snprintf(cha_err_code, sizeof(cha_err_code), "%02x", cha_id); + + if ((cha_id << JRSTA_CCBERR_CHAID_SHIFT) == JRSTA_CCBERR_CHAID_RNG && + err_id < ARRAY_SIZE(rng_err_id_list) && + strlen(rng_err_id_list[err_id])) { + /* RNG-only error */ + err_str = rng_err_id_list[err_id]; + } else if (err_id < ARRAY_SIZE(err_id_list)) { + err_str = err_id_list[err_id]; + } else { + snprintf(err_err_code, sizeof(err_err_code), "%02x", err_id); + } + + debug("%08x: %s: %s %d: %s%s: %s%s\n", + status, error, idx_str, idx, + cha_str, cha_err_code, + err_str, err_err_code); +} + +static void report_jump_status(const u32 status, + const char *error) +{ + debug("%08x: %s: %s() not implemented\n", + status, error, __func__); +} + +static void report_deco_status(const u32 status, + const char *error) +{ + u8 err_id = status & JRSTA_DECOERR_ERROR_MASK; + u8 idx = (status & JRSTA_DECOERR_INDEX_MASK) >> + JRSTA_DECOERR_INDEX_SHIFT; + char *idx_str; + const char *err_str = "unidentified error value 0x"; + char err_err_code[3] = { 0 }; + int i; + + if (status & JRSTA_DECOERR_JUMP) + idx_str = "jump tgt desc idx"; + else + idx_str = "desc idx"; + + for (i = 0; i < ARRAY_SIZE(desc_error_list); i++) + if (desc_error_list[i].value == err_id) + break; + + if (i != ARRAY_SIZE(desc_error_list) && desc_error_list[i].error_text) + err_str = desc_error_list[i].error_text; + else + snprintf(err_err_code, sizeof(err_err_code), "%02x", err_id); + + debug("%08x: %s: %s %d: %s%s\n", + status, error, idx_str, idx, err_str, err_err_code); +} + +static void report_jr_status(const u32 status, + const char *error) +{ + debug("%08x: %s: %s() not implemented\n", + status, error, __func__); +} + +static void report_cond_code_status(const u32 status, + const char *error) +{ + debug("%08x: %s: %s() not implemented\n", + status, error, __func__); +} + +void caam_jr_strstatus(u32 status) +{ + static const struct stat_src { + void (*report_ssed)(const u32 status, + const char *error); + const char *error; + } status_src[] = { + { NULL, "No error" }, + { NULL, NULL }, + { report_ccb_status, "CCB" }, + { report_jump_status, "Jump" }, + { report_deco_status, "DECO" }, + { NULL, NULL }, + { report_jr_status, "Job Ring" }, + { report_cond_code_status, "Condition Code" }, + }; + u32 ssrc = status >> JRSTA_SSRC_SHIFT; + const char *error = status_src[ssrc].error; + + /* + * If there is no further error handling function, just + * print the error code, error string and exit. Otherwise + * call the handler function. + */ + if (!status_src[ssrc].report_ssed) + debug("%08x: %s:\n", status, status_src[ssrc].error); + else + status_src[ssrc].report_ssed(status, error); +} diff --git a/drivers/crypto/fsl/fsl_blob.c b/drivers/crypto/fsl/fsl_blob.c new file mode 100644 index 0000000..bc01075 --- /dev/null +++ b/drivers/crypto/fsl/fsl_blob.c @@ -0,0 +1,61 @@ +/* + * Copyright 2014 Freescale Semiconductor, Inc. + * + * SPDX-License-Identifier: GPL-2.0+ + * + */ + +#include <common.h> +#include <malloc.h> +#include "jobdesc.h" +#include "desc.h" +#include "jr.h" + +int blob_decrypt(u8 *key_mod, u8 *src, u8 *dst, u8 len) +{ + int ret, i = 0; + u32 *desc; + + printf("\nDecapsulating data to form blob\n"); + desc = malloc(sizeof(int) * MAX_CAAM_DESCSIZE); + if (!desc) { + debug("Not enough memory for descriptor allocation\n"); + return -1; + } + + inline_cnstr_jobdesc_blob_decap(desc, key_mod, src, dst, len); + + for (i = 0; i < 14; i++) + printf("%x\n", *(desc + i)); + ret = run_descriptor_jr(desc); + + if (ret) + printf("Error in Decapsulation %d\n", ret); + + free(desc); + return ret; +} + +int blob_encrypt(u8 *key_mod, u8 *src, u8 *dst, u8 len) +{ + int ret, i = 0; + u32 *desc; + + printf("\nEncapsulating data to form blob\n"); + desc = malloc(sizeof(int) * MAX_CAAM_DESCSIZE); + if (!desc) { + debug("Not enough memory for descriptor allocation\n"); + return -1; + } + + inline_cnstr_jobdesc_blob_encap(desc, key_mod, src, dst, len); + for (i = 0; i < 14; i++) + printf("%x\n", *(desc + i)); + ret = run_descriptor_jr(desc); + + if (ret) + printf("Error in Encapsulation %d\n", ret); + + free(desc); + return ret; +} diff --git a/drivers/crypto/fsl/fsl_hash.c b/drivers/crypto/fsl/fsl_hash.c new file mode 100644 index 0000000..d77f257 --- /dev/null +++ b/drivers/crypto/fsl/fsl_hash.c @@ -0,0 +1,77 @@ +/* + * Copyright 2014 Freescale Semiconductor, Inc. + * + * SPDX-License-Identifier: GPL-2.0+ + * + */ + +#include <common.h> +#include <malloc.h> +#include "jobdesc.h" +#include "desc.h" +#include "jr.h" + +#define CRYPTO_MAX_ALG_NAME 80 +#define SHA1_DIGEST_SIZE 20 +#define SHA256_DIGEST_SIZE 32 + +struct caam_hash_template { + char name[CRYPTO_MAX_ALG_NAME]; + unsigned int digestsize; + u32 alg_type; +}; + +enum caam_hash_algos { + SHA1 = 0, + SHA256 +}; + +static struct caam_hash_template driver_hash[] = { + { + .name = "sha1", + .digestsize = SHA1_DIGEST_SIZE, + .alg_type = OP_ALG_ALGSEL_SHA1, + }, + { + .name = "sha256", + .digestsize = SHA256_DIGEST_SIZE, + .alg_type = OP_ALG_ALGSEL_SHA256, + }, +}; + +int caam_hash(const unsigned char *pbuf, unsigned int buf_len, + unsigned char *pout, enum caam_hash_algos algo) +{ + int ret = 0; + uint32_t *desc; + + desc = malloc(sizeof(int) * MAX_CAAM_DESCSIZE); + if (!desc) { + debug("Not enough memory for descriptor allocation\n"); + return -1; + } + + inline_cnstr_jobdesc_hash(desc, pbuf, buf_len, pout, + driver_hash[algo].alg_type, + driver_hash[algo].digestsize, + 0); + + ret = run_descriptor_jr(desc); + + free(desc); + return ret; +} + +void hw_sha256(const unsigned char *pbuf, unsigned int buf_len, + unsigned char *pout, unsigned int chunk_size) +{ + if (caam_hash(pbuf, buf_len, pout, SHA256)) + printf("CAAM was not setup properly or it is faulty\n"); +} + +void hw_sha1(const unsigned char *pbuf, unsigned int buf_len, + unsigned char *pout, unsigned int chunk_size) +{ + if (caam_hash(pbuf, buf_len, pout, SHA1)) + printf("CAAM was not setup properly or it is faulty\n"); +} diff --git a/drivers/crypto/fsl/jobdesc.c b/drivers/crypto/fsl/jobdesc.c new file mode 100644 index 0000000..1386bae --- /dev/null +++ b/drivers/crypto/fsl/jobdesc.c @@ -0,0 +1,125 @@ +/* + * SEC Descriptor Construction Library + * Basic job descriptor construction + * + * Copyright 2014 Freescale Semiconductor, Inc. + * + * SPDX-License-Identifier: GPL-2.0+ + * + */ + +#include <common.h> +#include "desc_constr.h" +#include "jobdesc.h" + +#define KEY_BLOB_SIZE 32 +#define MAC_SIZE 16 + +void inline_cnstr_jobdesc_hash(uint32_t *desc, + const uint8_t *msg, uint32_t msgsz, uint8_t *digest, + u32 alg_type, uint32_t alg_size, int sg_tbl) +{ + /* SHA 256 , output is of length 32 words */ + uint32_t storelen = alg_size; + u32 options; + dma_addr_t dma_addr_in, dma_addr_out; + + dma_addr_in = virt_to_phys((void *)msg); + dma_addr_out = virt_to_phys((void *)digest); + + init_job_desc(desc, 0); + append_operation(desc, OP_TYPE_CLASS2_ALG | + OP_ALG_AAI_HASH | OP_ALG_AS_INITFINAL | + OP_ALG_ENCRYPT | OP_ALG_ICV_OFF | alg_type); + + options = LDST_CLASS_2_CCB | FIFOLD_TYPE_MSG | FIFOLD_TYPE_LAST2; + if (sg_tbl) + options |= FIFOLDST_SGF; + if (msgsz > 0xffff) { + options |= FIFOLDST_EXT; + append_fifo_load(desc, dma_addr_in, 0, options); + append_cmd(desc, msgsz); + } else { + append_fifo_load(desc, dma_addr_in, msgsz, options); + } + + append_store(desc, dma_addr_out, storelen, + LDST_CLASS_2_CCB | LDST_SRCDST_BYTE_CONTEXT); +} + +void inline_cnstr_jobdesc_blob_encap(uint32_t *desc, uint8_t *key_idnfr, + uint8_t *plain_txt, uint8_t *enc_blob, + uint32_t in_sz) +{ + dma_addr_t dma_addr_key_idnfr, dma_addr_in, dma_addr_out; + uint32_t key_sz = KEY_IDNFR_SZ_BYTES; + /* output blob will have 32 bytes key blob in beginning and + * 16 byte HMAC identifier at end of data blob */ + uint32_t out_sz = in_sz + KEY_BLOB_SIZE + MAC_SIZE; + + dma_addr_key_idnfr = virt_to_phys((void *)key_idnfr); + dma_addr_in = virt_to_phys((void *)plain_txt); + dma_addr_out = virt_to_phys((void *)enc_blob); + + init_job_desc(desc, 0); + + append_key(desc, dma_addr_key_idnfr, key_sz, CLASS_2); + + append_seq_in_ptr(desc, dma_addr_in, in_sz, 0); + + append_seq_out_ptr(desc, dma_addr_out, out_sz, 0); + + append_operation(desc, OP_TYPE_ENCAP_PROTOCOL | OP_PCLID_BLOB); +} + +void inline_cnstr_jobdesc_blob_decap(uint32_t *desc, uint8_t *key_idnfr, + uint8_t *enc_blob, uint8_t *plain_txt, + uint32_t out_sz) +{ + dma_addr_t dma_addr_key_idnfr, dma_addr_in, dma_addr_out; + uint32_t key_sz = KEY_IDNFR_SZ_BYTES; + uint32_t in_sz = out_sz + KEY_BLOB_SIZE + MAC_SIZE; + + dma_addr_key_idnfr = virt_to_phys((void *)key_idnfr); + dma_addr_in = virt_to_phys((void *)enc_blob); + dma_addr_out = virt_to_phys((void *)plain_txt); + + init_job_desc(desc, 0); + + append_key(desc, dma_addr_key_idnfr, key_sz, CLASS_2); + + append_seq_in_ptr(desc, dma_addr_in, in_sz, 0); + + append_seq_out_ptr(desc, dma_addr_out, out_sz, 0); + + append_operation(desc, OP_TYPE_DECAP_PROTOCOL | OP_PCLID_BLOB); +} + +/* + * Descriptor to instantiate RNG State Handle 0 in normal mode and + * load the JDKEK, TDKEK and TDSK registers + */ +void inline_cnstr_jobdesc_rng_instantiation(uint32_t *desc) +{ + u32 *jump_cmd; + + init_job_desc(desc, 0); + + /* INIT RNG in non-test mode */ + append_operation(desc, OP_TYPE_CLASS1_ALG | OP_ALG_ALGSEL_RNG | + OP_ALG_AS_INIT); + + /* wait for done */ + jump_cmd = append_jump(desc, JUMP_CLASS_CLASS1); + set_jump_tgt_here(desc, jump_cmd); + + /* + * load 1 to clear written reg: + * resets the done interrrupt and returns the RNG to idle. + */ + append_load_imm_u32(desc, 1, LDST_SRCDST_WORD_CLRW); + + /* generate secure keys (non-test) */ + append_operation(desc, OP_TYPE_CLASS1_ALG | OP_ALG_ALGSEL_RNG | + OP_ALG_RNG4_SK); +} diff --git a/drivers/crypto/fsl/jobdesc.h b/drivers/crypto/fsl/jobdesc.h new file mode 100644 index 0000000..3cf7226 --- /dev/null +++ b/drivers/crypto/fsl/jobdesc.h @@ -0,0 +1,29 @@ +/* + * Copyright 2014 Freescale Semiconductor, Inc. + * + * SPDX-License-Identifier: GPL-2.0+ + * + */ + +#ifndef __JOBDESC_H +#define __JOBDESC_H + +#include <common.h> +#include <asm/io.h> + +#define KEY_IDNFR_SZ_BYTES 16 + +void inline_cnstr_jobdesc_hash(uint32_t *desc, + const uint8_t *msg, uint32_t msgsz, uint8_t *digest, + u32 alg_type, uint32_t alg_size, int sg_tbl); + +void inline_cnstr_jobdesc_blob_encap(uint32_t *desc, uint8_t *key_idnfr, + uint8_t *plain_txt, uint8_t *enc_blob, + uint32_t in_sz); + +void inline_cnstr_jobdesc_blob_decap(uint32_t *desc, uint8_t *key_idnfr, + uint8_t *enc_blob, uint8_t *plain_txt, + uint32_t out_sz); + +void inline_cnstr_jobdesc_rng_instantiation(uint32_t *desc); +#endif diff --git a/drivers/crypto/fsl/jr.c b/drivers/crypto/fsl/jr.c new file mode 100644 index 0000000..29681e1 --- /dev/null +++ b/drivers/crypto/fsl/jr.c @@ -0,0 +1,462 @@ +/* + * Copyright 2008-2014 Freescale Semiconductor, Inc. + * + * SPDX-License-Identifier: GPL-2.0+ + * + * Based on CAAM driver in drivers/crypto/caam in Linux + */ + +#include <common.h> +#include <malloc.h> +#include "fsl_sec.h" +#include "jr.h" +#include "jobdesc.h" + +#define CIRC_CNT(head, tail, size) (((head) - (tail)) & (size - 1)) +#define CIRC_SPACE(head, tail, size) CIRC_CNT((tail), (head) + 1, (size)) + +struct jobring jr; + +static inline void start_jr0(void) +{ + ccsr_sec_t *sec = (void *)CONFIG_SYS_FSL_SEC_ADDR; + u32 ctpr_ms = sec_in32(&sec->ctpr_ms); + u32 scfgr = sec_in32(&sec->scfgr); + + if (ctpr_ms & SEC_CTPR_MS_VIRT_EN_INCL) { + /* VIRT_EN_INCL = 1 & VIRT_EN_POR = 1 or + * VIRT_EN_INCL = 1 & VIRT_EN_POR = 0 & SEC_SCFGR_VIRT_EN = 1 + */ + if ((ctpr_ms & SEC_CTPR_MS_VIRT_EN_POR) || + (!(ctpr_ms & SEC_CTPR_MS_VIRT_EN_POR) && + (scfgr & SEC_SCFGR_VIRT_EN))) + sec_out32(&sec->jrstartr, CONFIG_JRSTARTR_JR0); + } else { + /* VIRT_EN_INCL = 0 && VIRT_EN_POR_VALUE = 1 */ + if (ctpr_ms & SEC_CTPR_MS_VIRT_EN_POR) + sec_out32(&sec->jrstartr, CONFIG_JRSTARTR_JR0); + } +} + +static inline void jr_reset_liodn(void) +{ + ccsr_sec_t *sec = (void *)CONFIG_SYS_FSL_SEC_ADDR; + sec_out32(&sec->jrliodnr[0].ls, 0); +} + +static inline void jr_disable_irq(void) +{ + struct jr_regs *regs = (struct jr_regs *)CONFIG_SYS_FSL_JR0_ADDR; + uint32_t jrcfg = sec_in32(®s->jrcfg1); + + jrcfg = jrcfg | JR_INTMASK; + + sec_out32(®s->jrcfg1, jrcfg); +} + +static void jr_initregs(void) +{ + struct jr_regs *regs = (struct jr_regs *)CONFIG_SYS_FSL_JR0_ADDR; + phys_addr_t ip_base = virt_to_phys((void *)jr.input_ring); + phys_addr_t op_base = virt_to_phys((void *)jr.output_ring); + +#ifdef CONFIG_PHYS_64BIT + sec_out32(®s->irba_h, ip_base >> 32); +#else + sec_out32(®s->irba_h, 0x0); +#endif + sec_out32(®s->irba_l, (uint32_t)ip_base); +#ifdef CONFIG_PHYS_64BIT + sec_out32(®s->orba_h, op_base >> 32); +#else + sec_out32(®s->orba_h, 0x0); +#endif + sec_out32(®s->orba_l, (uint32_t)op_base); + sec_out32(®s->ors, JR_SIZE); + sec_out32(®s->irs, JR_SIZE); + + if (!jr.irq) + jr_disable_irq(); +} + +static int jr_init(void) +{ + memset(&jr, 0, sizeof(struct jobring)); + + jr.jq_id = DEFAULT_JR_ID; + jr.irq = DEFAULT_IRQ; + +#ifdef CONFIG_FSL_CORENET + jr.liodn = DEFAULT_JR_LIODN; +#endif + jr.size = JR_SIZE; + jr.input_ring = (dma_addr_t *)malloc(JR_SIZE * sizeof(dma_addr_t)); + if (!jr.input_ring) + return -1; + jr.output_ring = + (struct op_ring *)malloc(JR_SIZE * sizeof(struct op_ring)); + if (!jr.output_ring) + return -1; + + memset(jr.input_ring, 0, JR_SIZE * sizeof(dma_addr_t)); + memset(jr.output_ring, 0, JR_SIZE * sizeof(struct op_ring)); + + start_jr0(); + + jr_initregs(); + + return 0; +} + +static int jr_sw_cleanup(void) +{ + jr.head = 0; + jr.tail = 0; + jr.read_idx = 0; + jr.write_idx = 0; + memset(jr.info, 0, sizeof(jr.info)); + memset(jr.input_ring, 0, jr.size * sizeof(dma_addr_t)); + memset(jr.output_ring, 0, jr.size * sizeof(struct op_ring)); + + return 0; +} + +static int jr_hw_reset(void) +{ + struct jr_regs *regs = (struct jr_regs *)CONFIG_SYS_FSL_JR0_ADDR; + uint32_t timeout = 100000; + uint32_t jrint, jrcr; + + sec_out32(®s->jrcr, JRCR_RESET); + do { + jrint = sec_in32(®s->jrint); + } while (((jrint & JRINT_ERR_HALT_MASK) == + JRINT_ERR_HALT_INPROGRESS) && --timeout); + + jrint = sec_in32(®s->jrint); + if (((jrint & JRINT_ERR_HALT_MASK) != + JRINT_ERR_HALT_INPROGRESS) && timeout == 0) + return -1; + + timeout = 100000; + sec_out32(®s->jrcr, JRCR_RESET); + do { + jrcr = sec_in32(®s->jrcr); + } while ((jrcr & JRCR_RESET) && --timeout); + + if (timeout == 0) + return -1; + + return 0; +} + +/* -1 --- error, can't enqueue -- no space available */ +static int jr_enqueue(uint32_t *desc_addr, + void (*callback)(uint32_t desc, uint32_t status, void *arg), + void *arg) +{ + struct jr_regs *regs = (struct jr_regs *)CONFIG_SYS_FSL_JR0_ADDR; + int head = jr.head; + dma_addr_t desc_phys_addr = virt_to_phys(desc_addr); + + if (sec_in32(®s->irsa) == 0 || + CIRC_SPACE(jr.head, jr.tail, jr.size) <= 0) + return -1; + + jr.input_ring[head] = desc_phys_addr; + jr.info[head].desc_phys_addr = desc_phys_addr; + jr.info[head].desc_addr = (uint32_t)desc_addr; + jr.info[head].callback = (void *)callback; + jr.info[head].arg = arg; + jr.info[head].op_done = 0; + + jr.head = (head + 1) & (jr.size - 1); + + sec_out32(®s->irja, 1); + + return 0; +} + +static int jr_dequeue(void) +{ + struct jr_regs *regs = (struct jr_regs *)CONFIG_SYS_FSL_JR0_ADDR; + int head = jr.head; + int tail = jr.tail; + int idx, i, found; + void (*callback)(uint32_t desc, uint32_t status, void *arg); + void *arg = NULL; + + while (sec_in32(®s->orsf) && CIRC_CNT(jr.head, jr.tail, jr.size)) { + found = 0; + + dma_addr_t op_desc = jr.output_ring[jr.tail].desc; + uint32_t status = jr.output_ring[jr.tail].status; + uint32_t desc_virt; + + for (i = 0; CIRC_CNT(head, tail + i, jr.size) >= 1; i++) { + idx = (tail + i) & (jr.size - 1); + if (op_desc == jr.info[idx].desc_phys_addr) { + desc_virt = jr.info[idx].desc_addr; + found = 1; + break; + } + } + + /* Error condition if match not found */ + if (!found) + return -1; + + jr.info[idx].op_done = 1; + callback = (void *)jr.info[idx].callback; + arg = jr.info[idx].arg; + + /* When the job on tail idx gets done, increment + * tail till the point where job completed out of oredr has + * been taken into account + */ + if (idx == tail) + do { + tail = (tail + 1) & (jr.size - 1); + } while (jr.info[tail].op_done); + + jr.tail = tail; + jr.read_idx = (jr.read_idx + 1) & (jr.size - 1); + + sec_out32(®s->orjr, 1); + jr.info[idx].op_done = 0; + + callback(desc_virt, status, arg); + } + + return 0; +} + +static void desc_done(uint32_t desc, uint32_t status, void *arg) +{ + struct result *x = arg; + x->status = status; + caam_jr_strstatus(status); + x->done = 1; +} + +int run_descriptor_jr(uint32_t *desc) +{ + unsigned long long timeval = get_ticks(); + unsigned long long timeout = usec2ticks(CONFIG_SEC_DEQ_TIMEOUT); + struct result op; + int ret = 0; + + memset(&op, sizeof(op), 0); + + ret = jr_enqueue(desc, desc_done, &op); + if (ret) { + debug("Error in SEC enq\n"); + ret = JQ_ENQ_ERR; + goto out; + } + + timeval = get_ticks(); + timeout = usec2ticks(CONFIG_SEC_DEQ_TIMEOUT); + while (op.done != 1) { + ret = jr_dequeue(); + if (ret) { + debug("Error in SEC deq\n"); + ret = JQ_DEQ_ERR; + goto out; + } + + if ((get_ticks() - timeval) > timeout) { + debug("SEC Dequeue timed out\n"); + ret = JQ_DEQ_TO_ERR; + goto out; + } + } + + if (!op.status) { + debug("Error %x\n", op.status); + ret = op.status; + } +out: + return ret; +} + +int jr_reset(void) +{ + if (jr_hw_reset() < 0) + return -1; + + /* Clean up the jobring structure maintained by software */ + jr_sw_cleanup(); + + return 0; +} + +int sec_reset(void) +{ + ccsr_sec_t *sec = (void *)CONFIG_SYS_FSL_SEC_ADDR; + uint32_t mcfgr = sec_in32(&sec->mcfgr); + uint32_t timeout = 100000; + + mcfgr |= MCFGR_SWRST; + sec_out32(&sec->mcfgr, mcfgr); + + mcfgr |= MCFGR_DMA_RST; + sec_out32(&sec->mcfgr, mcfgr); + do { + mcfgr = sec_in32(&sec->mcfgr); + } while ((mcfgr & MCFGR_DMA_RST) == MCFGR_DMA_RST && --timeout); + + if (timeout == 0) + return -1; + + timeout = 100000; + do { + mcfgr = sec_in32(&sec->mcfgr); + } while ((mcfgr & MCFGR_SWRST) == MCFGR_SWRST && --timeout); + + if (timeout == 0) + return -1; + + return 0; +} + +static int instantiate_rng(void) +{ + struct result op; + u32 *desc; + u32 rdsta_val; + int ret = 0; + ccsr_sec_t __iomem *sec = + (ccsr_sec_t __iomem *)CONFIG_SYS_FSL_SEC_ADDR; + struct rng4tst __iomem *rng = + (struct rng4tst __iomem *)&sec->rng; + + memset(&op, 0, sizeof(struct result)); + + desc = malloc(sizeof(int) * 6); + if (!desc) { + printf("cannot allocate RNG init descriptor memory\n"); + return -1; + } + + inline_cnstr_jobdesc_rng_instantiation(desc); + ret = run_descriptor_jr(desc); + + if (ret) + printf("RNG: Instantiation failed with error %x\n", ret); + + rdsta_val = sec_in32(&rng->rdsta); + if (op.status || !(rdsta_val & RNG_STATE0_HANDLE_INSTANTIATED)) + return -1; + + return ret; +} + +static u8 get_rng_vid(void) +{ + ccsr_sec_t *sec = (void *)CONFIG_SYS_FSL_SEC_ADDR; + u32 cha_vid = sec_in32(&sec->chavid_ls); + + return (cha_vid & SEC_CHAVID_RNG_LS_MASK) >> SEC_CHAVID_LS_RNG_SHIFT; +} + +/* + * By default, the TRNG runs for 200 clocks per sample; + * 1200 clocks per sample generates better entropy. + */ +static void kick_trng(int ent_delay) +{ + ccsr_sec_t __iomem *sec = + (ccsr_sec_t __iomem *)CONFIG_SYS_FSL_SEC_ADDR; + struct rng4tst __iomem *rng = + (struct rng4tst __iomem *)&sec->rng; + u32 val; + + /* put RNG4 into program mode */ + sec_setbits32(&rng->rtmctl, RTMCTL_PRGM); + /* rtsdctl bits 0-15 contain "Entropy Delay, which defines the + * length (in system clocks) of each Entropy sample taken + * */ + val = sec_in32(&rng->rtsdctl); + val = (val & ~RTSDCTL_ENT_DLY_MASK) | + (ent_delay << RTSDCTL_ENT_DLY_SHIFT); + sec_out32(&rng->rtsdctl, val); + /* min. freq. count, equal to 1/4 of the entropy sample length */ + sec_out32(&rng->rtfreqmin, ent_delay >> 2); + /* max. freq. count, equal to 8 times the entropy sample length */ + sec_out32(&rng->rtfreqmax, ent_delay << 3); + /* put RNG4 into run mode */ + sec_clrbits32(&rng->rtmctl, RTMCTL_PRGM); +} + +static int rng_init(void) +{ + int ret, ent_delay = RTSDCTL_ENT_DLY_MIN; + ccsr_sec_t __iomem *sec = + (ccsr_sec_t __iomem *)CONFIG_SYS_FSL_SEC_ADDR; + struct rng4tst __iomem *rng = + (struct rng4tst __iomem *)&sec->rng; + + u32 rdsta = sec_in32(&rng->rdsta); + + /* Check if RNG state 0 handler is already instantiated */ + if (rdsta & RNG_STATE0_HANDLE_INSTANTIATED) + return 0; + + do { + /* + * If either of the SH's were instantiated by somebody else + * then it is assumed that the entropy + * parameters are properly set and thus the function + * setting these (kick_trng(...)) is skipped. + * Also, if a handle was instantiated, do not change + * the TRNG parameters. + */ + kick_trng(ent_delay); + ent_delay += 400; + /* + * if instantiate_rng(...) fails, the loop will rerun + * and the kick_trng(...) function will modfiy the + * upper and lower limits of the entropy sampling + * interval, leading to a sucessful initialization of + * the RNG. + */ + ret = instantiate_rng(); + } while ((ret == -1) && (ent_delay < RTSDCTL_ENT_DLY_MAX)); + if (ret) { + printf("RNG: Failed to instantiate RNG\n"); + return ret; + } + + /* Enable RDB bit so that RNG works faster */ + sec_setbits32(&sec->scfgr, SEC_SCFGR_RDBENABLE); + + return ret; +} + +int sec_init(void) +{ + int ret = 0; + +#ifdef CONFIG_PHYS_64BIT + ccsr_sec_t *sec = (void *)CONFIG_SYS_FSL_SEC_ADDR; + uint32_t mcr = sec_in32(&sec->mcfgr); + + sec_out32(&sec->mcfgr, mcr | 1 << MCFGR_PS_SHIFT); +#endif + ret = jr_init(); + if (ret < 0) { + printf("SEC initialization failed\n"); + return -1; + } + + if (get_rng_vid() >= 4) { + if (rng_init() < 0) { + printf("RNG instantiation failed\n"); + return -1; + } + printf("SEC: RNG instantiated\n"); + } + + return ret; +} diff --git a/drivers/crypto/fsl/jr.h b/drivers/crypto/fsl/jr.h new file mode 100644 index 0000000..cce2c58 --- /dev/null +++ b/drivers/crypto/fsl/jr.h @@ -0,0 +1,97 @@ +/* + * Copyright 2008-2014 Freescale Semiconductor, Inc. + * + * SPDX-License-Identifier: GPL-2.0+ + * + */ + +#ifndef __JR_H +#define __JR_H + +#include <linux/compiler.h> + +#define JR_SIZE 4 +/* Timeout currently defined as 90 sec */ +#define CONFIG_SEC_DEQ_TIMEOUT 90000000U + +#define DEFAULT_JR_ID 0 +#define DEFAULT_JR_LIODN 0 +#define DEFAULT_IRQ 0 /* Interrupts not to be configured */ + +#define MCFGR_SWRST ((uint32_t)(1)<<31) /* Software Reset */ +#define MCFGR_DMA_RST ((uint32_t)(1)<<28) /* DMA Reset */ +#define MCFGR_PS_SHIFT 16 +#define JR_INTMASK 0x00000001 +#define JRCR_RESET 0x01 +#define JRINT_ERR_HALT_INPROGRESS 0x4 +#define JRINT_ERR_HALT_MASK 0xc +#define JRNSLIODN_SHIFT 16 +#define JRNSLIODN_MASK 0x0fff0000 +#define JRSLIODN_SHIFT 0 +#define JRSLIODN_MASK 0x00000fff + +#define JQ_DEQ_ERR -1 +#define JQ_DEQ_TO_ERR -2 +#define JQ_ENQ_ERR -3 + +struct op_ring { + dma_addr_t desc; + uint32_t status; +} __packed; + +struct jr_info { + void (*callback)(dma_addr_t desc, uint32_t status, void *arg); + dma_addr_t desc_phys_addr; + uint32_t desc_addr; + uint32_t desc_len; + uint32_t op_done; + void *arg; +}; + +struct jobring { + int jq_id; + int irq; + int liodn; + /* Head is the index where software would enq the descriptor in + * the i/p ring + */ + int head; + /* Tail index would be used by s/w ehile enqueuing to determine if + * there is any space left in the s/w maintained i/p rings + */ + /* Also in case of deq tail will be incremented only in case of + * in-order job completion + */ + int tail; + /* Read index of the output ring. It may not match with tail in case + * of out of order completetion + */ + int read_idx; + /* Write index to input ring. Would be always equal to head */ + int write_idx; + /* Size of the rings. */ + int size; + /* The ip and output rings have to be accessed by SEC. So the + * pointers will ahve to point to the housekeeping region provided + * by SEC + */ + /*Circular Ring of i/p descriptors */ + dma_addr_t *input_ring; + /* Circular Ring of o/p descriptors */ + /* Circula Ring containing info regarding descriptors in i/p + * and o/p ring + */ + /* This ring can be on the stack */ + struct jr_info info[JR_SIZE]; + struct op_ring *output_ring; +}; + +struct result { + int done; + uint32_t status; +}; + +void caam_jr_strstatus(u32 status); +int run_descriptor_jr(uint32_t *desc); + +#endif diff --git a/include/configs/B4860QDS.h b/include/configs/B4860QDS.h index 9063c57..dc1a9bc 100644 --- a/include/configs/B4860QDS.h +++ b/include/configs/B4860QDS.h @@ -82,6 +82,7 @@ #define CONFIG_SYS_FSL_CPC /* Corenet Platform Cache */ #define CONFIG_SYS_NUM_CPC CONFIG_NUM_DDR_CONTROLLERS #define CONFIG_FSL_IFC /* Enable IFC Support */ +#define CONFIG_FSL_CAAM /* Enable SEC/CAAM */ #define CONFIG_PCI /* Enable PCI/PCIE */ #define CONFIG_PCIE1 /* PCIE controler 1 */ #define CONFIG_FSL_PCI_INIT /* Use common FSL init code */ @@ -759,6 +760,12 @@ unsigned long get_board_ddr_clk(void); #define CONFIG_CMD_NET #endif +/* Hash command with SHA acceleration supported in hardware */ +#ifdef CONFIG_FSL_CAAM +#define CONFIG_CMD_HASH +#define CONFIG_SHA_HW_ACCEL +#endif + /* * USB */ @@ -913,4 +920,8 @@ unsigned long get_board_ddr_clk(void); #include <asm/fsl_secure_boot.h> +#ifdef CONFIG_SECURE_BOOT +#define CONFIG_CMD_BLOB +#endif + #endif /* __CONFIG_H */ diff --git a/include/configs/BSC9131RDB.h b/include/configs/BSC9131RDB.h index 56a3e94..bc5af52 100644 --- a/include/configs/BSC9131RDB.h +++ b/include/configs/BSC9131RDB.h @@ -55,6 +55,7 @@ #define CONFIG_BOOKE /* BOOKE */ #define CONFIG_E500 /* BOOKE e500 family */ #define CONFIG_FSL_IFC /* Enable IFC Support */ +#define CONFIG_FSL_CAAM /* Enable SEC/CAAM */ #define CONFIG_FSL_LAW /* Use common FSL init code */ #define CONFIG_TSEC_ENET @@ -382,6 +383,12 @@ extern unsigned long get_sdram_size(void); #define CONFIG_KGDB_BAUDRATE 230400 /* speed to run kgdb serial port */ #endif +/* Hash command with SHA acceleration supported in hardware */ +#ifdef CONFIG_FSL_CAAM +#define CONFIG_CMD_HASH +#define CONFIG_SHA_HW_ACCEL +#endif + #define CONFIG_USB_EHCI #ifdef CONFIG_USB_EHCI diff --git a/include/configs/BSC9132QDS.h b/include/configs/BSC9132QDS.h index aeded6d..989363c 100644 --- a/include/configs/BSC9132QDS.h +++ b/include/configs/BSC9132QDS.h @@ -78,6 +78,7 @@ #define CONFIG_BOOKE /* BOOKE */ #define CONFIG_E500 /* BOOKE e500 family */ #define CONFIG_FSL_IFC /* Enable IFC Support */ +#define CONFIG_FSL_CAAM /* Enable SEC/CAAM */ #define CONFIG_SYS_HAS_SERDES /* common SERDES init code */ #define CONFIG_PCI /* Enable PCI/PCIE */ @@ -598,6 +599,12 @@ combinations. this should be removed later #define CONFIG_DOS_PARTITION #endif +/* Hash command with SHA acceleration supported in hardware */ +#ifdef CONFIG_FSL_CAAM +#define CONFIG_CMD_HASH +#define CONFIG_SHA_HW_ACCEL +#endif + /* * Miscellaneous configurable options */ @@ -704,4 +711,8 @@ combinations. this should be removed later #include <asm/fsl_secure_boot.h> +#ifdef CONFIG_SECURE_BOOT +#define CONFIG_CMD_BLOB +#endif + #endif /* __CONFIG_H */ diff --git a/include/configs/C29XPCIE.h b/include/configs/C29XPCIE.h index 715616d..5d11278 100644 --- a/include/configs/C29XPCIE.h +++ b/include/configs/C29XPCIE.h @@ -86,6 +86,7 @@ #define CONFIG_BOOKE /* BOOKE */ #define CONFIG_E500 /* BOOKE e500 family */ #define CONFIG_FSL_IFC /* Enable IFC Support */ +#define CONFIG_FSL_CAAM /* Enable SEC/CAAM */ #define CONFIG_SYS_HAS_SERDES /* common SERDES init code */ #define CONFIG_PCI /* Enable PCI/PCIE */ @@ -506,6 +507,12 @@ #define CONFIG_CMD_SETEXPR #define CONFIG_CMD_REGINFO +/* Hash command with SHA acceleration supported in hardware */ +#ifdef CONFIG_FSL_CAAM +#define CONFIG_CMD_HASH +#define CONFIG_SHA_HW_ACCEL +#endif + /* * Miscellaneous configurable options */ diff --git a/include/configs/P1010RDB.h b/include/configs/P1010RDB.h index a373990..d378dbd 100644 --- a/include/configs/P1010RDB.h +++ b/include/configs/P1010RDB.h @@ -53,7 +53,7 @@ #ifdef CONFIG_SECURE_BOOT #define CONFIG_RAMBOOT_SPIFLASH #define CONFIG_SYS_TEXT_BASE 0x11000000 -#define CONFIG_RESET_VECTOR_ADDRESS 0x1107fffc +#define CONFIG_RESET_VECTOR_ADDRESS 0x110bfffc #else #define CONFIG_SPL_MPC8XXX_INIT_DDR_SUPPORT #define CONFIG_SPL_DRIVERS_MISC_SUPPORT @@ -170,6 +170,7 @@ #define CONFIG_BOOKE /* BOOKE */ #define CONFIG_E500 /* BOOKE e500 family */ #define CONFIG_FSL_IFC /* Enable IFC Support */ +#define CONFIG_FSL_CAAM /* Enable SEC/CAAM */ #define CONFIG_SYS_HAS_SERDES /* common SERDES init code */ #define CONFIG_PCI /* Enable PCI/PCIE */ @@ -832,6 +833,12 @@ extern unsigned long get_sdram_size(void); #define CONFIG_DOS_PARTITION #endif +/* Hash command with SHA acceleration supported in hardware */ +#ifdef CONFIG_FSL_CAAM +#define CONFIG_CMD_HASH +#define CONFIG_SHA_HW_ACCEL +#endif + /* * Miscellaneous configurable options */ @@ -956,4 +963,8 @@ extern unsigned long get_sdram_size(void); #include <asm/fsl_secure_boot.h> +#ifdef CONFIG_SECURE_BOOT +#define CONFIG_CMD_BLOB +#endif + #endif /* __CONFIG_H */ diff --git a/include/configs/P2041RDB.h b/include/configs/P2041RDB.h index 16f7525..2e11aaa 100644 --- a/include/configs/P2041RDB.h +++ b/include/configs/P2041RDB.h @@ -49,6 +49,7 @@ #define CONFIG_SYS_FSL_CPC /* Corenet Platform Cache */ #define CONFIG_SYS_NUM_CPC CONFIG_NUM_DDR_CONTROLLERS #define CONFIG_FSL_ELBC /* Has Enhanced localbus controller */ +#define CONFIG_FSL_CAAM /* Enable SEC/CAAM */ #define CONFIG_PCI /* Enable PCI/PCIE */ #define CONFIG_PCIE1 /* PCIE controler 1 */ #define CONFIG_PCIE2 /* PCIE controler 2 */ @@ -647,6 +648,12 @@ unsigned long get_board_sys_clk(unsigned long dummy); #define CONFIG_DOS_PARTITION #endif +/* Hash command with SHA acceleration supported in hardware */ +#ifdef CONFIG_FSL_CAAM +#define CONFIG_CMD_HASH +#define CONFIG_SHA_HW_ACCEL +#endif + /* * Miscellaneous configurable options */ @@ -743,4 +750,8 @@ unsigned long get_board_sys_clk(unsigned long dummy); #include <asm/fsl_secure_boot.h> +#ifdef CONFIG_SECURE_BOOT +#define CONFIG_CMD_BLOB +#endif + #endif /* __CONFIG_H */ diff --git a/include/configs/T1040QDS.h b/include/configs/T1040QDS.h index a781ba3..1d0664d 100644 --- a/include/configs/T1040QDS.h +++ b/include/configs/T1040QDS.h @@ -58,6 +58,7 @@ #define CONFIG_SYS_FSL_CPC /* Corenet Platform Cache */ #define CONFIG_SYS_NUM_CPC CONFIG_NUM_DDR_CONTROLLERS #define CONFIG_FSL_IFC /* Enable IFC Support */ +#define CONFIG_FSL_CAAM /* Enable SEC/CAAM */ #define CONFIG_PCI /* Enable PCI/PCIE */ #define CONFIG_PCI_INDIRECT_BRIDGE #define CONFIG_PCIE1 /* PCIE controler 1 */ @@ -716,6 +717,12 @@ unsigned long get_board_ddr_clk(void); #define CONFIG_CMD_NET #endif +/* Hash command with SHA acceleration supported in hardware */ +#ifdef CONFIG_FSL_CAAM +#define CONFIG_CMD_HASH +#define CONFIG_SHA_HW_ACCEL +#endif + /* * Miscellaneous configurable options */ @@ -818,6 +825,7 @@ unsigned long get_board_ddr_clk(void); #ifdef CONFIG_SECURE_BOOT #include <asm/fsl_secure_boot.h> +#define CONFIG_CMD_BLOB #endif #endif /* __CONFIG_H */ diff --git a/include/configs/T104xRDB.h b/include/configs/T104xRDB.h index 5e2c100..2bb86e4 100644 --- a/include/configs/T104xRDB.h +++ b/include/configs/T104xRDB.h @@ -113,6 +113,7 @@ #define CONFIG_SYS_FSL_CPC /* Corenet Platform Cache */ #define CONFIG_SYS_NUM_CPC CONFIG_NUM_DDR_CONTROLLERS #define CONFIG_FSL_IFC /* Enable IFC Support */ +#define CONFIG_FSL_CAAM /* Enable SEC/CAAM */ #define CONFIG_PCI /* Enable PCI/PCIE */ #define CONFIG_PCI_INDIRECT_BRIDGE #define CONFIG_PCIE1 /* PCIE controler 1 */ @@ -731,6 +732,12 @@ #define CONFIG_CMD_NET #endif +/* Hash command with SHA acceleration supported in hardware */ +#ifdef CONFIG_FSL_CAAM +#define CONFIG_CMD_HASH +#define CONFIG_SHA_HW_ACCEL +#endif + /* * Miscellaneous configurable options */ @@ -865,6 +872,7 @@ #ifdef CONFIG_SECURE_BOOT #include <asm/fsl_secure_boot.h> +#define CONFIG_CMD_BLOB #endif #endif /* __CONFIG_H */ diff --git a/include/configs/T208xQDS.h b/include/configs/T208xQDS.h index 395472b..2733358 100644 --- a/include/configs/T208xQDS.h +++ b/include/configs/T208xQDS.h @@ -44,6 +44,7 @@ #define CONFIG_SYS_FSL_CPC /* Corenet Platform Cache */ #define CONFIG_SYS_NUM_CPC CONFIG_NUM_DDR_CONTROLLERS #define CONFIG_FSL_IFC /* Enable IFC Support */ +#define CONFIG_FSL_CAAM /* Enable SEC/CAAM */ #define CONFIG_FSL_LAW /* Use common FSL init code */ #define CONFIG_ENV_OVERWRITE @@ -777,6 +778,12 @@ unsigned long get_board_ddr_clk(void); #define CONFIG_CMD_NET #endif +/* Hash command with SHA acceleration supported in hardware */ +#ifdef CONFIG_FSL_CAAM +#define CONFIG_CMD_HASH +#define CONFIG_SHA_HW_ACCEL +#endif + /* * Miscellaneous configurable options */ @@ -909,6 +916,7 @@ unsigned long get_board_ddr_clk(void); #ifdef CONFIG_SECURE_BOOT #include <asm/fsl_secure_boot.h> +#define CONFIG_CMD_BLOB #undef CONFIG_CMD_USB #endif diff --git a/include/configs/T208xRDB.h b/include/configs/T208xRDB.h index e5936c7..400d979 100644 --- a/include/configs/T208xRDB.h +++ b/include/configs/T208xRDB.h @@ -37,6 +37,7 @@ #define CONFIG_SYS_FSL_CPC /* Corenet Platform Cache */ #define CONFIG_SYS_NUM_CPC CONFIG_NUM_DDR_CONTROLLERS #define CONFIG_FSL_IFC /* Enable IFC Support */ +#define CONFIG_FSL_CAAM /* Enable SEC/CAAM */ #define CONFIG_FSL_LAW /* Use common FSL init code */ #define CONFIG_ENV_OVERWRITE @@ -736,6 +737,12 @@ unsigned long get_board_ddr_clk(void); #define CONFIG_CMD_NET #endif +/* Hash command with SHA acceleration supported in hardware */ +#ifdef CONFIG_FSL_CAAM +#define CONFIG_CMD_HASH +#define CONFIG_SHA_HW_ACCEL +#endif + /* * Miscellaneous configurable options */ @@ -868,6 +875,7 @@ unsigned long get_board_ddr_clk(void); #ifdef CONFIG_SECURE_BOOT #include <asm/fsl_secure_boot.h> +#define CONFIG_CMD_BLOB #undef CONFIG_CMD_USB #endif diff --git a/include/configs/T4240QDS.h b/include/configs/T4240QDS.h index ca97247..1e0f5ec 100644 --- a/include/configs/T4240QDS.h +++ b/include/configs/T4240QDS.h @@ -15,6 +15,7 @@ #define CONFIG_FSL_SATA_V2 #define CONFIG_PCIE4 +#define CONFIG_FSL_CAAM /* Enable SEC/CAAM */ #define CONFIG_ICS307_REFCLK_HZ 25000000 /* ICS307 ref clk freq */ @@ -506,6 +507,12 @@ unsigned long get_board_ddr_clk(void); #define CONFIG_PHY_GIGE /* Include GbE speed/duplex detection */ #endif +/* Hash command with SHA acceleration supported in hardware */ +#ifdef CONFIG_FSL_CAAM +#define CONFIG_CMD_HASH +#define CONFIG_SHA_HW_ACCEL +#endif + /* * USB */ @@ -625,4 +632,8 @@ unsigned long get_board_ddr_clk(void); #include <asm/fsl_secure_boot.h> +#ifdef CONFIG_SECURE_BOOT +#define CONFIG_CMD_BLOB +#endif + #endif /* __CONFIG_H */ diff --git a/include/configs/T4240RDB.h b/include/configs/T4240RDB.h index 183255d..13f4bd3 100644 --- a/include/configs/T4240RDB.h +++ b/include/configs/T4240RDB.h @@ -47,6 +47,7 @@ #define CONFIG_SYS_FSL_CPC /* Corenet Platform Cache */ #define CONFIG_SYS_NUM_CPC CONFIG_NUM_DDR_CONTROLLERS #define CONFIG_FSL_IFC /* Enable IFC Support */ +#define CONFIG_FSL_CAAM /* Enable SEC/CAAM */ #define CONFIG_PCI /* Enable PCI/PCIE */ #define CONFIG_PCIE1 /* PCIE controler 1 */ #define CONFIG_PCIE2 /* PCIE controler 2 */ @@ -668,6 +669,12 @@ unsigned long get_board_ddr_clk(void); #define CONFIG_DOS_PARTITION #endif +/* Hash command with SHA acceleration supported in hardware */ +#ifdef CONFIG_FSL_CAAM +#define CONFIG_CMD_HASH +#define CONFIG_SHA_HW_ACCEL +#endif + #define CONFIG_BOOTDELAY 10 /* -1 disables auto-boot */ #define __USB_PHY_TYPE utmi @@ -751,6 +758,7 @@ unsigned long get_board_ddr_clk(void); * which is anyways not used in Secure Environment. */ #undef CONFIG_CMD_USB +#define CONFIG_CMD_BLOB #endif #endif /* __CONFIG_H */ diff --git a/include/configs/corenet_ds.h b/include/configs/corenet_ds.h index 12b3296..72b7efa 100644 --- a/include/configs/corenet_ds.h +++ b/include/configs/corenet_ds.h @@ -57,6 +57,7 @@ #define CONFIG_SYS_FSL_CPC /* Corenet Platform Cache */ #define CONFIG_SYS_NUM_CPC CONFIG_NUM_DDR_CONTROLLERS #define CONFIG_FSL_ELBC /* Has Enhanced localbus controller */ +#define CONFIG_FSL_CAAM /* Enable SEC/CAAM */ #define CONFIG_PCI /* Enable PCI/PCIE */ #define CONFIG_PCIE1 /* PCIE controler 1 */ #define CONFIG_PCIE2 /* PCIE controler 2 */ @@ -648,6 +649,12 @@ #define CONFIG_DOS_PARTITION #endif +/* Hash command with SHA acceleration supported in hardware */ +#ifdef CONFIG_FSL_CAAM +#define CONFIG_CMD_HASH +#define CONFIG_SHA_HW_ACCEL +#endif + /* * Miscellaneous configurable options */ @@ -745,4 +752,8 @@ #include <asm/fsl_secure_boot.h> +#ifdef CONFIG_SECURE_BOOT +#define CONFIG_CMD_BLOB +#endif + #endif /* __CONFIG_H */ diff --git a/include/configs/ls1021aqds.h b/include/configs/ls1021aqds.h index bb47813..4221426 100644 --- a/include/configs/ls1021aqds.h +++ b/include/configs/ls1021aqds.h @@ -69,6 +69,7 @@ unsigned long get_board_ddr_clk(void); #define CONFIG_SYS_HAS_SERDES +#define CONFIG_FSL_CAAM /* Enable CAAM */ /* * IFC Definitions */ @@ -388,4 +389,14 @@ unsigned long get_board_ddr_clk(void); #define CONFIG_OF_BOARD_SETUP #define CONFIG_CMD_BOOTZ +#define CONFIG_MISC_INIT_R + +/* Hash command with SHA acceleration supported in hardware */ +#define CONFIG_CMD_HASH +#define CONFIG_SHA_HW_ACCEL + +#ifdef CONFIG_SECURE_BOOT +#define CONFIG_CMD_BLOB +#endif + #endif diff --git a/include/configs/ls1021atwr.h b/include/configs/ls1021atwr.h index 45b2272..5868287 100644 --- a/include/configs/ls1021atwr.h +++ b/include/configs/ls1021atwr.h @@ -48,6 +48,8 @@ #define CONFIG_SYS_HAS_SERDES +#define CONFIG_FSL_CAAM /* Enable CAAM */ + /* * IFC Definitions */ @@ -288,4 +290,14 @@ #define CONFIG_OF_BOARD_SETUP #define CONFIG_CMD_BOOTZ +#define CONFIG_MISC_INIT_R + +/* Hash command with SHA acceleration supported in hardware */ +#define CONFIG_CMD_HASH +#define CONFIG_SHA_HW_ACCEL + +#ifdef CONFIG_SECURE_BOOT +#define CONFIG_CMD_BLOB +#endif + #endif diff --git a/include/fsl_sec.h b/include/fsl_sec.h new file mode 100644 index 0000000..aa850a3 --- /dev/null +++ b/include/fsl_sec.h @@ -0,0 +1,181 @@ +/* + * Common internal memory map for some Freescale SoCs + * + * Copyright 2014 Freescale Semiconductor, Inc. + * + */ + +#ifndef __FSL_SEC_H +#define __FSL_SEC_H + +#include <common.h> +#include <asm/io.h> + +#ifdef CONFIG_SYS_FSL_SEC_LE +#define sec_in32(a) in_le32(a) +#define sec_out32(a, v) out_le32(a, v) +#define sec_in16(a) in_le16(a) +#define sec_clrbits32 clrbits_le32 +#define sec_setbits32 setbits_le32 +#elif defined(CONFIG_SYS_FSL_SEC_BE) +#define sec_in32(a) in_be32(a) +#define sec_out32(a, v) out_be32(a, v) +#define sec_in16(a) in_be16(a) +#define sec_clrbits32 clrbits_be32 +#define sec_setbits32 setbits_be32 +#else +#error Neither CONFIG_SYS_FSL_SEC_LE nor CONFIG_SYS_FSL_SEC_BE is defined +#endif + +/* Security Engine Block (MS = Most Sig., LS = Least Sig.) */ +#if CONFIG_SYS_FSL_SEC_COMPAT >= 4 +/* RNG4 TRNG test registers */ +struct rng4tst { +#define RTMCTL_PRGM 0x00010000 /* 1 -> program mode, 0 -> run mode */ + u32 rtmctl; /* misc. control register */ + u32 rtscmisc; /* statistical check misc. register */ + u32 rtpkrrng; /* poker range register */ +#define RTSDCTL_ENT_DLY_MIN 1200 +#define RTSDCTL_ENT_DLY_MAX 12800 + union { + u32 rtpkrmax; /* PRGM=1: poker max. limit register */ + u32 rtpkrsq; /* PRGM=0: poker square calc. result register */ + }; +#define RTSDCTL_ENT_DLY_SHIFT 16 +#define RTSDCTL_ENT_DLY_MASK (0xffff << RTSDCTL_ENT_DLY_SHIFT) + u32 rtsdctl; /* seed control register */ + union { + u32 rtsblim; /* PRGM=1: sparse bit limit register */ + u32 rttotsam; /* PRGM=0: total samples register */ + }; + u32 rtfreqmin; /* frequency count min. limit register */ + union { + u32 rtfreqmax; /* PRGM=1: freq. count max. limit register */ + u32 rtfreqcnt; /* PRGM=0: freq. count register */ + }; + u32 rsvd1[40]; +#define RNG_STATE0_HANDLE_INSTANTIATED 0x00000001 + u32 rdsta; /*RNG DRNG Status Register*/ + u32 rsvd2[15]; +}; + +typedef struct ccsr_sec { + u32 res0; + u32 mcfgr; /* Master CFG Register */ + u8 res1[0x4]; + u32 scfgr; + struct { + u32 ms; /* Job Ring LIODN Register, MS */ + u32 ls; /* Job Ring LIODN Register, LS */ + } jrliodnr[4]; + u8 res2[0x2c]; + u32 jrstartr; /* Job Ring Start Register */ + struct { + u32 ms; /* RTIC LIODN Register, MS */ + u32 ls; /* RTIC LIODN Register, LS */ + } rticliodnr[4]; + u8 res3[0x1c]; + u32 decorr; /* DECO Request Register */ + struct { + u32 ms; /* DECO LIODN Register, MS */ + u32 ls; /* DECO LIODN Register, LS */ + } decoliodnr[8]; + u8 res4[0x40]; + u32 dar; /* DECO Avail Register */ + u32 drr; /* DECO Reset Register */ + u8 res5[0x4d8]; + struct rng4tst rng; /* RNG Registers */ + u8 res11[0x8a0]; + u32 crnr_ms; /* CHA Revision Number Register, MS */ + u32 crnr_ls; /* CHA Revision Number Register, LS */ + u32 ctpr_ms; /* Compile Time Parameters Register, MS */ + u32 ctpr_ls; /* Compile Time Parameters Register, LS */ + u8 res6[0x10]; + u32 far_ms; /* Fault Address Register, MS */ + u32 far_ls; /* Fault Address Register, LS */ + u32 falr; /* Fault Address LIODN Register */ + u32 fadr; /* Fault Address Detail Register */ + u8 res7[0x4]; + u32 csta; /* CAAM Status Register */ + u8 res8[0x8]; + u32 rvid; /* Run Time Integrity Checking Version ID Reg.*/ + u32 ccbvid; /* CHA Cluster Block Version ID Register */ + u32 chavid_ms; /* CHA Version ID Register, MS */ + u32 chavid_ls; /* CHA Version ID Register, LS */ + u32 chanum_ms; /* CHA Number Register, MS */ + u32 chanum_ls; /* CHA Number Register, LS */ + u32 secvid_ms; /* SEC Version ID Register, MS */ + u32 secvid_ls; /* SEC Version ID Register, LS */ + u8 res9[0x6020]; + u32 qilcr_ms; /* Queue Interface LIODN CFG Register, MS */ + u32 qilcr_ls; /* Queue Interface LIODN CFG Register, LS */ + u8 res10[0x8fd8]; +} ccsr_sec_t; + +#define SEC_CTPR_MS_AXI_LIODN 0x08000000 +#define SEC_CTPR_MS_QI 0x02000000 +#define SEC_CTPR_MS_VIRT_EN_INCL 0x00000001 +#define SEC_CTPR_MS_VIRT_EN_POR 0x00000002 +#define SEC_RVID_MA 0x0f000000 +#define SEC_CHANUM_MS_JRNUM_MASK 0xf0000000 +#define SEC_CHANUM_MS_JRNUM_SHIFT 28 +#define SEC_CHANUM_MS_DECONUM_MASK 0x0f000000 +#define SEC_CHANUM_MS_DECONUM_SHIFT 24 +#define SEC_SECVID_MS_IPID_MASK 0xffff0000 +#define SEC_SECVID_MS_IPID_SHIFT 16 +#define SEC_SECVID_MS_MAJ_REV_MASK 0x0000ff00 +#define SEC_SECVID_MS_MAJ_REV_SHIFT 8 +#define SEC_CCBVID_ERA_MASK 0xff000000 +#define SEC_CCBVID_ERA_SHIFT 24 +#define SEC_SCFGR_RDBENABLE 0x00000400 +#define SEC_SCFGR_VIRT_EN 0x00008000 +#define SEC_CHAVID_LS_RNG_SHIFT 16 +#define SEC_CHAVID_RNG_LS_MASK 0x000f0000 + +#define CONFIG_JRSTARTR_JR0 0x00000001 + +struct jr_regs { +#ifdef CONFIG_SYS_FSL_SEC_LE + u32 irba_l; + u32 irba_h; +#else + u32 irba_h; + u32 irba_l; +#endif + u32 rsvd1; + u32 irs; + u32 rsvd2; + u32 irsa; + u32 rsvd3; + u32 irja; +#ifdef CONFIG_SYS_FSL_SEC_LE + u32 orba_l; + u32 orba_h; +#else + u32 orba_h; + u32 orba_l; +#endif + u32 rsvd4; + u32 ors; + u32 rsvd5; + u32 orjr; + u32 rsvd6; + u32 orsf; + u32 rsvd7; + u32 jrsta; + u32 rsvd8; + u32 jrint; + u32 jrcfg0; + u32 jrcfg1; + u32 rsvd9; + u32 irri; + u32 rsvd10; + u32 orwi; + u32 rsvd11; + u32 jrcr; +}; + +int sec_init(void); +#endif + +#endif /* __FSL_SEC_H */ |