On Tue, Oct 18, 2016 at 01:34:10AM +0530, Bhupesh Sharma wrote:
From: Sakar Arora sakar.arora@nxp.com
NXP/FSL ARMv8 SoCs currently use a EL3 platform and run-time security firmware which is called PPA (Primary Protected Application).
This firmware is placed on the flash device and is loaded into DDR and executed via a UEFI DXE driver. PPA does the initial platform EL3 settings and then returns the control back to UEFI in EL2 exception level.
Later implementations of PPA will allow it to start by itself in the EL3 level and start UEFI in EL2 exception level.
This patch adds the PPA load and execution handlers.
Again, excellent commit message.
Signed-off-by: Sakar Arora sakar.arora@nxp.com Signed-off-by: Bhupesh Sharma bhupesh.sharma@nxp.com
Chips/Nxp/QoriqLs/PpaInitDxe/PpaInit.c | 117 ++++++++++++++++++++++ Chips/Nxp/QoriqLs/PpaInitDxe/PpaInitDxe.inf | 63 ++++++++++++ Chips/Nxp/QoriqLs/PpaInitDxe/PpaInitHelper.S | 79 +++++++++++++++ Chips/Nxp/QoriqLs/PpaInitDxe/PpaItbParse.c | 144 +++++++++++++++++++++++++++ Chips/Nxp/QoriqLs/PpaInitDxe/PpaItbParse.h | 52 ++++++++++ 5 files changed, 455 insertions(+) create mode 100644 Chips/Nxp/QoriqLs/PpaInitDxe/PpaInit.c create mode 100644 Chips/Nxp/QoriqLs/PpaInitDxe/PpaInitDxe.inf create mode 100644 Chips/Nxp/QoriqLs/PpaInitDxe/PpaInitHelper.S create mode 100755 Chips/Nxp/QoriqLs/PpaInitDxe/PpaItbParse.c create mode 100755 Chips/Nxp/QoriqLs/PpaInitDxe/PpaItbParse.h
diff --git a/Chips/Nxp/QoriqLs/PpaInitDxe/PpaInit.c b/Chips/Nxp/QoriqLs/PpaInitDxe/PpaInit.c new file mode 100644 index 0000000..4e4cedb --- /dev/null +++ b/Chips/Nxp/QoriqLs/PpaInitDxe/PpaInit.c @@ -0,0 +1,117 @@ +/** @file +# +# DXE driver for loading Primary Protected Application +# +# Copyright (c) 2016, Freescale Semiconductor, Inc. All rights reserved. +# +# This program and the accompanying materials +# are licensed and made available under the terms and conditions of the BSD License +# which accompanies this distribution. The full text of the license may be found at +# http://opensource.org/licenses/bsd-license.php +# +# THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, +# WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. +# +**/
+#include <Chipset/AArch64.h> +#include <Library/ArmPlatformLib.h> +#include <Library/PcdLib.h> +#include <Library/DebugLib.h> +#include <Library/IoLib.h> +#include <Library/PrintLib.h> +#include <Library/MemoryAllocationLib.h> +#include <Library/BaseMemoryLib/MemLibInternals.h> +#include "PpaItbParse.h"
Please sort alphabetically.
+extern EFI_STATUS PpaInit(UINT64); +extern VOID InitMmu(ARM_MEMORY_REGION_DESCRIPTOR*);
These should be pulled in from an include file.
+/**
- Copying PPA firmware to DDR
- */
+VOID +CopyPpaImage (
- const char *title,
- UINTN image_addr,
- UINTN image_size,
- UINTN PpaRamAddr)
+{
- DEBUG((EFI_D_INFO, "%a copied to address 0x%x\n", title, PpaRamAddr));
- InternalMemCopyMem((void *)PpaRamAddr, (void *)image_addr, image_size);
+}
+UINTN +GetPpaImagefromFlash (
- VOID
- )
+{
- EFI_STATUS Status;
- EFI_PHYSICAL_ADDRESS FitImage;
- EFI_PHYSICAL_ADDRESS PpaImage;
- INT32 CfgNodeOffset;
- INT32 NodeOffset;
- INT32 PpaImageSize;
- UINTN PpaRamAddr;
- // Assuming that the PPA FW is present on NOR flash
- // FIXME: Add support for other flash devices.
No FIXME please.
- FitImage = PcdGet64 (PcdPpaNorBaseAddr);
- // PPA will be placed on DDR at this address:
- // Top of DDR - PcdPpaDdrOffsetAddr
- PpaRamAddr = PcdGet64 (PcdSystemMemoryBase) + PcdGet64 (PcdSystemMemorySize)
- PcdGet64 (PcdPpaDdrOffsetAddr);
- Status = FitCheckHeader(FitImage);
- if (EFI_ERROR (Status)) {
DEBUG((EFI_D_ERROR, "Bad FIT image header (0x%x).\n", Status));
goto EXIT_FREE_FIT;
- }
- Status = FitGetConfNode(FitImage, (void *)(PcdGetPtr(PcdPpaFitConfiguration)), &CfgNodeOffset);
- if (EFI_ERROR (Status)) {
DEBUG((EFI_D_ERROR, "Did not find configuration node in FIT header (0x%x).\n", Status));
goto EXIT_FREE_FIT;
- }
- Status = FitGetNodeFromConf(FitImage, CfgNodeOffset, FIT_FIRMWARE_IMAGE, &NodeOffset);
- if (EFI_ERROR (Status)) {
DEBUG((EFI_D_ERROR, "Did not find PPA node in FIT header (0x%x).\n", Status));
goto EXIT_FREE_FIT;
- }
- Status = FitGetNodeData(FitImage, NodeOffset, (VOID*)&PpaImage, &PpaImageSize);
- if (EFI_ERROR (Status)) {
DEBUG((EFI_D_ERROR, "Did not find PPA f/w in FIT image (0x%x).\n", Status));
goto EXIT_FREE_FIT;
- }
- CopyPpaImage ("PPA Firmware", PpaImage, PpaImageSize, PpaRamAddr);
- return PpaRamAddr;
+EXIT_FREE_FIT:
- // Flow should never reach here
- ASSERT (Status == EFI_SUCCESS);
- return 0;
+}
+EFI_STATUS +PpaInitialize (
- IN EFI_HANDLE ImageHandle,
- IN EFI_SYSTEM_TABLE *SystemTable
- )
+{
- EFI_STATUS Status;
- UINTN PpaRamAddr;
- ARM_MEMORY_REGION_DESCRIPTOR *MemoryTable;
- PpaRamAddr = GetPpaImagefromFlash();
- Status = PpaInit(PpaRamAddr);
- ArmPlatformGetVirtualMemoryMap (&MemoryTable);
- InitMmu(MemoryTable);
I won't comment on every missing space before function name and opening (, but please add here to keep it consistent.
- return Status;
+} diff --git a/Chips/Nxp/QoriqLs/PpaInitDxe/PpaInitDxe.inf b/Chips/Nxp/QoriqLs/PpaInitDxe/PpaInitDxe.inf new file mode 100644 index 0000000..80f9cb0 --- /dev/null +++ b/Chips/Nxp/QoriqLs/PpaInitDxe/PpaInitDxe.inf @@ -0,0 +1,63 @@ +#/** PpaInitDxe.inf +# +# Component description file for Ppa Initialization driver +# +# Copyright (c) 2016, Freescale Semiconductor, Inc. All rights reserved. +# +# This program and the accompanying materials +# are licensed and made available under the terms and conditions of the BSD License +# which accompanies this distribution. The full text of the license may be found at +# http://opensource.org/licenses/bsd-license.php +# +# THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, +# WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. +# +# +#**/
+[Defines]
- INF_VERSION = 0x00010005
- BASE_NAME = PpaInit
- FILE_GUID = 4d00ef14-c4e0-426b-81b7-30a00a14abb6
- MODULE_TYPE = DXE_DRIVER
- VERSION_STRING = 1.0
- ENTRY_POINT = PpaInitialize
+[Sources.common]
- PpaInit.c
- PpaInitHelper.S
- PpaItbParse.c
+[Packages]
- MdePkg/MdePkg.dec
- ArmPkg/ArmPkg.dec
- ArmPlatformPkg/ArmPlatformPkg.dec
- EmbeddedPkg/EmbeddedPkg.dec
- OpenPlatformPkg/Chips/Nxp/QoriqLs/NxpQoriqLs.dec
+[LibraryClasses]
- BaseLib
- UefiLib
- UefiDriverEntryPoint
- MemoryInitPeiLib
- ArmLib
- BdsLib
- FdtLib
+[Guids]
+[Protocols]
+[Pcd]
- gArmTokenSpaceGuid.PcdSystemMemoryBase
- gArmTokenSpaceGuid.PcdSystemMemorySize
- gNxpQoriqLsTokenSpaceGuid.PcdPpaNorBaseAddr
- gNxpQoriqLsTokenSpaceGuid.PcdPpaDdrOffsetAddr
- gNxpQoriqLsTokenSpaceGuid.PcdPpaFitConfiguration
Please sort alpabetically above.
+[FixedPcd]
+[depex]
- TRUE
diff --git a/Chips/Nxp/QoriqLs/PpaInitDxe/PpaInitHelper.S b/Chips/Nxp/QoriqLs/PpaInitDxe/PpaInitHelper.S new file mode 100644 index 0000000..237015c --- /dev/null +++ b/Chips/Nxp/QoriqLs/PpaInitDxe/PpaInitHelper.S @@ -0,0 +1,79 @@ +# @PpaInitHelper.S +# +# Copyright (c) 2016, Freescale Semiconductor, Inc. All rights +# reserved. +# +# This program and the accompanying materials +# are licensed and made available under the terms and conditions of the BSD License +# which accompanies this distribution. The full text of the license may be found at +# http://opensource.org/licenses/bsd-license.php +# +# THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, +# WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. +# +# +#include <AutoGen.h>
Huh? Why include this file?
+.text +.align 2
+GCC_ASM_EXPORT(PpaInit) +GCC_ASM_EXPORT(El2SwitchSetup)
+ASM_PFX(PpaInit): +//Push return address to the stack +//sub sp, sp, #16 +//stur x30, [sp, #0]
Please no commented out code. Delete it if not used.
+//Save stack pointer for EL2
- mov x1, sp
- msr sp_el2, x1
+//Set boot loc pointer
- adr x4, 1f
- adr x1, ADDR_BASE_SCFG
- ldr w2, [x1]
- mov x1, x4
- rev w3, w1
- str w3, [x2, #0x604]
- lsr x1, x4, #32
- rev w3, w1
- str w3, [x2, #0x600]
+//Call PPA monitor
- br x0
+1: +//Pop out return address from stack +//ldur x30, [sp, #0] +//add sp, sp, #16
Delete.
- // Enable GICv2 interrupts in EL2 mode
- mrs x0, hcr_el2
- orr x0, x0, #0x18
- msr hcr_el2, x0
+//return 0
- mov x0, #0
- ret
+ASM_PFX(El2SwitchSetup):
- mov x0, #0x5b1 // non-secure el0/el1 | hvc | 64bit el2
- msr scr_el3, x0
- msr cptr_el3, xzr // disable coprocessor traps to el3
- mov x0, #0x33ff
- msr cptr_el2, x0 // disable coprocessor traps to el2
- // initialize sctlr_el2
- msr sctlr_el2, xzr
- mov x0, #0x3c9
- msr spsr_el3, x0 // el2_sp2 | d | a | i | f
- ret
+ADDR_BASE_SCFG:
- .long 0x01570000
+ADDR_BASE_DCFG:
- .long 0x01EE0000
+ASM_FUNCTION_REMOVE_IF_UNREFERENCED diff --git a/Chips/Nxp/QoriqLs/PpaInitDxe/PpaItbParse.c b/Chips/Nxp/QoriqLs/PpaInitDxe/PpaItbParse.c new file mode 100755 index 0000000..9e6a477 --- /dev/null +++ b/Chips/Nxp/QoriqLs/PpaInitDxe/PpaItbParse.c @@ -0,0 +1,144 @@ +#include <libfdt.h> +#include <Library/DebugLib.h>
+#include "PpaItbParse.h"
+EFI_STATUS +FitCheckHeader(
- EFI_PHYSICAL_ADDRESS FitImage
+) +{
- if(fdt_check_header((VOID*) FitImage)) {
DEBUG((EFI_D_ERROR, "bad FIT header\n"));
return EFI_UNSUPPORTED;
- }
- /* mandatory / node 'description' property */
- if (fdt_getprop((VOID*)FitImage, 0, FIT_DESC_PROP, NULL) == NULL) {
DEBUG((EFI_D_ERROR, "Wrong FIT format: no description\n"));
return EFI_UNSUPPORTED;
- }
- /* mandatory subimages parent '/images' node */
- if (fdt_path_offset((VOID*)FitImage, FIT_IMAGES_PATH) < 0) {
DEBUG((EFI_D_ERROR, "Wrong FIT format: no images parent node\n"));
return EFI_UNSUPPORTED;
- }
- return EFI_SUCCESS;
+}
+EFI_STATUS +FitGetConfNode (
- EFI_PHYSICAL_ADDRESS FitImage,
- VOID* ConfigPtr,
- INT32* NodeOffset
+) +{
- INT32 noffset, confs_noffset;
- INT32 len;
- char* ConfigName;
CHAR8
- confs_noffset = fdt_path_offset((VOID*)FitImage, FIT_CONFS_PATH);
- if (confs_noffset < 0) {
- DEBUG((EFI_D_ERROR, "Can't find configurations parent node '%s' (%s)\n",
FIT_CONFS_PATH, fdt_strerror(confs_noffset)));
- return EFI_UNSUPPORTED;
- }
- ConfigName = (char*)ConfigPtr;
CHAR8
- if(ConfigName && *ConfigName == '\0')
- ConfigName = NULL;
- if (ConfigName == NULL) {
/* get configuration unit name from the default property
* */
- DEBUG((EFI_D_ERROR, "No configuration specified, trying default...\n"));
- ConfigName = (CHAR8 *)fdt_getprop((VOID*)FitImage, confs_noffset,
FIT_DEFAULT_PROP, &len);
- }
- noffset = fdt_subnode_offset((VOID*)FitImage, confs_noffset, ConfigName);
- if (noffset < 0) {
DEBUG((EFI_D_ERROR,
"Can't get node offset for configuration unit name: '%s' (%s)\n",
ConfigName, fdt_strerror(noffset)));
return EFI_UNSUPPORTED;
- }
- *NodeOffset = noffset;
- return EFI_SUCCESS;
+}
+EFI_STATUS +FitGetNodeFromConf (
- EFI_PHYSICAL_ADDRESS FitImage,
- INT32 CfgNodeOffset,
- CHAR8* ConfPropName,
- INT32* NodeOffset
+) +{
- INT32 noffset, len, img_noffset;
- CHAR8* PropName;
- PropName = (char *)fdt_getprop((VOID*)FitImage, CfgNodeOffset,
CHAR8
ConfPropName, &len);
- if (PropName == NULL) {
return EFI_UNSUPPORTED;
- }
- img_noffset = fdt_path_offset((VOID*)FitImage, FIT_IMAGES_PATH);
- if (img_noffset < 0) {
return EFI_UNSUPPORTED;
- }
- noffset = fdt_subnode_offset((VOID*)FitImage, img_noffset, PropName);
- if (noffset < 0) {
return EFI_UNSUPPORTED;
- }
- *NodeOffset = noffset;
- return EFI_SUCCESS;
+}
+EFI_STATUS +FitGetNodeData (
- EFI_PHYSICAL_ADDRESS FitImage,
- INT32 NodeOffset,
These parameter names need aligning (and it's not just the tabs here).
- EFI_PHYSICAL_ADDRESS* Addr,
- INT32* Size
+) +{
- VOID *Data;
- Data = (VOID*)fdt_getprop((VOID*)FitImage, NodeOffset, FIT_IMAGE_DATA, Size);
- if(Data == NULL) {
Space after if (please address globally).
return EFI_UNSUPPORTED;
- }
- *Addr = (EFI_PHYSICAL_ADDRESS)Data;
- return EFI_SUCCESS;
+}
+EFI_STATUS +FitGetNodeLoad (
- EFI_PHYSICAL_ADDRESS FitImage,
- INT32 NodeOffset,
- EFI_PHYSICAL_ADDRESS* Addr
+) +{
- INT32 Size;
- VOID* Load;
- Load = (VOID*)fdt_getprop((VOID*)FitImage, NodeOffset, FIT_IMAGE_LOAD, &Size);
- if(Load == NULL) {
return EFI_UNSUPPORTED;
- }
- if(Size == 4)
And braces on all if/else please (globally).
*Addr = MmioReadBe32((UINTN) Load);
- else if(Size == 8)
*Addr = MmioReadBe64((UINTN) Load);
- else {
return EFI_UNSUPPORTED;
- }
- return EFI_SUCCESS;
+} diff --git a/Chips/Nxp/QoriqLs/PpaInitDxe/PpaItbParse.h b/Chips/Nxp/QoriqLs/PpaInitDxe/PpaItbParse.h new file mode 100755 index 0000000..a6f78c0 --- /dev/null +++ b/Chips/Nxp/QoriqLs/PpaInitDxe/PpaItbParse.h @@ -0,0 +1,52 @@ +#ifndef __PPA_ITB_PARSE__ +#define __PPA_ITB_PARSE__
+#include <Library/IoLib.h>
+#define FIT_DESC_PROP "description" +#define FIT_IMAGES_PATH "/images" +#define FIT_KERNEL_IMAGE "kernel" +#define FIT_INITRD_IMAGE "ramdisk" +#define FIT_FIRMWARE_IMAGE "firmware" +#define FIT_FDT_IMAGE "fdt" +#define FIT_CONFS_PATH "/configurations" +#define FIT_DEFAULT_PROP "default" +#define FIT_IMAGE_DATA "data" +#define FIT_IMAGE_LOAD "load"
Is there any logical ordering of the above that makes more sense than alphabetical? If not, can these be sorted please?
+EFI_STATUS +FitCheckHeader(
- EFI_PHYSICAL_ADDRESS FitImage
+);
+EFI_STATUS +FitGetConfNode (
- EFI_PHYSICAL_ADDRESS FitImage,
- VOID* ConfigPtr,
- INT32* NodeOffset
+);
+EFI_STATUS +FitGetNodeFromConf (
- EFI_PHYSICAL_ADDRESS FitImage,
- INT32 CfgNodeOffset,
- CHAR8* ConfPropName,
- INT32* NodeOffset
+);
+EFI_STATUS +FitGetNodeData (
- EFI_PHYSICAL_ADDRESS FitImage,
- INT32 NodeOffset,
- EFI_PHYSICAL_ADDRESS* Addr,
- INT32* Size
+);
+EFI_STATUS +FitGetNodeLoad (
- EFI_PHYSICAL_ADDRESS FitImage,
- INT32 NodeOffset,
- EFI_PHYSICAL_ADDRESS* Addr
+);
+#endif
1.9.1