Hello,
Here is v2 version of the support. The patchset shrank a bit, because the custom RamDisk driver was replaced with the one already existing in a tree - yet because of lack of FAT formatting it's not functional for the platform purposes, but it's not crucial at this point. Also a custom UART driver has been replaced. Detailed list of changes is below.
For convenience purpose whole patchset is available in the github: https://github.com/MarvellEmbeddedProcessors/edk2-open-platform/commits/opp-...
Any comments or remarks are mostly welcome.
Best regards, Marcin
Changelog: v1 -> v2
* Fix "may be used uninitialized" variables issue, branch compiles both with DEBUG and RELEASE flags * Remove I2C_FLAG_NORESTART dependency - replace it with local definition * Remove Marvell UART Library: - DW8250 IP has programming interface compatible with NS-16550. Since in edk2 there is support for 16550, internal library is unnecessary. - /Library/BaseSerialPortLib16550/BaseSerialPortLib16550.inf is used instead * RamDisk driver: - Remove old driver imported from EFI TOOLKIT 2.0 - Replace it with new MdeModulePkg/Universal/Disk/RamDiskDxe from edk2 - Lack of FAT formatting issue emerged * Add explicit dependency on IoLib in Drivers/Spi/SpiDxe.inf * Add poster's "Signed-off-by" registry to every commit message * Move to 05.04.2016 HEAD of edk2/master - Update CpuExceptionHandlerLib within OPP.
Bartosz Szczepanek (6): Drivers/I2c: Create MvI2cDxe driver Platforms/Marvell: Copy BdsLib to Armada7040 directory Platforms/Marvell: Add necessary BdsLibConnectAll call Drivers/I2c: Add MvEeprom driver Platforms/Marvell: Enable EEPROM driver on Armada7040 platforms Aplications/Eeprom: Add 'eeprom' command to shell
Jan Dąbroś (14): Platforms/Marvell: Create MppLib Platforms/Marvell: Armada: Enable MppLib on Armada7040 platforms Platforms/Marvell: Enable I2C driver on Armada7040 platforms Platforms/Marvell: Enable 'eeprom' command on Armada7040 platforms Platforms/Marvell: Add EFI_SPI_MASTER_PROTOCOL Drivers/Spi: Add Spi master driver Platforms/Marvell: Enable Spi master driver for Armada7040 boards Platforms/Marvell: Add EFI_SPI_FLASH_PROTOCOL Drivers/Spi: Implement Spi flash driver Platforms/Marvell: Enable Spi flash driver on Armada7040 platforms Applications/SpiTool: Add 'sf' command utility Platforms/Marvell: Enable 'sf' command on Armada7040 platforms Applications/FirmwareUpdate: Add 'fupdate' comand to shell Platforms/Marvell: Enable 'fupdate' command on Armada7040 platforms
Marcin Wojtas (1): Platforms/Marvell: Enable RamDisk usage on Armada7040 platforms
Yehuda Yitschak (2): Platforms/Marvell: Add initial support for Armada7040 SOC lib Platforms/Marvell: Add initial support for Armada7040 Platforms
Applications/EepromCmd/EepromCmd.c | 365 +++++++++++ Applications/EepromCmd/EepromCmd.inf | 74 +++ Applications/EepromCmd/EepromCmd.uni | Bin 0 -> 6816 bytes Applications/FirmwareUpdate/FUpdate.c | 437 +++++++++++++ Applications/FirmwareUpdate/FUpdate.inf | 69 +++ Applications/FirmwareUpdate/FUpdate.uni | Bin 0 -> 5838 bytes Applications/SpiTool/SpiFlashCmd.c | 529 ++++++++++++++++ Applications/SpiTool/SpiFlashCmd.inf | 76 +++ Applications/SpiTool/SpiFlashCmd.uni | Bin 0 -> 7216 bytes Documentation/Marvell/Drivers/EepromDriver.txt | 95 +++ Documentation/Marvell/Drivers/I2cDriver.txt | 64 ++ Documentation/Marvell/Drivers/SpiDriver.txt | 116 ++++ Documentation/Marvell/PortingGuide/I2c.txt | 16 + Documentation/Marvell/PortingGuide/Mpp.txt | 48 ++ Documentation/Marvell/PortingGuide/Spi.txt | 15 + Documentation/Marvell/PortingGuide/SpiFlash.txt | 19 + Drivers/I2c/Devices/MvEeprom/MvEeprom.c | 292 +++++++++ Drivers/I2c/Devices/MvEeprom/MvEeprom.h | 90 +++ Drivers/I2c/Devices/MvEeprom/MvEeprom.inf | 70 +++ Drivers/I2c/MvI2cDxe/MvI2cDxe.c | 686 +++++++++++++++++++++ Drivers/I2c/MvI2cDxe/MvI2cDxe.h | 254 ++++++++ Drivers/I2c/MvI2cDxe/MvI2cDxe.inf | 73 +++ Drivers/Spi/Devices/MvSpiFlash.c | 523 ++++++++++++++++ Drivers/Spi/Devices/MvSpiFlash.h | 130 ++++ Drivers/Spi/Devices/MvSpiFlash.inf | 74 +++ Drivers/Spi/SpiDxe.c | 378 ++++++++++++ Drivers/Spi/SpiDxe.h | 145 +++++ Drivers/Spi/SpiDxe.inf | 74 +++ Platforms/Marvell/Armada/Apn806.dsc | 81 +++ Platforms/Marvell/Armada/Armada.dsc.inc | 465 ++++++++++++++ Platforms/Marvell/Armada/Armada7040.fdf | 277 +++++++++ Platforms/Marvell/Armada/Armada7040_rz.dsc | 93 +++ .../Library/Armada7040BdsLib/Armada7040BdsLib.c | 428 +++++++++++++ .../Library/Armada7040BdsLib/Armada7040BdsLib.h | 37 ++ .../Library/Armada7040BdsLib/Armada7040BdsLib.inf | 66 ++ .../Armada7040Lib/AArch64/ArmPlatformHelper.S | 65 ++ .../Armada/Library/Armada7040Lib/Armada7040Lib.c | 156 +++++ .../Armada/Library/Armada7040Lib/Armada7040Lib.inf | 47 ++ .../Library/Armada7040Lib/Armada7040LibMem.c | 73 +++ Platforms/Marvell/Include/Library/MppLib.h | 42 ++ Platforms/Marvell/Include/Protocol/Eeprom.h | 60 ++ Platforms/Marvell/Include/Protocol/Spi.h | 105 ++++ Platforms/Marvell/Include/Protocol/SpiFlash.h | 102 +++ Platforms/Marvell/Library/MppLib/MppLib.c | 175 ++++++ Platforms/Marvell/Library/MppLib/MppLib.inf | 108 ++++ Platforms/Marvell/Marvell.dec | 132 ++++ 46 files changed, 7224 insertions(+) create mode 100644 Applications/EepromCmd/EepromCmd.c create mode 100644 Applications/EepromCmd/EepromCmd.inf create mode 100644 Applications/EepromCmd/EepromCmd.uni create mode 100644 Applications/FirmwareUpdate/FUpdate.c create mode 100644 Applications/FirmwareUpdate/FUpdate.inf create mode 100644 Applications/FirmwareUpdate/FUpdate.uni create mode 100644 Applications/SpiTool/SpiFlashCmd.c create mode 100644 Applications/SpiTool/SpiFlashCmd.inf create mode 100644 Applications/SpiTool/SpiFlashCmd.uni create mode 100644 Documentation/Marvell/Drivers/EepromDriver.txt create mode 100644 Documentation/Marvell/Drivers/I2cDriver.txt create mode 100644 Documentation/Marvell/Drivers/SpiDriver.txt create mode 100644 Documentation/Marvell/PortingGuide/I2c.txt create mode 100644 Documentation/Marvell/PortingGuide/Mpp.txt create mode 100644 Documentation/Marvell/PortingGuide/Spi.txt create mode 100644 Documentation/Marvell/PortingGuide/SpiFlash.txt create mode 100644 Drivers/I2c/Devices/MvEeprom/MvEeprom.c create mode 100644 Drivers/I2c/Devices/MvEeprom/MvEeprom.h create mode 100644 Drivers/I2c/Devices/MvEeprom/MvEeprom.inf create mode 100644 Drivers/I2c/MvI2cDxe/MvI2cDxe.c create mode 100644 Drivers/I2c/MvI2cDxe/MvI2cDxe.h create mode 100644 Drivers/I2c/MvI2cDxe/MvI2cDxe.inf create mode 100644 Drivers/Spi/Devices/MvSpiFlash.c create mode 100644 Drivers/Spi/Devices/MvSpiFlash.h create mode 100644 Drivers/Spi/Devices/MvSpiFlash.inf create mode 100644 Drivers/Spi/SpiDxe.c create mode 100644 Drivers/Spi/SpiDxe.h create mode 100644 Drivers/Spi/SpiDxe.inf create mode 100644 Platforms/Marvell/Armada/Apn806.dsc create mode 100644 Platforms/Marvell/Armada/Armada.dsc.inc create mode 100644 Platforms/Marvell/Armada/Armada7040.fdf create mode 100644 Platforms/Marvell/Armada/Armada7040_rz.dsc create mode 100644 Platforms/Marvell/Armada/Library/Armada7040BdsLib/Armada7040BdsLib.c create mode 100644 Platforms/Marvell/Armada/Library/Armada7040BdsLib/Armada7040BdsLib.h create mode 100644 Platforms/Marvell/Armada/Library/Armada7040BdsLib/Armada7040BdsLib.inf create mode 100644 Platforms/Marvell/Armada/Library/Armada7040Lib/AArch64/ArmPlatformHelper.S create mode 100644 Platforms/Marvell/Armada/Library/Armada7040Lib/Armada7040Lib.c create mode 100644 Platforms/Marvell/Armada/Library/Armada7040Lib/Armada7040Lib.inf create mode 100644 Platforms/Marvell/Armada/Library/Armada7040Lib/Armada7040LibMem.c create mode 100644 Platforms/Marvell/Include/Library/MppLib.h create mode 100644 Platforms/Marvell/Include/Protocol/Eeprom.h create mode 100644 Platforms/Marvell/Include/Protocol/Spi.h create mode 100644 Platforms/Marvell/Include/Protocol/SpiFlash.h create mode 100644 Platforms/Marvell/Library/MppLib/MppLib.c create mode 100644 Platforms/Marvell/Library/MppLib/MppLib.inf create mode 100644 Platforms/Marvell/Marvell.dec
From: Yehuda Yitschak yehuday@marvell.com
This patch adds initial support for Armada7040 SoC's initialization. It implements empty mandatory hooks which are currently mostly empty except for Memory mapping information.
Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Yehuda Yitschak yehuday@marvell.com Signed-off-by: Marcin Wojtas mw@semihalf.com --- .../Armada7040Lib/AArch64/ArmPlatformHelper.S | 65 +++++++++ .../Armada/Library/Armada7040Lib/Armada7040Lib.c | 154 +++++++++++++++++++++ .../Armada/Library/Armada7040Lib/Armada7040Lib.inf | 45 ++++++ .../Library/Armada7040Lib/Armada7040LibMem.c | 73 ++++++++++ 4 files changed, 337 insertions(+) create mode 100644 Platforms/Marvell/Armada/Library/Armada7040Lib/AArch64/ArmPlatformHelper.S create mode 100644 Platforms/Marvell/Armada/Library/Armada7040Lib/Armada7040Lib.c create mode 100644 Platforms/Marvell/Armada/Library/Armada7040Lib/Armada7040Lib.inf create mode 100644 Platforms/Marvell/Armada/Library/Armada7040Lib/Armada7040LibMem.c
diff --git a/Platforms/Marvell/Armada/Library/Armada7040Lib/AArch64/ArmPlatformHelper.S b/Platforms/Marvell/Armada/Library/Armada7040Lib/AArch64/ArmPlatformHelper.S new file mode 100644 index 0000000..8c099b4 --- /dev/null +++ b/Platforms/Marvell/Armada/Library/Armada7040Lib/AArch64/ArmPlatformHelper.S @@ -0,0 +1,65 @@ +// +// Copyright (c) 2012-2013, ARM Limited. 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 <AsmMacroIoLibV8.h> +#include <Library/ArmLib.h> + +.text +.align 2 + +GCC_ASM_EXPORT(ArmPlatformPeiBootAction) +GCC_ASM_EXPORT(ArmPlatformGetCorePosition) +GCC_ASM_EXPORT(ArmPlatformGetPrimaryCoreMpId) +GCC_ASM_EXPORT(ArmPlatformIsPrimaryCore) + +GCC_ASM_IMPORT(_gPcd_FixedAtBuild_PcdArmPrimaryCore) +GCC_ASM_IMPORT(_gPcd_FixedAtBuild_PcdArmPrimaryCoreMask) + +ASM_PFX(ArmPlatformPeiBootAction): + ret + +//UINTN +//ArmPlatformGetCorePosition ( +// IN UINTN MpId +// ); +// With this function: CorePos = (ClusterId * 4) + CoreId +ASM_PFX(ArmPlatformGetCorePosition): + and x1, x0, #ARM_CORE_MASK + and x0, x0, #ARM_CLUSTER_MASK + add x0, x1, x0, LSR #6 + ret + +//UINTN +//ArmPlatformGetPrimaryCoreMpId ( +// VOID +// ); +ASM_PFX(ArmPlatformGetPrimaryCoreMpId): + LoadConstantToReg (_gPcd_FixedAtBuild_PcdArmPrimaryCore, x0) + ldrh w0, [x0] + ret + +//UINTN +//ArmPlatformIsPrimaryCore ( +// IN UINTN MpId +// ); +ASM_PFX(ArmPlatformIsPrimaryCore): + LoadConstantToReg (_gPcd_FixedAtBuild_PcdArmPrimaryCoreMask, x1) + ldrh w1, [x1] + and x0, x0, x1 + LoadConstantToReg (_gPcd_FixedAtBuild_PcdArmPrimaryCore, x1) + ldrh w1, [x1] + cmp w0, w1 + mov x0, #1 + mov x1, #0 + csel x0, x0, x1, eq + ret diff --git a/Platforms/Marvell/Armada/Library/Armada7040Lib/Armada7040Lib.c b/Platforms/Marvell/Armada/Library/Armada7040Lib/Armada7040Lib.c new file mode 100644 index 0000000..1e83afe --- /dev/null +++ b/Platforms/Marvell/Armada/Library/Armada7040Lib/Armada7040Lib.c @@ -0,0 +1,154 @@ +/** @file +* +* Copyright (c) 2011-2012, ARM Limited. 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 <Library/ArmLib.h> +#include <Library/ArmPlatformLib.h> +#include <Ppi/ArmMpCoreInfo.h> + + +ARM_CORE_INFO mArmPlatformNullMpCoreInfoTable[] = { + { + // Cluster 0, Core 0 + 0x0, 0x0, + + // MP Core MailBox Set/Get/Clear Addresses and Clear Value + (EFI_PHYSICAL_ADDRESS)0, + (EFI_PHYSICAL_ADDRESS)0, + (EFI_PHYSICAL_ADDRESS)0, + (UINT64)0xFFFFFFFF + }, + { + // Cluster 0, Core 1 + 0x0, 0x1, + + // MP Core MailBox Set/Get/Clear Addresses and Clear Value + (EFI_PHYSICAL_ADDRESS)0, + (EFI_PHYSICAL_ADDRESS)0, + (EFI_PHYSICAL_ADDRESS)0, + (UINT64)0xFFFFFFFF + }, + { + // Cluster 0, Core 2 + 0x0, 0x2, + + // MP Core MailBox Set/Get/Clear Addresses and Clear Value + (EFI_PHYSICAL_ADDRESS)0, + (EFI_PHYSICAL_ADDRESS)0, + (EFI_PHYSICAL_ADDRESS)0, + (UINT64)0xFFFFFFFF + }, + { + // Cluster 0, Core 3 + 0x0, 0x3, + + // MP Core MailBox Set/Get/Clear Addresses and Clear Value + (EFI_PHYSICAL_ADDRESS)0, + (EFI_PHYSICAL_ADDRESS)0, + (EFI_PHYSICAL_ADDRESS)0, + (UINT64)0xFFFFFFFF + } +}; + +/** + Return the current Boot Mode + + This function returns the boot reason on the platform + +**/ +EFI_BOOT_MODE +ArmPlatformGetBootMode ( + VOID + ) +{ + return BOOT_WITH_FULL_CONFIGURATION; +} + +/** + Initialize controllers that must setup in the normal world + + This function is called by the ArmPlatformPkg/PrePi or ArmPlatformPkg/PlatformPei + in the PEI phase. + +**/ +RETURN_STATUS +ArmPlatformInitialize ( + IN UINTN MpId + ) +{ + if (!ArmPlatformIsPrimaryCore (MpId)) { + return RETURN_SUCCESS; + } + + //TODO: Add basic platfrom initialization + + return RETURN_SUCCESS; +} + +/** + Initialize the system (or sometimes called permanent) memory + + This memory is generally represented by the DRAM. + +**/ +VOID +ArmPlatformInitializeSystemMemory ( + VOID + ) +{ + //TODO: Initialize DRAM controller here +} + +EFI_STATUS +PrePeiCoreGetMpCoreInfo ( + OUT UINTN *CoreCount, + OUT ARM_CORE_INFO **ArmCoreTable + ) +{ + if (ArmIsMpCore()) { + *CoreCount = sizeof(mArmPlatformNullMpCoreInfoTable) / sizeof(ARM_CORE_INFO); + *ArmCoreTable = mArmPlatformNullMpCoreInfoTable; + return EFI_SUCCESS; + } else { + return EFI_UNSUPPORTED; + } +} + +// Needs to be declared in the file. Otherwise gArmMpCoreInfoPpiGuid is undefined in the contect of PrePeiCore +EFI_GUID mArmMpCoreInfoPpiGuid = ARM_MP_CORE_INFO_PPI_GUID; +ARM_MP_CORE_INFO_PPI mMpCoreInfoPpi = { PrePeiCoreGetMpCoreInfo }; + +EFI_PEI_PPI_DESCRIPTOR gPlatformPpiTable[] = { + { + EFI_PEI_PPI_DESCRIPTOR_PPI, + &mArmMpCoreInfoPpiGuid, + &mMpCoreInfoPpi + } +}; + +VOID +ArmPlatformGetPlatformPpiList ( + OUT UINTN *PpiListSize, + OUT EFI_PEI_PPI_DESCRIPTOR **PpiList + ) +{ + if (ArmIsMpCore()) { + *PpiListSize = sizeof(gPlatformPpiTable); + *PpiList = gPlatformPpiTable; + } else { + *PpiListSize = 0; + *PpiList = NULL; + } +} + + diff --git a/Platforms/Marvell/Armada/Library/Armada7040Lib/Armada7040Lib.inf b/Platforms/Marvell/Armada/Library/Armada7040Lib/Armada7040Lib.inf new file mode 100644 index 0000000..a4a9107 --- /dev/null +++ b/Platforms/Marvell/Armada/Library/Armada7040Lib/Armada7040Lib.inf @@ -0,0 +1,45 @@ +#/* @file +# Copyright (C) Marvell International Ltd. and its affiliates +# +# 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 = Armada7040Lib + FILE_GUID = 3f29b642-4a49-4dfd-8f4a-205dd38432bb + MODULE_TYPE = BASE + VERSION_STRING = 1.0 + LIBRARY_CLASS = ArmPlatformLib + +[Packages] + MdePkg/MdePkg.dec + MdeModulePkg/MdeModulePkg.dec + ArmPkg/ArmPkg.dec + ArmPlatformPkg/ArmPlatformPkg.dec + +[LibraryClasses] + ArmLib + DebugLib + MemoryAllocationLib + +[Sources.common] + Armada7040Lib.c + Armada7040LibMem.c + +[Sources.AArch64] + AArch64/ArmPlatformHelper.S + +[FixedPcd] + gArmTokenSpaceGuid.PcdSystemMemoryBase + gArmTokenSpaceGuid.PcdSystemMemorySize + + gArmTokenSpaceGuid.PcdArmPrimaryCoreMask + gArmTokenSpaceGuid.PcdArmPrimaryCore diff --git a/Platforms/Marvell/Armada/Library/Armada7040Lib/Armada7040LibMem.c b/Platforms/Marvell/Armada/Library/Armada7040Lib/Armada7040LibMem.c new file mode 100644 index 0000000..f1c1f6c --- /dev/null +++ b/Platforms/Marvell/Armada/Library/Armada7040Lib/Armada7040LibMem.c @@ -0,0 +1,73 @@ +/** @file +* +* Copyright (C) Marvell International Ltd. and its affiliates +* +* 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 <Base.h> +#include <Library/ArmPlatformLib.h> +#include <Library/DebugLib.h> +#include <Library/MemoryAllocationLib.h> + +// The total number of descriptors, including the final "end-of-table" descriptor. +#define MAX_VIRTUAL_MEMORY_MAP_DESCRIPTORS 16 + +// DDR attributes +#define DDR_ATTRIBUTES_CACHED ARM_MEMORY_REGION_ATTRIBUTE_NONSECURE_WRITE_BACK +#define DDR_ATTRIBUTES_UNCACHED ARM_MEMORY_REGION_ATTRIBUTE_UNCACHED_UNBUFFERED + +/** + Return the Virtual Memory Map of your platform + + This Virtual Memory Map is used by MemoryInitPei Module to initialize the MMU on your platform. + + @param[out] VirtualMemoryMap Array of ARM_MEMORY_REGION_DESCRIPTOR describing a Physical-to- + Virtual Memory mapping. This array must be ended by a zero-filled + entry + +**/ +VOID +ArmPlatformGetVirtualMemoryMap ( + IN ARM_MEMORY_REGION_DESCRIPTOR** VirtualMemoryMap + ) +{ + ARM_MEMORY_REGION_DESCRIPTOR *VirtualMemoryTable; + UINTN Index = 0; + + ASSERT (VirtualMemoryMap != NULL); + + VirtualMemoryTable = (ARM_MEMORY_REGION_DESCRIPTOR*)AllocatePages(EFI_SIZE_TO_PAGES (sizeof(ARM_MEMORY_REGION_DESCRIPTOR) * MAX_VIRTUAL_MEMORY_MAP_DESCRIPTORS)); + if (VirtualMemoryTable == NULL) { + return; + } + + // DDR + VirtualMemoryTable[Index].PhysicalBase = PcdGet64 (PcdSystemMemoryBase); + VirtualMemoryTable[Index].VirtualBase = PcdGet64 (PcdSystemMemoryBase); + VirtualMemoryTable[Index].Length = PcdGet64 (PcdSystemMemorySize); + VirtualMemoryTable[Index].Attributes = DDR_ATTRIBUTES_CACHED; + + // Configuration space 0xF000_0000 - 0xFFFF_FFFF + VirtualMemoryTable[++Index].PhysicalBase = 0xF0000000; + VirtualMemoryTable[Index].VirtualBase = 0xF0000000; + VirtualMemoryTable[Index].Length = 0x10000000; + VirtualMemoryTable[Index].Attributes = ARM_MEMORY_REGION_ATTRIBUTE_DEVICE; + + // End of Table + VirtualMemoryTable[++Index].PhysicalBase = 0; + VirtualMemoryTable[Index].VirtualBase = 0; + VirtualMemoryTable[Index].Length = 0; + VirtualMemoryTable[Index].Attributes = 0; + + ASSERT((Index + 1) <= MAX_VIRTUAL_MEMORY_MAP_DESCRIPTORS); + + *VirtualMemoryMap = VirtualMemoryTable; +}
From: Yehuda Yitschak yehuday@marvell.com
This patch add initial support for Armada7040 platforms - Apn806 and Armada7040_rz. Both include Armada.dsc.inc and share common Armada7040.fdf files. Code currently supports: - GICv2 - ARM architected timer - ARM watchdog timer - UART port
Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Yehuda Yitschak yehuday@marvell.com Signed-off-by: Jan Dabros jsd@semihalf.com Signed-off-by: Marcin Wojtas mw@semihalf.com --- Platforms/Marvell/Armada/Apn806.dsc | 48 +++ Platforms/Marvell/Armada/Armada.dsc.inc | 452 +++++++++++++++++++++++++++++ Platforms/Marvell/Armada/Armada7040.fdf | 271 +++++++++++++++++ Platforms/Marvell/Armada/Armada7040_rz.dsc | 48 +++ 4 files changed, 819 insertions(+) create mode 100644 Platforms/Marvell/Armada/Apn806.dsc create mode 100644 Platforms/Marvell/Armada/Armada.dsc.inc create mode 100644 Platforms/Marvell/Armada/Armada7040.fdf create mode 100644 Platforms/Marvell/Armada/Armada7040_rz.dsc
diff --git a/Platforms/Marvell/Armada/Apn806.dsc b/Platforms/Marvell/Armada/Apn806.dsc new file mode 100644 index 0000000..62edf69 --- /dev/null +++ b/Platforms/Marvell/Armada/Apn806.dsc @@ -0,0 +1,48 @@ +#Copyright (C) 2016 Marvell International Ltd. +# +#Marvell BSD License Option +# +#If you received this File from Marvell, you may opt to use, redistribute and/or +#modify this File under the following licensing terms. +#Redistribution and use in source and binary forms, with or without modification, +#are permitted provided that the following conditions are met: +# +# * Redistributions of source code must retain the above copyright notice, +# this list of conditions and the following disclaimer. +# +# * Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# +# * Neither the name of Marvell nor the names of its contributors may be +# used to endorse or promote products derived from this software without +# specific prior written permission. +# +#THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +#ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +#WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +#DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR +#ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +#(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +#LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON +#ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +#(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +#SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +# +################################################################################ +# +# Defines Section - statements that will be processed to create a Makefile. +# +################################################################################ +[Defines] + PLATFORM_NAME = Apn806 + PLATFORM_GUID = 97b80287-f30a-4790-b1bf-c52b8a05c27c + PLATFORM_VERSION = 0.1 + DSC_SPECIFICATION = 0x00010005 + OUTPUT_DIRECTORY = Build/$(PLATFORM_NAME) + SUPPORTED_ARCHITECTURES = AARCH64 + BUILD_TARGETS = DEBUG|RELEASE + SKUID_IDENTIFIER = DEFAULT + FLASH_DEFINITION = OpenPlatformPkg/Platforms/Marvell/Armada/Armada7040.fdf + +!include Armada.dsc.inc diff --git a/Platforms/Marvell/Armada/Armada.dsc.inc b/Platforms/Marvell/Armada/Armada.dsc.inc new file mode 100644 index 0000000..027c95f --- /dev/null +++ b/Platforms/Marvell/Armada/Armada.dsc.inc @@ -0,0 +1,452 @@ +#Copyright (C) 2016 Marvell International Ltd. +# +#Marvell BSD License Option +# +#If you received this File from Marvell, you may opt to use, redistribute and/or +#modify this File under the following licensing terms. +#Redistribution and use in source and binary forms, with or without modification, +#are permitted provided that the following conditions are met: +# +# * Redistributions of source code must retain the above copyright notice, +# this list of conditions and the following disclaimer. +# +# * Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# +# * Neither the name of Marvell nor the names of its contributors may be +# used to endorse or promote products derived from this software without +# specific prior written permission. +# +#THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +#ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +#WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +#DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR +#ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +#(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +#LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON +#ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +#(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +#SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +# +[LibraryClasses.common] + ArmPlatformLib|OpenPlatformPkg/Platforms/Marvell/Armada/Library/Armada7040Lib/Armada7040Lib.inf + +!if $(TARGET) == RELEASE + DebugLib|MdePkg/Library/BaseDebugLibNull/BaseDebugLibNull.inf + UncachedMemoryAllocationLib|ArmPkg/Library/UncachedMemoryAllocationLib/UncachedMemoryAllocationLib.inf +!else + DebugLib|MdePkg/Library/BaseDebugLibSerialPort/BaseDebugLibSerialPort.inf + UncachedMemoryAllocationLib|ArmPkg/Library/UncachedMemoryAllocationLib/UncachedMemoryAllocationLib.inf +!endif + DebugPrintErrorLevelLib|MdePkg/Library/BaseDebugPrintErrorLevelLib/BaseDebugPrintErrorLevelLib.inf + +# Basic utility libraries + BaseLib|MdePkg/Library/BaseLib/BaseLib.inf + SynchronizationLib|MdePkg/Library/BaseSynchronizationLib/BaseSynchronizationLib.inf + PerformanceLib|MdePkg/Library/BasePerformanceLibNull/BasePerformanceLibNull.inf + PrintLib|MdePkg/Library/BasePrintLib/BasePrintLib.inf + PeCoffGetEntryPointLib|MdePkg/Library/BasePeCoffGetEntryPointLib/BasePeCoffGetEntryPointLib.inf + PeCoffLib|MdePkg/Library/BasePeCoffLib/BasePeCoffLib.inf + IoLib|MdePkg/Library/BaseIoLibIntrinsic/BaseIoLibIntrinsic.inf + UefiDecompressLib|MdePkg/Library/BaseUefiDecompressLib/BaseUefiDecompressLib.inf + CpuLib|MdePkg/Library/BaseCpuLib/BaseCpuLib.inf + PciLib|MdePkg/Library/BasePciLibCf8/BasePciLibCf8.inf + PciCf8Lib|MdePkg/Library/BasePciCf8Lib/BasePciCf8Lib.inf + +# Basic UEFI services libraries + UefiLib|MdePkg/Library/UefiLib/UefiLib.inf + HobLib|MdePkg/Library/DxeHobLib/DxeHobLib.inf + UefiRuntimeServicesTableLib|MdePkg/Library/UefiRuntimeServicesTableLib/UefiRuntimeServicesTableLib.inf + DevicePathLib|MdePkg/Library/UefiDevicePathLib/UefiDevicePathLib.inf + UefiBootServicesTableLib|MdePkg/Library/UefiBootServicesTableLib/UefiBootServicesTableLib.inf + DxeServicesTableLib|MdePkg/Library/DxeServicesTableLib/DxeServicesTableLib.inf + UefiDriverEntryPoint|MdePkg/Library/UefiDriverEntryPoint/UefiDriverEntryPoint.inf + UefiApplicationEntryPoint|MdePkg/Library/UefiApplicationEntryPoint/UefiApplicationEntryPoint.inf + HiiLib|MdeModulePkg/Library/UefiHiiLib/UefiHiiLib.inf + UefiHiiServicesLib|MdeModulePkg/Library/UefiHiiServicesLib/UefiHiiServicesLib.inf + UefiRuntimeLib|MdePkg/Library/UefiRuntimeLib/UefiRuntimeLib.inf + + # Assume everything is fixed at build. do not use runtime PCD feature + PcdLib|MdePkg/Library/BasePcdLibNull/BasePcdLibNull.inf + + # 1/123 faster than Stm or Vstm version + #BaseMemoryLib|MdePkg/Library/BaseMemoryLib/BaseMemoryLib.inf + BaseMemoryLib|ArmPkg/Library/BaseMemoryLibStm/BaseMemoryLibStm.inf + + # ARM Architectural Libraries + CacheMaintenanceLib|ArmPkg/Library/ArmCacheMaintenanceLib/ArmCacheMaintenanceLib.inf + DefaultExceptionHandlerLib|ArmPkg/Library/DefaultExceptionHandlerLib/DefaultExceptionHandlerLib.inf + CpuExceptionHandlerLib|ArmPkg/Library/ArmExceptionLib/ArmExceptionLib.inf + ArmDisassemblerLib|ArmPkg/Library/ArmDisassemblerLib/ArmDisassemblerLib.inf + DmaLib|ArmPkg/Library/ArmDmaLib/ArmDmaLib.inf + ArmGicLib|ArmPkg/Drivers/ArmGic/ArmGicLib.inf + ArmGicArchLib|ArmPkg/Library/ArmGicArchLib/ArmGicArchLib.inf + ArmPlatformStackLib|ArmPlatformPkg/Library/ArmPlatformStackLib/ArmPlatformStackLib.inf + ArmSmcLib|ArmPkg/Library/ArmSmcLib/ArmSmcLib.inf + TimerLib|ArmPkg/Library/ArmArchTimerLib/ArmArchTimerLib.inf + + # Serial port libraries + SerialPortLib|MdeModulePkg/Library/BaseSerialPortLib16550/BaseSerialPortLib16550.inf + PlatformHookLib|MdeModulePkg/Library/BasePlatformHookLibNull/BasePlatformHookLibNull.inf + + # Reset and Time libraries + EfiResetSystemLib|EmbeddedPkg/Library/TemplateResetSystemLib/TemplateResetSystemLib.inf + RealTimeClockLib|EmbeddedPkg/Library/TemplateRealTimeClockLib/TemplateRealTimeClockLib.inf + + # Networking Requirements for ArmPlatformPkg/Bds + NetLib|MdeModulePkg/Library/DxeNetLib/DxeNetLib.inf + + # These libraries are used by the dynamic EFI Shell commands + ShellLib|ShellPkg/Library/UefiShellLib/UefiShellLib.inf + FileHandleLib|MdePkg/Library/UefiFileHandleLib/UefiFileHandleLib.inf + SortLib|MdeModulePkg/Library/UefiSortLib/UefiSortLib.inf + + # EBL Related Libraries + EblCmdLib|ArmPlatformPkg/Library/EblCmdLib/EblCmdLib.inf + EfiFileLib|EmbeddedPkg/Library/EfiFileLib/EfiFileLib.inf + EblAddExternalCommandLib|EmbeddedPkg/Library/EblAddExternalCommandLib/EblAddExternalCommandLib.inf + EblNetworkLib|EmbeddedPkg/Library/EblNetworkLib/EblNetworkLib.inf + + # + # Uncomment (and comment out the next line) For RealView Debugger. The Standard IO window + # in the debugger will show load and unload commands for symbols. You can cut and paste this + # into the command window to load symbols. We should be able to use a script to do this, but + # the version of RVD I have does not support scripts accessing system memory. + # + #PeCoffExtraActionLib|ArmPkg/Library/RvdPeCoffExtraActionLib/RvdPeCoffExtraActionLib.inf + PeCoffExtraActionLib|ArmPkg/Library/DebugPeCoffExtraActionLib/DebugPeCoffExtraActionLib.inf + #PeCoffExtraActionLib|MdePkg/Library/BasePeCoffExtraActionLibNull/BasePeCoffExtraActionLibNull.inf + + DebugAgentLib|MdeModulePkg/Library/DebugAgentLibNull/DebugAgentLibNull.inf + DebugAgentTimerLib|EmbeddedPkg/Library/DebugAgentTimerLibNull/DebugAgentTimerLibNull.inf + # SemihostLib|ArmPkg/Library/SemihostLib/SemihostLib.inf + + # BDS Libraries + BdsLib|ArmPkg/Library/BdsLib/BdsLib.inf + CapsuleLib|MdeModulePkg/Library/DxeCapsuleLibNull/DxeCapsuleLibNull.inf + GenericBdsLib|IntelFrameworkModulePkg/Library/GenericBdsLib/GenericBdsLib.inf + PlatformBdsLib|ArmPlatformPkg/Library/PlatformIntelBdsLib/PlatformIntelBdsLib.inf + CustomizedDisplayLib|MdeModulePkg/Library/CustomizedDisplayLib/CustomizedDisplayLib.inf + FdtLib|EmbeddedPkg/Library/FdtLib/FdtLib.inf + +[LibraryClasses.AARCH64] + ArmLib|ArmPkg/Library/ArmLib/AArch64/AArch64Lib.inf + ArmCpuLib|ArmPkg/Drivers/ArmCpuLib/ArmCortexAEMv8Lib/ArmCortexAEMv8Lib.inf + ArmGenericTimerCounterLib|ArmPkg/Library/ArmGenericTimerPhyCounterLib/ArmGenericTimerPhyCounterLib.inf + +[LibraryClasses.common.SEC] + ArmLib|ArmPkg/Library/ArmLib/AArch64/AArch64LibSec.inf + + DebugAgentLib|ArmPkg/Library/DebugAgentSymbolsBaseLib/DebugAgentSymbolsBaseLib.inf + DefaultExceptionHandlerLib|ArmPkg/Library/DefaultExceptionHandlerLib/DefaultExceptionHandlerLibBase.inf + + PrePiLib|EmbeddedPkg/Library/PrePiLib/PrePiLib.inf + ExtractGuidedSectionLib|EmbeddedPkg/Library/PrePiExtractGuidedSectionLib/PrePiExtractGuidedSectionLib.inf + LzmaDecompressLib|MdeModulePkg/Library/LzmaCustomDecompressLib/LzmaCustomDecompressLib.inf + MemoryAllocationLib|EmbeddedPkg/Library/PrePiMemoryAllocationLib/PrePiMemoryAllocationLib.inf + HobLib|EmbeddedPkg/Library/PrePiHobLib/PrePiHobLib.inf + PrePiHobListPointerLib|ArmPlatformPkg/Library/PrePiHobListPointerLib/PrePiHobListPointerLib.inf + PlatformPeiLib|ArmPlatformPkg/PlatformPei/PlatformPeiLib.inf + ArmGicArchLib|ArmPkg/Library/ArmGicArchSecLib/ArmGicArchSecLib.inf + +[LibraryClasses.common.SEC, LibraryClasses.common.PEIM] + MemoryInitPeiLib|ArmPlatformPkg/MemoryInitPei/MemoryInitPeiLib.inf + +[LibraryClasses.common.DXE_CORE] + HobLib|MdePkg/Library/DxeCoreHobLib/DxeCoreHobLib.inf + MemoryAllocationLib|MdeModulePkg/Library/DxeCoreMemoryAllocationLib/DxeCoreMemoryAllocationLib.inf + DxeCoreEntryPoint|MdePkg/Library/DxeCoreEntryPoint/DxeCoreEntryPoint.inf + ReportStatusCodeLib|IntelFrameworkModulePkg/Library/DxeReportStatusCodeLibFramework/DxeReportStatusCodeLib.inf + ExtractGuidedSectionLib|MdePkg/Library/DxeExtractGuidedSectionLib/DxeExtractGuidedSectionLib.inf + UefiDecompressLib|MdePkg/Library/BaseUefiDecompressLib/BaseUefiDecompressLib.inf + DxeServicesLib|MdePkg/Library/DxeServicesLib/DxeServicesLib.inf + PerformanceLib|MdeModulePkg/Library/DxeCorePerformanceLib/DxeCorePerformanceLib.inf + +[LibraryClasses.common.DXE_DRIVER] + ReportStatusCodeLib|IntelFrameworkModulePkg/Library/DxeReportStatusCodeLibFramework/DxeReportStatusCodeLib.inf + DxeServicesLib|MdePkg/Library/DxeServicesLib/DxeServicesLib.inf + SecurityManagementLib|MdeModulePkg/Library/DxeSecurityManagementLib/DxeSecurityManagementLib.inf + PerformanceLib|MdeModulePkg/Library/DxePerformanceLib/DxePerformanceLib.inf + MemoryAllocationLib|MdePkg/Library/UefiMemoryAllocationLib/UefiMemoryAllocationLib.inf + +[LibraryClasses.common.UEFI_APPLICATION] + UefiDecompressLib|IntelFrameworkModulePkg/Library/BaseUefiTianoCustomDecompressLib/BaseUefiTianoCustomDecompressLib.inf + PerformanceLib|MdeModulePkg/Library/DxePerformanceLib/DxePerformanceLib.inf + MemoryAllocationLib|MdePkg/Library/UefiMemoryAllocationLib/UefiMemoryAllocationLib.inf + HiiLib|MdeModulePkg/Library/UefiHiiLib/UefiHiiLib.inf + +[LibraryClasses.common.UEFI_DRIVER] + ReportStatusCodeLib|IntelFrameworkModulePkg/Library/DxeReportStatusCodeLibFramework/DxeReportStatusCodeLib.inf + UefiDecompressLib|IntelFrameworkModulePkg/Library/BaseUefiTianoCustomDecompressLib/BaseUefiTianoCustomDecompressLib.inf + ExtractGuidedSectionLib|MdePkg/Library/DxeExtractGuidedSectionLib/DxeExtractGuidedSectionLib.inf + PerformanceLib|MdeModulePkg/Library/DxePerformanceLib/DxePerformanceLib.inf + MemoryAllocationLib|MdePkg/Library/UefiMemoryAllocationLib/UefiMemoryAllocationLib.inf + +[LibraryClasses.common.DXE_RUNTIME_DRIVER] + HobLib|MdePkg/Library/DxeHobLib/DxeHobLib.inf + MemoryAllocationLib|MdePkg/Library/UefiMemoryAllocationLib/UefiMemoryAllocationLib.inf + ReportStatusCodeLib|IntelFrameworkModulePkg/Library/DxeReportStatusCodeLibFramework/DxeReportStatusCodeLib.inf + CapsuleLib|MdeModulePkg/Library/DxeCapsuleLibNull/DxeCapsuleLibNull.inf + +[LibraryClasses.ARM, LibraryClasses.AARCH64] + # + # It is not possible to prevent the ARM compiler for generic intrinsic functions. + # This library provides the instrinsic functions generate by a given compiler. + # [LibraryClasses.ARM] and NULL mean link this library into all ARM images. + # + NULL|ArmPkg/Library/CompilerIntrinsicsLib/CompilerIntrinsicsLib.inf + + # Add support for GCC stack protector + NULL|MdePkg/Library/BaseStackCheckLib/BaseStackCheckLib.inf + +[BuildOptions] + XCODE:*_*_ARM_PLATFORM_FLAGS == -arch armv7 + + GCC:*_*_ARM_PLATFORM_FLAGS == -march=armv7-a + + RVCT:*_*_ARM_PLATFORM_FLAGS == --cpu Cortex-A8 + +################################################################################ +# +# Pcd Section - list of all EDK II PCD Entries defined by this Platform +# +################################################################################ + +[PcdsFeatureFlag.common] + gEfiMdePkgTokenSpaceGuid.PcdComponentNameDisable|TRUE + gEfiMdePkgTokenSpaceGuid.PcdDriverDiagnosticsDisable|TRUE + gEfiMdePkgTokenSpaceGuid.PcdComponentName2Disable|TRUE + gEfiMdePkgTokenSpaceGuid.PcdDriverDiagnostics2Disable|TRUE + + # + # Control what commands are supported from the UI + # Turn these on and off to add features or save size + # + gEmbeddedTokenSpaceGuid.PcdEmbeddedMacBoot|TRUE + gEmbeddedTokenSpaceGuid.PcdEmbeddedDirCmd|TRUE + gEmbeddedTokenSpaceGuid.PcdEmbeddedHobCmd|TRUE + gEmbeddedTokenSpaceGuid.PcdEmbeddedHwDebugCmd|TRUE + gEmbeddedTokenSpaceGuid.PcdEmbeddedPciDebugCmd|TRUE + gEmbeddedTokenSpaceGuid.PcdEmbeddedIoEnable|FALSE + gEmbeddedTokenSpaceGuid.PcdEmbeddedScriptCmd|FALSE + + gEmbeddedTokenSpaceGuid.PcdCacheEnable|TRUE + + # Use the Vector Table location in CpuDxe. + # We will not copy the Vector Table at PcdCpuVectorBaseAddress + gArmTokenSpaceGuid.PcdRelocateVectorTable|FALSE + + gEmbeddedTokenSpaceGuid.PcdPrePiProduceMemoryTypeInformationHob|TRUE + + # If TRUE, Graphics Output Protocol will be installed on virtual + # handle created by ConsplitterDxe. It could be set FALSE to save size. + gEfiMdeModulePkgTokenSpaceGuid.PcdConOutGopSupport|TRUE + gEfiMdeModulePkgTokenSpaceGuid.PcdConOutUgaSupport|FALSE + + # USB support + gEfiMdeModulePkgTokenSpaceGuid.PcdTurnOffUsbLegacySupport|TRUE + +[PcdsFixedAtBuild.common] + gArmPlatformTokenSpaceGuid.PcdFirmwareVendor|"Marvell" +!ifdef $(FIRMWARE_VER) + gEfiMdeModulePkgTokenSpaceGuid.PcdFirmwareVersionString|L"$(FIRMWARE_VER)" +!endif + gArmPlatformTokenSpaceGuid.PcdCoreCount|4 + # gArmPlatformTokenSpaceGuid.PcdClusterCount|1 + + ## Use the serial console (ConIn & ConOut) and the Graphic driver (ConOut) + gArmPlatformTokenSpaceGuid.PcdDefaultConOutPaths|L"VenHw(D3987D4B-971A-435F-8CAF-4967EB627241)/Uart(115200,8,N,1)/VenPcAnsi()" + gArmPlatformTokenSpaceGuid.PcdDefaultConInPaths|L"VenHw(D3987D4B-971A-435F-8CAF-4967EB627241)/Uart(115200,8,N,1)/VenPcAnsi()" + + gEmbeddedTokenSpaceGuid.PcdEmbeddedPrompt|"Marvell>> " + gEfiMdePkgTokenSpaceGuid.PcdMaximumUnicodeStringLength|1000000 + gEfiMdePkgTokenSpaceGuid.PcdMaximumAsciiStringLength|1000000 + gEfiMdePkgTokenSpaceGuid.PcdMaximumLinkedListLength|1000000 + gEfiMdePkgTokenSpaceGuid.PcdSpinLockTimeout|10000000 + gEfiMdePkgTokenSpaceGuid.PcdDebugClearMemoryValue|0xAF + gEfiMdePkgTokenSpaceGuid.PcdPerformanceLibraryPropertyMask|1 + gEfiMdePkgTokenSpaceGuid.PcdPostCodePropertyMask|0 + gEfiMdePkgTokenSpaceGuid.PcdUefiLibMaxPrintBufferSize|320 + gEfiMdePkgTokenSpaceGuid.PcdDefaultTerminalType|1 + gEfiMdePkgTokenSpaceGuid.PcdPlatformBootTimeOut|3 + + # Required for Intel BDS + gEfiMdeModulePkgTokenSpaceGuid.PcdResetOnMemoryTypeInformationChange|FALSE + gEfiIntelFrameworkModulePkgTokenSpaceGuid.PcdShellFile|{ 0x83, 0xA5, 0x04, 0x7C, 0x3E, 0x9E, 0x1C, 0x4F, 0xAD, 0x65, 0xE0, 0x52, 0x68, 0xD0, 0xB4, 0xD1 } + + ## Trustzone enable (to make the transition from EL3 to NS EL2 in ArmPlatformPkg/Sec) + gArmTokenSpaceGuid.PcdTrustzoneSupport|TRUE + + # ARM Generic Interrupt Controller + gArmTokenSpaceGuid.PcdGicDistributorBase|0xF0210000 + gArmTokenSpaceGuid.PcdGicInterruptInterfaceBase|0xF0220000 + + # ARM Architectural Timer Support + gArmTokenSpaceGuid.PcdArmArchTimerFreqInHz|25000000 + gEmbeddedTokenSpaceGuid.PcdMetronomeTickPeriod|1000 + + # ARM SBSA Watchdog + gArmTokenSpaceGuid.PcdGenericWatchdogControlBase|0xF0620000 + gArmTokenSpaceGuid.PcdGenericWatchdogRefreshBase|0xF0600000 + gArmTokenSpaceGuid.PcdGenericWatchdogEl2IntrNum|34 + + # Serial + gEfiMdeModulePkgTokenSpaceGuid.PcdSerialUseMmio|TRUE + gEfiMdeModulePkgTokenSpaceGuid.PcdSerialUseHardwareFlowControl|FALSE + gEfiMdeModulePkgTokenSpaceGuid.PcdSerialRegisterBase|0xF0512000 + gEfiMdeModulePkgTokenSpaceGuid.PcdSerialBaudRate|115200 + gEfiMdeModulePkgTokenSpaceGuid.PcdSerialClockRate|200000000 + gEfiMdeModulePkgTokenSpaceGuid.PcdSerialRegisterStride|4 + + # DEBUG_ASSERT_ENABLED 0x01 + # DEBUG_PRINT_ENABLED 0x02 + # DEBUG_CODE_ENABLED 0x04 + # CLEAR_MEMORY_ENABLED 0x08 + # ASSERT_BREAKPOINT_ENABLED 0x10 + # ASSERT_DEADLOOP_ENABLED 0x20 +!if $(TARGET) == RELEASE + gEfiMdePkgTokenSpaceGuid.PcdDebugPropertyMask|0x21 +!else + gEfiMdePkgTokenSpaceGuid.PcdDebugPropertyMask|0x2f +!endif + + # DEBUG_INIT 0x00000001 // Initialization + # DEBUG_WARN 0x00000002 // Warnings + # DEBUG_LOAD 0x00000004 // Load events + # DEBUG_FS 0x00000008 // EFI File system + # DEBUG_POOL 0x00000010 // Alloc & Free's + # DEBUG_PAGE 0x00000020 // Alloc & Free's + # DEBUG_INFO 0x00000040 // Verbose + # DEBUG_DISPATCH 0x00000080 // PEI/DXE Dispatchers + # DEBUG_VARIABLE 0x00000100 // Variable + # DEBUG_BM 0x00000400 // Boot Manager + # DEBUG_BLKIO 0x00001000 // BlkIo Driver + # DEBUG_NET 0x00004000 // SNI Driver + # DEBUG_UNDI 0x00010000 // UNDI Driver + # DEBUG_LOADFILE 0x00020000 // UNDI Driver + # DEBUG_EVENT 0x00080000 // Event messages + # DEBUG_ERROR 0x80000000 // Error + gEfiMdePkgTokenSpaceGuid.PcdDebugPrintErrorLevel|0x8000000F + gEfiMdePkgTokenSpaceGuid.PcdReportStatusCodePropertyMask|0x07 + + gEmbeddedTokenSpaceGuid.PcdEmbeddedAutomaticBootCommand|"" + gEmbeddedTokenSpaceGuid.PcdEmbeddedDefaultTextColor|0x07 + gEmbeddedTokenSpaceGuid.PcdEmbeddedMemVariableStoreSize|0x10000 + + # + # Optional feature to help prevent EFI memory map fragments + # Turned on and off via: PcdPrePiProduceMemoryTypeInformationHob + # Values are in EFI Pages (4K). DXE Core will make sure that + # at least this much of each type of memory can be allocated + # from a single memory range. This way you only end up with + # maximum of two fragements for each type in the memory map + # (the memory used, and the free memory that was prereserved + # but not used). + # + gEmbeddedTokenSpaceGuid.PcdMemoryTypeEfiACPIReclaimMemory|0 + gEmbeddedTokenSpaceGuid.PcdMemoryTypeEfiACPIMemoryNVS|0 + gEmbeddedTokenSpaceGuid.PcdMemoryTypeEfiReservedMemoryType|0 + gEmbeddedTokenSpaceGuid.PcdMemoryTypeEfiRuntimeServicesData|50 + gEmbeddedTokenSpaceGuid.PcdMemoryTypeEfiRuntimeServicesCode|20 + gEmbeddedTokenSpaceGuid.PcdMemoryTypeEfiBootServicesCode|400 + gEmbeddedTokenSpaceGuid.PcdMemoryTypeEfiBootServicesData|20000 + gEmbeddedTokenSpaceGuid.PcdMemoryTypeEfiLoaderCode|20 + gEmbeddedTokenSpaceGuid.PcdMemoryTypeEfiLoaderData|0 + + # We want to use the Shell Libraries but don't want it to initialise + # automatically. We initialise the libraries when the command is called by the + # Shell. + gEfiShellPkgTokenSpaceGuid.PcdShellLibAutoInitialize|FALSE + + # ARM Pcds + gArmTokenSpaceGuid.PcdArmUncachedMemoryMask|0x0000000000000000 + gArmTokenSpaceGuid.PcdSystemMemoryBase|0 + gArmTokenSpaceGuid.PcdSystemMemorySize|0x40000000 + gArmTokenSpaceGuid.PcdArmScr|0x531 + +################################################################################ +# +# Components Section - list of all EDK II Modules needed by this Platform +# +################################################################################ +[Components.common] + + # PEI Phase modules + ArmPlatformPkg/PrePi/PeiMPCore.inf + + # DXE + MdeModulePkg/Core/Dxe/DxeMain.inf { + <LibraryClasses> + PcdLib|MdePkg/Library/BasePcdLibNull/BasePcdLibNull.inf + NULL|MdeModulePkg/Library/DxeCrc32GuidedSectionExtractLib/DxeCrc32GuidedSectionExtractLib.inf + } + + # Architectural Protocols DXE + ArmPkg/Drivers/CpuDxe/CpuDxe.inf + ArmPkg/Drivers/ArmGic/ArmGicDxe.inf + ArmPkg/Drivers/TimerDxe/TimerDxe.inf + ArmPkg/Drivers/GenericWatchdogDxe/GenericWatchdogDxe.inf + + MdeModulePkg/Core/RuntimeDxe/RuntimeDxe.inf + MdeModulePkg/Universal/SecurityStubDxe/SecurityStubDxe.inf + MdeModulePkg/Universal/CapsuleRuntimeDxe/CapsuleRuntimeDxe.inf + MdeModulePkg/Universal/Variable/EmuRuntimeDxe/EmuVariableRuntimeDxe.inf + + EmbeddedPkg/EmbeddedMonotonicCounter/EmbeddedMonotonicCounter.inf + EmbeddedPkg/ResetRuntimeDxe/ResetRuntimeDxe.inf + EmbeddedPkg/RealTimeClockRuntimeDxe/RealTimeClockRuntimeDxe.inf + EmbeddedPkg/MetronomeDxe/MetronomeDxe.inf + + # Console packages + MdeModulePkg/Universal/Console/ConPlatformDxe/ConPlatformDxe.inf + MdeModulePkg/Universal/Console/ConSplitterDxe/ConSplitterDxe.inf + MdeModulePkg/Universal/Console/GraphicsConsoleDxe/GraphicsConsoleDxe.inf + MdeModulePkg/Universal/Console/TerminalDxe/TerminalDxe.inf + MdeModulePkg/Universal/SerialDxe/SerialDxe.inf + + # Simple TextIn/TextOut for UEFI Terminal + #EmbeddedPkg/SimpleTextInOutSerial/SimpleTextInOutSerial.inf + + # Human interface: + MdeModulePkg/Universal/HiiDatabaseDxe/HiiDatabaseDxe.inf + + # FAT filesystem + GPT/MBR partitioning + MdeModulePkg/Universal/Disk/DiskIoDxe/DiskIoDxe.inf + MdeModulePkg/Universal/Disk/PartitionDxe/PartitionDxe.inf + MdeModulePkg/Universal/Disk/UnicodeCollation/EnglishDxe/EnglishDxe.inf + + # Application + EmbeddedPkg/Ebl/Ebl.inf + + # Bds - Use Intel BDS + MdeModulePkg/Universal/DevicePathDxe/DevicePathDxe.inf + MdeModulePkg/Universal/DisplayEngineDxe/DisplayEngineDxe.inf + MdeModulePkg/Universal/SetupBrowserDxe/SetupBrowserDxe.inf + IntelFrameworkModulePkg/Universal/BdsDxe/BdsDxe.inf + #ArmPlatformPkg/Bds/Bds.inf + + # Legacy Linux Loader + ArmPkg/Application/LinuxLoader/LinuxLoader.inf + + # UEFI application (Shell Embedded Boot Loader) + ShellPkg/Application/Shell/Shell.inf { + <LibraryClasses> + ShellCommandLib|ShellPkg/Library/UefiShellCommandLib/UefiShellCommandLib.inf + NULL|ShellPkg/Library/UefiShellLevel2CommandsLib/UefiShellLevel2CommandsLib.inf + NULL|ShellPkg/Library/UefiShellLevel1CommandsLib/UefiShellLevel1CommandsLib.inf + NULL|ShellPkg/Library/UefiShellLevel3CommandsLib/UefiShellLevel3CommandsLib.inf + NULL|ShellPkg/Library/UefiShellDriver1CommandsLib/UefiShellDriver1CommandsLib.inf + NULL|ShellPkg/Library/UefiShellDebug1CommandsLib/UefiShellDebug1CommandsLib.inf + NULL|ShellPkg/Library/UefiShellInstall1CommandsLib/UefiShellInstall1CommandsLib.inf + NULL|ShellPkg/Library/UefiShellNetwork1CommandsLib/UefiShellNetwork1CommandsLib.inf + NULL|ShellPkg/Library/UefiShellTftpCommandLib/UefiShellTftpCommandLib.inf + HandleParsingLib|ShellPkg/Library/UefiHandleParsingLib/UefiHandleParsingLib.inf + PrintLib|MdePkg/Library/BasePrintLib/BasePrintLib.inf + BcfgCommandLib|ShellPkg/Library/UefiShellBcfgCommandLib/UefiShellBcfgCommandLib.inf + + <PcdsFixedAtBuild> + gEfiMdePkgTokenSpaceGuid.PcdDebugPropertyMask|0xFF + gEfiShellPkgTokenSpaceGuid.PcdShellLibAutoInitialize|FALSE + gEfiMdePkgTokenSpaceGuid.PcdUefiLibMaxPrintBufferSize|8000 + } diff --git a/Platforms/Marvell/Armada/Armada7040.fdf b/Platforms/Marvell/Armada/Armada7040.fdf new file mode 100644 index 0000000..f1aa722 --- /dev/null +++ b/Platforms/Marvell/Armada/Armada7040.fdf @@ -0,0 +1,271 @@ +# +# Copyright (C) Marvell International Ltd. and its affiliates +# +# 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. +# + +################################################################################ +# +# FD Section +# The [FD] Section is made up of the definition statements and a +# description of what goes into the Flash Device Image. Each FD section +# defines one flash "device" image. A flash device image may be one of +# the following: Removable media bootable image (like a boot floppy +# image,) an Option ROM image (that would be "flashed" into an add-in +# card,) a System "Flash" image (that would be burned into a system's +# flash) or an Update ("Capsule") image that will be used to update and +# existing system flash. +# +################################################################################ + +[FD.Armada7040_EFI] +BaseAddress = 0x00000000|gArmTokenSpaceGuid.PcdFdBaseAddress # The base address of the Firmware in NOR Flash. +Size = 0x00400000|gArmTokenSpaceGuid.PcdFdSize # The size in bytes of the FLASH Device +ErasePolarity = 1 + +# This one is tricky, it must be: BlockSize * NumBlocks = Size +BlockSize = 0x00001000 +NumBlocks = 0x400 + +################################################################################ +# +# Following are lists of FD Region layout which correspond to the locations of different +# images within the flash device. +# +# Regions must be defined in ascending order and may not overlap. +# +# A Layout Region start with a eight digit hex offset (leading "0x" required) followed by +# the pipe "|" character, followed by the size of the region, also in hex with the leading +# "0x" characters. Like: +# Offset|Size +# PcdOffsetCName|PcdSizeCName +# RegionType <FV, DATA, or FILE> +# +################################################################################ + +0x00000000|0x00400000 +gArmTokenSpaceGuid.PcdFvBaseAddress|gArmTokenSpaceGuid.PcdFvSize +FV = FVMAIN_COMPACT + + +################################################################################ +# +# FV Section +# +# [FV] section is used to define what components or modules are placed within a flash +# device file. This section also defines order the components and modules are positioned +# within the image. The [FV] section consists of define statements, set statements and +# module statements. +# +################################################################################ + +# DXE phase firmware volume +[FV.FvMain] +BlockSize = 0x40 +NumBlocks = 0 # This FV gets compressed so make it just big enough +FvAlignment = 8 # FV alignment and FV attributes setting. +ERASE_POLARITY = 1 +MEMORY_MAPPED = TRUE +STICKY_WRITE = TRUE +LOCK_CAP = TRUE +LOCK_STATUS = TRUE +WRITE_DISABLED_CAP = TRUE +WRITE_ENABLED_CAP = TRUE +WRITE_STATUS = TRUE +WRITE_LOCK_CAP = TRUE +WRITE_LOCK_STATUS = TRUE +READ_DISABLED_CAP = TRUE +READ_ENABLED_CAP = TRUE +READ_STATUS = TRUE +READ_LOCK_CAP = TRUE +READ_LOCK_STATUS = TRUE +FvNameGuid = 5eda4200-2c5f-43cb-9da3-0baf74b1b30c + + INF MdeModulePkg/Core/Dxe/DxeMain.inf + + # PI DXE Drivers producing Architectural Protocols (EFI Services) + INF ArmPkg/Drivers/CpuDxe/CpuDxe.inf + INF ArmPkg/Drivers/ArmGic/ArmGicDxe.inf + INF ArmPkg/Drivers/TimerDxe/TimerDxe.inf + INF ArmPkg/Drivers/GenericWatchdogDxe/GenericWatchdogDxe.inf + INF MdeModulePkg/Core/RuntimeDxe/RuntimeDxe.inf + INF MdeModulePkg/Universal/SecurityStubDxe/SecurityStubDxe.inf + INF MdeModulePkg/Universal/CapsuleRuntimeDxe/CapsuleRuntimeDxe.inf + INF MdeModulePkg/Universal/Variable/EmuRuntimeDxe/EmuVariableRuntimeDxe.inf + INF EmbeddedPkg/EmbeddedMonotonicCounter/EmbeddedMonotonicCounter.inf + INF EmbeddedPkg/ResetRuntimeDxe/ResetRuntimeDxe.inf + INF EmbeddedPkg/RealTimeClockRuntimeDxe/RealTimeClockRuntimeDxe.inf + INF EmbeddedPkg/MetronomeDxe/MetronomeDxe.inf + + # Multiple Console IO support + INF MdeModulePkg/Universal/Console/ConPlatformDxe/ConPlatformDxe.inf + INF MdeModulePkg/Universal/Console/ConSplitterDxe/ConSplitterDxe.inf + INF MdeModulePkg/Universal/Console/GraphicsConsoleDxe/GraphicsConsoleDxe.inf + INF MdeModulePkg/Universal/Console/TerminalDxe/TerminalDxe.inf + INF MdeModulePkg/Universal/SerialDxe/SerialDxe.inf + + # Simple TextIn/TextOut for UEFI Terminal + #INF EmbeddedPkg/SimpleTextInOutSerial/SimpleTextInOutSerial.inf + + # Human interface + INF MdeModulePkg/Universal/HiiDatabaseDxe/HiiDatabaseDxe.inf + + # FAT filesystem + GPT/MBR partitioning + INF MdeModulePkg/Universal/Disk/DiskIoDxe/DiskIoDxe.inf + INF MdeModulePkg/Universal/Disk/PartitionDxe/PartitionDxe.inf + INF FatBinPkg/EnhancedFatDxe/Fat.inf + INF MdeModulePkg/Universal/Disk/UnicodeCollation/EnglishDxe/EnglishDxe.inf + + # UEFI application (Shell Embedded Boot Loader) + INF EmbeddedPkg/Ebl/Ebl.inf + + # UEFI application (Shell Embedded Boot Loader) + INF ShellPkg/Application/Shell/Shell.inf + + # Bds + INF MdeModulePkg/Universal/DevicePathDxe/DevicePathDxe.inf + INF MdeModulePkg/Universal/DisplayEngineDxe/DisplayEngineDxe.inf + INF MdeModulePkg/Universal/SetupBrowserDxe/SetupBrowserDxe.inf + INF IntelFrameworkModulePkg/Universal/BdsDxe/BdsDxe.inf + #INF ArmPlatformPkg/Bds/Bds.inf + + # Legacy Linux Loader + INF ArmPkg/Application/LinuxLoader/LinuxLoader.inf + + +# PEI phase firmware volume +[FV.FVMAIN_COMPACT] +FvAlignment = 8 +FvForceRebase = TRUE +ERASE_POLARITY = 1 +MEMORY_MAPPED = TRUE +STICKY_WRITE = TRUE +LOCK_CAP = TRUE +LOCK_STATUS = TRUE +WRITE_DISABLED_CAP = TRUE +WRITE_ENABLED_CAP = TRUE +WRITE_STATUS = TRUE +WRITE_LOCK_CAP = TRUE +WRITE_LOCK_STATUS = TRUE +READ_DISABLED_CAP = TRUE +READ_ENABLED_CAP = TRUE +READ_STATUS = TRUE +READ_LOCK_CAP = TRUE +READ_LOCK_STATUS = TRUE + + INF ArmPlatformPkg/PrePi/PeiMPCore.inf + + FILE FV_IMAGE = 9E21FD93-9C72-4c15-8C4B-E77F1DB2D792 { + SECTION GUIDED EE4E5898-3914-4259-9D6E-DC7BD79403CF PROCESSING_REQUIRED = TRUE { + SECTION FV_IMAGE = FVMAIN + } + } + +################################################################################ +# +# Rules are use with the [FV] section's module INF type to define +# how an FFS file is created for a given INF file. The following Rule are the default +# rules for the different module type. User can add the customized rules to define the +# content of the FFS file. +# +################################################################################ + + +############################################################################ +# Example of a DXE_DRIVER FFS file with a Checksum encapsulation section # +############################################################################ +# +#[Rule.Common.DXE_DRIVER] +# FILE DRIVER = $(NAMED_GUID) { +# DXE_DEPEX DXE_DEPEX Optional $(INF_OUTPUT)/$(MODULE_NAME).depex +# COMPRESS PI_STD { +# GUIDED { +# PE32 PE32 $(INF_OUTPUT)/$(MODULE_NAME).efi +# UI STRING="$(MODULE_NAME)" Optional +# VERSION STRING="$(INF_VERSION)" Optional BUILD_NUM=$(BUILD_NUMBER) +# } +# } +# } +# +############################################################################ + +[Rule.ARM.SEC] + FILE SEC = $(NAMED_GUID) RELOCS_STRIPPED { + TE TE Align = 32 $(INF_OUTPUT)/$(MODULE_NAME).efi + } + +# The AArch64 Vector Table requires a 2K alignment that is not supported by the FDF specification. +# It is the reason 4K is used instead of 2K for the module alignment. +[Rule.AARCH64.SEC] + FILE SEC = $(NAMED_GUID) RELOCS_STRIPPED { + TE TE Align = 4K $(INF_OUTPUT)/$(MODULE_NAME).efi + } + +[Rule.Common.PEI_CORE] + FILE PEI_CORE = $(NAMED_GUID) { + TE TE $(INF_OUTPUT)/$(MODULE_NAME).efi + UI STRING ="$(MODULE_NAME)" Optional + } + +[Rule.Common.PEIM] + FILE PEIM = $(NAMED_GUID) { + PEI_DEPEX PEI_DEPEX Optional $(INF_OUTPUT)/$(MODULE_NAME).depex + TE TE $(INF_OUTPUT)/$(MODULE_NAME).efi + UI STRING="$(MODULE_NAME)" Optional + } + +[Rule.Common.PEIM.TIANOCOMPRESSED] + FILE PEIM = $(NAMED_GUID) DEBUG_MYTOOLS_IA32 { + PEI_DEPEX PEI_DEPEX Optional $(INF_OUTPUT)/$(MODULE_NAME).depex + GUIDED A31280AD-481E-41B6-95E8-127F4C984779 PROCESSING_REQUIRED = TRUE { + PE32 PE32 $(INF_OUTPUT)/$(MODULE_NAME).efi + UI STRING="$(MODULE_NAME)" Optional + } + } + +[Rule.Common.DXE_CORE] + FILE DXE_CORE = $(NAMED_GUID) { + PE32 PE32 $(INF_OUTPUT)/$(MODULE_NAME).efi + UI STRING="$(MODULE_NAME)" Optional + } + +[Rule.Common.UEFI_DRIVER] + FILE DRIVER = $(NAMED_GUID) { + DXE_DEPEX DXE_DEPEX Optional $(INF_OUTPUT)/$(MODULE_NAME).depex + PE32 PE32 $(INF_OUTPUT)/$(MODULE_NAME).efi + UI STRING="$(MODULE_NAME)" Optional + } + +[Rule.Common.UEFI_DRIVER.BINARY] + FILE DRIVER = $(NAMED_GUID) { + DXE_DEPEX DXE_DEPEX Optional |.depex + PE32 PE32 |.efi + UI STRING="$(MODULE_NAME)" Optional + VERSION STRING="$(INF_VERSION)" Optional BUILD_NUM=$(BUILD_NUMBER) + } + +[Rule.Common.DXE_DRIVER] + FILE DRIVER = $(NAMED_GUID) { + DXE_DEPEX DXE_DEPEX Optional $(INF_OUTPUT)/$(MODULE_NAME).depex + PE32 PE32 $(INF_OUTPUT)/$(MODULE_NAME).efi + UI STRING="$(MODULE_NAME)" Optional + } + +[Rule.Common.DXE_RUNTIME_DRIVER] + FILE DRIVER = $(NAMED_GUID) { + DXE_DEPEX DXE_DEPEX Optional $(INF_OUTPUT)/$(MODULE_NAME).depex + PE32 PE32 $(INF_OUTPUT)/$(MODULE_NAME).efi + UI STRING="$(MODULE_NAME)" Optional + } + +[Rule.Common.UEFI_APPLICATION] + FILE APPLICATION = $(NAMED_GUID) { + UI STRING ="$(MODULE_NAME)" Optional + PE32 PE32 $(INF_OUTPUT)/$(MODULE_NAME).efi + } diff --git a/Platforms/Marvell/Armada/Armada7040_rz.dsc b/Platforms/Marvell/Armada/Armada7040_rz.dsc new file mode 100644 index 0000000..5510c85 --- /dev/null +++ b/Platforms/Marvell/Armada/Armada7040_rz.dsc @@ -0,0 +1,48 @@ +#Copyright (C) 2016 Marvell International Ltd. +# +#Marvell BSD License Option +# +#If you received this File from Marvell, you may opt to use, redistribute and/or +#modify this File under the following licensing terms. +#Redistribution and use in source and binary forms, with or without modification, +#are permitted provided that the following conditions are met: +# +# * Redistributions of source code must retain the above copyright notice, +# this list of conditions and the following disclaimer. +# +# * Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# +# * Neither the name of Marvell nor the names of its contributors may be +# used to endorse or promote products derived from this software without +# specific prior written permission. +# +#THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +#ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +#WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +#DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR +#ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +#(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +#LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON +#ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +#(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +#SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +# +################################################################################ +# +# Defines Section - statements that will be processed to create a Makefile. +# +################################################################################ +[Defines] + PLATFORM_NAME = Armada7040_rz + PLATFORM_GUID = 617dfbfc-b506-4365-9690-b212b6538b71 + PLATFORM_VERSION = 0.1 + DSC_SPECIFICATION = 0x00010005 + OUTPUT_DIRECTORY = Build/$(PLATFORM_NAME) + SUPPORTED_ARCHITECTURES = AARCH64 + BUILD_TARGETS = DEBUG|RELEASE + SKUID_IDENTIFIER = DEFAULT + FLASH_DEFINITION = OpenPlatformPkg/Platforms/Marvell/Armada/Armada7040.fdf + +!include Armada.dsc.inc
From: Jan Dąbroś jsd@semihalf.com
- Create Mpp Library, which allows to set MPP on board. - Create Platforms/Marvell/Marvell.dec file, which holds PCDs' declaration. - Export configuration capabilities via PCDs. - Prepare porting guide document
Because GetMppPcd has to be adjusted to possible 8 MPP registers, although unused, additional PcdChip<X>MppSel are added in order to satisfy preprocessor demands. For the same reason there are MPP PCDs for all of 4 possible chips.
Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Jan Dabros jsd@semihalf.com Signed-off-by: Marcin Wojtas mw@semihalf.com --- Documentation/Marvell/PortingGuide/Mpp.txt | 48 ++++++++ Platforms/Marvell/Include/Library/MppLib.h | 42 +++++++ Platforms/Marvell/Library/MppLib/MppLib.c | 175 ++++++++++++++++++++++++++++ Platforms/Marvell/Library/MppLib/MppLib.inf | 108 +++++++++++++++++ Platforms/Marvell/Marvell.dec | 106 +++++++++++++++++ 5 files changed, 479 insertions(+) create mode 100644 Documentation/Marvell/PortingGuide/Mpp.txt create mode 100644 Platforms/Marvell/Include/Library/MppLib.h create mode 100644 Platforms/Marvell/Library/MppLib/MppLib.c create mode 100644 Platforms/Marvell/Library/MppLib/MppLib.inf create mode 100644 Platforms/Marvell/Marvell.dec
diff --git a/Documentation/Marvell/PortingGuide/Mpp.txt b/Documentation/Marvell/PortingGuide/Mpp.txt new file mode 100644 index 0000000..3e36b5f --- /dev/null +++ b/Documentation/Marvell/PortingGuide/Mpp.txt @@ -0,0 +1,48 @@ +MPP configuration +----------------- +Multi-Purpose Ports (MPP) are configurable through platform PCDs. +In order to set desired pin multiplexing, .dsc file needs to be modified. +(OpenPlatformPkg/Platforms/Marvell/Armada/{platform_name}.dsc - please refer to +Documentation/Build.txt for currently supported {platftorm_name} ) +Following PCDs are available: + + gMarvellTokenSpaceGuid.PcdMppChipCount + +Indicates how many different chips are placed on board. So far up to 4 chips +are supported. + +Every MPP PCD has <Num> part where + <Num> stands for chip ID (order is not important, but configuration will be + set for first PcdMppChipCount chips). + +Below is example for the first chip (Chip0). + + gMarvellTokenSpaceGuid.PcdChip0MppReverseFlag + +Indicates that register order is reversed. (Needs to be used only for AP806-Z1) + + gMarvellTokenSpaceGuid.PcdChip0MppBaseAddress + +This is base address for MPP configuration register. + + gMarvellTokenSpaceGuid.PcdChip0MppPinCount + +Defines how many MPP pins are available. + + gMarvellTokenSpaceGuid.PcdChip0MppSel0 + gMarvellTokenSpaceGuid.PcdChip0MppSel1 + gMarvellTokenSpaceGuid.PcdChip0MppSel2 + +This registers defines functions of 10 pins in ascending order. + +Examples +-------- +#APN806-A0 MPP SET + gMarvellTokenSpaceGuid.PcdChip0MppReverseFlag|FALSE + gMarvellTokenSpaceGuid.PcdChip0MppBaseAddress|0xF06F4000 + gMarvellTokenSpaceGuid.PcdChip0MppRegCount|3 + gMarvellTokenSpaceGuid.PcdChip0MppSel0|{ 0x1, 0x1, 0x1, 0x1, 0x1, 0x1, 0x1, 0x1, 0x1, 0x0 } + gMarvellTokenSpaceGuid.PcdChip0MppSel1|{ 0x0, 0x0, 0x0, 0x1, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0 } + +Set pin 6 and 7 to 0xa function: + gMarvellTokenSpaceGuid.PcdChip0MppSel0|{ 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0xa, 0xa, 0x0, 0x0 } diff --git a/Platforms/Marvell/Include/Library/MppLib.h b/Platforms/Marvell/Include/Library/MppLib.h new file mode 100644 index 0000000..77c6cdb --- /dev/null +++ b/Platforms/Marvell/Include/Library/MppLib.h @@ -0,0 +1,42 @@ +/******************************************************************************** +Copyright (C) 2016 Marvell International Ltd. + +Marvell BSD License Option + +If you received this File from Marvell, you may opt to use, redistribute and/or +modify this File under the following licensing terms. +Redistribution and use in source and binary forms, with or without modification, +are permitted provided that the following conditions are met: + +* Redistributions of source code must retain the above copyright notice, + this list of conditions and the following disclaimer. + +* Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + +* Neither the name of Marvell nor the names of its contributors may be + used to endorse or promote products derived from this software without + specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR +ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON +ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +*******************************************************************************/ + +#ifndef __MPPLIB_H__ +#define __MPPLIB_H__ + +EFI_STATUS +MppInitialize ( + ); + +#endif diff --git a/Platforms/Marvell/Library/MppLib/MppLib.c b/Platforms/Marvell/Library/MppLib/MppLib.c new file mode 100644 index 0000000..7a298c7 --- /dev/null +++ b/Platforms/Marvell/Library/MppLib/MppLib.c @@ -0,0 +1,175 @@ +/******************************************************************************** +Copyright (C) 2016 Marvell International Ltd. + +Marvell BSD License Option + +If you received this File from Marvell, you may opt to use, redistribute and/or +modify this File under the following licensing terms. +Redistribution and use in source and binary forms, with or without modification, +are permitted provided that the following conditions are met: + +* Redistributions of source code must retain the above copyright notice, + this list of conditions and the following disclaimer. + +* Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + +* Neither the name of Marvell nor the names of its contributors may be + used to endorse or promote products derived from this software without + specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR +ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON +ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +*******************************************************************************/ + +#include <Library/ArmLib.h> +#include <Library/ArmPlatformLib.h> +#include <Library/DebugLib.h> +#include <Library/PcdLib.h> +#include <Library/MemoryAllocationLib.h> +#include <Library/IoLib.h> + +#define MPP_PIN_VAL(pin,func) (((func) & 0xf) << ((pin) * 4)) +#define MPP_MAX_REGS 8 +#define MPP_PINS_PER_REG 8 +#define PCD_PINS_PER_GROUP 10 + +#define MAX_CHIPS 4 + +#define GET_PCD_PTR(id,num) _PCD_GET_MODE_PTR_PcdChip##id##MppSel##num +#define GET_PIN_COUNT(id) _PCD_GET_MODE_32_PcdChip##id##MppPinCount +#define GET_BASE(id) _PCD_GET_MODE_64_PcdChip##id##MppBaseAddress +#define GET_REV_FLAG(id) _PCD_GET_MODE_BOOL_PcdChip##id##MppReverseFlag + +/* We get chip number */ +#define GetMppPcd(id) { \ + PinCount[id] = GET_PIN_COUNT(id); \ + PcdGroupCount = PinCount[id] / 10; \ + if ((PinCount[id] % 10) != 0) \ + PcdGroupCount += 1; \ + /* Fall through */ \ + switch (PcdGroupCount) { \ + case 8: \ + MppRegPcd[id][7] = GET_PCD_PTR(id,7); \ + case 7: \ + MppRegPcd[id][6] = GET_PCD_PTR(id,6); \ + case 6: \ + MppRegPcd[id][5] = GET_PCD_PTR(id,5); \ + case 5: \ + MppRegPcd[id][4] = GET_PCD_PTR(id,4); \ + case 4: \ + MppRegPcd[id][3] = GET_PCD_PTR(id,3); \ + case 3: \ + MppRegPcd[id][2] = GET_PCD_PTR(id,2); \ + case 2: \ + MppRegPcd[id][1] = GET_PCD_PTR(id,1); \ + case 1: \ + MppRegPcd[id][0] = GET_PCD_PTR(id,0); \ + } \ + BaseAddr[id] = GET_BASE(id); \ + ReverseFlag[id] = GET_REV_FLAG(id); \ +} + +VOID +SetRegisterValue ( + UINT8 RegCount, + UINT8 **MppRegPcd, + UINTN BaseAddr, + BOOLEAN ReverseFlag + ) +{ + UINT32 i, j, CtrlVal; + INTN Sign; + + Sign = ReverseFlag ? -1 : 1; + + for (i = 0; i < RegCount; i++) { + CtrlVal = 0; + for (j = 0; j < MPP_PINS_PER_REG; j++) { + CtrlVal |= MPP_PIN_VAL(7 * (UINTN) ReverseFlag + j * Sign, + MppRegPcd[i][7 * (UINTN) ReverseFlag + j * Sign]); + } + MmioWrite32 (BaseAddr + 4 * i * Sign, CtrlVal); + } +} + +/* Transform PCD MPP group format into hardware register format */ +UINT8 +PcdToMppRegs ( + UINTN PinCount, + UINT8 **MppRegPcd + ) +{ + UINT8 MppRegPcdTmp[MPP_MAX_REGS][MPP_PINS_PER_REG]; + UINT8 PcdGroupCount, MppRegCount; + UINTN i, j, k, l; + + if (PinCount == 0) { + return 0; + } + + PcdGroupCount = PinCount / PCD_PINS_PER_GROUP; + if ((PinCount % PCD_PINS_PER_GROUP) != 0) { + PcdGroupCount += 1; + } + + MppRegCount = PinCount / MPP_PINS_PER_REG; + if ((PinCount % MPP_PINS_PER_REG) != 0) { + MppRegCount += 1; + } + + /* Fill temporary table with data from PCD groups in HW format */ + for (i = 0; i < PcdGroupCount; i++) { + for (j = 0; j < PCD_PINS_PER_GROUP; j++) { + k = (PCD_PINS_PER_GROUP * i + j) / MPP_PINS_PER_REG; + l = (PCD_PINS_PER_GROUP * i + j) % MPP_PINS_PER_REG; + MppRegPcdTmp[k][l] = MppRegPcd[i][j]; + } + } + + /* Update input table */ + for (i = 0; i < MppRegCount; i++) { + for (j = 0; j < MPP_PINS_PER_REG; j++) { + MppRegPcd[i][j] = MppRegPcdTmp[i][j]; + } + } + + return MppRegCount; +} + +EFI_STATUS +MppInitialize ( + ) +{ + UINTN BaseAddr[MAX_CHIPS], PinCount[MAX_CHIPS], RegCount, PcdGroupCount; + BOOLEAN ReverseFlag[MAX_CHIPS]; + UINT8 *MppRegPcd[MAX_CHIPS][MPP_MAX_REGS]; + UINT32 i, ChipCount; + + ChipCount = PcdGet32 (PcdMppChipCount); + + /* Read all needed PCD for MPP configuration */ + GetMppPcd(0); + GetMppPcd(1); + GetMppPcd(2); + GetMppPcd(3); + + for (i = 0; i < MAX_CHIPS; i++) { + if (i == ChipCount) + break; + RegCount = PcdToMppRegs (PinCount[i], MppRegPcd[i]); + SetRegisterValue (RegCount, MppRegPcd[i], BaseAddr[i], ReverseFlag[i]); + } + + return EFI_SUCCESS; +} diff --git a/Platforms/Marvell/Library/MppLib/MppLib.inf b/Platforms/Marvell/Library/MppLib/MppLib.inf new file mode 100644 index 0000000..65d20d1 --- /dev/null +++ b/Platforms/Marvell/Library/MppLib/MppLib.inf @@ -0,0 +1,108 @@ +# Copyright (C) 2016 Marvell International Ltd. +# +# Marvell BSD License Option +# +# If you received this File from Marvell, you may opt to use, redistribute and/or +# modify this File under the following licensing terms. +# Redistribution and use in source and binary forms, with or without modification, +# are permitted provided that the following conditions are met: +# +# * Redistributions of source code must retain the above copyright notice, +# this list of conditions and the following disclaimer. +# +# * Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# +# * Neither the name of Marvell nor the names of its contributors may be +# used to endorse or promote products derived from this software without +# specific prior written permission. +# +# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +# DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR +# ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +# (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +# LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON +# ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +# SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +# + +[Defines] + INF_VERSION = 0x00010005 + BASE_NAME = MarvellMppLib + FILE_GUID = 3f19b642-4a49-4dfd-8f4a-205dd38432bb + MODULE_TYPE = BASE + VERSION_STRING = 1.0 + LIBRARY_CLASS = MppLib + +[Packages] + MdePkg/MdePkg.dec + MdeModulePkg/MdeModulePkg.dec + ArmPkg/ArmPkg.dec + ArmPlatformPkg/ArmPlatformPkg.dec + OpenPlatformPkg/Platforms/Marvell/Marvell.dec + +[LibraryClasses] + ArmLib + DebugLib + MemoryAllocationLib + PcdLib + IoLib + +[Sources.common] + MppLib.c + +[FixedPcd] + gMarvellTokenSpaceGuid.PcdMppChipCount + + gMarvellTokenSpaceGuid.PcdChip0MppReverseFlag + gMarvellTokenSpaceGuid.PcdChip0MppBaseAddress + gMarvellTokenSpaceGuid.PcdChip0MppPinCount + gMarvellTokenSpaceGuid.PcdChip0MppSel0 + gMarvellTokenSpaceGuid.PcdChip0MppSel1 + gMarvellTokenSpaceGuid.PcdChip0MppSel2 + gMarvellTokenSpaceGuid.PcdChip0MppSel3 + gMarvellTokenSpaceGuid.PcdChip0MppSel4 + gMarvellTokenSpaceGuid.PcdChip0MppSel5 + gMarvellTokenSpaceGuid.PcdChip0MppSel6 + gMarvellTokenSpaceGuid.PcdChip0MppSel7 + + gMarvellTokenSpaceGuid.PcdChip1MppReverseFlag + gMarvellTokenSpaceGuid.PcdChip1MppBaseAddress + gMarvellTokenSpaceGuid.PcdChip1MppPinCount + gMarvellTokenSpaceGuid.PcdChip1MppSel0 + gMarvellTokenSpaceGuid.PcdChip1MppSel1 + gMarvellTokenSpaceGuid.PcdChip1MppSel2 + gMarvellTokenSpaceGuid.PcdChip1MppSel3 + gMarvellTokenSpaceGuid.PcdChip1MppSel4 + gMarvellTokenSpaceGuid.PcdChip1MppSel5 + gMarvellTokenSpaceGuid.PcdChip1MppSel6 + gMarvellTokenSpaceGuid.PcdChip1MppSel7 + + gMarvellTokenSpaceGuid.PcdChip2MppReverseFlag + gMarvellTokenSpaceGuid.PcdChip2MppBaseAddress + gMarvellTokenSpaceGuid.PcdChip2MppPinCount + gMarvellTokenSpaceGuid.PcdChip2MppSel0 + gMarvellTokenSpaceGuid.PcdChip2MppSel1 + gMarvellTokenSpaceGuid.PcdChip2MppSel2 + gMarvellTokenSpaceGuid.PcdChip2MppSel3 + gMarvellTokenSpaceGuid.PcdChip2MppSel4 + gMarvellTokenSpaceGuid.PcdChip2MppSel5 + gMarvellTokenSpaceGuid.PcdChip2MppSel6 + gMarvellTokenSpaceGuid.PcdChip2MppSel7 + + gMarvellTokenSpaceGuid.PcdChip3MppReverseFlag + gMarvellTokenSpaceGuid.PcdChip3MppBaseAddress + gMarvellTokenSpaceGuid.PcdChip3MppPinCount + gMarvellTokenSpaceGuid.PcdChip3MppSel0 + gMarvellTokenSpaceGuid.PcdChip3MppSel1 + gMarvellTokenSpaceGuid.PcdChip3MppSel2 + gMarvellTokenSpaceGuid.PcdChip3MppSel3 + gMarvellTokenSpaceGuid.PcdChip3MppSel4 + gMarvellTokenSpaceGuid.PcdChip3MppSel5 + gMarvellTokenSpaceGuid.PcdChip3MppSel6 + gMarvellTokenSpaceGuid.PcdChip3MppSel7 + diff --git a/Platforms/Marvell/Marvell.dec b/Platforms/Marvell/Marvell.dec new file mode 100644 index 0000000..ae923a9 --- /dev/null +++ b/Platforms/Marvell/Marvell.dec @@ -0,0 +1,106 @@ +# Copyright (C) 2016 Marvell International Ltd. +# +# Marvell BSD License Option +# +# If you received this File from Marvell, you may opt to use, redistribute and/or +# modify this File under the following licensing terms. +# Redistribution and use in source and binary forms, with or without modification, +# are permitted provided that the following conditions are met: +# +#* Redistributions of source code must retain the above copyright notice, +# this list of conditions and the following disclaimer. +# +#* Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# +#* Neither the name of Marvell nor the names of its contributors may be +# used to endorse or promote products derived from this software without +# specific prior written permission. +# +# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +# DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR +# ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +# (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +# LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON +# ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +# SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +# + +[Defines] + DEC_SPECIFICATION = 0x00010005 + PACKAGE_NAME = OpenPlatformPkg + PACKAGE_GUID = c372916e-83ad-4b2a-8410-bbc31bd9e68f + PACKAGE_VERSION = 0.1 + +################################################################################ +# +# Include Section - list of Include Paths that are provided by this package. +# Comments are used for Keywords and Module Types. +# +# Supported Module Types: +# BASE SEC PEI_CORE PEIM DXE_CORE DXE_DRIVER DXE_RUNTIME_DRIVER DXE_SMM_DRIVER DXE_SAL_DRIVER UEFI_DRIVER UEFI_APPLICATION +# +################################################################################ + +[Includes] + Include + +[Guids.common] + gMarvellTokenSpaceGuid = { 0xf995c6c8, 0xbc9b, 0x4e93, { 0xbd, 0xcf, 0x49, 0x90, 0xc6, 0xe7, 0x8c, 0x7f } } + +[PcdsFixedAtBuild.common] +#MPP + gMarvellTokenSpaceGuid.PcdMppChipCount|0|UINT32|0x30000001 + + gMarvellTokenSpaceGuid.PcdChip0MppReverseFlag|FALSE|BOOLEAN|0x30000002 + gMarvellTokenSpaceGuid.PcdChip0MppBaseAddress|0|UINT64|0x30000003 + gMarvellTokenSpaceGuid.PcdChip0MppPinCount|0|UINT32|0x30000004 + gMarvellTokenSpaceGuid.PcdChip0MppSel0|{ 0 }|VOID*|0x30000005 + gMarvellTokenSpaceGuid.PcdChip0MppSel1|{ 0 }|VOID*|0x30000006 + gMarvellTokenSpaceGuid.PcdChip0MppSel2|{ 0 }|VOID*|0x30000007 + gMarvellTokenSpaceGuid.PcdChip0MppSel3|{ 0 }|VOID*|0x30000008 + gMarvellTokenSpaceGuid.PcdChip0MppSel4|{ 0 }|VOID*|0x30000009 + gMarvellTokenSpaceGuid.PcdChip0MppSel5|{ 0 }|VOID*|0x30000010 + gMarvellTokenSpaceGuid.PcdChip0MppSel6|{ 0 }|VOID*|0x30000011 + gMarvellTokenSpaceGuid.PcdChip0MppSel7|{ 0 }|VOID*|0x30000012 + + gMarvellTokenSpaceGuid.PcdChip1MppReverseFlag|FALSE|BOOLEAN|0x30000013 + gMarvellTokenSpaceGuid.PcdChip1MppBaseAddress|0|UINT64|0x30000014 + gMarvellTokenSpaceGuid.PcdChip1MppPinCount|0|UINT32|0x30000015 + gMarvellTokenSpaceGuid.PcdChip1MppSel0|{ 0 }|VOID*|0x30000016 + gMarvellTokenSpaceGuid.PcdChip1MppSel1|{ 0 }|VOID*|0x30000017 + gMarvellTokenSpaceGuid.PcdChip1MppSel2|{ 0 }|VOID*|0x30000018 + gMarvellTokenSpaceGuid.PcdChip1MppSel3|{ 0 }|VOID*|0x30000019 + gMarvellTokenSpaceGuid.PcdChip1MppSel4|{ 0 }|VOID*|0x30000020 + gMarvellTokenSpaceGuid.PcdChip1MppSel5|{ 0 }|VOID*|0x30000021 + gMarvellTokenSpaceGuid.PcdChip1MppSel6|{ 0 }|VOID*|0x30000022 + gMarvellTokenSpaceGuid.PcdChip1MppSel7|{ 0 }|VOID*|0x30000023 + + gMarvellTokenSpaceGuid.PcdChip2MppReverseFlag|FALSE|BOOLEAN|0x30000024 + gMarvellTokenSpaceGuid.PcdChip2MppBaseAddress|0|UINT64|0x30000025 + gMarvellTokenSpaceGuid.PcdChip2MppPinCount|0|UINT32|0x30000026 + gMarvellTokenSpaceGuid.PcdChip2MppSel0|{ 0 }|VOID*|0x30000027 + gMarvellTokenSpaceGuid.PcdChip2MppSel1|{ 0 }|VOID*|0x30000028 + gMarvellTokenSpaceGuid.PcdChip2MppSel2|{ 0 }|VOID*|0x30000029 + gMarvellTokenSpaceGuid.PcdChip2MppSel3|{ 0 }|VOID*|0x30000030 + gMarvellTokenSpaceGuid.PcdChip2MppSel4|{ 0 }|VOID*|0x30000031 + gMarvellTokenSpaceGuid.PcdChip2MppSel5|{ 0 }|VOID*|0x30000032 + gMarvellTokenSpaceGuid.PcdChip2MppSel6|{ 0 }|VOID*|0x30000033 + gMarvellTokenSpaceGuid.PcdChip2MppSel7|{ 0 }|VOID*|0x30000034 + + gMarvellTokenSpaceGuid.PcdChip3MppReverseFlag|FALSE|BOOLEAN|0x30000035 + gMarvellTokenSpaceGuid.PcdChip3MppBaseAddress|0|UINT64|0x30000036 + gMarvellTokenSpaceGuid.PcdChip3MppPinCount|0|UINT32|0x30000037 + gMarvellTokenSpaceGuid.PcdChip3MppSel0|{ 0 }|VOID*|0x30000038 + gMarvellTokenSpaceGuid.PcdChip3MppSel1|{ 0 }|VOID*|0x30000039 + gMarvellTokenSpaceGuid.PcdChip3MppSel2|{ 0 }|VOID*|0x30000040 + gMarvellTokenSpaceGuid.PcdChip3MppSel3|{ 0 }|VOID*|0x30000041 + gMarvellTokenSpaceGuid.PcdChip3MppSel4|{ 0 }|VOID*|0x30000042 + gMarvellTokenSpaceGuid.PcdChip3MppSel5|{ 0 }|VOID*|0x30000043 + gMarvellTokenSpaceGuid.PcdChip3MppSel6|{ 0 }|VOID*|0x30000044 + gMarvellTokenSpaceGuid.PcdChip3MppSel7|{ 0 }|VOID*|0x30000045 +
From: Jan Dąbroś jsd@semihalf.com
Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Jan Dabros jsd@semihalf.com Signed-off-by: Marcin Wojtas mw@semihalf.com --- Platforms/Marvell/Armada/Apn806.dsc | 16 +++++++++++++ Platforms/Marvell/Armada/Armada.dsc.inc | 1 + Platforms/Marvell/Armada/Armada7040_rz.dsc | 28 ++++++++++++++++++++++ .../Armada/Library/Armada7040Lib/Armada7040Lib.c | 2 ++ .../Armada/Library/Armada7040Lib/Armada7040Lib.inf | 2 ++ 5 files changed, 49 insertions(+)
diff --git a/Platforms/Marvell/Armada/Apn806.dsc b/Platforms/Marvell/Armada/Apn806.dsc index 62edf69..d3c73cf 100644 --- a/Platforms/Marvell/Armada/Apn806.dsc +++ b/Platforms/Marvell/Armada/Apn806.dsc @@ -46,3 +46,19 @@ FLASH_DEFINITION = OpenPlatformPkg/Platforms/Marvell/Armada/Armada7040.fdf
!include Armada.dsc.inc + +################################################################################ +# +# Pcd Section - list of all EDK II PCD Entries defined by this Platform +# +################################################################################ +[PcdsFixedAtBuild.common] + # MPP + gMarvellTokenSpaceGuid.PcdMppChipCount|1 + + # APN806-Z1 MPP SET + gMarvellTokenSpaceGuid.PcdChip0MppReverseFlag|TRUE + gMarvellTokenSpaceGuid.PcdChip0MppBaseAddress|0xF06F008C + gMarvellTokenSpaceGuid.PcdChip0MppPinCount|16 + gMarvellTokenSpaceGuid.PcdChip0MppSel0|{ 0x1, 0x1, 0x1, 0x1, 0x1, 0x1, 0x1, 0x1, 0x1, 0x0 } + gMarvellTokenSpaceGuid.PcdChip0MppSel1|{ 0x0, 0x0, 0x0, 0x1, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0 } diff --git a/Platforms/Marvell/Armada/Armada.dsc.inc b/Platforms/Marvell/Armada/Armada.dsc.inc index 027c95f..b5108d9 100644 --- a/Platforms/Marvell/Armada/Armada.dsc.inc +++ b/Platforms/Marvell/Armada/Armada.dsc.inc @@ -31,6 +31,7 @@ # [LibraryClasses.common] ArmPlatformLib|OpenPlatformPkg/Platforms/Marvell/Armada/Library/Armada7040Lib/Armada7040Lib.inf + MppLib|OpenPlatformPkg/Platforms/Marvell/Library/MppLib/MppLib.inf
!if $(TARGET) == RELEASE DebugLib|MdePkg/Library/BaseDebugLibNull/BaseDebugLibNull.inf diff --git a/Platforms/Marvell/Armada/Armada7040_rz.dsc b/Platforms/Marvell/Armada/Armada7040_rz.dsc index 5510c85..8627885 100644 --- a/Platforms/Marvell/Armada/Armada7040_rz.dsc +++ b/Platforms/Marvell/Armada/Armada7040_rz.dsc @@ -46,3 +46,31 @@ FLASH_DEFINITION = OpenPlatformPkg/Platforms/Marvell/Armada/Armada7040.fdf
!include Armada.dsc.inc + +################################################################################ +# +# Pcd Section - list of all EDK II PCD Entries defined by this Platform +# +################################################################################ +[PcdsFixedAtBuild.common] + #MPP + gMarvellTokenSpaceGuid.PcdMppChipCount|2 + + # APN806-Z1 MPP SET + gMarvellTokenSpaceGuid.PcdChip0MppReverseFlag|TRUE + gMarvellTokenSpaceGuid.PcdChip0MppBaseAddress|0xF06F008C + gMarvellTokenSpaceGuid.PcdChip0MppPinCount|16 + gMarvellTokenSpaceGuid.PcdChip0MppSel0|{ 0x1, 0x1, 0x1, 0x1, 0x1, 0x1, 0x1, 0x1, 0x1, 0x0 } + gMarvellTokenSpaceGuid.PcdChip0MppSel1|{ 0x0, 0x0, 0x0, 0x1, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0 } + + # CP110 MPP SET - Router configuration + gMarvellTokenSpaceGuid.PcdChip1MppReverseFlag|FALSE + gMarvellTokenSpaceGuid.PcdChip1MppBaseAddress|0xF2440000 + gMarvellTokenSpaceGuid.PcdChip1MppPinCount|64 + gMarvellTokenSpaceGuid.PcdChip1MppSel0|{ 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3 } + gMarvellTokenSpaceGuid.PcdChip1MppSel1|{ 0x3, 0x3, 0x0, 0x3, 0x3, 0x3, 0x3, 0x0, 0x0, 0x0 } + gMarvellTokenSpaceGuid.PcdChip1MppSel2|{ 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x9, 0xA } + gMarvellTokenSpaceGuid.PcdChip1MppSel3|{ 0xA, 0x0, 0x7, 0x0, 0x7, 0x0, 0x6, 0x2, 0x2, 0x0 } + gMarvellTokenSpaceGuid.PcdChip1MppSel4|{ 0x7, 0x7, 0x8, 0x8, 0x1, 0x1, 0x1, 0x1, 0x1, 0x1 } + gMarvellTokenSpaceGuid.PcdChip1MppSel5|{ 0x1, 0x1, 0x1, 0x1, 0x1, 0x1, 0xE, 0xE, 0xE, 0xE } + gMarvellTokenSpaceGuid.PcdChip1MppSel6|{ 0xE, 0xE, 0xE, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0 } diff --git a/Platforms/Marvell/Armada/Library/Armada7040Lib/Armada7040Lib.c b/Platforms/Marvell/Armada/Library/Armada7040Lib/Armada7040Lib.c index 1e83afe..2a34455 100644 --- a/Platforms/Marvell/Armada/Library/Armada7040Lib/Armada7040Lib.c +++ b/Platforms/Marvell/Armada/Library/Armada7040Lib/Armada7040Lib.c @@ -14,6 +14,7 @@
#include <Library/ArmLib.h> #include <Library/ArmPlatformLib.h> +#include <Library/MppLib.h> #include <Ppi/ArmMpCoreInfo.h>
@@ -92,6 +93,7 @@ ArmPlatformInitialize (
//TODO: Add basic platfrom initialization
+ MppInitialize (); return RETURN_SUCCESS; }
diff --git a/Platforms/Marvell/Armada/Library/Armada7040Lib/Armada7040Lib.inf b/Platforms/Marvell/Armada/Library/Armada7040Lib/Armada7040Lib.inf index a4a9107..f586e65 100644 --- a/Platforms/Marvell/Armada/Library/Armada7040Lib/Armada7040Lib.inf +++ b/Platforms/Marvell/Armada/Library/Armada7040Lib/Armada7040Lib.inf @@ -24,11 +24,13 @@ MdeModulePkg/MdeModulePkg.dec ArmPkg/ArmPkg.dec ArmPlatformPkg/ArmPlatformPkg.dec + OpenPlatformPkg/Platforms/Marvell/Marvell.dec
[LibraryClasses] ArmLib DebugLib MemoryAllocationLib + MppLib
[Sources.common] Armada7040Lib.c
From: Bartosz Szczepanek bsz@semihalf.com
MvI2cDxe driver was adapted to generic UEFI I2C stack. Connection with following interfaces was required: - EFI_I2C_MASTER_PROTOCOL - EFI_I2C_BUS_CONFIGURATION_MANAGEMENT_PROTOCOL - EFI_I2C_ENUMERATE_PROTOCOL
Driver exports configuration options via PCDs. Configurable options include: - PcdI2cSlaveAddresses - should contain a list of valid I2C devices' addresses on bus - PcdI2cBaseAddress - physical address of I2C controller registers - PcdI2cClockFrequency - I2c clock frequency on platform
Drivers of devices on I2C bus should never use EFI_I2C_MASTER_PROTOCOL directly. Instead, these ought to utilise EFI_I2C_IO_PROTOCOL produced by generic UEFI stack.
Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Bartosz Szczepanek bsz@semihalf.com Signed-off-by: Marcin Wojtas mw@semihalf.com --- Documentation/Marvell/Drivers/I2cDriver.txt | 64 +++ Documentation/Marvell/PortingGuide/I2c.txt | 16 + Drivers/I2c/MvI2cDxe/MvI2cDxe.c | 686 ++++++++++++++++++++++++++++ Drivers/I2c/MvI2cDxe/MvI2cDxe.h | 254 ++++++++++ Drivers/I2c/MvI2cDxe/MvI2cDxe.inf | 73 +++ Platforms/Marvell/Marvell.dec | 6 + 6 files changed, 1099 insertions(+) create mode 100644 Documentation/Marvell/Drivers/I2cDriver.txt create mode 100644 Documentation/Marvell/PortingGuide/I2c.txt create mode 100644 Drivers/I2c/MvI2cDxe/MvI2cDxe.c create mode 100644 Drivers/I2c/MvI2cDxe/MvI2cDxe.h create mode 100644 Drivers/I2c/MvI2cDxe/MvI2cDxe.inf
diff --git a/Documentation/Marvell/Drivers/I2cDriver.txt b/Documentation/Marvell/Drivers/I2cDriver.txt new file mode 100644 index 0000000..2f890de --- /dev/null +++ b/Documentation/Marvell/Drivers/I2cDriver.txt @@ -0,0 +1,64 @@ +1. Introduction +--------------- +**MvI2cDxe** is a driver supporting I2C controller on Marvell SOCs boards. +It is connected through protocols to generic UEFI I2C stack, which exposes +IO functionality to drivers of specific devices on I2C bus. + +2. MvI2cDxe driver design +-------------------------- +MvI2cDxe produces several protocols from generic I2C stack: + - EFI_I2C_MASTER_PROTOCOL, + - EFI_I2C_ENUMERATE_PROTOCOL, + - EFI_I2C_BUS_CONFIGURATION_MANAGEMENT_PROTOCOL + - general-purpose EFI_DRIVER_BINDING_PROTOCOL. + + 2.1 EFI_I2C_MASTER_PROTOCOL + --------------------------- + This is the most important protocol produced by MvI2cDxe. Following functions + are implemented: + + /// + /// Reset the I2C host controller. + /// + EFI_I2C_MASTER_PROTOCOL_RESET Reset; + + /// + /// Start an I2C transaction in master mode on the host controller. + /// + EFI_I2C_MASTER_PROTOCOL_START_REQUEST StartRequest; + + StartRequest and Reset functions are used by I2cHost. + These should **not** be used by I2C device drivers - required + synchronization is not provided. Instead, members of EFI_I2C_IO_PROTOCOL + should be used. + + 2.2 EFI_I2C_BUS_CONFIGURATION_MANAGEMENT_PROTOCOL + ------------------------------------------------- + The only function exposed via this protocol is MvI2cEnableConf. It is + required by I2C stack in order to allow changing I2C bus configuration from + device drivers. + + 2.3 EFI_I2C_ENUMERATE_PROTOCOL + ------------------------------ + Provides Enumerate function, which is used by I2cBus code as an iterator over + devices on I2C bus. + + typedef + EFI_STATUS + (EFIAPI *EFI_I2C_ENUMERATE_PROTOCOL_ENUMERATE) ( + IN CONST EFI_I2C_ENUMERATE_PROTOCOL *This, + IN OUT CONST EFI_I2C_DEVICE **Device + ); + + /// + /// Traverse the set of I2C devices on an I2C bus. This routine + /// returns the next I2C device on an I2C bus. + /// + EFI_I2C_ENUMERATE_PROTOCOL_ENUMERATE Enumerate; + + MvI2cDevice creates EFI_I2C_DEVICE structure for every device on the bus. + Due to the fact that hardware-based I2C enumeration isn't safe, information + about attached devices should be provided through PCDs. After EFI_I2C_DEVICE + structure is created and filled properly, it is returned to I2cBus. It is + followed by attachment of I2C device driver. + diff --git a/Documentation/Marvell/PortingGuide/I2c.txt b/Documentation/Marvell/PortingGuide/I2c.txt new file mode 100644 index 0000000..7b78367 --- /dev/null +++ b/Documentation/Marvell/PortingGuide/I2c.txt @@ -0,0 +1,16 @@ +1. Porting I2C driver to a new SOC +---------------------------------- +In order to enable driver on a new platform, following steps need to be taken: + - add following line to .dsc file: + OpenPlatformPkg/Drivers/I2c/MvI2cDxe/MvI2cDxe.inf + - add following line to .fdf file: + INF OpenPlatformPkg/Drivers/I2c/MvI2cDxe/MvI2cDxe.inf + - add PCDs with relevant values to .dsc file: + gMarvellTokenSpaceGuid.PcdI2cSlaveAddresses|{ 0x50, 0x57 } + (addresses of I2C slave devices on bus) + gMarvellTokenSpaceGuid.PcdI2cBaseAddress|0xF0511000 + (base address of I2C controller) + gMarvellTokenSpaceGuid.PcdI2cClockFrequency|200000000 + (I2C host controller clock frequency) + gMarvellTokenSpaceGuid.PcdI2cBaudRate|100000 + (baud rate used in I2C transmission) diff --git a/Drivers/I2c/MvI2cDxe/MvI2cDxe.c b/Drivers/I2c/MvI2cDxe/MvI2cDxe.c new file mode 100644 index 0000000..d1d5293 --- /dev/null +++ b/Drivers/I2c/MvI2cDxe/MvI2cDxe.c @@ -0,0 +1,686 @@ +/******************************************************************************** +Copyright (C) 2016 Marvell International Ltd. + +Marvell BSD License Option + +If you received this File from Marvell, you may opt to use, redistribute and/or +modify this File under the following licensing terms. +Redistribution and use in source and binary forms, with or without modification, +are permitted provided that the following conditions are met: + +* Redistributions of source code must retain the above copyright notice, + this list of conditions and the following disclaimer. + +* Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + +* Neither the name of Marvell nor the names of its contributors may be + used to endorse or promote products derived from this software without + specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR +ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON +ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +*******************************************************************************/ + +#include <Protocol/I2cMaster.h> +#include <Protocol/I2cEnumerate.h> +#include <Protocol/I2cBusConfigurationManagement.h> +#include <Protocol/DevicePath.h> + +#include <Library/BaseLib.h> +#include <Library/IoLib.h> +#include <Library/DebugLib.h> +#include <Library/PcdLib.h> +#include <Library/UefiLib.h> +#include <Library/MemoryAllocationLib.h> +#include <Library/UefiBootServicesTableLib.h> + +#include "MvI2cDxe.h" + +STATIC MV_I2C_BAUD_RATE baud_rate; + +MV_I2C_DEVICE_PATH gDevicePathProtocol = { + { + { + HARDWARE_DEVICE_PATH, + HW_VENDOR_DP, + { + (UINT8) (sizeof(VENDOR_DEVICE_PATH)), + (UINT8) (sizeof(VENDOR_DEVICE_PATH) >> 8), + }, + }, + EFI_CALLER_ID_GUID + }, + { + END_DEVICE_PATH_TYPE, + END_ENTIRE_DEVICE_PATH_SUBTYPE, + { + sizeof(EFI_DEVICE_PATH_PROTOCOL), + 0 + } + } +}; + +STATIC +UINT32 +I2C_READ( + IN I2C_MASTER_CONTEXT *I2cMasterContext, + IN UINTN off) +{ + ASSERT (I2cMasterContext != NULL); + return MmioRead32 (I2cMasterContext->BaseAddress + off); +} + +STATIC +EFI_STATUS +I2C_WRITE ( + IN I2C_MASTER_CONTEXT *I2cMasterContext, + IN UINTN off, + IN UINT32 Value) +{ + ASSERT (I2cMasterContext != NULL); + return MmioWrite32 (I2cMasterContext->BaseAddress + off, Value); +} + +EFI_STATUS +EFIAPI +MvI2cInitialise ( + IN EFI_HANDLE ImageHandle, + IN EFI_SYSTEM_TABLE *SystemTable + ) +{ + EFI_STATUS Status; + I2C_MASTER_CONTEXT *I2cMasterContext; + + /* if attachment succeeds, this gets freed at ExitBootServices */ + I2cMasterContext = AllocateZeroPool (sizeof (I2C_MASTER_CONTEXT)); + if (I2cMasterContext == NULL) { + DEBUG((DEBUG_ERROR, "MvI2cDxe: I2C master context allocation failed\n")); + return EFI_OUT_OF_RESOURCES; + } + I2cMasterContext->Signature = I2C_MASTER_SIGNATURE; + I2cMasterContext->I2cMaster.Reset = MvI2cReset; + I2cMasterContext->I2cMaster.StartRequest = MvI2cStartRequest; + I2cMasterContext->I2cEnumerate.Enumerate = MvI2cEnumerate; + I2cMasterContext->I2cBusConf.EnableI2cBusConfiguration = MvI2cEnableConf; + I2cMasterContext->TclkFrequency = PcdGet32 (PcdI2cClockFrequency); + I2cMasterContext->BaseAddress = PcdGet64 (PcdI2cBaseAddress); + + /* I2cMasterContext->Lock is responsible for serializing I2C operations */ + EfiInitializeLock(&I2cMasterContext->Lock, TPL_NOTIFY); + + /* Checks if protocol is *not yet* installed */ + ASSERT_PROTOCOL_ALREADY_INSTALLED(NULL, &gEfiI2cMasterProtocolGuid); + ASSERT_PROTOCOL_ALREADY_INSTALLED(NULL, &gEfiI2cEnumerateProtocolGuid); + ASSERT_PROTOCOL_ALREADY_INSTALLED(NULL, &gEfiI2cBusConfigurationManagementProtocolGuid); + + MvI2cCalBaudRate( I2cMasterContext, + PcdGet32 (PcdI2cBaudRate), + &baud_rate, + I2cMasterContext->TclkFrequency + ); + + Status = gBS->InstallMultipleProtocolInterfaces( + &I2cMasterContext->Controller, + &gEfiI2cMasterProtocolGuid, + &I2cMasterContext->I2cMaster, + &gEfiI2cEnumerateProtocolGuid, + &I2cMasterContext->I2cEnumerate, + &gEfiI2cBusConfigurationManagementProtocolGuid, + &I2cMasterContext->I2cBusConf, + &gEfiDevicePathProtocolGuid, + (EFI_DEVICE_PATH_PROTOCOL *) &gDevicePathProtocol, + NULL); + + if (EFI_ERROR(Status)) { + DEBUG((DEBUG_ERROR, "MvI2cDxe: Installing protocol interfaces failed!\n")); + goto fail; + } + + return EFI_SUCCESS; + +fail: + FreePool(I2cMasterContext); + return Status; +} + +STATIC +VOID +MvI2cControlClear ( + IN I2C_MASTER_CONTEXT *I2cMasterContext, + IN UINT32 Mask) +{ + UINT32 Value; + + /* clears given bits in I2C_CONTROL register */ + Value = I2C_READ(I2cMasterContext, I2C_CONTROL); + Value &= ~Mask; + I2C_WRITE(I2cMasterContext, I2C_CONTROL, Value); +} + +STATIC +VOID +MvI2cControlSet ( + IN I2C_MASTER_CONTEXT *I2cMasterContext, + IN UINT32 Mask) +{ + UINT32 Value; + + /* sets given bits in I2C_CONTROL register */ + Value = I2C_READ(I2cMasterContext, I2C_CONTROL); + Value |= Mask; + I2C_WRITE(I2cMasterContext, I2C_CONTROL, Value); +} + +STATIC +VOID +MvI2cClearIflg ( + IN I2C_MASTER_CONTEXT *I2cMasterContext + ) +{ + + gBS->Stall(I2C_OPERATION_TIMEOUT); + MvI2cControlClear(I2cMasterContext, I2C_CONTROL_IFLG); + gBS->Stall(I2C_OPERATION_TIMEOUT); +} + +/* Timeout is given in us */ +STATIC +UINTN +MvI2cPollCtrl ( + IN I2C_MASTER_CONTEXT *I2cMasterContext, + IN UINTN Timeout, + IN UINT32 Mask) +{ + + Timeout /= 10; + while (!(I2C_READ(I2cMasterContext, I2C_CONTROL) & Mask)) { + gBS->Stall(10); + if (--Timeout == 0) + return (Timeout); + } + return (0); +} + +/* + * 'Timeout' is given in us. Note also that Timeout handling is not exact -- + * MvI2cLockedStart() total wait can be more than 2 x Timeout + * (MvI2cPollCtrl() is called twice). 'Mask' can be either I2C_STATUS_START + * or I2C_STATUS_RPTD_START + */ +STATIC +EFI_STATUS +MvI2cLockedStart ( + IN I2C_MASTER_CONTEXT *I2cMasterContext, + IN INT32 Mask, + IN UINT8 Slave, + IN UINTN Timeout + ) +{ + UINTN ReadAccess, IflgSet = 0; + UINT32 I2cStatus; + + if (Mask == I2C_STATUS_RPTD_START) + /* read IFLG to know if it should be cleared later */ + IflgSet = I2C_READ(I2cMasterContext, I2C_CONTROL) & I2C_CONTROL_IFLG; + + MvI2cControlSet(I2cMasterContext, I2C_CONTROL_START); + + if (Mask == I2C_STATUS_RPTD_START && IflgSet) { + DEBUG((DEBUG_INFO, "MvI2cDxe: IFLG set, clearing\n")); + MvI2cClearIflg(I2cMasterContext); + } + + /* Without this delay we Timeout checking IFLG if the Timeout is 0 */ + gBS->Stall(I2C_OPERATION_TIMEOUT); + + if (MvI2cPollCtrl(I2cMasterContext, Timeout, I2C_CONTROL_IFLG)) { + DEBUG((DEBUG_ERROR, "MvI2cDxe: Timeout sending %sSTART condition\n", + Mask == I2C_STATUS_START ? "" : "repeated ")); + return EFI_NO_RESPONSE; + } + + I2cStatus = I2C_READ(I2cMasterContext, I2C_STATUS); + if (I2cStatus != Mask) { + DEBUG((DEBUG_ERROR, "MvI2cDxe: wrong I2cStatus (%02x) after sending %sSTART condition\n", + I2cStatus, Mask == I2C_STATUS_START ? "" : "repeated ")); + return EFI_DEVICE_ERROR; + } + + I2C_WRITE(I2cMasterContext, I2C_DATA, Slave); + gBS->Stall(I2C_OPERATION_TIMEOUT); + MvI2cClearIflg(I2cMasterContext); + + if (MvI2cPollCtrl(I2cMasterContext, Timeout, I2C_CONTROL_IFLG)) { + DEBUG((DEBUG_ERROR, "MvI2cDxe: Timeout sending Slave address\n")); + return EFI_NO_RESPONSE; + } + + ReadAccess = (Slave & 0x1) ? 1 : 0; + I2cStatus = I2C_READ(I2cMasterContext, I2C_STATUS); + if (I2cStatus != (ReadAccess ? + I2C_STATUS_ADDR_R_ACK : I2C_STATUS_ADDR_W_ACK)) { + DEBUG((DEBUG_ERROR, "MvI2cDxe: no ACK (I2cStatus: %02x) after sending Slave address\n", + I2cStatus)); + return EFI_NO_RESPONSE; + } + + return EFI_SUCCESS; +} + +#define ABSSUB(a,b) (((a) > (b)) ? (a) - (b) : (b) - (a)) +STATIC +VOID +MvI2cCalBaudRate ( + IN I2C_MASTER_CONTEXT *I2cMasterContext, + IN CONST UINT32 target, + IN OUT MV_I2C_BAUD_RATE *rate, + UINT32 clk + ) +{ + UINT32 cur, diff, diff0, baud; + UINTN m, n, m0, n0; + + /* Read initial m0, n0 values from register */ + baud = I2C_READ(I2cMasterContext, I2C_BAUD_RATE); + m0 = I2C_M_FROM_BAUD(baud); + n0 = I2C_N_FROM_BAUD(baud); + /* Calculate baud rate. */ + diff0 = 0xffffffff; + + for (n = 0; n < 8; n++) { + for (m = 0; m < 16; m++) { + cur = I2C_BAUD_RATE_RAW(clk,m,n); + diff = ABSSUB(target, cur); + if (diff < diff0) { + m0 = m; + n0 = n; + diff0 = diff; + } + } + } + rate->raw = I2C_BAUD_RATE_RAW(clk, m0, n0); + rate->param = I2C_BAUD_RATE_PARAM(m0, n0); + rate->m = m0; + rate->n = n0; +} + +EFI_STATUS +EFIAPI +MvI2cReset ( + IN CONST EFI_I2C_MASTER_PROTOCOL *This + ) +{ + UINT32 param; + I2C_MASTER_CONTEXT *I2cMasterContext = I2C_SC_FROM_MASTER(This); + + param = baud_rate.param; + + EfiAcquireLock (&I2cMasterContext->Lock); + I2C_WRITE(I2cMasterContext, I2C_SOFT_RESET, 0x0); + gBS->Stall(2 * I2C_OPERATION_TIMEOUT); + I2C_WRITE(I2cMasterContext, I2C_BAUD_RATE, param); + I2C_WRITE(I2cMasterContext, I2C_CONTROL, I2C_CONTROL_I2CEN | I2C_CONTROL_ACK); + gBS->Stall(I2C_OPERATION_TIMEOUT); + EfiReleaseLock (&I2cMasterContext->Lock); + + return EFI_SUCCESS; +} + +/* + * Timeout is given in us + */ +STATIC +EFI_STATUS +MvI2cRepeatedStart ( + IN I2C_MASTER_CONTEXT *I2cMasterContext, + IN UINT8 Slave, + IN UINTN Timeout + ) +{ + EFI_STATUS Status; + + EfiAcquireLock (&I2cMasterContext->Lock); + Status = MvI2cLockedStart(I2cMasterContext, I2C_STATUS_RPTD_START, Slave, + Timeout); + EfiReleaseLock (&I2cMasterContext->Lock); + + if (EFI_ERROR(Status)) { + MvI2cStop(I2cMasterContext); + } + return Status; +} + +/* + * Timeout is given in us + */ +STATIC +EFI_STATUS +MvI2cStart ( + IN I2C_MASTER_CONTEXT *I2cMasterContext, + IN UINT8 Slave, + IN UINTN Timeout + ) +{ + EFI_STATUS Status; + + EfiAcquireLock (&I2cMasterContext->Lock); + Status = MvI2cLockedStart(I2cMasterContext, I2C_STATUS_START, Slave, Timeout); + EfiReleaseLock (&I2cMasterContext->Lock); + + if (EFI_ERROR(Status)) { + MvI2cStop(I2cMasterContext); + } + return Status; +} + +STATIC +EFI_STATUS +MvI2cStop ( + IN I2C_MASTER_CONTEXT *I2cMasterContext + ) +{ + + EfiAcquireLock (&I2cMasterContext->Lock); + MvI2cControlSet(I2cMasterContext, I2C_CONTROL_STOP); + gBS->Stall(I2C_OPERATION_TIMEOUT); + MvI2cClearIflg(I2cMasterContext); + EfiReleaseLock (&I2cMasterContext->Lock); + + return EFI_SUCCESS; +} + +STATIC +EFI_STATUS +MvI2cRead ( + IN I2C_MASTER_CONTEXT *I2cMasterContext, + IN OUT UINT8 *Buf, + IN UINTN Length, + IN OUT UINTN *read, + IN UINTN last, + IN UINTN delay + ) +{ + UINT32 I2cStatus; + UINTN LastByte; + EFI_STATUS Status; + + EfiAcquireLock (&I2cMasterContext->Lock); + *read = 0; + while (*read < Length) { + /* + * Check if we are reading last byte of the last Buffer, + * do not send ACK then, per I2C specs + */ + LastByte = ((*read == Length - 1) && last) ? 1 : 0; + if (LastByte) + MvI2cControlClear(I2cMasterContext, I2C_CONTROL_ACK); + else + MvI2cControlSet(I2cMasterContext, I2C_CONTROL_ACK); + + gBS->Stall (I2C_OPERATION_TIMEOUT); + MvI2cClearIflg(I2cMasterContext); + + if (MvI2cPollCtrl(I2cMasterContext, delay, I2C_CONTROL_IFLG)) { + DEBUG((DEBUG_ERROR, "MvI2cDxe: Timeout reading data\n")); + Status = EFI_NO_RESPONSE; + goto out; + } + + I2cStatus = I2C_READ(I2cMasterContext, I2C_STATUS); + if (I2cStatus != (LastByte ? + I2C_STATUS_DATA_RD_NOACK : I2C_STATUS_DATA_RD_ACK)) { + DEBUG((DEBUG_ERROR, "MvI2cDxe: wrong I2cStatus (%02x) while reading\n", I2cStatus)); + Status = EFI_DEVICE_ERROR; + goto out; + } + + *Buf++ = I2C_READ(I2cMasterContext, I2C_DATA); + (*read)++; + } + Status = EFI_SUCCESS; +out: + EfiReleaseLock (&I2cMasterContext->Lock); + return (Status); +} + +STATIC +EFI_STATUS +MvI2cWrite ( + IN I2C_MASTER_CONTEXT *I2cMasterContext, + IN OUT CONST UINT8 *Buf, + IN UINTN Length, + IN OUT UINTN *Sent, + IN UINTN Timeout + ) +{ + UINT32 status; + EFI_STATUS Status; + + EfiAcquireLock (&I2cMasterContext->Lock); + *Sent = 0; + while (*Sent < Length) { + I2C_WRITE(I2cMasterContext, I2C_DATA, *Buf++); + + MvI2cClearIflg(I2cMasterContext); + if (MvI2cPollCtrl(I2cMasterContext, Timeout, I2C_CONTROL_IFLG)) { + DEBUG((DEBUG_ERROR, "MvI2cDxe: Timeout writing data\n")); + Status = EFI_NO_RESPONSE; + goto out; + } + + status = I2C_READ(I2cMasterContext, I2C_STATUS); + if (status != I2C_STATUS_DATA_WR_ACK) { + DEBUG((DEBUG_ERROR, "MvI2cDxe: wrong status (%02x) while writing\n", status)); + Status = EFI_DEVICE_ERROR; + goto out; + } + (*Sent)++; + } + Status = EFI_SUCCESS; +out: + EfiReleaseLock (&I2cMasterContext->Lock); + return (Status); +} + +/* + * MvI2cStartRequest should be called only by I2cHost. + * I2C device drivers ought to use EFI_I2C_IO_PROTOCOL instead. + */ +STATIC +EFI_STATUS +MvI2cStartRequest ( + IN CONST EFI_I2C_MASTER_PROTOCOL *This, + IN UINTN SlaveAddress, + IN EFI_I2C_REQUEST_PACKET *RequestPacket, + IN EFI_EVENT Event OPTIONAL, + OUT EFI_STATUS *I2cStatus OPTIONAL + ) +{ + UINTN Count; + UINTN ReadMode; + UINTN Transmitted; + I2C_MASTER_CONTEXT *I2cMasterContext = I2C_SC_FROM_MASTER(This); + EFI_I2C_OPERATION *Operation; + + ASSERT (RequestPacket != NULL); + ASSERT (I2cMasterContext != NULL); + + for (Count = 0; Count < RequestPacket->OperationCount; Count++) { + Operation = &RequestPacket->Operation[Count]; + ReadMode = Operation->Flags & I2C_FLAG_READ; + + if (Count == 0) { + MvI2cStart ( I2cMasterContext, + (SlaveAddress << 1) | ReadMode, + I2C_TRANSFER_TIMEOUT + ); + } else if (!(Operation->Flags & I2C_FLAG_NORESTART)) { + MvI2cRepeatedStart ( I2cMasterContext, + (SlaveAddress << 1) | ReadMode, + I2C_TRANSFER_TIMEOUT + ); + } + + if (ReadMode) { + MvI2cRead ( I2cMasterContext, + Operation->Buffer, + Operation->LengthInBytes, + &Transmitted, + Count == 1, + I2C_TRANSFER_TIMEOUT + ); + } else { + MvI2cWrite ( I2cMasterContext, + Operation->Buffer, + Operation->LengthInBytes, + &Transmitted, + I2C_TRANSFER_TIMEOUT + ); + } + if (Count == RequestPacket->OperationCount - 1) { + MvI2cStop ( I2cMasterContext ); + } + } + + if (I2cStatus != NULL) + I2cStatus = EFI_SUCCESS; + if (Event != NULL) + gBS->SignalEvent(Event); + return EFI_SUCCESS; +} + +/* + * I2C_GUID is embedded in EFI_I2C_DEVICE structure, with last byte set to + * address of device on I2C bus. Device driver should compare its GUID with + * offered one in Supported() function. + */ +#define I2C_GUID \ + { \ + 0x391fc679, 0x6cb0, 0x4f01, { 0x9a, 0xc7, 0x8e, 0x1b, 0x78, 0x6b, 0x7a, 0x00 } \ + } + +STATIC +EFI_STATUS +MvI2cAllocDevice ( + IN UINT8 SlaveAddress, + IN OUT CONST EFI_I2C_DEVICE **Device + ) +{ + EFI_STATUS Status; + EFI_I2C_DEVICE *Dev; + UINT32 *TmpSlaveArray; + EFI_GUID DevGuid = I2C_GUID; + EFI_GUID *TmpGuidP; + + DevGuid.Data4[7] = SlaveAddress; + + Status = gBS->AllocatePool ( EfiBootServicesData, + sizeof(EFI_I2C_DEVICE), + (VOID **) &Dev ); + if (EFI_ERROR(Status)) { + DEBUG((DEBUG_ERROR, "MvI2cDxe: I2C device memory allocation failed\n")); + return Status; + } + *Device = Dev; + Dev->DeviceIndex = SlaveAddress; + Dev->SlaveAddressCount = 1; + Dev->I2cBusConfiguration = 0; + Status = gBS->AllocatePool ( EfiBootServicesData, + sizeof(UINT32), + (VOID **) &TmpSlaveArray); + if (EFI_ERROR(Status)) { + goto fail1; + } + TmpSlaveArray[0] = SlaveAddress; + Dev->SlaveAddressArray = TmpSlaveArray; + + Status = gBS->AllocatePool ( EfiBootServicesData, + sizeof(EFI_GUID), + (VOID **) &TmpGuidP); + if (EFI_ERROR(Status)) { + goto fail2; + } + *TmpGuidP = DevGuid; + Dev->DeviceGuid = TmpGuidP; + + DEBUG((DEBUG_INFO, "MvI2c: allocated device with address %x\n", (UINTN)SlaveAddress)); + return EFI_SUCCESS; + +fail2: + FreePool(TmpSlaveArray); +fail1: + FreePool(Dev); + + return Status; +} + +/* + * It is called by I2cBus to enumerate devices on I2C bus. In this case, + * enumeration is based on PCD configuration - all Slave addresses specified + * in PCD get their corresponding EFI_I2C_DEVICE structures here. + * + * After enumeration succeeds, Supported() function of drivers that installed + * DriverBinding protocol is called. + */ +STATIC +EFI_STATUS +EFIAPI +MvI2cEnumerate ( + IN CONST EFI_I2C_ENUMERATE_PROTOCOL *This, + IN OUT CONST EFI_I2C_DEVICE **Device + ) +{ + UINT8 *DevicesPcd; + UINTN Index; + UINT8 NextDeviceAddress; + + DevicesPcd = PcdGetPtr (PcdI2cSlaveAddresses); + if (*Device == NULL) { + if (DevicesPcd[0] != '\0') + MvI2cAllocDevice (DevicesPcd[0], Device); + return EFI_SUCCESS; + } else { + /* Device is not NULL, so something was already allocated */ + for (Index = 0; DevicesPcd[Index] != '\0'; Index++) { + if (DevicesPcd[Index] == (*Device)->DeviceIndex) { + NextDeviceAddress = DevicesPcd[Index + 1]; + if (NextDeviceAddress != '\0') { + MvI2cAllocDevice(NextDeviceAddress, Device); + return EFI_SUCCESS; + } + break; + } + } + *Device = NULL; + return EFI_SUCCESS; + } +} + +STATIC +EFI_STATUS +EFIAPI +MvI2cEnableConf ( + IN CONST EFI_I2C_BUS_CONFIGURATION_MANAGEMENT_PROTOCOL *This, + IN UINTN I2cBusConfiguration, + IN EFI_EVENT Event OPTIONAL, + IN EFI_STATUS *I2cStatus OPTIONAL + ) +{ + /* do nothing */ + if (I2cStatus != NULL) + I2cStatus = EFI_SUCCESS; + if (Event != NULL) + gBS->SignalEvent(Event); + return EFI_SUCCESS; +} diff --git a/Drivers/I2c/MvI2cDxe/MvI2cDxe.h b/Drivers/I2c/MvI2cDxe/MvI2cDxe.h new file mode 100644 index 0000000..8322eac --- /dev/null +++ b/Drivers/I2c/MvI2cDxe/MvI2cDxe.h @@ -0,0 +1,254 @@ +/******************************************************************************** +Copyright (C) 2016 Marvell International Ltd. + +Marvell BSD License Option + +If you received this File from Marvell, you may opt to use, redistribute and/or +modify this File under the following licensing terms. +Redistribution and use in source and binary forms, with or without modification, +are permitted provided that the following conditions are met: + +* Redistributions of source code must retain the above copyright notice, + this list of conditions and the following disclaimer. + +* Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + +* Neither the name of Marvell nor the names of its contributors may be + used to endorse or promote products derived from this software without + specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR +ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON +ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +*******************************************************************************/ + +#ifndef __MV_I2C_H__ +#define __MV_I2C_H__ + +#include <Uefi.h> + +#define I2C_BASE_ADDRESS 0xf0511000 + +#define I2C_SLAVE_ADDR 0x00 +#define I2C_EXT_SLAVE_ADDR 0x10 +#define I2C_DATA 0x04 + +#define I2C_CONTROL 0x08 +#define I2C_CONTROL_ACK (1 << 2) +#define I2C_CONTROL_IFLG (1 << 3) +#define I2C_CONTROL_STOP (1 << 4) +#define I2C_CONTROL_START (1 << 5) +#define I2C_CONTROL_I2CEN (1 << 6) +#define I2C_CONTROL_INTEN (1 << 7) + +#define I2C_STATUS 0x0c +#define I2C_STATUS_START 0x08 +#define I2C_STATUS_RPTD_START 0x10 +#define I2C_STATUS_ADDR_W_ACK 0x18 +#define I2C_STATUS_DATA_WR_ACK 0x28 +#define I2C_STATUS_ADDR_R_ACK 0x40 +#define I2C_STATUS_DATA_RD_ACK 0x50 +#define I2C_STATUS_DATA_RD_NOACK 0x58 + +#define I2C_BAUD_RATE 0x0c +#define I2C_BAUD_RATE_PARAM(M,N) ((((M) << 3) | ((N) & 0x7)) & 0x7f) +#define I2C_BAUD_RATE_RAW(C,M,N) ((C)/((10*(M+1))<<(N+1))) +#define I2C_M_FROM_BAUD(baud) (((baud) >> 3) & 0xf) +#define I2C_N_FROM_BAUD(baud) ((baud) & 0x7) + +#define I2C_SOFT_RESET 0x1c +#define I2C_TRANSFER_TIMEOUT 10000 +#define I2C_OPERATION_TIMEOUT 1000 + +#define I2C_UNKNOWN 0x0 +#define I2C_SLOW 0x1 +#define I2C_FAST 0x2 +#define I2C_FASTEST 0x3 + +#define I2C_FLAG_NORESTART 0x00000002 + +#define I2C_MASTER_SIGNATURE SIGNATURE_32 ('I', '2', 'C', 'M') + +typedef struct { + UINT32 Signature; + EFI_HANDLE Controller; + EFI_LOCK Lock; + UINTN TclkFrequency; + UINTN BaseAddress; + EFI_I2C_MASTER_PROTOCOL I2cMaster; + EFI_I2C_ENUMERATE_PROTOCOL I2cEnumerate; + EFI_I2C_BUS_CONFIGURATION_MANAGEMENT_PROTOCOL I2cBusConf; +} I2C_MASTER_CONTEXT; + +#define I2C_SC_FROM_MASTER(a) CR (a, I2C_MASTER_CONTEXT, I2cMaster, I2C_MASTER_SIGNATURE) +#define I2C_SC_FROM_ENUMERATE(a) CR (a, I2C_MASTER_CONTEXT, I2cEnumerate, I2C_MASTER_SIGNATURE) +#define I2C_SC_FROM_BUSCONF(a) CR (a, I2C_MASTER_CONTEXT, I2cBusConf, I2C_MASTER_SIGNATURE) + +typedef struct { + UINT32 raw; + UINTN param; + UINTN m; + UINTN n; +} MV_I2C_BAUD_RATE; + +typedef struct { + VENDOR_DEVICE_PATH Guid; + EFI_DEVICE_PATH_PROTOCOL End; +} MV_I2C_DEVICE_PATH; + +STATIC +UINT32 +I2C_READ( + IN I2C_MASTER_CONTEXT *I2cMasterContext, + IN UINTN off + ); + +STATIC +EFI_STATUS +I2C_WRITE ( + IN I2C_MASTER_CONTEXT *I2cMasterContext, + IN UINTN off, + IN UINT32 val + ); + +EFI_STATUS +EFIAPI +MvI2cInitialise ( + IN EFI_HANDLE ImageHandle, + IN EFI_SYSTEM_TABLE *SystemTable + ); + +STATIC +VOID +MvI2cControlClear ( + IN I2C_MASTER_CONTEXT *I2cMasterContext, + IN UINT32 mask + ); + +STATIC +VOID +MvI2cControlSet ( + IN I2C_MASTER_CONTEXT *I2cMasterContext, + IN UINT32 mask + ); + +STATIC +VOID +MvI2cClearIflg ( + IN I2C_MASTER_CONTEXT *I2cMasterContext + ); +STATIC +UINTN +MvI2cPollCtrl ( + IN I2C_MASTER_CONTEXT *I2cMasterContext, + IN UINTN timeout, + IN UINT32 mask + ); + +STATIC +EFI_STATUS +MvI2cLockedStart ( + IN I2C_MASTER_CONTEXT *I2cMasterContext, + IN INT32 mask, + IN UINT8 slave, + IN UINTN timeout + ); + +STATIC +VOID +MvI2cCalBaudRate ( + IN I2C_MASTER_CONTEXT *I2cMasterContext, + IN CONST UINT32 target, + IN OUT MV_I2C_BAUD_RATE *rate, + UINT32 clk + ); + +EFI_STATUS +EFIAPI +MvI2cReset ( + IN CONST EFI_I2C_MASTER_PROTOCOL *This + ); + +STATIC +EFI_STATUS +MvI2cRepeatedStart ( + IN I2C_MASTER_CONTEXT *I2cMasterContext, + IN UINT8 slave, + IN UINTN timeout + ); + +STATIC +EFI_STATUS +MvI2cStart ( + IN I2C_MASTER_CONTEXT *I2cMasterContext, + IN UINT8 slave, + IN UINTN timeout + ); + +STATIC +EFI_STATUS +MvI2cStop ( + IN I2C_MASTER_CONTEXT *I2cMasterContext + ); + +STATIC +EFI_STATUS +MvI2cRead ( + IN I2C_MASTER_CONTEXT *I2cMasterContext, + IN OUT UINT8 *buf, + IN UINTN len, + IN OUT UINTN *read, + IN UINTN last, + IN UINTN delay + ); + +STATIC +EFI_STATUS +MvI2cWrite ( + IN I2C_MASTER_CONTEXT *I2cMasterContext, + IN OUT CONST UINT8 *buf, + IN UINTN len, + IN OUT UINTN *sent, + IN UINTN timeout + ); + +STATIC +EFI_STATUS +EFIAPI +MvI2cStartRequest ( + IN CONST EFI_I2C_MASTER_PROTOCOL *This, + IN UINTN SlaveAddress, + IN EFI_I2C_REQUEST_PACKET *RequestPacket, + IN EFI_EVENT Event OPTIONAL, + OUT EFI_STATUS *I2cStatus OPTIONAL + ); + +STATIC +EFI_STATUS +EFIAPI +MvI2cEnumerate ( + IN CONST EFI_I2C_ENUMERATE_PROTOCOL *This, + IN OUT CONST EFI_I2C_DEVICE **Device + ); + +STATIC +EFI_STATUS +EFIAPI +MvI2cEnableConf ( + IN CONST EFI_I2C_BUS_CONFIGURATION_MANAGEMENT_PROTOCOL *This, + IN UINTN I2cBusConfiguration, + IN EFI_EVENT Event OPTIONAL, + IN EFI_STATUS *I2cStatus OPTIONAL + ); + +#endif // __MV_I2C_H__ diff --git a/Drivers/I2c/MvI2cDxe/MvI2cDxe.inf b/Drivers/I2c/MvI2cDxe/MvI2cDxe.inf new file mode 100644 index 0000000..28b0199 --- /dev/null +++ b/Drivers/I2c/MvI2cDxe/MvI2cDxe.inf @@ -0,0 +1,73 @@ +# Copyright (C) 2016 Marvell International Ltd. +# +# Marvell BSD License Option +# +# If you received this File from Marvell, you may opt to use, redistribute and/or +# modify this File under the following licensing terms. +# Redistribution and use in source and binary forms, with or without modification, +# are permitted provided that the following conditions are met: +# +#* Redistributions of source code must retain the above copyright notice, +# this list of conditions and the following disclaimer. +# +#* Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# +#* Neither the name of Marvell nor the names of its contributors may be +# used to endorse or promote products derived from this software without +# specific prior written permission. +# +# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +# DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR +# ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +# (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +# LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON +# ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +# SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +# + +[Defines] + INF_VERSION = 0x00010005 + BASE_NAME = MvI2cDxe + FILE_GUID = 59fc3843-d8d4-40aa-ae07-38967138509b + MODULE_TYPE = DXE_DRIVER + VERSION_STRING = 1.0 + ENTRY_POINT = MvI2cInitialise + +[Sources.common] + MvI2cDxe.c + +[Packages] + MdePkg/MdePkg.dec + MdeModulePkg/MdeModulePkg.dec + ArmPlatformPkg/ArmPlatformPkg.dec + ArmPkg/ArmPkg.dec + OpenPlatformPkg/Platforms/Marvell/Marvell.dec + +[LibraryClasses] + IoLib + PcdLib + BaseLib + DebugLib + UefiLib + UefiDriverEntryPoint + UefiBootServicesTableLib + +[Protocols] + gEfiI2cMasterProtocolGuid + gEfiDevicePathProtocolGuid + gEfiI2cEnumerateProtocolGuid + gEfiI2cBusConfigurationManagementProtocolGuid + +[Pcd] + gMarvellTokenSpaceGuid.PcdI2cSlaveAddresses + gMarvellTokenSpaceGuid.PcdI2cBaseAddress + gMarvellTokenSpaceGuid.PcdI2cClockFrequency + gMarvellTokenSpaceGuid.PcdI2cBaudRate + +[Depex] + TRUE diff --git a/Platforms/Marvell/Marvell.dec b/Platforms/Marvell/Marvell.dec index ae923a9..2a7a7e2 100644 --- a/Platforms/Marvell/Marvell.dec +++ b/Platforms/Marvell/Marvell.dec @@ -104,3 +104,9 @@ gMarvellTokenSpaceGuid.PcdChip3MppSel6|{ 0 }|VOID*|0x30000044 gMarvellTokenSpaceGuid.PcdChip3MppSel7|{ 0 }|VOID*|0x30000045
+#I2C + gMarvellTokenSpaceGuid.PcdI2cSlaveAddresses|{ 0 }|VOID*|0x3000046 + gMarvellTokenSpaceGuid.PcdI2cBaseAddress|0|UINT64|0x3000047 + gMarvellTokenSpaceGuid.PcdI2cClockFrequency|0|UINT32|0x3000048 + gMarvellTokenSpaceGuid.PcdI2cBaudRate|0|UINT32|0x3000049 +
From: Jan Dąbroś jsd@semihalf.com
Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Bartosz Szczepanek bsz@semihalf.com Signed-off-by: Marcin Wojtas mw@semihalf.com --- Platforms/Marvell/Armada/Apn806.dsc | 6 ++++++ Platforms/Marvell/Armada/Armada.dsc.inc | 4 ++++ Platforms/Marvell/Armada/Armada7040.fdf | 2 ++ Platforms/Marvell/Armada/Armada7040_rz.dsc | 6 ++++++ 4 files changed, 18 insertions(+)
diff --git a/Platforms/Marvell/Armada/Apn806.dsc b/Platforms/Marvell/Armada/Apn806.dsc index d3c73cf..0971937 100644 --- a/Platforms/Marvell/Armada/Apn806.dsc +++ b/Platforms/Marvell/Armada/Apn806.dsc @@ -62,3 +62,9 @@ gMarvellTokenSpaceGuid.PcdChip0MppPinCount|16 gMarvellTokenSpaceGuid.PcdChip0MppSel0|{ 0x1, 0x1, 0x1, 0x1, 0x1, 0x1, 0x1, 0x1, 0x1, 0x0 } gMarvellTokenSpaceGuid.PcdChip0MppSel1|{ 0x0, 0x0, 0x0, 0x1, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0 } + + # I2C + gMarvellTokenSpaceGuid.PcdI2cSlaveAddresses|{ 0x50, 0x57, 0x60 } + gMarvellTokenSpaceGuid.PcdI2cBaseAddress|0xF0511000 + gMarvellTokenSpaceGuid.PcdI2cClockFrequency|200000000 + gMarvellTokenSpaceGuid.PcdI2cBaudRate|100000 diff --git a/Platforms/Marvell/Armada/Armada.dsc.inc b/Platforms/Marvell/Armada/Armada.dsc.inc index b5108d9..6c1518f 100644 --- a/Platforms/Marvell/Armada/Armada.dsc.inc +++ b/Platforms/Marvell/Armada/Armada.dsc.inc @@ -389,6 +389,10 @@ ArmPkg/Drivers/TimerDxe/TimerDxe.inf ArmPkg/Drivers/GenericWatchdogDxe/GenericWatchdogDxe.inf
+ # Platform drivers + OpenPlatformPkg/Drivers/I2c/MvI2cDxe/MvI2cDxe.inf + MdeModulePkg/Bus/I2c/I2cDxe/I2cDxe.inf + MdeModulePkg/Core/RuntimeDxe/RuntimeDxe.inf MdeModulePkg/Universal/SecurityStubDxe/SecurityStubDxe.inf MdeModulePkg/Universal/CapsuleRuntimeDxe/CapsuleRuntimeDxe.inf diff --git a/Platforms/Marvell/Armada/Armada7040.fdf b/Platforms/Marvell/Armada/Armada7040.fdf index f1aa722..23a8db5 100644 --- a/Platforms/Marvell/Armada/Armada7040.fdf +++ b/Platforms/Marvell/Armada/Armada7040.fdf @@ -102,6 +102,8 @@ FvNameGuid = 5eda4200-2c5f-43cb-9da3-0baf74b1b30c INF EmbeddedPkg/ResetRuntimeDxe/ResetRuntimeDxe.inf INF EmbeddedPkg/RealTimeClockRuntimeDxe/RealTimeClockRuntimeDxe.inf INF EmbeddedPkg/MetronomeDxe/MetronomeDxe.inf + INF OpenPlatformPkg/Drivers/I2c/MvI2cDxe/MvI2cDxe.inf + INF MdeModulePkg/Bus/I2c/I2cDxe/I2cDxe.inf
# Multiple Console IO support INF MdeModulePkg/Universal/Console/ConPlatformDxe/ConPlatformDxe.inf diff --git a/Platforms/Marvell/Armada/Armada7040_rz.dsc b/Platforms/Marvell/Armada/Armada7040_rz.dsc index 8627885..f7aca6d 100644 --- a/Platforms/Marvell/Armada/Armada7040_rz.dsc +++ b/Platforms/Marvell/Armada/Armada7040_rz.dsc @@ -74,3 +74,9 @@ gMarvellTokenSpaceGuid.PcdChip1MppSel4|{ 0x7, 0x7, 0x8, 0x8, 0x1, 0x1, 0x1, 0x1, 0x1, 0x1 } gMarvellTokenSpaceGuid.PcdChip1MppSel5|{ 0x1, 0x1, 0x1, 0x1, 0x1, 0x1, 0xE, 0xE, 0xE, 0xE } gMarvellTokenSpaceGuid.PcdChip1MppSel6|{ 0xE, 0xE, 0xE, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0 } + + # I2C + gMarvellTokenSpaceGuid.PcdI2cSlaveAddresses|{ 0x50, 0x57, 0x60 } + gMarvellTokenSpaceGuid.PcdI2cBaseAddress|0xF0511000 + gMarvellTokenSpaceGuid.PcdI2cClockFrequency|200000000 + gMarvellTokenSpaceGuid.PcdI2cBaudRate|100000
From: Bartosz Szczepanek bsz@semihalf.com
BdsLib requires modification - moving it into our directory reduces the impact of change, not affecting other platforms.
Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Bartosz Szczepanek bsz@semihalf.com Signed-off-by: Marcin Wojtas mw@semihalf.com --- Platforms/Marvell/Armada/Armada.dsc.inc | 2 +- .../Library/Armada7040BdsLib/Armada7040BdsLib.c | 427 +++++++++++++++++++++ .../Library/Armada7040BdsLib/Armada7040BdsLib.h | 37 ++ .../Library/Armada7040BdsLib/Armada7040BdsLib.inf | 66 ++++ 4 files changed, 531 insertions(+), 1 deletion(-) create mode 100644 Platforms/Marvell/Armada/Library/Armada7040BdsLib/Armada7040BdsLib.c create mode 100644 Platforms/Marvell/Armada/Library/Armada7040BdsLib/Armada7040BdsLib.h create mode 100644 Platforms/Marvell/Armada/Library/Armada7040BdsLib/Armada7040BdsLib.inf
diff --git a/Platforms/Marvell/Armada/Armada.dsc.inc b/Platforms/Marvell/Armada/Armada.dsc.inc index 6c1518f..fa223f9 100644 --- a/Platforms/Marvell/Armada/Armada.dsc.inc +++ b/Platforms/Marvell/Armada/Armada.dsc.inc @@ -127,7 +127,7 @@ BdsLib|ArmPkg/Library/BdsLib/BdsLib.inf CapsuleLib|MdeModulePkg/Library/DxeCapsuleLibNull/DxeCapsuleLibNull.inf GenericBdsLib|IntelFrameworkModulePkg/Library/GenericBdsLib/GenericBdsLib.inf - PlatformBdsLib|ArmPlatformPkg/Library/PlatformIntelBdsLib/PlatformIntelBdsLib.inf + PlatformBdsLib|OpenPlatformPkg/Platforms/Marvell/Armada/Library/Armada7040BdsLib/Armada7040BdsLib.inf CustomizedDisplayLib|MdeModulePkg/Library/CustomizedDisplayLib/CustomizedDisplayLib.inf FdtLib|EmbeddedPkg/Library/FdtLib/FdtLib.inf
diff --git a/Platforms/Marvell/Armada/Library/Armada7040BdsLib/Armada7040BdsLib.c b/Platforms/Marvell/Armada/Library/Armada7040BdsLib/Armada7040BdsLib.c new file mode 100644 index 0000000..04a5bab --- /dev/null +++ b/Platforms/Marvell/Armada/Library/Armada7040BdsLib/Armada7040BdsLib.c @@ -0,0 +1,427 @@ +/** @file + +Copyright (c) 2004 - 2008, Intel Corporation. All rights reserved.<BR> +Copyright (c) 2014, ARM Ltd. All rights reserved.<BR> +Copyright (c) 2016 Marvell International Ltd. + +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 "Armada7040BdsLib.h" + +/// +/// Predefined platform default time out value +/// +UINT16 gPlatformBootTimeOutDefault; + +EFI_STATUS +EFIAPI +Armada7040BdsConstructor ( + IN EFI_HANDLE ImageHandle, + IN EFI_SYSTEM_TABLE *SystemTable + ) +{ + gPlatformBootTimeOutDefault = (UINT16)PcdGet16 (PcdPlatformBootTimeOut); + return EFI_SUCCESS; +} + +/** + An empty function to pass error checking of CreateEventEx (). + + @param Event Event whose notification function is being invoked. + @param Context Pointer to the notification function's context, + which is implementation-dependent. + +**/ +STATIC +VOID +EFIAPI +EmptyCallbackFunction ( + IN EFI_EVENT Event, + IN VOID *Context + ) +{ +} + +// +// BDS Platform Functions +// +/** + Platform Bds init. Include the platform firmware vendor, revision + and so crc check. + +**/ +VOID +EFIAPI +PlatformBdsInit ( + VOID + ) +{ + EFI_EVENT EndOfDxeEvent; + EFI_STATUS Status; + + // + // Signal EndOfDxe PI Event + // + Status = gBS->CreateEventEx ( + EVT_NOTIFY_SIGNAL, + TPL_CALLBACK, + EmptyCallbackFunction, + NULL, + &gEfiEndOfDxeEventGroupGuid, + &EndOfDxeEvent + ); + if (!EFI_ERROR (Status)) { + gBS->SignalEvent (EndOfDxeEvent); + gBS->CloseEvent (EndOfDxeEvent); + } +} + +STATIC +EFI_STATUS +GetConsoleDevicePathFromVariable ( + IN CHAR16* ConsoleVarName, + IN CHAR16* DefaultConsolePaths, + OUT EFI_DEVICE_PATH** DevicePaths + ) +{ + EFI_STATUS Status; + UINTN Size; + EFI_DEVICE_PATH_PROTOCOL* DevicePathInstances; + EFI_DEVICE_PATH_PROTOCOL* DevicePathInstance; + CHAR16* DevicePathStr; + CHAR16* NextDevicePathStr; + EFI_DEVICE_PATH_FROM_TEXT_PROTOCOL *EfiDevicePathFromTextProtocol; + + Status = EFI_SUCCESS; + Size = 0; + + DevicePathInstances = BdsLibGetVariableAndSize (ConsoleVarName, &gEfiGlobalVariableGuid, &Size); + if (DevicePathInstances == NULL) { + // In case no default console device path has been defined we assume a driver handles the console (eg: SimpleTextInOutSerial) + if ((DefaultConsolePaths == NULL) || (DefaultConsolePaths[0] == L'\0')) { + *DevicePaths = NULL; + return EFI_SUCCESS; + } + + Status = gBS->LocateProtocol (&gEfiDevicePathFromTextProtocolGuid, NULL, (VOID **)&EfiDevicePathFromTextProtocol); + ASSERT_EFI_ERROR(Status); + + // Extract the Device Path instances from the multi-device path string + while ((DefaultConsolePaths != NULL) && (DefaultConsolePaths[0] != L'\0')) { + NextDevicePathStr = StrStr (DefaultConsolePaths, L";"); + if (NextDevicePathStr == NULL) { + DevicePathStr = DefaultConsolePaths; + DefaultConsolePaths = NULL; + } else { + DevicePathStr = (CHAR16*)AllocateCopyPool ((NextDevicePathStr - DefaultConsolePaths + 1) * sizeof(CHAR16), DefaultConsolePaths); + *(DevicePathStr + (NextDevicePathStr - DefaultConsolePaths)) = L'\0'; + DefaultConsolePaths = NextDevicePathStr; + if (DefaultConsolePaths[0] == L';') { + DefaultConsolePaths++; + } + } + + DevicePathInstance = EfiDevicePathFromTextProtocol->ConvertTextToDevicePath (DevicePathStr); + ASSERT(DevicePathInstance != NULL); + DevicePathInstances = AppendDevicePathInstance (DevicePathInstances, DevicePathInstance); + + if (NextDevicePathStr != NULL) { + FreePool (DevicePathStr); + } + FreePool (DevicePathInstance); + } + + // Set the environment variable with this device path multi-instances + Size = GetDevicePathSize (DevicePathInstances); + if (Size > 0) { + gRT->SetVariable ( + ConsoleVarName, + &gEfiGlobalVariableGuid, + EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_BOOTSERVICE_ACCESS | EFI_VARIABLE_RUNTIME_ACCESS, + Size, + DevicePathInstances + ); + } else { + Status = EFI_INVALID_PARAMETER; + } + } + + if (!EFI_ERROR(Status)) { + *DevicePaths = DevicePathInstances; + } + return Status; +} + +STATIC +EFI_STATUS +InitializeConsolePipe ( + IN EFI_DEVICE_PATH *ConsoleDevicePaths, + IN EFI_GUID *Protocol, + OUT EFI_HANDLE *Handle, + OUT VOID* *Interface + ) +{ + EFI_STATUS Status; + UINTN Size; + UINTN NoHandles; + EFI_HANDLE *Buffer; + EFI_DEVICE_PATH_PROTOCOL* DevicePath; + + // Connect all the Device Path Consoles + while (ConsoleDevicePaths != NULL) { + DevicePath = GetNextDevicePathInstance (&ConsoleDevicePaths, &Size); + + Status = BdsLibConnectDevicePath (DevicePath); + if (!EFI_ERROR (Status)) { + // + // If BdsLibConnectDevicePath () succeeded, *Handle must have a non-NULL + // value. So ASSERT that this is the case. + // + gBS->LocateDevicePath (&gEfiDevicePathProtocolGuid, &DevicePath, Handle); + ASSERT (*Handle != NULL); + } + DEBUG_CODE_BEGIN(); + if (EFI_ERROR(Status)) { + // We convert back to the text representation of the device Path + EFI_DEVICE_PATH_TO_TEXT_PROTOCOL *DevicePathToTextProtocol; + CHAR16 *DevicePathTxt; + + DevicePathToTextProtocol = NULL; + gBS->LocateProtocol(&gEfiDevicePathToTextProtocolGuid, NULL, (VOID **) &DevicePathToTextProtocol); + if (DevicePathToTextProtocol != NULL) { + DevicePathTxt = DevicePathToTextProtocol->ConvertDevicePathToText (DevicePath, TRUE, TRUE); + + DEBUG((EFI_D_ERROR,"Fail to start the console with the Device Path '%s'. (Error '%r')\n", DevicePathTxt, Status)); + + FreePool (DevicePathTxt); + } + } + DEBUG_CODE_END(); + + // If the console splitter driver is not supported by the platform then use the first Device Path + // instance for the console interface. + if (!EFI_ERROR(Status) && (*Interface == NULL)) { + Status = gBS->HandleProtocol (*Handle, Protocol, Interface); + } + } + + // No Device Path has been defined for this console interface. We take the first protocol implementation + if (*Interface == NULL) { + Status = gBS->LocateHandleBuffer (ByProtocol, Protocol, NULL, &NoHandles, &Buffer); + if (EFI_ERROR (Status)) { + BdsLibConnectAll (); + Status = gBS->LocateHandleBuffer (ByProtocol, Protocol, NULL, &NoHandles, &Buffer); + } + + if (!EFI_ERROR(Status)) { + *Handle = Buffer[0]; + Status = gBS->HandleProtocol (*Handle, Protocol, Interface); + ASSERT_EFI_ERROR (Status); + FreePool (Buffer); + } + } else { + Status = EFI_SUCCESS; + } + + return Status; +} + +/** + Connect the predefined platform default console device. Always try to find + and enable the vga device if have. + + @param PlatformConsole Predefined platform default console device array. + + @retval EFI_SUCCESS Success connect at least one ConIn and ConOut + device, there must have one ConOut device is + active vga device. + @return Return the status of BdsLibConnectAllDefaultConsoles () + +**/ +EFI_STATUS +PlatformBdsConnectConsole ( + VOID + ) +{ + EFI_STATUS Status; + EFI_DEVICE_PATH* ConOutDevicePaths; + EFI_DEVICE_PATH* ConInDevicePaths; + EFI_DEVICE_PATH* ConErrDevicePaths; + + // By getting the Console Device Paths from the environment variables before initializing the console pipe, we + // create the 3 environment variables (ConIn, ConOut, ConErr) that allows to initialize all the console interface + // of newly installed console drivers + Status = GetConsoleDevicePathFromVariable (L"ConOut", (CHAR16*)PcdGetPtr(PcdDefaultConOutPaths), &ConOutDevicePaths); + ASSERT_EFI_ERROR (Status); + Status = GetConsoleDevicePathFromVariable (L"ConIn", (CHAR16*)PcdGetPtr(PcdDefaultConInPaths), &ConInDevicePaths); + ASSERT_EFI_ERROR (Status); + Status = GetConsoleDevicePathFromVariable (L"ErrOut", (CHAR16*)PcdGetPtr(PcdDefaultConOutPaths), &ConErrDevicePaths); + ASSERT_EFI_ERROR (Status); + + // Initialize the Consoles + Status = InitializeConsolePipe (ConOutDevicePaths, &gEfiSimpleTextOutProtocolGuid, &gST->ConsoleOutHandle, (VOID **)&gST->ConOut); + ASSERT_EFI_ERROR (Status); + Status = InitializeConsolePipe (ConInDevicePaths, &gEfiSimpleTextInProtocolGuid, &gST->ConsoleInHandle, (VOID **)&gST->ConIn); + ASSERT_EFI_ERROR (Status); + Status = InitializeConsolePipe (ConErrDevicePaths, &gEfiSimpleTextOutProtocolGuid, &gST->StandardErrorHandle, (VOID **)&gST->StdErr); + if (EFI_ERROR(Status)) { + // In case of error, we reuse the console output for the error output + gST->StandardErrorHandle = gST->ConsoleOutHandle; + gST->StdErr = gST->ConOut; + } + + return Status; +} + +/** + Connect with predefined platform connect sequence, + the OEM/IBV can customize with their own connect sequence. +**/ +VOID +PlatformBdsConnectSequence ( + VOID + ) +{ +} + +/** + Load the predefined driver option, OEM/IBV can customize this + to load their own drivers + + @param BdsDriverLists - The header of the driver option link list. + +**/ +VOID +PlatformBdsGetDriverOption ( + IN OUT LIST_ENTRY *BdsDriverLists + ) +{ +} + +/** + Perform the platform diagnostic, such like test memory. OEM/IBV also + can customize this function to support specific platform diagnostic. + + @param MemoryTestLevel The memory test intensive level + @param QuietBoot Indicate if need to enable the quiet boot + @param BaseMemoryTest A pointer to BdsMemoryTest() + +**/ +VOID +PlatformBdsDiagnostics ( + IN EXTENDMEM_COVERAGE_LEVEL MemoryTestLevel, + IN BOOLEAN QuietBoot, + IN BASEM_MEMORY_TEST BaseMemoryTest + ) +{ +} + +/** + The function will execute with as the platform policy, current policy + is driven by boot mode. IBV/OEM can customize this code for their specific + policy action. + + @param DriverOptionList The header of the driver option link list + @param BootOptionList The header of the boot option link list + @param ProcessCapsules A pointer to ProcessCapsules() + @param BaseMemoryTest A pointer to BaseMemoryTest() + +**/ +VOID +EFIAPI +PlatformBdsPolicyBehavior ( + IN LIST_ENTRY *DriverOptionList, + IN LIST_ENTRY *BootOptionList, + IN PROCESS_CAPSULES ProcessCapsules, + IN BASEM_MEMORY_TEST BaseMemoryTest + ) +{ + EFI_STATUS Status; + + Status = PlatformBdsConnectConsole (); + ASSERT_EFI_ERROR (Status); + + // + // Show the splash screen. + // + EnableQuietBoot (PcdGetPtr (PcdLogoFile)); +} + +/** + Hook point after a boot attempt succeeds. We don't expect a boot option to + return, so the UEFI 2.0 specification defines that you will default to an + interactive mode and stop processing the BootOrder list in this case. This + is also a platform implementation and can be customized by IBV/OEM. + + @param Option Pointer to Boot Option that succeeded to boot. + +**/ +VOID +EFIAPI +PlatformBdsBootSuccess ( + IN BDS_COMMON_OPTION *Option + ) +{ +} + +/** + Hook point after a boot attempt fails. + + @param Option Pointer to Boot Option that failed to boot. + @param Status Status returned from failed boot. + @param ExitData Exit data returned from failed boot. + @param ExitDataSize Exit data size returned from failed boot. + +**/ +VOID +EFIAPI +PlatformBdsBootFail ( + IN BDS_COMMON_OPTION *Option, + IN EFI_STATUS Status, + IN CHAR16 *ExitData, + IN UINTN ExitDataSize + ) +{ +} + +/** + This function locks platform flash that is not allowed to be updated during normal boot path. + The flash layout is platform specific. +**/ +VOID +EFIAPI +PlatformBdsLockNonUpdatableFlash ( + VOID + ) +{ + return; +} + + +/** + Lock the ConsoleIn device in system table. All key + presses will be ignored until the Password is typed in. The only way to + disable the password is to type it in to a ConIn device. + + @param Password Password used to lock ConIn device. + + @retval EFI_SUCCESS lock the Console In Spliter virtual handle successfully. + @retval EFI_UNSUPPORTED Password not found + +**/ +EFI_STATUS +EFIAPI +LockKeyboards ( + IN CHAR16 *Password + ) +{ + return EFI_UNSUPPORTED; +} diff --git a/Platforms/Marvell/Armada/Library/Armada7040BdsLib/Armada7040BdsLib.h b/Platforms/Marvell/Armada/Library/Armada7040BdsLib/Armada7040BdsLib.h new file mode 100644 index 0000000..5a8458a --- /dev/null +++ b/Platforms/Marvell/Armada/Library/Armada7040BdsLib/Armada7040BdsLib.h @@ -0,0 +1,37 @@ +/** @file + Head file for BDS Platform specific code + +Copyright (c) 2004 - 2008, Intel Corporation. All rights reserved.<BR> +Copyright (c) 2016 Marvell International Ltd. + +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. + +**/ + +#ifndef _INTEL_BDS_PLATFORM_H_ +#define _INTEL_BDS_PLATFORM_H_ + +#include <Protocol/DevicePathFromText.h> +#include <Protocol/DevicePathToText.h> + +#include <Library/BaseMemoryLib.h> +#include <Library/DebugLib.h> +#include <Library/DevicePathLib.h> +#include <Library/UefiBootServicesTableLib.h> +#include <Library/UefiRuntimeServicesTableLib.h> +#include <Library/MemoryAllocationLib.h> +#include <Library/BaseLib.h> +#include <Library/PcdLib.h> +#include <Library/GenericBdsLib.h> +#include <Library/PlatformBdsLib.h> + +#include <Guid/GlobalVariable.h> +#include <Guid/EventGroup.h> + +#endif // _INTEL_BDS_PLATFORM_H diff --git a/Platforms/Marvell/Armada/Library/Armada7040BdsLib/Armada7040BdsLib.inf b/Platforms/Marvell/Armada/Library/Armada7040BdsLib/Armada7040BdsLib.inf new file mode 100644 index 0000000..d1167d0 --- /dev/null +++ b/Platforms/Marvell/Armada/Library/Armada7040BdsLib/Armada7040BdsLib.inf @@ -0,0 +1,66 @@ +## @file +# Implementation for PlatformBdsLib library class interfaces. +# using ARM Platform framework. +# +# Copyright (c) 2007 - 2014, Intel Corporation. All rights reserved.<BR> +# Copyright (c) 2014, ARM Ltd. All rights reserved.<BR> +# Copyright (c) 2016 Marvell International Ltd. +# +# 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 = Armada7040BdsLib + FILE_GUID = 67780d14-60eb-4894-ab7c-eed6af427f9f + MODULE_TYPE = DXE_DRIVER + VERSION_STRING = 1.0 + LIBRARY_CLASS = PlatformBdsLib|DXE_DRIVER + CONSTRUCTOR = Armada7040BdsConstructor + +# +# The following information is for reference only and not required by the build tools. +# +# VALID_ARCHITECTURES = ARM AARCH64 +# + +[Sources] + Armada7040BdsLib.c + Armada7040BdsLib.h + +[Packages] + ArmPkg/ArmPkg.dec + ArmPlatformPkg/ArmPlatformPkg.dec + MdePkg/MdePkg.dec + MdeModulePkg/MdeModulePkg.dec + IntelFrameworkModulePkg/IntelFrameworkModulePkg.dec + +[LibraryClasses] + BaseLib + BaseMemoryLib + DebugLib + DevicePathLib + MemoryAllocationLib + UefiBootServicesTableLib + PcdLib + GenericBdsLib + +[Guids] + gEfiEndOfDxeEventGroupGuid + +[Pcd] + gArmPlatformTokenSpaceGuid.PcdDefaultConInPaths + gArmPlatformTokenSpaceGuid.PcdDefaultConOutPaths + gEfiMdePkgTokenSpaceGuid.PcdPlatformBootTimeOut + gEfiIntelFrameworkModulePkgTokenSpaceGuid.PcdLogoFile + +[Protocols] + gEfiDevicePathFromTextProtocolGuid + gEfiDevicePathToTextProtocolGuid
From: Bartosz Szczepanek bsz@semihalf.com
BdsLibConnectAll() call repeats process of driver-controller connecting after drivers' initialisation. It is required to attach I2cDxe properly (after EFI_I2C_ENUMERATION_PROTOCOL is provided).
Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Bartosz Szczepanek bsz@semihalf.com Signed-off-by: Marcin Wojtas mw@semihalf.com --- Platforms/Marvell/Armada/Library/Armada7040BdsLib/Armada7040BdsLib.c | 1 + 1 file changed, 1 insertion(+)
diff --git a/Platforms/Marvell/Armada/Library/Armada7040BdsLib/Armada7040BdsLib.c b/Platforms/Marvell/Armada/Library/Armada7040BdsLib/Armada7040BdsLib.c index 04a5bab..01f7ebd 100644 --- a/Platforms/Marvell/Armada/Library/Armada7040BdsLib/Armada7040BdsLib.c +++ b/Platforms/Marvell/Armada/Library/Armada7040BdsLib/Armada7040BdsLib.c @@ -349,6 +349,7 @@ PlatformBdsPolicyBehavior ( Status = PlatformBdsConnectConsole (); ASSERT_EFI_ERROR (Status);
+ BdsLibConnectAll(); // // Show the splash screen. //
From: Bartosz Szczepanek bsz@semihalf.com
MvEeprom driver produces EFI_EEPROM_PROTOCOL, which can be used by other drivers or applications. Working EFI_I2C_IO_PROTOCOL is required by driver to operate.
EEPROM devices' addresses need to be fed via 'PcdEepromI2cAddresses'.
Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Bartosz Szczepanek bsz@semihalf.com Signed-off-by: Marcin Wojtas mw@semihalf.com --- Documentation/Marvell/Drivers/EepromDriver.txt | 95 ++++++++ Drivers/I2c/Devices/MvEeprom/MvEeprom.c | 292 +++++++++++++++++++++++++ Drivers/I2c/Devices/MvEeprom/MvEeprom.h | 90 ++++++++ Drivers/I2c/Devices/MvEeprom/MvEeprom.inf | 70 ++++++ Platforms/Marvell/Include/Protocol/Eeprom.h | 60 +++++ Platforms/Marvell/Marvell.dec | 4 + 6 files changed, 611 insertions(+) create mode 100644 Documentation/Marvell/Drivers/EepromDriver.txt create mode 100644 Drivers/I2c/Devices/MvEeprom/MvEeprom.c create mode 100644 Drivers/I2c/Devices/MvEeprom/MvEeprom.h create mode 100644 Drivers/I2c/Devices/MvEeprom/MvEeprom.inf create mode 100644 Platforms/Marvell/Include/Protocol/Eeprom.h
diff --git a/Documentation/Marvell/Drivers/EepromDriver.txt b/Documentation/Marvell/Drivers/EepromDriver.txt new file mode 100644 index 0000000..8c352c8 --- /dev/null +++ b/Documentation/Marvell/Drivers/EepromDriver.txt @@ -0,0 +1,95 @@ +1. Introduction +--------------- +**MvEeprom** driver creates EFI_EEPROM_PROTOCOL, which ++is used for managing eeprom. + +2. MvEeprom driver design +------------------------- +Every I2C device driver should implement EFI_DRIVER_BINDING_PROTOCOL and +consume EFI_I2C_IO_PROTOCOL for transactions on I2C bus. MvEeprom driver +additionally implements EFI_EEPROM_PROTOCOL. + + 2.1 EFI_DRIVER_BINDING_PROTOCOL + ------------------------------- + Driver Binding protocol is extensively covered in UEFI documentation, as + it is not specific to I2C stack. The only difference is that Supported() + function should check if EFI_I2C_IO_PROTOCOL provides valid EFI_GUID value. + Excerpt from MvEepromSupported(): + + Status = gBS->OpenProtocol ( + ControllerHandle, + &gEfiI2cIoProtocolGuid, + (VOID **) &TmpI2cIo, + gImageHandle, + ControllerHandle, + EFI_OPEN_PROTOCOL_BY_DRIVER + ); + if (EFI_ERROR(Status)) { + return EFI_UNSUPPORTED; + } + + /* get EEPROM devices' addresses from PCD */ + EepromAddresses = PcdGetPtr (PcdEepromI2cAddresses); + if (EepromAddresses == 0) { + Status = EFI_UNSUPPORTED; + goto out; + } + + Status = EFI_UNSUPPORTED; + for (i = 0; EepromAddresses[i] != '\0'; i++) { + /* last byte of GUID contains address on I2C bus */ + EepromGuid.Data4[7] = EepromAddresses[i]; + if (CompareGuid(TmpI2cIo->DeviceGuid, &EepromGuid)) { + DEBUG((DEBUG_INFO, "A8kEepromSupported: offered GUID fits desired\n")); + Status = EFI_SUCCESS; + break; + } + } + + 2.2 EFI_I2C_IO_PROTOCOL + ----------------------- + This protocol is provided by generic I2C stack. Multiple drivers can use IO + protocol at once, as queueing is implemented. + + QueueRequest is a routine that queues an I2C transaction to the I2C + controller for execution on the I2C bus. + + 2.3 EFI_EEPROM_PROTOCOL + ----------------------- + typedef struct _EFI_EEPROM_PROTOCOL EFI_EEPROM_PROTOCOL; + + #define EEPROM_READ 0x1 + #define EEPROM_WRITE 0x0 + typedef + EFI_STATUS + (EFIAPI *EFI_EEPROM_TRANSFER) ( + IN CONST EFI_EEPROM_PROTOCOL *This, + IN UINT16 Address, + IN UINT32 Length, + IN UINT8 *Buffer, + IN UINT8 Operation + ); + + struct _EFI_EEPROM_PROTOCOL { + EFI_EEPROM_TRANSFER Transfer; + UINT8 Identifier; + }; + +3. Adding new I2C slave device drivers +-------------------------------------- +In order to support I2C slave device other than EEPROM, new driver should +be created. Required steps follow. + + 1. Create driver directory (OpenPlatformPkg/Drivers/I2c/Devices/...). + 2. Create stubs of .inf and .c files (MvEeprom files are a reference), + include .inf file in platform .dsc and .fdf files. + 3. Implement EFI_DRIVER_BINDING_PROTOCOL - Start(), Stop(), Supported() + functions' implementation is a must. EFI_DRIVER_BINDING_PROTOCOL + should be installed at driver's entry point. + 4. Add I2C address of device to PcdI2cSlaveAddresses in .dsc file. + 5. Test available EFI_I2C_IO_PROTOCOLs in Supported() - find instance + with valid GUID (consisting of I2C_GUID and slave I2C address). + 6. Open EFI_I2C_IO_PROTOCOL for usage in Start(). After that, QueueRequest + function should be available. + 7. Implement core functionality of driver (using QueueRequest to access I2C). + 8. (not mandatory) Produce/consume additional protocols. diff --git a/Drivers/I2c/Devices/MvEeprom/MvEeprom.c b/Drivers/I2c/Devices/MvEeprom/MvEeprom.c new file mode 100644 index 0000000..2b0d191 --- /dev/null +++ b/Drivers/I2c/Devices/MvEeprom/MvEeprom.c @@ -0,0 +1,292 @@ +/******************************************************************************** +Copyright (C) 2016 Marvell International Ltd. + +Marvell BSD License Option + +If you received this File from Marvell, you may opt to use, redistribute and/or +modify this File under the following licensing terms. +Redistribution and use in source and binary forms, with or without modification, +are permitted provided that the following conditions are met: + +* Redistributions of source code must retain the above copyright notice, + this list of conditions and the following disclaimer. + +* Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + +* Neither the name of Marvell nor the names of its contributors may be + used to endorse or promote products derived from this software without + specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR +ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON +ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +*******************************************************************************/ + +#include <Protocol/DriverBinding.h> +#include <Protocol/I2cIo.h> +#include <Protocol/Eeprom.h> + +#include <Library/BaseLib.h> +#include <Library/BaseMemoryLib.h> +#include <Library/MemoryAllocationLib.h> +#include <Library/IoLib.h> +#include <Library/DebugLib.h> +#include <Library/PcdLib.h> +#include <Library/UefiLib.h> +#include <Library/UefiBootServicesTableLib.h> + +#include <Pi/PiI2c.h> + +#include "MvEeprom.h" + +/* Last byte of GUID will contain address of device */ +#define I2C_GUID \ + { \ + 0x391fc679, 0x6cb0, 0x4f01, { 0x9a, 0xc7, 0x8e, 0x1b, 0x78, 0x6b, 0x7a, 0x00 } \ + } + +EFI_DRIVER_BINDING_PROTOCOL gDriverBindingProtocol = { + MvEepromSupported, + MvEepromStart, + MvEepromStop +}; + +EFI_STATUS +EFIAPI +MvEepromSupported ( + IN EFI_DRIVER_BINDING_PROTOCOL *This, + IN EFI_HANDLE ControllerHandle, + IN EFI_DEVICE_PATH_PROTOCOL *RemainingDevicePath OPTIONAL + ) +{ + EFI_STATUS Status = EFI_UNSUPPORTED; + EFI_GUID EepromGuid = I2C_GUID; + EFI_I2C_IO_PROTOCOL *TmpI2cIo; + UINT8 *EepromAddresses; + UINTN i; + + Status = gBS->OpenProtocol ( + ControllerHandle, + &gEfiI2cIoProtocolGuid, + (VOID **) &TmpI2cIo, + gImageHandle, + ControllerHandle, + EFI_OPEN_PROTOCOL_BY_DRIVER + ); + if (EFI_ERROR(Status)) { + return EFI_UNSUPPORTED; + } + + /* get EEPROM devices' addresses from PCD */ + EepromAddresses = PcdGetPtr (PcdEepromI2cAddresses); + if (EepromAddresses == 0) { + Status = EFI_UNSUPPORTED; + DEBUG((DEBUG_INFO, "MvEepromSupported: I2C device found, but it's not EEPROM\n")); + goto out; + } + + Status = EFI_UNSUPPORTED; + for (i = 0; EepromAddresses[i] != '\0'; i++) { + /* last byte of GUID contains address on I2C bus */ + EepromGuid.Data4[7] = EepromAddresses[i]; + if (CompareGuid(TmpI2cIo->DeviceGuid, &EepromGuid)) { + DEBUG((DEBUG_INFO, "MvEepromSupported: attached to EEPROM device\n")); + Status = EFI_SUCCESS; + break; + } + } + +out: + gBS->CloseProtocol ( + ControllerHandle, + &gEfiI2cIoProtocolGuid, + gImageHandle, + ControllerHandle + ); + return Status; +} + +EFI_STATUS +EFIAPI +MvEepromTransfer ( + IN CONST EFI_EEPROM_PROTOCOL *This, + IN UINT16 Address, + IN UINT32 Length, + IN UINT8 *Buffer, + IN UINT8 Operation + ) +{ + EFI_I2C_REQUEST_PACKET *RequestPacket; + UINTN RequestPacketSize; + EFI_STATUS Status = EFI_SUCCESS; + EEPROM_CONTEXT *EepromContext = EEPROM_SC_FROM_EEPROM(This); + UINT32 BufferLength; + UINT32 Transmitted = 0; + UINT32 CurrentAddress = Address; + + ASSERT(EepromContext != NULL); + ASSERT(EepromContext->I2cIo != NULL); + + RequestPacketSize = sizeof(UINTN) + sizeof (EFI_I2C_OPERATION) * 2; + RequestPacket = AllocateZeroPool (RequestPacketSize); + if (RequestPacket == NULL) + return EFI_OUT_OF_RESOURCES; + /* First operation contains address, the second is buffer */ + RequestPacket->OperationCount = 2; + RequestPacket->Operation[0].LengthInBytes = 2; + RequestPacket->Operation[0].Buffer = AllocateZeroPool ( RequestPacket->Operation[0].LengthInBytes ); + if (RequestPacket->Operation[0].Buffer == NULL) { + FreePool(RequestPacket); + return EFI_OUT_OF_RESOURCES; + } + RequestPacket->Operation[1].Flags = (Operation == EEPROM_READ ? I2C_FLAG_READ : I2C_FLAG_NORESTART); + + while (Length > 0) { + CurrentAddress = Address + Transmitted; + BufferLength = (Length <= MAX_BUFFER_LENGTH ? Length : MAX_BUFFER_LENGTH); + RequestPacket->Operation[0].Buffer[0] = (CurrentAddress >> 8) & 0xff; + RequestPacket->Operation[0].Buffer[1] = CurrentAddress & 0xff; + RequestPacket->Operation[1].LengthInBytes = BufferLength; + RequestPacket->Operation[1].Buffer = Buffer + Transmitted; + Status = EepromContext->I2cIo->QueueRequest(EepromContext->I2cIo, 0, NULL, RequestPacket, NULL); + if (EFI_ERROR(Status)) { + DEBUG((DEBUG_ERROR, "MvEepromTransfer: error %d during transmission\n", Status)); + break; + } + Length -= BufferLength; + Transmitted += BufferLength; + } + + FreePool(RequestPacket->Operation[0].Buffer); + FreePool(RequestPacket); + return Status; +} + +EFI_STATUS +EFIAPI +MvEepromStart ( + IN EFI_DRIVER_BINDING_PROTOCOL *This, + IN EFI_HANDLE ControllerHandle, + IN EFI_DEVICE_PATH_PROTOCOL *RemainingDevicePath OPTIONAL + ) +{ + EFI_STATUS Status = EFI_SUCCESS; + EEPROM_CONTEXT *EepromContext; + + EepromContext = AllocateZeroPool (sizeof(EEPROM_CONTEXT)); + if (EepromContext == NULL) { + DEBUG((DEBUG_ERROR, "MvEeprom: allocation fail\n")); + return EFI_OUT_OF_RESOURCES; + } + + EepromContext->ControllerHandle = ControllerHandle; + EepromContext->Signature = EEPROM_SIGNATURE; + EepromContext->EepromProtocol.Transfer = MvEepromTransfer; + + Status = gBS->OpenProtocol ( + ControllerHandle, + &gEfiI2cIoProtocolGuid, + (VOID **) &EepromContext->I2cIo, + gImageHandle, + ControllerHandle, + EFI_OPEN_PROTOCOL_BY_DRIVER + ); + if (EFI_ERROR(Status)) { + DEBUG((DEBUG_ERROR, "MvEeprom: failed to open I2cIo\n")); + FreePool(EepromContext); + return EFI_UNSUPPORTED; + } + + EepromContext->EepromProtocol.Identifier = EepromContext->I2cIo->DeviceIndex; + Status = gBS->InstallMultipleProtocolInterfaces ( + &ControllerHandle, + &gEfiEepromProtocolGuid, &EepromContext->EepromProtocol, + NULL + ); + if (EFI_ERROR(Status)) { + DEBUG((DEBUG_ERROR, "MvEeprom: failed to install EEPROM protocol\n")); + goto fail; + } + + return Status; + +fail: + FreePool(EepromContext); + gBS->CloseProtocol ( + ControllerHandle, + &gEfiI2cIoProtocolGuid, + gImageHandle, + ControllerHandle + ); + + return Status; +} + +EFI_STATUS +EFIAPI +MvEepromStop ( + IN EFI_DRIVER_BINDING_PROTOCOL *This, + IN EFI_HANDLE ControllerHandle, + IN UINTN NumberOfChildren, + IN EFI_HANDLE *ChildHandleBuffer OPTIONAL + ) +{ + EFI_EEPROM_PROTOCOL *EepromProtocol; + EFI_STATUS Status; + EEPROM_CONTEXT *EepromContext; + + Status = gBS->OpenProtocol ( + ControllerHandle, + &gEfiEepromProtocolGuid, + (VOID **) &EepromProtocol, + This->DriverBindingHandle, + ControllerHandle, + EFI_OPEN_PROTOCOL_GET_PROTOCOL + ); + + if (EFI_ERROR (Status)) { + return EFI_DEVICE_ERROR; + } + EepromContext = EEPROM_SC_FROM_EEPROM(EepromProtocol); + + gBS->UninstallMultipleProtocolInterfaces ( + &ControllerHandle, + &gEfiEepromProtocolGuid, &EepromContext->EepromProtocol, + &gEfiDriverBindingProtocolGuid, &gDriverBindingProtocol, + NULL + ); + gBS->CloseProtocol ( + ControllerHandle, + &gEfiI2cIoProtocolGuid, + gImageHandle, + ControllerHandle + ); + FreePool(EepromContext); + return EFI_SUCCESS; +} + +EFI_STATUS +EFIAPI +MvEepromInitialise ( + IN EFI_HANDLE ImageHandle, + IN EFI_SYSTEM_TABLE *SystemTable + ) +{ + EFI_STATUS Status; + Status = gBS->InstallMultipleProtocolInterfaces ( + &ImageHandle, + &gEfiDriverBindingProtocolGuid, &gDriverBindingProtocol, + NULL + ); + return Status; +} diff --git a/Drivers/I2c/Devices/MvEeprom/MvEeprom.h b/Drivers/I2c/Devices/MvEeprom/MvEeprom.h new file mode 100644 index 0000000..bcbe4a5 --- /dev/null +++ b/Drivers/I2c/Devices/MvEeprom/MvEeprom.h @@ -0,0 +1,90 @@ +/******************************************************************************** +Copyright (C) 2016 Marvell International Ltd. + +Marvell BSD License Option + +If you received this File from Marvell, you may opt to use, redistribute and/or +modify this File under the following licensing terms. +Redistribution and use in source and binary forms, with or without modification, +are permitted provided that the following conditions are met: + +* Redistributions of source code must retain the above copyright notice, + this list of conditions and the following disclaimer. + +* Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + +* Neither the name of Marvell nor the names of its contributors may be + used to endorse or promote products derived from this software without + specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR +ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON +ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +*******************************************************************************/ + +#ifndef __MV_EEPROM_H__ +#define __MV_EEPROM_H__ + +#include <Uefi.h> + +#define EEPROM_SIGNATURE SIGNATURE_32 ('E', 'E', 'P', 'R') + +#define MAX_BUFFER_LENGTH 64 + +#define I2C_FLAG_NORESTART 0x00000002 + +typedef struct { + UINT32 Signature; + EFI_HANDLE ControllerHandle; + EFI_I2C_IO_PROTOCOL *I2cIo; + EFI_EEPROM_PROTOCOL EepromProtocol; +} EEPROM_CONTEXT; + +#define EEPROM_SC_FROM_IO(a) CR (a, EEPROM_CONTEXT, I2cIo, EEPROM_SIGNATURE) +#define EEPROM_SC_FROM_EEPROM(a) CR (a, EEPROM_CONTEXT, EepromProtocol, EEPROM_SIGNATURE) + +EFI_STATUS +EFIAPI +MvEepromSupported ( + IN EFI_DRIVER_BINDING_PROTOCOL *This, + IN EFI_HANDLE ControllerHandle, + IN EFI_DEVICE_PATH_PROTOCOL *RemainingDevicePath OPTIONAL + ); + +EFI_STATUS +EFIAPI +MvEepromStart ( + IN EFI_DRIVER_BINDING_PROTOCOL *This, + IN EFI_HANDLE ControllerHandle, + IN EFI_DEVICE_PATH_PROTOCOL *RemainingDevicePath OPTIONAL + ); + +EFI_STATUS +EFIAPI +MvEepromStop ( + IN EFI_DRIVER_BINDING_PROTOCOL *This, + IN EFI_HANDLE ControllerHandle, + IN UINTN NumberOfChildren, + IN EFI_HANDLE *ChildHandleBuffer OPTIONAL + ); + +EFI_STATUS +EFIAPI +MvEepromTransfer ( + IN CONST EFI_EEPROM_PROTOCOL *This, + IN UINT16 Address, + IN UINT32 Length, + IN UINT8 *Buffer, + IN UINT8 Operation + ); +#endif // __MV_EEPROM_H__ diff --git a/Drivers/I2c/Devices/MvEeprom/MvEeprom.inf b/Drivers/I2c/Devices/MvEeprom/MvEeprom.inf new file mode 100644 index 0000000..767c13e --- /dev/null +++ b/Drivers/I2c/Devices/MvEeprom/MvEeprom.inf @@ -0,0 +1,70 @@ +# Copyright (C) 2016 Marvell International Ltd. +# +# Marvell BSD License Option +# +# If you received this File from Marvell, you may opt to use, redistribute and/or +# modify this File under the following licensing terms. +# Redistribution and use in source and binary forms, with or without modification, +# are permitted provided that the following conditions are met: +# +#* Redistributions of source code must retain the above copyright notice, +# this list of conditions and the following disclaimer. +# +#* Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# +#* Neither the name of Marvell nor the names of its contributors may be +# used to endorse or promote products derived from this software without +# specific prior written permission. +# +# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +# DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR +# ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +# (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +# LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON +# ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +# SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +# + +[Defines] + INF_VERSION = 0x00010005 + BASE_NAME = MvEeprom + FILE_GUID = 59fc3843-d8d4-40aa-ae07-38967138509c + MODULE_TYPE = DXE_DRIVER + VERSION_STRING = 1.0 + ENTRY_POINT = MvEepromInitialise + +[Sources.common] + MvEeprom.c + +[Packages] + MdePkg/MdePkg.dec + MdeModulePkg/MdeModulePkg.dec + ArmPlatformPkg/ArmPlatformPkg.dec + ArmPkg/ArmPkg.dec + OpenPlatformPkg/Platforms/Marvell/Marvell.dec + +[LibraryClasses] + IoLib + PcdLib + BaseLib + BaseMemoryLib + DebugLib + UefiLib + UefiDriverEntryPoint + UefiBootServicesTableLib + +[Protocols] + gEfiI2cIoProtocolGuid + gEfiDriverBindingProtocolGuid + gEfiEepromProtocolGuid + +[Pcd] + gMarvellTokenSpaceGuid.PcdEepromI2cAddresses + +[Depex] + TRUE diff --git a/Platforms/Marvell/Include/Protocol/Eeprom.h b/Platforms/Marvell/Include/Protocol/Eeprom.h new file mode 100644 index 0000000..41f7e0e --- /dev/null +++ b/Platforms/Marvell/Include/Protocol/Eeprom.h @@ -0,0 +1,60 @@ +/******************************************************************************** +Copyright (C) 2016 Marvell International Ltd. + +Marvell BSD License Option + +If you received this File from Marvell, you may opt to use, redistribute and/or +modify this File under the following licensing terms. +Redistribution and use in source and binary forms, with or without modification, +are permitted provided that the following conditions are met: + +* Redistributions of source code must retain the above copyright notice, + this list of conditions and the following disclaimer. + +* Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + +* Neither the name of Marvell nor the names of its contributors may be + used to endorse or promote products derived from this software without + specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR +ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON +ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +*******************************************************************************/ + +#ifndef __EEPROM_H__ +#define __EEPROM_H__ + +#define EFI_EEPROM_PROTOCOL_GUID { 0xcd728a1f, 0x45b5, 0x4feb, { 0x98, 0xc8, 0x31, 0x3d, 0xa8, 0x11, 0x74, 0x62 }} + +typedef struct _EFI_EEPROM_PROTOCOL EFI_EEPROM_PROTOCOL; + +#define EEPROM_READ 0x1 +#define EEPROM_WRITE 0x0 +typedef +EFI_STATUS +(EFIAPI *EFI_EEPROM_TRANSFER) ( + IN CONST EFI_EEPROM_PROTOCOL *This, + IN UINT16 Address, + IN UINT32 Length, + IN UINT8 *Buffer, + IN UINT8 Operation + ); + +struct _EFI_EEPROM_PROTOCOL { + EFI_EEPROM_TRANSFER Transfer; + UINT8 Identifier; +}; + +extern EFI_GUID gEfiEepromProtocolGuid; +#endif diff --git a/Platforms/Marvell/Marvell.dec b/Platforms/Marvell/Marvell.dec index 2a7a7e2..a07a6d2 100644 --- a/Platforms/Marvell/Marvell.dec +++ b/Platforms/Marvell/Marvell.dec @@ -106,7 +106,11 @@
#I2C gMarvellTokenSpaceGuid.PcdI2cSlaveAddresses|{ 0 }|VOID*|0x3000046 + gMarvellTokenSpaceGuid.PcdEepromI2cAddresses|{ 0 }|VOID*|0x3000050 gMarvellTokenSpaceGuid.PcdI2cBaseAddress|0|UINT64|0x3000047 gMarvellTokenSpaceGuid.PcdI2cClockFrequency|0|UINT32|0x3000048 gMarvellTokenSpaceGuid.PcdI2cBaudRate|0|UINT32|0x3000049
+[Protocols] + gEfiEepromProtocolGuid = { 0xcd728a1f, 0x45b5, 0x4feb, { 0x98, 0xc8, 0x31, 0x3d, 0xa8, 0x11, 0x74, 0x62 }} +
From: Bartosz Szczepanek bsz@semihalf.com
Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Bartosz Szczepanek bsz@semihalf.com Signed-off-by: Marcin Wojtas mw@semihalf.com --- Platforms/Marvell/Armada/Apn806.dsc | 1 + Platforms/Marvell/Armada/Armada.dsc.inc | 1 + Platforms/Marvell/Armada/Armada7040.fdf | 1 + Platforms/Marvell/Armada/Armada7040_rz.dsc | 1 + 4 files changed, 4 insertions(+)
diff --git a/Platforms/Marvell/Armada/Apn806.dsc b/Platforms/Marvell/Armada/Apn806.dsc index 0971937..b85cf69 100644 --- a/Platforms/Marvell/Armada/Apn806.dsc +++ b/Platforms/Marvell/Armada/Apn806.dsc @@ -65,6 +65,7 @@
# I2C gMarvellTokenSpaceGuid.PcdI2cSlaveAddresses|{ 0x50, 0x57, 0x60 } + gMarvellTokenSpaceGuid.PcdEepromI2cAddresses|{ 0x50, 0x57 } gMarvellTokenSpaceGuid.PcdI2cBaseAddress|0xF0511000 gMarvellTokenSpaceGuid.PcdI2cClockFrequency|200000000 gMarvellTokenSpaceGuid.PcdI2cBaudRate|100000 diff --git a/Platforms/Marvell/Armada/Armada.dsc.inc b/Platforms/Marvell/Armada/Armada.dsc.inc index fa223f9..bfe6881 100644 --- a/Platforms/Marvell/Armada/Armada.dsc.inc +++ b/Platforms/Marvell/Armada/Armada.dsc.inc @@ -392,6 +392,7 @@ # Platform drivers OpenPlatformPkg/Drivers/I2c/MvI2cDxe/MvI2cDxe.inf MdeModulePkg/Bus/I2c/I2cDxe/I2cDxe.inf + OpenPlatformPkg/Drivers/I2c/Devices/MvEeprom/MvEeprom.inf
MdeModulePkg/Core/RuntimeDxe/RuntimeDxe.inf MdeModulePkg/Universal/SecurityStubDxe/SecurityStubDxe.inf diff --git a/Platforms/Marvell/Armada/Armada7040.fdf b/Platforms/Marvell/Armada/Armada7040.fdf index 23a8db5..7a26eec 100644 --- a/Platforms/Marvell/Armada/Armada7040.fdf +++ b/Platforms/Marvell/Armada/Armada7040.fdf @@ -104,6 +104,7 @@ FvNameGuid = 5eda4200-2c5f-43cb-9da3-0baf74b1b30c INF EmbeddedPkg/MetronomeDxe/MetronomeDxe.inf INF OpenPlatformPkg/Drivers/I2c/MvI2cDxe/MvI2cDxe.inf INF MdeModulePkg/Bus/I2c/I2cDxe/I2cDxe.inf + INF OpenPlatformPkg/Drivers/I2c/Devices/MvEeprom/MvEeprom.inf
# Multiple Console IO support INF MdeModulePkg/Universal/Console/ConPlatformDxe/ConPlatformDxe.inf diff --git a/Platforms/Marvell/Armada/Armada7040_rz.dsc b/Platforms/Marvell/Armada/Armada7040_rz.dsc index f7aca6d..d4d3926 100644 --- a/Platforms/Marvell/Armada/Armada7040_rz.dsc +++ b/Platforms/Marvell/Armada/Armada7040_rz.dsc @@ -77,6 +77,7 @@
# I2C gMarvellTokenSpaceGuid.PcdI2cSlaveAddresses|{ 0x50, 0x57, 0x60 } + gMarvellTokenSpaceGuid.PcdEepromI2cAddresses|{ 0x50, 0x57 } gMarvellTokenSpaceGuid.PcdI2cBaseAddress|0xF0511000 gMarvellTokenSpaceGuid.PcdI2cClockFrequency|200000000 gMarvellTokenSpaceGuid.PcdI2cBaudRate|100000
From: Bartosz Szczepanek bsz@semihalf.com
'eeprom' command brings MvEeprom driver capabilities to UEFI shell. It allows reading & writing from/to onboard EEPROM device.
Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Bartosz Szczepanek bsz@semihalf.com Signed-off-by: Marcin Wojtas mw@semihalf.com --- Applications/EepromCmd/EepromCmd.c | 365 +++++++++++++++++++++++++++++++++++ Applications/EepromCmd/EepromCmd.inf | 74 +++++++ Applications/EepromCmd/EepromCmd.uni | Bin 0 -> 6816 bytes Platforms/Marvell/Marvell.dec | 2 + 4 files changed, 441 insertions(+) create mode 100644 Applications/EepromCmd/EepromCmd.c create mode 100644 Applications/EepromCmd/EepromCmd.inf create mode 100644 Applications/EepromCmd/EepromCmd.uni
diff --git a/Applications/EepromCmd/EepromCmd.c b/Applications/EepromCmd/EepromCmd.c new file mode 100644 index 0000000..b3efa03 --- /dev/null +++ b/Applications/EepromCmd/EepromCmd.c @@ -0,0 +1,365 @@ +/******************************************************************************** +Copyright (C) 2016 Marvell International Ltd. + +Marvell BSD License Option + +If you received this File from Marvell, you may opt to use, redistribute and/or +modify this File under the following licensing terms. +Redistribution and use in source and binary forms, with or without modification, +are permitted provided that the following conditions are met: + +* Redistributions of source code must retain the above copyright notice, + this list of conditions and the following disclaimer. + +* Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + +* Neither the name of Marvell nor the names of its contributors may be + used to endorse or promote products derived from this software without + specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR +ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON +ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +*******************************************************************************/ + +#include <Uefi.h> + +#include <ShellBase.h> +#include <Library/BaseLib.h> +#include <Library/BaseMemoryLib.h> +#include <Library/DebugLib.h> +#include <Library/MemoryAllocationLib.h> +#include <Library/ShellCommandLib.h> +#include <Library/ShellLib.h> +#include <Library/UefiLib.h> +#include <Library/UefiRuntimeServicesTableLib.h> +#include <Library/UefiBootServicesTableLib.h> +#include <Library/PrintLib.h> +#include <Library/HiiLib.h> + +#include <Library/UefiLib.h> +#include <Library/ShellCEntryLib.h> +#include <Library/UefiBootServicesTableLib.h> + +#include <Protocol/Eeprom.h> + +CONST CHAR16 gShellEepromFileName[] = L"ShellCommand"; +EFI_HANDLE gShellEepromHiiHandle = NULL; + +STATIC CONST SHELL_PARAM_ITEM ParamList[] = { + {L"-d", TypeValue}, + {L"-m", TypeValue}, + {L"read", TypeFlag}, + {L"write", TypeFlag}, + {L"list", TypeFlag}, + {L"help", TypeFlag}, + {NULL , TypeMax} + }; + +/** + Return the file name of the help text file if not using HII. + + @return The string pointer to the file name. +**/ +CONST CHAR16* +EFIAPI +ShellCommandGetManFileNameEeprom ( + VOID + ) +{ + return gShellEepromFileName; +} + +VOID +Usage ( + VOID + ) +{ + Print (L"Basic EEPROM commands:\n" + "eeprom [read] [write] [list] [<Chip>] [<Address>] [<Length>] [-d <Data>] [-m <Source>]\n" + "All modes except 'list' require Address, Length and Chip set.\n\n" + "read - read from EEPROM\n" + "write - write Data to EEPROM, requires -d\n" + "list - list available EEPROM devices\n\n" + "-m - transfer from/to RAM memory\n\n" + "Chip - EEPROM bus address\n" + "Address - address in EEPROM to read/write\n" + "Data - data byte to be written\n" + "Length - length of data to read/write/copy\n" + "Source - address of data in RAM to be copied\n" + "Examples:\n" + "List devices:\n" + " eeprom list\n" + "Read 16 bytes from address 0x0 in chip 0x57:\n" + " eeprom read 0x57 0x0 0x10\n" + "Fill 16 bytes with 0xab at address 0x0 in chip 0x57:\n" + " eeprom write 0x57 0x0 0x10 -d 0xab\n" + "Copy 32 bytes from 0x2000000 in RAM to EEPROM:\n" + " eeprom write 0x57 0x0 0x20 -m 0x2000000\n" + "Copy 32 bytes from EEPROM to RAM:\n" + " eeprom read 0x57 0x0 0x20 -m 0x2000000\n" + ); +} + +EFI_STATUS +EepromList ( + ) +{ + EFI_HANDLE *HandleBuffer; + EFI_STATUS Status; + UINTN ProtocolCount; + EFI_EEPROM_PROTOCOL *EepromProtocol; + UINTN i; + Status = gBS->LocateHandleBuffer ( ByProtocol, + &gEfiEepromProtocolGuid, + NULL, + &ProtocolCount, + &HandleBuffer + ); + if (ProtocolCount == 0) { + Print (L"0 devices found.\n"); + } else { + Print (L"%u devices found: ", ProtocolCount); + } + + for (i = 0; i < ProtocolCount; i++) { + Status = gBS->OpenProtocol ( + HandleBuffer[i], + &gEfiEepromProtocolGuid, + (VOID **) &EepromProtocol, + gImageHandle, + NULL, + EFI_OPEN_PROTOCOL_BY_HANDLE_PROTOCOL ); + Print (L" 0x%x ", EepromProtocol->Identifier); + Status = gBS->CloseProtocol ( HandleBuffer[i], + &gEfiEepromProtocolGuid, + gImageHandle, + NULL ); + } + Print (L"\n"); + return Status; +} + +EFI_STATUS +EepromLocateProtocol ( + IN UINT32 Identifier, + OUT EFI_HANDLE *FoundHandle, + OUT EFI_EEPROM_PROTOCOL **FoundEepromProtocol + ) +{ + EFI_HANDLE *HandleBuffer; + EFI_STATUS Status; + UINTN ProtocolCount; + EFI_EEPROM_PROTOCOL *EepromProtocol; + UINTN i; + Status = gBS->LocateHandleBuffer ( ByProtocol, + &gEfiEepromProtocolGuid, + NULL, + &ProtocolCount, + &HandleBuffer + ); + if (EFI_ERROR(Status)) + return Status; + + for (i = 0; i < ProtocolCount; i++) { + Status = gBS->OpenProtocol ( + HandleBuffer[i], + &gEfiEepromProtocolGuid, + (VOID **) &EepromProtocol, + gImageHandle, + NULL, + EFI_OPEN_PROTOCOL_BY_HANDLE_PROTOCOL ); + if (EepromProtocol->Identifier == Identifier) { + *FoundEepromProtocol = EepromProtocol; + *FoundHandle = HandleBuffer[i]; + return EFI_SUCCESS; + } + Status = gBS->CloseProtocol ( HandleBuffer[i], + &gEfiEepromProtocolGuid, + gImageHandle, + NULL ); + } + *FoundEepromProtocol = NULL; + return EFI_UNSUPPORTED; +} + +SHELL_STATUS +EFIAPI +ShellCommandRunEeprom ( + IN EFI_HANDLE ImageHandle, + IN EFI_SYSTEM_TABLE *SystemTable + ) +{ + EFI_STATUS Status; + LIST_ENTRY *CheckPackage; + CHAR16 *ProblemParam; + CONST CHAR16 *ValueStr; + UINTN Address, Length, Chip, Source; + UINT8 Data; + UINT8 *Buffer; + BOOLEAN ReadMode, MemMode; + EFI_HANDLE Handle; + EFI_EEPROM_PROTOCOL *EepromProtocol; + UINTN Count; + + Source = 0; + + Status = ShellInitialize (); + if (EFI_ERROR (Status)) { + Print (L"Error - failed to initialize shell\n"); + return SHELL_ABORTED; + } + + Status = ShellCommandLineParse (ParamList, &CheckPackage, &ProblemParam, TRUE); + if (EFI_ERROR (Status)) { + Print (L"Error - failed to parse command line\n"); + return SHELL_ABORTED; + } + + if (ShellCommandLineGetFlag (CheckPackage, L"list")) { + EepromList(); + return SHELL_SUCCESS; + } + + if (ShellCommandLineGetFlag (CheckPackage, L"help")) { + Usage(); + return SHELL_SUCCESS; + } + + if (ShellCommandLineGetCount(CheckPackage) < 4) { + Print (L"Not enough arguments given.\n"); + Usage(); + } + + ReadMode = ShellCommandLineGetFlag (CheckPackage, L"read"); + if (ReadMode == ShellCommandLineGetFlag (CheckPackage, L"write")) { + Print (L"Error - type read, write, list or help.\n"); + return SHELL_INVALID_PARAMETER; + } + + MemMode = ShellCommandLineGetFlag (CheckPackage, L"-m"); + Data = 0; + if (!ReadMode && !MemMode) { + ValueStr = ShellCommandLineGetValue (CheckPackage, L"-d"); + if (ValueStr == NULL) { + Print (L"Error - no data to write.\n"); + return SHELL_INVALID_PARAMETER; + } + Data = ShellHexStrToUintn (ValueStr); + } + + ValueStr = ShellCommandLineGetRawValue(CheckPackage, 1); + Chip = ShellHexStrToUintn (ValueStr); + + ValueStr = ShellCommandLineGetRawValue(CheckPackage, 2); + Address = ShellHexStrToUintn (ValueStr); + + ValueStr = ShellCommandLineGetRawValue(CheckPackage, 3); + Length = ShellHexStrToUintn (ValueStr); + + if (MemMode) { + ValueStr = ShellCommandLineGetValue (CheckPackage, L"-m"); + if (ValueStr == NULL) { + Print (L"Error - no memory address given.\n"); + return SHELL_INVALID_PARAMETER; + } + Source = ShellHexStrToUintn (ValueStr); + } + + EepromLocateProtocol (Chip, &Handle, &EepromProtocol); + if (EepromProtocol == NULL) { + Print (L"Failed to locate EEPROM protocol.\n"); + return SHELL_INVALID_PARAMETER; + } + + if (MemMode) { + Buffer = (VOID *) Source; + } else { + Buffer = AllocateZeroPool (Length); + if (Buffer == NULL) { + Status = SHELL_OUT_OF_RESOURCES; + Print (L"Error - out of resources.\n"); + goto out_close; + } + if (!ReadMode) { + for (Count = 0; Count < Length; Count++) + Buffer[Count] = Data; + } + } + EepromProtocol->Transfer(EepromProtocol, Address, Length, Buffer, + ReadMode ? EEPROM_READ : EEPROM_WRITE); + + if (MemMode) { + Print (L"Transfered succesfully.\n"); + } else { + Print (L"Transfered:\n"); + for (Count = 0; Count < Length; Count++) { + Print(L"0x%x ", Buffer[Count]); + if (Count % 8 == 7) + Print(L"\n"); + } + Print (L"\n"); + } + + Status = SHELL_SUCCESS; + + if (!MemMode) + FreePool(Buffer); +out_close: + gBS->CloseProtocol ( Handle, + &gEfiEepromProtocolGuid, + gImageHandle, + NULL ); + + return Status; +} + +EFI_STATUS +EFIAPI +EepromCmdConstructor ( + IN EFI_HANDLE ImageHandle, + IN EFI_SYSTEM_TABLE *SystemTable + ) +{ + + gShellEepromHiiHandle = NULL; + + gShellEepromHiiHandle = HiiAddPackages ( + &gShellEepromHiiGuid, gImageHandle, + EepromToolShellStrings, NULL + ); + if (gShellEepromHiiHandle == NULL) { + Print (L"Filed to add Hii package\n"); + return EFI_DEVICE_ERROR; + } + ShellCommandRegisterCommandName ( + L"eeprom", ShellCommandRunEeprom, ShellCommandGetManFileNameEeprom, 0, + L"eeprom", TRUE , gShellEepromHiiHandle, STRING_TOKEN (STR_GET_HELP_EEPROM) + ); + + return EFI_SUCCESS; +} + +EFI_STATUS +EFIAPI +EepromCmdDestructor ( + IN EFI_HANDLE ImageHandle, + IN EFI_SYSTEM_TABLE *SystemTable + ) +{ + + if (gShellEepromHiiHandle != NULL) { + HiiRemovePackages (gShellEepromHiiHandle); + } + return EFI_SUCCESS; +} diff --git a/Applications/EepromCmd/EepromCmd.inf b/Applications/EepromCmd/EepromCmd.inf new file mode 100644 index 0000000..02b149a --- /dev/null +++ b/Applications/EepromCmd/EepromCmd.inf @@ -0,0 +1,74 @@ +# Copyright (C) 2016 Marvell International Ltd. +# +# Marvell BSD License Option +# +# If you received this File from Marvell, you may opt to use, redistribute and/or +# modify this File under the following licensing terms. +# Redistribution and use in source and binary forms, with or without modification, +# are permitted provided that the following conditions are met: +# +# * Redistributions of source code must retain the above copyright notice, +# this list of conditions and the following disclaimer. +# +# * Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# +# * Neither the name of Marvell nor the names of its contributors may be +# used to endorse or promote products derived from this software without +# specific prior written permission. +# +# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +# DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR +# ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +# (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +# LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON +# ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +# SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +# + +[Defines] + INF_VERSION = 0x00010006 + BASE_NAME = EepromToolShell + FILE_GUID = adf4b61c-2ca3-4e1a-9597-99282f5a4aa2 + MODULE_TYPE = UEFI_APPLICATION + VERSION_STRING = 0.1 + LIBRARY_CLASS = NULL|UEFI_APPLICATION UEFI_DRIVER + CONSTRUCTOR = EepromCmdConstructor + DESTRUCTOR = EepromCmdDestructor + +# +# VALID_ARCHITECTURES = IA32 X64 IPF +# +[Sources] + EepromCmd.c + EepromCmd.uni + +[Packages] + MdePkg/MdePkg.dec + ShellPkg/ShellPkg.dec + StdLib/StdLib.dec + MdeModulePkg/MdeModulePkg.dec + OpenPlatformPkg/Platforms/Marvell/Marvell.dec + +[LibraryClasses] + UefiLib + UefiBootServicesTableLib + MemoryAllocationLib + BaseLib + BaseMemoryLib + DebugLib + ShellCommandLib + ShellLib + UefiLib + UefiRuntimeServicesTableLib + PcdLib + +[Protocols] + gEfiEepromProtocolGuid + +[Guids] + gShellEepromHiiGuid diff --git a/Applications/EepromCmd/EepromCmd.uni b/Applications/EepromCmd/EepromCmd.uni new file mode 100644 index 0000000000000000000000000000000000000000..e41c6d812ef5d8e3b23c54e5fcbee017507b5c2f GIT binary patch literal 6816 zcmd6rZEsUY5QX=1rT&Mj@P#50L#wtDrIj4Vfk@6vZHE*=g%UfVmSQKhO@Tk(_B=bD z?C!OlP^3!8^1b^ybLQ;K?C$;N??!m=MgP7IUxik<3fJLdn1)e!8~zCMP=)(y{YLL^ z!=vyx{Gif)IMs;1!g;vVuL^r%qLJrno2X~5xmU47Uq|&}*a}GJU!S`jdSNGy8-;;n zOu|ghDjW)jOY*sU;X*whCH<Y=Q;lQBC?XlEWiG@c&9B0)-j`9%g~nZlvD!+_57pw5 z#zOs3b!^Atxk{CEfP`^q8b--;l}F)Beb`%R-b6hOjh{yA#ws!LBFbBZ=UtouSB4iU z7n%i=SK+<pPQ-krTH?dojN`Fz8K2#ixQu<r=5|z3a;3SjH;v4tF=w%tRfPxeOvTwO zS`Q{HfgezN9XYU-YzA>!|A&zgWMbpBp2$QNcCcR8YPr(tja0K1^dRAOZU&kK@5nN1 zS##GkmaKVra^rE8`tsic)ox=BSy$21O0LifPAtYZK#6U0X=a5I=2LkHb}^P&^@y6N z4di&Qv6SQUa`GO0!Sorfb@szaLb1xL%!>!|E-=H?G>c8w?C(!u$}C^)KXs;Ty@z5C z%M;Su`6BuqQT{GjG-($7|1V!2NvzL#^s*e4mxo&8fh>h%vSW%1k2=d5_?k%~w#Y;l z<s+3Ywd$*)#3L{<xSX9VE>hlgT>fTl4}{HPyUa&qad3Mal$o=VJ(dX!H+37IA_u9| z%v1BM$xM1Y=bqidp=Dt6X)-cQ!YdLC9h{k0k%cTL=U!$gh+6VC5s9?4C!`o7)-NRC zy=<|J<t$sCTjzzdnArxBexd(hfd}?2SEAQ49vLEK!I^BRuTeid*IwGwxSsaE-Ovvw zp{ZQeR*SVCsdgA%sJ5fl9kp+VmwGajQ7!czsimtC&(zje+jF&b;`nZq-PF1>ld%UH z!PxC^tkR*%Xy1@l-ss%W+h)K3CG@q!Z_)#@UL46x#_y}Oqqku*^xZhCA6t8IN7<8< zmc|_m2jyq6)iB_dhY>e&_Vw>Cq=Ap!*ljJffo_#PP7=GCwJ#}MX??yx)0EA75o<qM z<gDyQjR!ZD?M7DMpptE@29~shy%TG+9;@|8<9eFKNO%Dc*7c&LO_e~fqihRL2YO;B zOuo>cbzs#&*U>LoxoSlZWhn^Z+?Zd#mfIS~DQr)YxAmrGHs$LHQc$;q1CBwss;#9S zJP*7eWo%EjGZPKgf_JnRz5p99<G36tO#Ld}Op?v4B)O?sP5A?U1-|<c$>;lu#S5#2 zb*z9fZ9dUcJLgYUw68LrR!RGzemiP+c0t>XQP)zb7k-M^IvVBPkB1$r){d592mHW} zS#3DXx0vtk_<S$g=#d2T;OOdiEM~z*oN@vul26o!$FTM-=`gLtvwJY3^R=~j0SA$5 zmb*Ws2mtGeG_<9Wr^PdVntZEy;~#KF-oRgyca_r2a?2|HwW~=Sw8c4ySa&i5t6;Oq z1cv5B{qPG9_!KqE9Uf1fo5%uYDJ$w0d)6?%@>V3lS3T##h({+nSmUPrg6s<tI5#$3 zw&ehDmANH(8~La7^Rz>M*|)<+<OrS`;pcGgrgkr$CAqV(%W^;C$4<Q&eUsgU+S_=e znd!{5k<H~)%MNLG9`mX<(GU9JO<ehoV&IL~ZtKn7x4+Qf=a}?PNZx4=e=DtZ9Hx0g zIhYlr_x$GcQ0aCH)@{vYXJ#iawQ`mj$8!s(kS&dUE$pv_J;^15<I&`?_EJB$j#JHT z=#*jS0x%BM#`!RvOB#_8yM?w3jGW3i>2Ob5r@bfdXKy)*5z<>4S1q-aJiL;0!}+@~ zy~?m!-A~t6+Y}xvJyqm#|Go~t+_W@h-7w1IyhD2(by`14ufkJh0`nKnW-e({QY!WB zEVxSTv)JAfCw{A4rDaQ8urjdX8TC_`0h6;)BK6v4F(RETbKl8*gn9YuyPWh!Vm`uc z=Csc#IG0S00^gsqezf4ZQsfQAbMi}M`>G{9c?q3q#Hmio+z+`Wp6Q8~=34RD^LTIP z9yg1+>iY1DTtit#ACb@ZlbN!H-9MbY#==rgj{6#!d;L0#SEF!`EVX+L6s28!*}<cT z(&V>w+e)u?Y5qoPIp1%Lr7l}d_pUrA)b%9~a2@#@eJO{WDKpqT$mDasO8!L8WXU)3 zh|48g8Tt4CIhvUCTVc|<-jYVV0rLH$Zc`qyt98~nv~M3tt9^NJAIYt?Z!RNYF5|$n z0OwOYi@OTvuH~FmZ>i6CvNWfoc(HFZWo#^utnWJ>cXgdz;fI52@zvE=7XS1}S@yI? z;X~ZXjGe(EBeT1G2;YYv^<Av4r;f)xGR?6P`y)~w>sgm!-&-$NV)c8p%_gIOdLEy7 zlqD^nk3G+uZgG<9=q*DgJaubY%Cq=v6~5C~?@EX*rb_0K#y9cw^EfYkGLQPZ*}vNY zbYj6+&t(jsXG@OJ_ZhR|Zp3%_%YVb`G0J_7J6Ts}nHP#yz7~91tmZSTV(uzi?AG0u z{Ep6<+z4Co24Xk6GBfoRO=QzkWi|iuOm5}GXy3ZV@*8p`d6vkv9vEVWX0NoKt)&P; x6K51h!fl;9kbnIsk+ijU^6h-8S?^<v+b(V2zHC?K6l>?|^5j~22q${}{{kxp-hluB
literal 0 HcmV?d00001
diff --git a/Platforms/Marvell/Marvell.dec b/Platforms/Marvell/Marvell.dec index a07a6d2..96767d5 100644 --- a/Platforms/Marvell/Marvell.dec +++ b/Platforms/Marvell/Marvell.dec @@ -52,6 +52,8 @@ [Guids.common] gMarvellTokenSpaceGuid = { 0xf995c6c8, 0xbc9b, 0x4e93, { 0xbd, 0xcf, 0x49, 0x90, 0xc6, 0xe7, 0x8c, 0x7f } }
+ gShellEepromHiiGuid = { 0xb2f4c714, 0x147f, 0x4ff7, { 0x82, 0x1b, 0xce, 0x7b, 0x91, 0x7f, 0x5f, 0x2f } } + [PcdsFixedAtBuild.common] #MPP gMarvellTokenSpaceGuid.PcdMppChipCount|0|UINT32|0x30000001
From: Jan Dąbroś jsd@semihalf.com
Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Bartosz Szczepanek bsz@semihalf.com Signed-off-by: Marcin Wojtas mw@semihalf.com --- Platforms/Marvell/Armada/Armada.dsc.inc | 1 + 1 file changed, 1 insertion(+)
diff --git a/Platforms/Marvell/Armada/Armada.dsc.inc b/Platforms/Marvell/Armada/Armada.dsc.inc index bfe6881..9b8427e 100644 --- a/Platforms/Marvell/Armada/Armada.dsc.inc +++ b/Platforms/Marvell/Armada/Armada.dsc.inc @@ -447,6 +447,7 @@ NULL|ShellPkg/Library/UefiShellInstall1CommandsLib/UefiShellInstall1CommandsLib.inf NULL|ShellPkg/Library/UefiShellNetwork1CommandsLib/UefiShellNetwork1CommandsLib.inf NULL|ShellPkg/Library/UefiShellTftpCommandLib/UefiShellTftpCommandLib.inf + NULL|OpenPlatformPkg/Applications/EepromCmd/EepromCmd.inf HandleParsingLib|ShellPkg/Library/UefiHandleParsingLib/UefiHandleParsingLib.inf PrintLib|MdePkg/Library/BasePrintLib/BasePrintLib.inf BcfgCommandLib|ShellPkg/Library/UefiShellBcfgCommandLib/UefiShellBcfgCommandLib.inf
From: Jan Dąbroś jsd@semihalf.com
Add EFI_SPI_MASTER_PROTOCOL and register its GUID in Marvell.dec file in order to make it public.
Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Jan Dabros jsd@semihalf.com Signed-off-by: Marcin Wojtas mw@semihalf.com --- Platforms/Marvell/Include/Protocol/Spi.h | 105 +++++++++++++++++++++++++++++++ Platforms/Marvell/Marvell.dec | 1 + 2 files changed, 106 insertions(+) create mode 100644 Platforms/Marvell/Include/Protocol/Spi.h
diff --git a/Platforms/Marvell/Include/Protocol/Spi.h b/Platforms/Marvell/Include/Protocol/Spi.h new file mode 100644 index 0000000..95a7981 --- /dev/null +++ b/Platforms/Marvell/Include/Protocol/Spi.h @@ -0,0 +1,105 @@ +/******************************************************************************* +Copyright (C) 2016 Marvell International Ltd. + +Marvell BSD License Option + +If you received this File from Marvell, you may opt to use, redistribute and/or +modify this File under the following licensing terms. +Redistribution and use in source and binary forms, with or without modification, +are permitted provided that the following conditions are met: + +* Redistributions of source code must retain the above copyright notice, + this list of conditions and the following disclaimer. + +* Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + +* Neither the name of Marvell nor the names of its contributors may be + used to endorse or promote products derived from this software without + specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR +ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON +ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +*******************************************************************************/ +#ifndef __EFI_SPI_MASTER_PROTOCOL_H__ +#define __EFI_SPI_MASTER_PROTOCOL_H__ + +extern EFI_GUID gEfiSpiMasterProtocolGuid; + +typedef struct _EFI_SPI_MASTER_PROTOCOL EFI_SPI_MASTER_PROTOCOL; + +typedef enum { + SPI_MODE0, // CPOL = 0 & CPHA = 0 + SPI_MODE1, // CPOL = 0 & CPHA = 1 + SPI_MODE2, // CPOL = 1 & CPHA = 0 + SPI_MODE3 // CPOL = 1 & CPHA = 1 +} SPI_MODE; + +typedef struct { + INTN Cs; + INTN MaxFreq; + SPI_MODE Mode; +} SPI_DEVICE; + +typedef +EFI_STATUS +(EFIAPI *EFI_SPI_INIT) ( + IN EFI_SPI_MASTER_PROTOCOL *This + ); + +typedef +EFI_STATUS +(EFIAPI *EFI_SPI_TRANSFER) ( + IN EFI_SPI_MASTER_PROTOCOL *This, + IN SPI_DEVICE *Slave, + IN UINTN DataByteCount, + IN VOID *DataOut, + IN VOID *DataIn, + IN UINTN Flag + ); + +typedef +EFI_STATUS +(EFIAPI * EFI_SPI_READ_WRITE) ( + IN EFI_SPI_MASTER_PROTOCOL *This, + IN SPI_DEVICE *Slave, + IN UINT8 *Cmd, + IN UINTN CmdSize, + IN UINT8 *DataOut, + OUT UINT8 *DataIn, + IN UINTN DataSize + ); + +typedef +SPI_DEVICE * +(EFIAPI *EFI_SPI_SETUP_DEVICE) ( + IN EFI_SPI_MASTER_PROTOCOL *This, + IN UINTN Cs, + IN SPI_MODE Mode + ); + +typedef +EFI_STATUS +(EFIAPI *EFI_SPI_FREE_DEVICE) ( + IN SPI_DEVICE *SpiDev + ); + +struct _EFI_SPI_MASTER_PROTOCOL { + EFI_SPI_INIT Init; + EFI_SPI_READ_WRITE ReadWrite; + EFI_SPI_TRANSFER Transfer; + EFI_SPI_SETUP_DEVICE SetupDevice; + EFI_SPI_FREE_DEVICE FreeDevice; +}; + +#endif // __EFI_SPI_MASTER_PROTOCOL_H__ diff --git a/Platforms/Marvell/Marvell.dec b/Platforms/Marvell/Marvell.dec index 96767d5..ad90ffc 100644 --- a/Platforms/Marvell/Marvell.dec +++ b/Platforms/Marvell/Marvell.dec @@ -115,4 +115,5 @@
[Protocols] gEfiEepromProtocolGuid = { 0xcd728a1f, 0x45b5, 0x4feb, { 0x98, 0xc8, 0x31, 0x3d, 0xa8, 0x11, 0x74, 0x62 }} + gEfiSpiMasterProtocolGuid = { 0x23de66a3, 0xf666, 0x4b3e, { 0xaa, 0xa2, 0x68, 0x9b, 0x18, 0xae, 0x2e, 0x19 }}
From: Jan Dąbroś jsd@semihalf.com
Spi master driver implements EFI_SPI_MASTER_PROTOCOL. It configures and manages SPI controller.
Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Jan Dabros jsd@semihalf.com Signed-off-by: Marcin Wojtas mw@semihalf.com --- Documentation/Marvell/Drivers/SpiDriver.txt | 116 +++++++++ Documentation/Marvell/PortingGuide/Spi.txt | 15 ++ Drivers/Spi/SpiDxe.c | 378 ++++++++++++++++++++++++++++ Drivers/Spi/SpiDxe.h | 145 +++++++++++ Drivers/Spi/SpiDxe.inf | 74 ++++++ Platforms/Marvell/Marvell.dec | 5 + 6 files changed, 733 insertions(+) create mode 100644 Documentation/Marvell/Drivers/SpiDriver.txt create mode 100644 Documentation/Marvell/PortingGuide/Spi.txt create mode 100644 Drivers/Spi/SpiDxe.c create mode 100644 Drivers/Spi/SpiDxe.h create mode 100644 Drivers/Spi/SpiDxe.inf
diff --git a/Documentation/Marvell/Drivers/SpiDriver.txt b/Documentation/Marvell/Drivers/SpiDriver.txt new file mode 100644 index 0000000..fc323ef --- /dev/null +++ b/Documentation/Marvell/Drivers/SpiDriver.txt @@ -0,0 +1,116 @@ +1. Introduction +--------------- +**SpiDxe** driver implements EFI_SPI_MASTER_PROTOCOL in order to manage SPI +controller on Marvell A8k boards. It exposes below functionalities: + - create and setup SPI slaves + - raw transfer over SPI bus + +2. SpiDxe driver design +----------------------- + + 2.1 EFI_SPI_MASTER_PROTOCOL + ----------------------- + First member of SPI_MASTER protocol is Init function, implemented for SPI + master controller initialization. + + ->Init() + + // + //Initializes the host controller to execute SPI commands. + // + + param[IN] This Pointer to the EFI_SPI_MASTER_PROTOCOL instance + + return EFI_SUCCESS Opcode initialization on the SPI host + controller completed. + return EFI_ACCESS_DENIED The SPI configuration interface is + locked. + return EFI_OUT_OF_RESOURCES Not enough resource available to + initialize the device. + return EFI_DEVICE_ERROR Device error, operation failed. + + ******** + + SPI devices (slaves) do not support any kind of automatic discovery or + enumaration, so every device needs manual configuration, which may be done + with SetupDevice function. + + ->SetupDevice() + + // + //Allocate and zero all fields in the SPI_DEVICE struct. Set the chip + //select, max frequency and transfer mode supported by slave device. + // + + param[IN] Cs Chip select ID of the slave chip. + param[IN] MaxFreq Maximum SCK rate in Hz. + param[IN] Mode Clock polarity and clock phase. + + return *SPI_DEVICE Pointer to new allocated struct SPI_DEVICE. + return NULL NULL pointer if any eroor occured. + + ******** + + Developers have to destroy all created SPI device structs (with FreeDevice + function) in order to prevent from memory leak. + + ->FreeDevice() + + // + //Free any memory associated with a SPI device. + // + + param[in] SpiDev Pointer to the SPI_DEVICE struct. + + return EFI_SUCCESS Memory fried succesfully. + return EFI_DEVICE_ERROR Device error, operation failed. + + ******** + + Transfer function allows write/read raw bytes over SPI bus. + + ->Transfer() + + // + //Perform transfer over SPI bus + // + param[in] This Pointer to the EFI_SPI_MASTER_PROTOCOL + instance. + param[in] Slave Pointer to the SPI_DEVICE struct. + param[in] DataByteCount Number of bytes in the data portion of + the SPI cycle. + param[in] DataOut Pointer to caller-allocated buffer + containing the data to send. + param[out] DataIn Pointer to caller-allocated buffer + where received data will be placed. + param[in] Flag Flags which indicate state of CS line + during/after transfer (see file + Drivers/Spi/Devices/A8kSpiFlash.h) + + return EFI_SUCCESS Memory fried succesfully. + return EFI_DEVICE_ERROR Device error, operation failed. + + ********* + + When working with SPI devices it is often necessary to perform "command and + address" transactions. It may be done via ReadWrite function. + + ->ReadWrite() + + // + //Perform two steps transactions. First write Command, then read/write + //buffer + // + + param[in] This Pointer to the EFI_SPI_MASTER_PROTOCOL + instance. + param[in] Slave Pointer to the SPI_DEVICE struct. + param[in] Cmd Pointer to caller-allocated buffer + containing the command to send. + param[in] CmdSize Size of command (in bytes). + param[in] DataOut Pointer to caller-allocated buffer + containing the data to send. + param[out] DataIn Pointer to caller-allocated buffer + where received data will be placed. + param[in] DataSize Number of bytes in the data portion of + the SPI cycle. diff --git a/Documentation/Marvell/PortingGuide/Spi.txt b/Documentation/Marvell/PortingGuide/Spi.txt new file mode 100644 index 0000000..f1f36ad --- /dev/null +++ b/Documentation/Marvell/PortingGuide/Spi.txt @@ -0,0 +1,15 @@ +Spi driver configuration +------------------------ +Following PCDs are available for configuration of spi driver: + + gMarvellTokenSpaceGuid.PcdSpiClockFrequency + +Frequency (in Hz) of SPI clock + + gMarvellTokenSpaceGuid.PcdSpiMaxFrequency + +Max SCLK line frequency (in Hz) (max transfer frequency) + + gMarvellTokenSpaceGuid.PcdSpiDefaultMode + +default SCLK mode (see SPI_MODE enum in file OpenPlatformPkg/Drivers/Spi/MvSpi.h) diff --git a/Drivers/Spi/SpiDxe.c b/Drivers/Spi/SpiDxe.c new file mode 100644 index 0000000..e609069 --- /dev/null +++ b/Drivers/Spi/SpiDxe.c @@ -0,0 +1,378 @@ +/******************************************************************************* +Copyright (C) 2016 Marvell International Ltd. + +Marvell BSD License Option + +If you received this File from Marvell, you may opt to use, redistribute and/or +modify this File under the following licensing terms. +Redistribution and use in source and binary forms, with or without modification, +are permitted provided that the following conditions are met: + +* Redistributions of source code must retain the above copyright notice, + this list of conditions and the following disclaimer. + +* Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + +* Neither the name of Marvell nor the names of its contributors may be + used to endorse or promote products derived from this software without + specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR +ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON +ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +*******************************************************************************/ +#include "SpiDxe.h" + +SPI_MASTER *mSpiMasterInstance; + +STATIC +EFI_STATUS +SpiSetBaudRate ( + IN UINT32 CpuClock, + IN UINT32 MaxFreq + ) +{ + UINT32 Spr, BestSpr, Sppr, BestSppr, ClockDivider, Match, Reg, MinBaudDiff; + UINTN SpiRegBase = PcdGet32 (PcdSpiRegBase); + + MinBaudDiff = 0xFFFFFFFF; + BestSppr = 0; + + //Spr is in range 1-15 and Sppr in range 0-8 + for (Spr = 1; Spr <= 15; Spr++) { + for (Sppr = 0; Sppr <= 7; Sppr++) { + ClockDivider = Spr * (1 << Sppr); + + if ((CpuClock / ClockDivider) > MaxFreq) { + continue; + } + + if ((CpuClock / ClockDivider) == MaxFreq) { + BestSpr = Spr; + BestSppr = Sppr; + Match = 1; + break; + } + + if ((MaxFreq - (CpuClock / ClockDivider)) < MinBaudDiff) { + MinBaudDiff = (MaxFreq - (CpuClock / ClockDivider)); + BestSpr = Spr; + BestSppr = Sppr; + } + } + + if (Match == 1) { + break; + } + } + + if (BestSpr == 0) { + return (EFI_INVALID_PARAMETER); + } + + Reg = MmioRead32 (SpiRegBase + SPI_CONF_REG); + Reg &= ~(SPI_SPR_MASK | SPI_SPPR_0_MASK | SPI_SPPR_HI_MASK); + Reg |= (BestSpr << SPI_SPR_OFFSET) | + ((BestSppr & 0x1) << SPI_SPPR_0_OFFSET) | + ((BestSppr >> 1) << SPI_SPPR_HI_OFFSET); + MmioWrite32 (SpiRegBase + SPI_CONF_REG, Reg); + + return EFI_SUCCESS; +} + +STATIC +VOID +SpiSetCs ( + UINT8 CsId + ) +{ + UINT32 Reg, SpiRegBase = PcdGet32 (PcdSpiRegBase); + + Reg = MmioRead32 (SpiRegBase + SPI_CTRL_REG); + Reg &= ~SPI_CS_NUM_MASK; + Reg |= (CsId << SPI_CS_NUM_OFFSET); + MmioWrite32 (SpiRegBase + SPI_CTRL_REG, Reg); +} + +STATIC +VOID +SpiActivateCs ( + UINT8 IN CsId + ) +{ + UINT32 Reg, SpiRegBase = PcdGet32 (PcdSpiRegBase); + + SpiSetCs(CsId); + Reg = MmioRead32 (SpiRegBase + SPI_CTRL_REG); + Reg |= SPI_CS_EN_MASK; + MmioWrite32(SpiRegBase + SPI_CTRL_REG, Reg); +} + +STATIC +VOID +SpiDeactivateCs ( + VOID + ) +{ + UINT32 Reg, SpiRegBase = PcdGet32 (PcdSpiRegBase); + + Reg = MmioRead32 (SpiRegBase + SPI_CTRL_REG); + Reg &= ~SPI_CS_EN_MASK; + MmioWrite32(SpiRegBase + SPI_CTRL_REG, Reg); +} + +STATIC +VOID +SpiSetupTransfer ( + IN EFI_SPI_MASTER_PROTOCOL *This, + IN SPI_DEVICE *Slave + ) +{ + SPI_MASTER *SpiMaster; + UINT32 Reg, SpiRegBase, CoreClock, SpiMaxFreq; + + SpiMaster = SPI_MASTER_FROM_SPI_MASTER_PROTOCOL (This); + + // Initialize values from PCDs + SpiRegBase = PcdGet32 (PcdSpiRegBase); + CoreClock = PcdGet32 (PcdSpiClockFrequency); + SpiMaxFreq = PcdGet32 (PcdSpiMaxFrequency); + + EfiAcquireLock (&SpiMaster->Lock); + + Reg = MmioRead32 (SpiRegBase + SPI_CONF_REG); + Reg |= SPI_BYTE_LENGTH; + MmioWrite32 (SpiRegBase + SPI_CONF_REG, Reg); + + SpiSetCs(Slave->Cs); + + SpiSetBaudRate (CoreClock, SpiMaxFreq); + + Reg = MmioRead32 (SpiRegBase + SPI_CONF_REG); + Reg &= ~(SPI_CPOL_MASK | SPI_CPHA_MASK | SPI_TXLSBF_MASK | SPI_RXLSBF_MASK); + + switch (Slave->Mode) { + case SPI_MODE0: + break; + case SPI_MODE1: + Reg |= SPI_CPHA_MASK; + break; + case SPI_MODE2: + Reg |= SPI_CPOL_MASK; + break; + case SPI_MODE3: + Reg |= SPI_CPOL_MASK; + Reg |= SPI_CPHA_MASK; + break; + } + + MmioWrite32 (SpiRegBase + SPI_CONF_REG, Reg); + + EfiReleaseLock (&SpiMaster->Lock); +} + +EFI_STATUS +EFIAPI +EfiSpiTransfer ( + IN EFI_SPI_MASTER_PROTOCOL *This, + IN SPI_DEVICE *Slave, + IN UINTN DataByteCount, + IN VOID *DataOut, + IN VOID *DataIn, + IN UINTN Flag + ) +{ + SPI_MASTER *SpiMaster; + UINT64 Length; + UINT32 Iterator, Reg, SpiRegBase; + UINT8 *DataOutPtr = (UINT8 *)DataOut; + UINT8 *DataInPtr = (UINT8 *)DataIn; + UINT8 DataToSend = 0; + + SpiMaster = SPI_MASTER_FROM_SPI_MASTER_PROTOCOL (This); + + SpiRegBase = PcdGet32 (PcdSpiRegBase); + + Length = 8 * DataByteCount; + + EfiAcquireLock (&SpiMaster->Lock); + + if (Flag & SPI_TRANSFER_BEGIN) { + SpiActivateCs (Slave->Cs); + } + + // Set 8-bit mode + Reg = MmioRead32 (SpiRegBase + SPI_CONF_REG); + Reg &= ~SPI_BYTE_LENGTH; + MmioWrite32 (SpiRegBase + SPI_CONF_REG, Reg); + + while (Length > 0) { + if (DataOut != NULL) { + DataToSend = *DataOutPtr & 0xFF; + } + // Transmit Data + MmioWrite32 (SpiRegBase + SPI_DATA_OUT_REG, DataToSend); + // Wait for memory ready + for (Iterator = 0; Iterator < SPI_TIMEOUT; Iterator++) { + if ((MmioRead32 (SpiRegBase + SPI_CTRL_REG) & SPI_MEM_READY_MASK) != 0) { + *DataInPtr = MmioRead32 (SpiRegBase + SPI_DATA_IN_REG); + + if (DataInPtr != NULL) { + DataInPtr++; + } + if (DataOutPtr != NULL) { + DataOutPtr++; + } + Length -= 8; + break; + } + } + + if (Iterator >= SPI_TIMEOUT) { + DEBUG ((DEBUG_ERROR, "Timeout\n")); + } + } + + if (Flag & SPI_TRANSFER_END) { + SpiDeactivateCs (); + } + + EfiReleaseLock (&SpiMaster->Lock); + + return EFI_SUCCESS; +} + +EFI_STATUS +EFIAPI +EfiSpiReadWrite ( + IN EFI_SPI_MASTER_PROTOCOL *This, + IN SPI_DEVICE *Slave, + IN UINT8 *Cmd, + IN UINTN CmdSize, + IN UINT8 *DataOut, + OUT UINT8 *DataIn, + IN UINTN DataSize + ) +{ + EFI_STATUS Status; + + Status = EfiSpiTransfer (This, Slave, CmdSize, Cmd, NULL, SPI_TRANSFER_BEGIN); + if (EFI_ERROR (Status)) { + Print (L"Spi Transfer Error\n"); + return EFI_DEVICE_ERROR; + } + + Status = EfiSpiTransfer (This, Slave, DataSize, DataOut, DataIn, SPI_TRANSFER_END); + if (EFI_ERROR (Status)) { + Print (L"Spi Transfer Error\n"); + return EFI_DEVICE_ERROR; + } + + return EFI_SUCCESS; +} + +EFI_STATUS +EFIAPI +EfiSpiInit ( + IN EFI_SPI_MASTER_PROTOCOL * This + ) +{ + + return EFI_SUCCESS; +} + +SPI_DEVICE * +EFIAPI +EfiSpiSetupSlave ( + IN EFI_SPI_MASTER_PROTOCOL *This, + IN UINTN Cs, + IN SPI_MODE Mode + ) +{ + SPI_DEVICE *Slave; + + Slave = AllocateZeroPool (sizeof(SPI_DEVICE)); + if (Slave == NULL) { + DEBUG((DEBUG_ERROR, "Cannot allocate memory\n")); + return NULL; + } + + Slave->Cs = Cs; + Slave->Mode = Mode; + + SpiSetupTransfer (This, Slave); + + return Slave; +} + +EFI_STATUS +EFIAPI +EfiSpiFreeSlave ( + IN SPI_DEVICE *Slave + ) +{ + FreePool (Slave); + + return EFI_SUCCESS; +} + +STATIC +EFI_STATUS +SpiMasterInitProtocol ( + IN EFI_SPI_MASTER_PROTOCOL *SpiMasterProtocol + ) +{ + + SpiMasterProtocol->Init = EfiSpiInit; + SpiMasterProtocol->SetupDevice = EfiSpiSetupSlave; + SpiMasterProtocol->FreeDevice = EfiSpiFreeSlave; + SpiMasterProtocol->Transfer = EfiSpiTransfer; + SpiMasterProtocol->ReadWrite = EfiSpiReadWrite; + + return EFI_SUCCESS; +} + +EFI_STATUS +EFIAPI +SpiMasterEntryPoint ( + IN EFI_HANDLE ImageHandle, + IN EFI_SYSTEM_TABLE *SystemTable + ) +{ + EFI_STATUS Status; + + mSpiMasterInstance = AllocateZeroPool (sizeof (SPI_MASTER)); + + if (mSpiMasterInstance == NULL) { + return EFI_OUT_OF_RESOURCES; + } + + EfiInitializeLock (&mSpiMasterInstance->Lock, TPL_NOTIFY); + + SpiMasterInitProtocol (&mSpiMasterInstance->SpiMasterProtocol); + + mSpiMasterInstance->Signature = SPI_MASTER_SIGNATURE; + + Status = gBS->InstallMultipleProtocolInterfaces ( + &(mSpiMasterInstance->Handle), + &gEfiSpiMasterProtocolGuid, + &(mSpiMasterInstance->SpiMasterProtocol), + NULL + ); + if (EFI_ERROR (Status)) { + FreePool (mSpiMasterInstance); + return EFI_DEVICE_ERROR; + } + + return EFI_SUCCESS; +} diff --git a/Drivers/Spi/SpiDxe.h b/Drivers/Spi/SpiDxe.h new file mode 100644 index 0000000..dee0177 --- /dev/null +++ b/Drivers/Spi/SpiDxe.h @@ -0,0 +1,145 @@ +/******************************************************************************* +Copyright (C) 2016 Marvell International Ltd. + +Marvell BSD License Option + +If you received this File from Marvell, you may opt to use, redistribute and/or +modify this File under the following licensing terms. +Redistribution and use in source and binary forms, with or without modification, +are permitted provided that the following conditions are met: + +* Redistributions of source code must retain the above copyright notice, + this list of conditions and the following disclaimer. + +* Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + +* Neither the name of Marvell nor the names of its contributors may be + used to endorse or promote products derived from this software without + specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR +ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON +ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +*******************************************************************************/ +#ifndef __SPI_MASTER_H__ +#define __SPI_MASTER_H__ + +#include <Library/IoLib.h> +#include <Library/PcdLib.h> +#include <Library/UefiLib.h> +#include <Library/DebugLib.h> +#include <Library/MemoryAllocationLib.h> +#include <Uefi/UefiBaseType.h> +#include <Library/BaseMemoryLib.h> +#include <Library/UefiBootServicesTableLib.h> + +#include <Protocol/Spi.h> + +#define SPI_MASTER_SIGNATURE SIGNATURE_32 ('M', 'S', 'P', 'I') +#define SPI_MASTER_FROM_SPI_MASTER_PROTOCOL(a) CR (a, SPI_MASTER, SpiMasterProtocol, SPI_MASTER_SIGNATURE) + +// Marvell Flash Device Controller Registers +#define SPI_CTRL_REG (0x00) +#define SPI_CONF_REG (0x04) +#define SPI_DATA_OUT_REG (0x08) +#define SPI_DATA_IN_REG (0x0c) +#define SPI_INT_CAUSE_REG (0x10) + +// Serial Memory Interface Control Register Masks +#define SPI_CS_NUM_OFFSET 2 +#define SPI_CS_NUM_MASK (0x7 << SPI_CS_NUM_OFFSET) +#define SPI_MEM_READY_MASK (0x1 << 1) +#define SPI_CS_EN_MASK (0x1 << 0) + +// Serial Memory Interface Configuration Register Masks +#define SPI_BYTE_LENGTH_OFFSET 5 +#define SPI_BYTE_LENGTH (0x1 << SPI_BYTE_LENGTH_OFFSET) +#define SPI_CPOL_OFFSET 11 +#define SPI_CPOL_MASK (0x1 << SPI_CPOL_OFFSET) +#define SPI_CPHA_OFFSET 12 +#define SPI_CPHA_MASK (0x1 << SPI_CPHA_OFFSET) +#define SPI_TXLSBF_OFFSET 13 +#define SPI_TXLSBF_MASK (0x1 << SPI_TXLSBF_OFFSET) +#define SPI_RXLSBF_OFFSET 14 +#define SPI_RXLSBF_MASK (0x1 << SPI_RXLSBF_OFFSET) + +#define SPI_SPR_OFFSET 0 +#define SPI_SPR_MASK (0xf << SPI_SPR_OFFSET) +#define SPI_SPPR_0_OFFSET 4 +#define SPI_SPPR_0_MASK (0x1 << SPI_SPPR_0_OFFSET) +#define SPI_SPPR_HI_OFFSET 6 +#define SPI_SPPR_HI_MASK (0x3 << SPI_SPPR_HI_OFFSET) + +#define SPI_TRANSFER_BEGIN 0x01 // Assert CS before transfer +#define SPI_TRANSFER_END 0x02 // Deassert CS after transfers + +#define SPI_TIMEOUT 100000 + +typedef struct { + EFI_SPI_MASTER_PROTOCOL SpiMasterProtocol; + UINTN Signature; + EFI_HANDLE Handle; + EFI_LOCK Lock; +} SPI_MASTER; + +EFI_STATUS +EFIAPI +EfiSpiTransfer ( + IN EFI_SPI_MASTER_PROTOCOL *This, + IN SPI_DEVICE *Slave, + IN UINTN DataByteCount, + IN VOID *DataOut, + IN VOID *DataIn, + IN UINTN Flag + ); + +EFI_STATUS +EFIAPI +EfiSpiReadWrite ( + IN EFI_SPI_MASTER_PROTOCOL *This, + IN SPI_DEVICE *Slave, + IN UINT8 *Cmd, + IN UINTN CmdSize, + IN UINT8 *DataOut, + OUT UINT8 *DataIn, + IN UINTN DataSize + ); + +EFI_STATUS +EFIAPI +EfiSpiInit ( + IN EFI_SPI_MASTER_PROTOCOL * This + ); + +SPI_DEVICE * +EFIAPI +EfiSpiSetupSlave ( + IN EFI_SPI_MASTER_PROTOCOL * This, + IN UINTN Cs, + IN SPI_MODE Mode + ); + +EFI_STATUS +EFIAPI +EfiSpiFreeSlave ( + IN SPI_DEVICE *Slave + ); + +EFI_STATUS +EFIAPI +SpiMasterEntryPoint ( + IN EFI_HANDLE ImageHandle, + IN EFI_SYSTEM_TABLE *SystemTable + ); + +#endif // __SPI_MASTER_H__ diff --git a/Drivers/Spi/SpiDxe.inf b/Drivers/Spi/SpiDxe.inf new file mode 100644 index 0000000..6f315a9a --- /dev/null +++ b/Drivers/Spi/SpiDxe.inf @@ -0,0 +1,74 @@ +#/******************************************************************************* +#Copyright (C) 2016 Marvell International Ltd. +# +#Marvell BSD License Option +# +#If you received this File from Marvell, you may opt to use, redistribute and/or +#modify this File under the following licensing terms. +#Redistribution and use in source and binary forms, with or without modification, +#are permitted provided that the following conditions are met: +# +#* Redistributions of source code must retain the above copyright notice, +# this list of conditions and the following disclaimer. +# +#* Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# +#* Neither the name of Marvell nor the names of its contributors may be +# used to endorse or promote products derived from this software without +# specific prior written permission. +# +#THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +#ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +#WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +#DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR +#ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +#(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +#LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON +#ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +#(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +#SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +# +#*******************************************************************************/ + +################################################################################ +# +# Defines Section - statements that will be processed to create a Makefile. +# +################################################################################ +[Defines] + INF_VERSION = 0x00010005 + BASE_NAME = SpiMasterDxe + FILE_GUID = c19dbc8a-f4f9-43b0-aee5-802e3ed03d15 + MODULE_TYPE = DXE_DRIVER + VERSION_STRING = 1.0 + ENTRY_POINT = SpiMasterEntryPoint + +[Sources] + SpiDxe.c + SpiDxe.h + +[Packages] + MdePkg/MdePkg.dec + OpenPlatformPkg/Platforms/Marvell/Marvell.dec + +[LibraryClasses] + UefiBootServicesTableLib + UefiDriverEntryPoint + TimerLib + UefiLib + DebugLib + MemoryAllocationLib + IoLib + +[FixedPcd] + gMarvellTokenSpaceGuid.PcdSpiRegBase + gMarvellTokenSpaceGuid.PcdSpiClockFrequency + gMarvellTokenSpaceGuid.PcdSpiMaxFrequency + +[Protocols] + gEfiSpiMasterProtocolGuid + +[Depex] + TRUE diff --git a/Platforms/Marvell/Marvell.dec b/Platforms/Marvell/Marvell.dec index ad90ffc..b0d7d9c 100644 --- a/Platforms/Marvell/Marvell.dec +++ b/Platforms/Marvell/Marvell.dec @@ -113,6 +113,11 @@ gMarvellTokenSpaceGuid.PcdI2cClockFrequency|0|UINT32|0x3000048 gMarvellTokenSpaceGuid.PcdI2cBaudRate|0|UINT32|0x3000049
+#SPI + gMarvellTokenSpaceGuid.PcdSpiRegBase|0|UINT32|0x3000051 + gMarvellTokenSpaceGuid.PcdSpiMaxFrequency|0|UINT32|0x30000052 + gMarvellTokenSpaceGuid.PcdSpiClockFrequency|0|UINT32|0x30000053 + [Protocols] gEfiEepromProtocolGuid = { 0xcd728a1f, 0x45b5, 0x4feb, { 0x98, 0xc8, 0x31, 0x3d, 0xa8, 0x11, 0x74, 0x62 }} gEfiSpiMasterProtocolGuid = { 0x23de66a3, 0xf666, 0x4b3e, { 0xaa, 0xa2, 0x68, 0x9b, 0x18, 0xae, 0x2e, 0x19 }}
From: Jan Dąbroś jsd@semihalf.com
Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Jan Dabros jsd@semihalf.com Signed-off-by: Marcin Wojtas mw@semihalf.com --- Platforms/Marvell/Armada/Apn806.dsc | 5 +++++ Platforms/Marvell/Armada/Armada.dsc.inc | 1 + Platforms/Marvell/Armada/Armada7040.fdf | 1 + Platforms/Marvell/Armada/Armada7040_rz.dsc | 5 +++++ 4 files changed, 12 insertions(+)
diff --git a/Platforms/Marvell/Armada/Apn806.dsc b/Platforms/Marvell/Armada/Apn806.dsc index b85cf69..6c7c2e9 100644 --- a/Platforms/Marvell/Armada/Apn806.dsc +++ b/Platforms/Marvell/Armada/Apn806.dsc @@ -69,3 +69,8 @@ gMarvellTokenSpaceGuid.PcdI2cBaseAddress|0xF0511000 gMarvellTokenSpaceGuid.PcdI2cClockFrequency|200000000 gMarvellTokenSpaceGuid.PcdI2cBaudRate|100000 + + # SPI + gMarvellTokenSpaceGuid.PcdSpiRegBase|0xF0510600 + gMarvellTokenSpaceGuid.PcdSpiMaxFrequency|10000000 + gMarvellTokenSpaceGuid.PcdSpiClockFrequency|200000000 diff --git a/Platforms/Marvell/Armada/Armada.dsc.inc b/Platforms/Marvell/Armada/Armada.dsc.inc index 9b8427e..fca1c57 100644 --- a/Platforms/Marvell/Armada/Armada.dsc.inc +++ b/Platforms/Marvell/Armada/Armada.dsc.inc @@ -393,6 +393,7 @@ OpenPlatformPkg/Drivers/I2c/MvI2cDxe/MvI2cDxe.inf MdeModulePkg/Bus/I2c/I2cDxe/I2cDxe.inf OpenPlatformPkg/Drivers/I2c/Devices/MvEeprom/MvEeprom.inf + OpenPlatformPkg/Drivers/Spi/SpiDxe.inf
MdeModulePkg/Core/RuntimeDxe/RuntimeDxe.inf MdeModulePkg/Universal/SecurityStubDxe/SecurityStubDxe.inf diff --git a/Platforms/Marvell/Armada/Armada7040.fdf b/Platforms/Marvell/Armada/Armada7040.fdf index 7a26eec..19ec16b 100644 --- a/Platforms/Marvell/Armada/Armada7040.fdf +++ b/Platforms/Marvell/Armada/Armada7040.fdf @@ -105,6 +105,7 @@ FvNameGuid = 5eda4200-2c5f-43cb-9da3-0baf74b1b30c INF OpenPlatformPkg/Drivers/I2c/MvI2cDxe/MvI2cDxe.inf INF MdeModulePkg/Bus/I2c/I2cDxe/I2cDxe.inf INF OpenPlatformPkg/Drivers/I2c/Devices/MvEeprom/MvEeprom.inf + INF OpenPlatformPkg/Drivers/Spi/SpiDxe.inf
# Multiple Console IO support INF MdeModulePkg/Universal/Console/ConPlatformDxe/ConPlatformDxe.inf diff --git a/Platforms/Marvell/Armada/Armada7040_rz.dsc b/Platforms/Marvell/Armada/Armada7040_rz.dsc index d4d3926..8e46776 100644 --- a/Platforms/Marvell/Armada/Armada7040_rz.dsc +++ b/Platforms/Marvell/Armada/Armada7040_rz.dsc @@ -81,3 +81,8 @@ gMarvellTokenSpaceGuid.PcdI2cBaseAddress|0xF0511000 gMarvellTokenSpaceGuid.PcdI2cClockFrequency|200000000 gMarvellTokenSpaceGuid.PcdI2cBaudRate|100000 + + #SPI + gMarvellTokenSpaceGuid.PcdSpiRegBase|0xF2700680 + gMarvellTokenSpaceGuid.PcdSpiMaxFrequency|10000000 + gMarvellTokenSpaceGuid.PcdSpiClockFrequency|200000000
From: Jan Dąbroś jsd@semihalf.com
Add EFI_SPI_FLASH_PROTOCOL and register containg folder in Marvell/Marvell.dec in order to make it public. This protocol contains functions used to manage SPI flash.
Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Jan Dabros jsd@semihalf.com Signed-off-by: Marcin Wojtas mw@semihalf.com --- Platforms/Marvell/Include/Protocol/SpiFlash.h | 102 ++++++++++++++++++++++++++ Platforms/Marvell/Marvell.dec | 1 + 2 files changed, 103 insertions(+) create mode 100644 Platforms/Marvell/Include/Protocol/SpiFlash.h
diff --git a/Platforms/Marvell/Include/Protocol/SpiFlash.h b/Platforms/Marvell/Include/Protocol/SpiFlash.h new file mode 100644 index 0000000..3a60893 --- /dev/null +++ b/Platforms/Marvell/Include/Protocol/SpiFlash.h @@ -0,0 +1,102 @@ +/******************************************************************************* +Copyright (C) 2016 Marvell International Ltd. + +Marvell BSD License Option + +If you received this File from Marvell, you may opt to use, redistribute and/or +modify this File under the following licensing terms. +Redistribution and use in source and binary forms, with or without modification, +are permitted provided that the following conditions are met: + +* Redistributions of source code must retain the above copyright notice, + this list of conditions and the following disclaimer. + +* Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + +* Neither the name of Marvell nor the names of its contributors may be + used to endorse or promote products derived from this software without + specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR +ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON +ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +*******************************************************************************/ +#ifndef __EFI_SPI_FLASH_H__ +#define __EFI_SPI_FLASH_H__ + +#include <Protocol/Spi.h> + +extern EFI_GUID gEfiSpiFlashProtocolGuid; + +typedef struct _EFI_SPI_FLASH_PROTOCOL EFI_SPI_FLASH_PROTOCOL; + +typedef +EFI_STATUS +(EFIAPI *EFI_SPI_FLASH_INIT) ( + IN EFI_SPI_FLASH_PROTOCOL *This, + IN SPI_DEVICE *SpiDev + ); + +typedef +EFI_STATUS +(EFIAPI *EFI_SPI_FLASH_READ_ID) ( + IN SPI_DEVICE *SpiDev, + IN UINT32 DataByteCount, + IN OUT UINT8 *Buffer + ); + +typedef +EFI_STATUS +(EFIAPI *EFI_SPI_FLASH_READ) ( + IN SPI_DEVICE *SpiDev, + IN UINT32 Address, + IN UINTN DataByteCount, + IN VOID *Buffer + ); + +typedef +EFI_STATUS +(EFIAPI *EFI_SPI_FLASH_WRITE) ( + IN SPI_DEVICE *SpiDev, + IN UINT32 Address, + IN UINTN DataByteCount, + IN VOID *Buffer + ); + +typedef +EFI_STATUS +(EFIAPI *EFI_SPI_FLASH_ERASE) ( + IN SPI_DEVICE *SpiDev, + IN UINTN Address, + IN UINTN DataByteCount + ); + +typedef +EFI_STATUS +(EFIAPI *EFI_SPI_FLASH_UPDATE) ( + IN SPI_DEVICE *SpiDev, + IN UINT32 Address, + IN UINTN DataByteCount, + IN UINT8 *Buffer + ); + +struct _EFI_SPI_FLASH_PROTOCOL { + EFI_SPI_FLASH_INIT Init; + EFI_SPI_FLASH_READ_ID ReadId; + EFI_SPI_FLASH_READ Read; + EFI_SPI_FLASH_WRITE Write; + EFI_SPI_FLASH_ERASE Erase; + EFI_SPI_FLASH_UPDATE Update; +}; + +#endif // __EFI_SPI_FLASH_H__ diff --git a/Platforms/Marvell/Marvell.dec b/Platforms/Marvell/Marvell.dec index b0d7d9c..97497fd 100644 --- a/Platforms/Marvell/Marvell.dec +++ b/Platforms/Marvell/Marvell.dec @@ -121,4 +121,5 @@ [Protocols] gEfiEepromProtocolGuid = { 0xcd728a1f, 0x45b5, 0x4feb, { 0x98, 0xc8, 0x31, 0x3d, 0xa8, 0x11, 0x74, 0x62 }} gEfiSpiMasterProtocolGuid = { 0x23de66a3, 0xf666, 0x4b3e, { 0xaa, 0xa2, 0x68, 0x9b, 0x18, 0xae, 0x2e, 0x19 }} + gEfiSpiFlashProtocolGuid = { 0x9accb423, 0x5bd2, 0x4fca, { 0x9b, 0x4c, 0x2e, 0x65, 0xfc, 0x25, 0xdf, 0x21 }}
From: Jan Dąbroś jsd@semihalf.com
This patch add driver for managing Spi flash It consumes EFI_SPI_FLASH_PROTOCOL and enables configuration by PCD entries.
Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Jan Dabros jsd@semihalf.com Signed-off-by: Marcin Wojtas mw@semihalf.com --- Documentation/Marvell/PortingGuide/SpiFlash.txt | 19 + Drivers/Spi/Devices/MvSpiFlash.c | 523 ++++++++++++++++++++++++ Drivers/Spi/Devices/MvSpiFlash.h | 130 ++++++ Drivers/Spi/Devices/MvSpiFlash.inf | 74 ++++ Platforms/Marvell/Marvell.dec | 5 + 5 files changed, 751 insertions(+) create mode 100644 Documentation/Marvell/PortingGuide/SpiFlash.txt create mode 100644 Drivers/Spi/Devices/MvSpiFlash.c create mode 100644 Drivers/Spi/Devices/MvSpiFlash.h create mode 100644 Drivers/Spi/Devices/MvSpiFlash.inf
diff --git a/Documentation/Marvell/PortingGuide/SpiFlash.txt b/Documentation/Marvell/PortingGuide/SpiFlash.txt new file mode 100644 index 0000000..aa024c2 --- /dev/null +++ b/Documentation/Marvell/PortingGuide/SpiFlash.txt @@ -0,0 +1,19 @@ +SpiFlash driver configuration +----------------------------- +Folowing PCDs for spi flash driver configuration must be set properly: + + gMarvellTokenSpaceGuid.PcdSpiFlashAddressCycles + +Size of SPI flash address in bytes (3 or 4) + + gMarvellTokenSpaceGuid.PcdSpiFlashEraseSize + +Size of minimal erase block in bytes + + gMarvellTokenSpaceGuid.PcdSpiFlashPageSize + +Size of SPI flash page + + gMarvellTokenSpaceGuid.PcdSpiFlashId + +Id of SPI flash diff --git a/Drivers/Spi/Devices/MvSpiFlash.c b/Drivers/Spi/Devices/MvSpiFlash.c new file mode 100644 index 0000000..9de2631 --- /dev/null +++ b/Drivers/Spi/Devices/MvSpiFlash.c @@ -0,0 +1,523 @@ +/******************************************************************************* +Copyright (C) 2016 Marvell International Ltd. + +Marvell BSD License Option + +If you received this File from Marvell, you may opt to use, redistribute and/or +modify this File under the following licensing terms. +Redistribution and use in source and binary forms, with or without modification, +are permitted provided that the following conditions are met: + +* Redistributions of source code must retain the above copyright notice, + this list of conditions and the following disclaimer. + +* Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + +* Neither the name of Marvell nor the names of its contributors may be + used to endorse or promote products derived from this software without + specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR +ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON +ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +*******************************************************************************/ +#include "MvSpiFlash.h" + +EFI_SPI_MASTER_PROTOCOL *SpiMasterProtocol; +SPI_FLASH_INSTANCE *mSpiFlashInstance; + +STATIC +VOID +SpiFlashFormatAddress ( + IN UINT32 Address, + IN UINT8 AddrSize, + IN OUT UINT8 *Cmd + ) +{ + if (AddrSize == 4) { + Cmd[1] = Address >> 24; + Cmd[2] = Address >> 16; + Cmd[3] = Address >> 8; + Cmd[4] = Address; + } else { + Cmd[1] = Address >> 16; + Cmd[2] = Address >> 8; + Cmd[3] = Address; + } +} + +STATIC +EFI_STATUS +SpiFlashReadCmd ( + IN SPI_DEVICE *Slave, + IN UINT8 *Cmd, + IN UINTN CmdSize, + OUT UINT8 *DataIn, + IN UINTN DataSize + ) +{ + EFI_STATUS Status; + + // Send command and gather response + Status = SpiMasterProtocol->ReadWrite (SpiMasterProtocol, Slave, Cmd, + CmdSize, NULL, DataIn, DataSize); + + return Status; +} + +STATIC +EFI_STATUS +SpiFlashWriteEnableCmd ( + IN SPI_DEVICE *Slave + ) +{ + EFI_STATUS Status; + UINT8 CmdEn = CMD_WRITE_ENABLE; + + // Send write_enable command + Status = SpiMasterProtocol->Transfer (SpiMasterProtocol, Slave, 1, + &CmdEn, NULL, SPI_TRANSFER_BEGIN | SPI_TRANSFER_END); + + return Status; +} + +STATIC +EFI_STATUS +SpiFlashWriteCommon ( + IN SPI_DEVICE *Slave, + IN UINT8 *Cmd, + IN UINT32 Length, + IN UINT8* Buffer, + IN UINT32 BufferLength + ) +{ + UINT8 CmdStatus = CMD_FLAG_STATUS; + UINT8 State; + UINT32 Counter = 0xFFFFF; + + // Send command + SpiFlashWriteEnableCmd (Slave); + + // Write data + SpiMasterProtocol->ReadWrite (SpiMasterProtocol, Slave, Cmd, Length, + Buffer, NULL, BufferLength); + + // Poll status register + SpiMasterProtocol->Transfer (SpiMasterProtocol, Slave, 1, &CmdStatus, + NULL, SPI_TRANSFER_BEGIN); + do { + SpiMasterProtocol->Transfer (SpiMasterProtocol, Slave, 1, NULL, &State, + 0); + Counter--; + if (((State & STATUS_REG_POLL_BIT) == STATUS_REG_POLL_BIT)) + break; + } while (Counter > 0); + if (Counter == 0) { + DEBUG((DEBUG_ERROR, "SpiFlash: Timeout while writing to spi flash\n")); + return EFI_DEVICE_ERROR; + } + + // Deactivate CS + SpiMasterProtocol->Transfer (SpiMasterProtocol, Slave, 0, NULL, NULL, SPI_TRANSFER_END); + + return EFI_SUCCESS; +} + +STATIC +VOID +SpiFlashCmdBankaddrWrite ( + IN SPI_DEVICE *Slave, + IN UINT8 BankSel + ) +{ + UINT8 Cmd = CMD_BANK_WRITE; + + SpiFlashWriteCommon (Slave, &Cmd, 1, &BankSel, 1); +} + +STATIC +UINT8 +SpiFlashBank ( + IN SPI_DEVICE *Slave, + IN UINT32 Offset + ) +{ + UINT8 BankSel; + + BankSel = Offset / SPI_FLASH_16MB_BOUN; + + SpiFlashCmdBankaddrWrite (Slave, BankSel); + + return BankSel; +} + +EFI_STATUS +SpiFlashErase ( + IN SPI_DEVICE *Slave, + IN UINTN Offset, + IN UINTN Length + ) +{ + EFI_STATUS Status; + UINT32 AddrSize, EraseAddr; + UINTN EraseSize; + UINT8 Cmd[5]; + + AddrSize = PcdGet32 (PcdSpiFlashAddressCycles); + EraseSize = PcdGet64 (PcdSpiFlashEraseSize); + + // Check input parameters + if (Offset % EraseSize || Length % EraseSize) { + DEBUG((DEBUG_ERROR, "Spiflash: Either erase offset or length" + "is not multiple of erase size\n")); + return EFI_DEVICE_ERROR; + } + + Cmd[0] = CMD_ERASE_64K; + while (Length) { + EraseAddr = Offset; + + SpiFlashBank (Slave, EraseAddr); + + SpiFlashFormatAddress (EraseAddr, AddrSize, Cmd); + + // Programm proper erase address + Status = SpiFlashWriteCommon (Slave, Cmd, AddrSize + 1, NULL, 0); + if (EFI_ERROR (Status)) { + DEBUG((DEBUG_ERROR, "Spiflash: Error while programming target address\n")); + return Status; + } + + Offset += EraseSize; + Length -= EraseSize; + } + return EFI_SUCCESS; +} + +EFI_STATUS +SpiFlashRead ( + IN SPI_DEVICE *Slave, + IN UINT32 Offset, + IN UINTN Length, + IN VOID *Buf + ) +{ + EFI_STATUS Status = EFI_SUCCESS; + UINT8 Cmd[6]; + UINT32 AddrSize, ReadAddr, ReadLength, RemainLength; + UINTN BankSel = 0; + + AddrSize = PcdGet32 (PcdSpiFlashAddressCycles); + + Cmd[0] = CMD_READ_ARRAY_FAST; + + // Sign end of address with 0 byte + Cmd[5] = 0; + + while (Length) { + ReadAddr = Offset; + + BankSel = SpiFlashBank (Slave, ReadAddr); + + RemainLength = (SPI_FLASH_16MB_BOUN * (BankSel + 1)) - Offset; + if (Length < RemainLength) { + ReadLength = Length; + } else { + ReadLength = RemainLength; + } + SpiFlashFormatAddress (ReadAddr, AddrSize, Cmd); + // Program proper read address and read data + Status = SpiFlashReadCmd (Slave, Cmd, AddrSize + 2, Buf, Length); + + Offset += ReadLength; + Length -= ReadLength; + Buf += ReadLength; + } + + return Status; +} + +EFI_STATUS +SpiFlashWrite ( + IN SPI_DEVICE *Slave, + IN UINT32 Offset, + IN UINTN Length, + IN VOID *Buf + ) +{ + EFI_STATUS Status; + UINTN ByteAddr, ChunkLength, ActualIndex, PageSize; + UINT32 WriteAddr; + UINT8 Cmd[5], AddrSize; + + AddrSize = PcdGet32 (PcdSpiFlashAddressCycles); + PageSize = PcdGet32 (PcdSpiFlashPageSize); + + Cmd[0] = CMD_PAGE_PROGRAM; + + for (ActualIndex = 0; ActualIndex < Length; ActualIndex += ChunkLength) { + WriteAddr = Offset; + + SpiFlashBank (Slave, WriteAddr); + + ByteAddr = Offset % PageSize; + + ChunkLength = MIN(Length - ActualIndex, (UINT64) (PageSize - ByteAddr)); + + SpiFlashFormatAddress (WriteAddr, AddrSize, Cmd); + + // Program proper write address and write data + Status = SpiFlashWriteCommon (Slave, Cmd, AddrSize + 1, Buf + ActualIndex, + ChunkLength); + if (EFI_ERROR (Status)) { + DEBUG((DEBUG_ERROR, "SpiFlash: Error while programming write address\n")); + return Status; + } + + Offset += ChunkLength; + } + return EFI_SUCCESS; +} + +STATIC +EFI_STATUS +SpiFlashUpdateBlock ( + IN SPI_DEVICE *Slave, + IN UINT32 Offset, + IN UINTN ToUpdate, + IN UINT8 *Buf, + IN UINT8 *TmpBuf, + IN UINTN EraseSize + ) +{ + EFI_STATUS Status; + + // Read backup + Status = SpiFlashRead (Slave, Offset, EraseSize, TmpBuf); + if (EFI_ERROR (Status)) { + DEBUG((DEBUG_ERROR, "SpiFlash: Update: Error while reading old data\n")); + return Status; + } + + // Erase entire sector + Status = SpiFlashErase (Slave, Offset, EraseSize); + if (EFI_ERROR (Status)) { + DEBUG((DEBUG_ERROR, "SpiFlash: Update: Error while erasing block\n")); + return Status; + } + + // Write new data + SpiFlashWrite (Slave, Offset, ToUpdate, Buf); + if (EFI_ERROR (Status)) { + DEBUG((DEBUG_ERROR, "SpiFlash: Update: Error while writing new data\n")); + return Status; + } + + // Write backup + if (ToUpdate != EraseSize) { + Status = SpiFlashWrite (Slave, Offset + ToUpdate, EraseSize - ToUpdate, + &TmpBuf[ToUpdate]); + if (EFI_ERROR (Status)) { + DEBUG((DEBUG_ERROR, "SpiFlash: Update: Error while writing backup\n")); + return Status; + } + } + + return EFI_SUCCESS; +} + +EFI_STATUS +SpiFlashUpdate ( + IN SPI_DEVICE *Slave, + IN UINT32 Offset, + IN UINTN ByteCount, + IN UINT8 *Buf + ) +{ + EFI_STATUS Status; + UINT64 EraseSize, ToUpdate, Scale = 1; + UINT8 *TmpBuf, *End; + + EraseSize = PcdGet64 (PcdSpiFlashEraseSize); + + End = Buf + ByteCount; + + TmpBuf = (UINT8 *)AllocateZeroPool (EraseSize); + if (TmpBuf == NULL) { + DEBUG((DEBUG_ERROR, "SpiFlash: Cannot allocate memory\n")); + return EFI_OUT_OF_RESOURCES; + } + + if (End - Buf >= 200) + Scale = (End - Buf) / 100; + + for (; Buf < End; Buf += ToUpdate, Offset += ToUpdate) { + ToUpdate = MIN((UINT64)(End - Buf), EraseSize); + Print (L" \rUpdating, %d%%", 100 - (End - Buf) / Scale); + Status = SpiFlashUpdateBlock (Slave, Offset, ToUpdate, Buf, TmpBuf, EraseSize); + + if (EFI_ERROR (Status)) { + DEBUG((DEBUG_ERROR, "SpiFlash: Error while updating\n")); + return Status; + } + } + + Print(L"\n"); + FreePool (TmpBuf); + + return EFI_SUCCESS; +} + +EFI_STATUS +EFIAPI +SpiFlashReadId ( + IN SPI_DEVICE *SpiDev, + IN UINT32 DataByteCount, + IN OUT UINT8 *Buffer + ) +{ + EFI_STATUS Status; + UINT8 *DataOut; + + DataOut = (UINT8 *) AllocateZeroPool (DataByteCount); + if (DataOut == NULL) { + DEBUG((DEBUG_ERROR, "SpiFlash: Cannot allocate memory\n")); + return EFI_OUT_OF_RESOURCES; + } + Status = SpiMasterProtocol->Transfer (SpiMasterProtocol, SpiDev, + DataByteCount, Buffer, DataOut, SPI_TRANSFER_BEGIN | SPI_TRANSFER_END); + if (EFI_ERROR(Status)) { + FreePool (DataOut); + DEBUG((DEBUG_ERROR, "SpiFlash: Spi transfer error\n")); + return Status; + } + + // Bytes 1,2 and 3 contain SPI flash ID + Buffer[0] = DataOut[1]; + Buffer[1] = DataOut[2]; + Buffer[2] = DataOut[3]; + + FreePool (DataOut); + + return EFI_SUCCESS; +} + +EFI_STATUS +EFIAPI +SpiFlashInit ( + IN EFI_SPI_FLASH_PROTOCOL *This, + IN SPI_DEVICE *Slave + ) +{ + EFI_STATUS Status; + UINT8 Cmd, StatusRegister; + UINT32 AddrSize; + + AddrSize = PcdGet32 (PcdSpiFlashAddressCycles); + + if (AddrSize == 4) { + // Set 4 byte address mode + Status = SpiFlashWriteEnableCmd (Slave); + if (EFI_ERROR (Status)) { + DEBUG((DEBUG_ERROR, "SpiFlash: Error while setting write_enable\n")); + return Status; + } + + Cmd = CMD_4B_ADDR_ENABLE; + Status = SpiMasterProtocol->Transfer (SpiMasterProtocol, Slave, 1, &Cmd, NULL, + SPI_TRANSFER_BEGIN | SPI_TRANSFER_END); + if (EFI_ERROR (Status)) { + DEBUG((DEBUG_ERROR, "SpiFlash: Error while setting 4B address\n")); + return Status; + } + } + + // Write flash status register + Status = SpiFlashWriteEnableCmd (Slave); + if (EFI_ERROR (Status)) { + DEBUG((DEBUG_ERROR, "SpiFlash: Error while setting write_enable\n")); + return Status; + } + + Cmd = CMD_WRITE_STATUS_REG; + StatusRegister = 0x0; + Status = SpiMasterProtocol->ReadWrite (SpiMasterProtocol, Slave, &Cmd, 1, + &StatusRegister, NULL, 1); + if (EFI_ERROR (Status)) { + DEBUG((DEBUG_ERROR, "SpiFlash: Error with spi transfer\n")); + return Status; + } + + return EFI_SUCCESS; +} + +EFI_STATUS +SpiFlashInitProtocol ( + IN EFI_SPI_FLASH_PROTOCOL *SpiFlashProtocol + ) +{ + + SpiFlashProtocol->Init = SpiFlashInit; + SpiFlashProtocol->ReadId = SpiFlashReadId; + SpiFlashProtocol->Read = SpiFlashRead; + SpiFlashProtocol->Write = SpiFlashWrite; + SpiFlashProtocol->Erase = SpiFlashErase; + SpiFlashProtocol->Update = SpiFlashUpdate; + + return EFI_SUCCESS; +} + +EFI_STATUS +EFIAPI +SpiFlashEntryPoint ( + IN EFI_HANDLE ImageHandle, + IN EFI_SYSTEM_TABLE *SystemTable + ) +{ + EFI_STATUS Status; + + Status = gBS->LocateProtocol ( + &gEfiSpiMasterProtocolGuid, + NULL, + (VOID **)&SpiMasterProtocol + ); + if (EFI_ERROR (Status)) { + DEBUG((DEBUG_ERROR, "SpiFlash: Cannot locate SPI Master protocol\n")); + return EFI_DEVICE_ERROR; + } + + mSpiFlashInstance = AllocateZeroPool (sizeof (SPI_FLASH_INSTANCE)); + + if (mSpiFlashInstance == NULL) { + DEBUG((DEBUG_ERROR, "SpiFlash: Cannot allocate memory\n")); + return EFI_OUT_OF_RESOURCES; + } + + SpiFlashInitProtocol (&mSpiFlashInstance->SpiFlashProtocol); + + mSpiFlashInstance->Signature = SPI_FLASH_SIGNATURE; + + Status = gBS->InstallMultipleProtocolInterfaces ( + &(mSpiFlashInstance->Handle), + &gEfiSpiFlashProtocolGuid, + &(mSpiFlashInstance->SpiFlashProtocol), + NULL + ); + if (EFI_ERROR (Status)) { + FreePool (mSpiFlashInstance); + DEBUG((DEBUG_ERROR, "SpiFlash: Cannot install SPI flash protocol\n")); + return EFI_DEVICE_ERROR; + } + + return EFI_SUCCESS; +} diff --git a/Drivers/Spi/Devices/MvSpiFlash.h b/Drivers/Spi/Devices/MvSpiFlash.h new file mode 100644 index 0000000..063168b --- /dev/null +++ b/Drivers/Spi/Devices/MvSpiFlash.h @@ -0,0 +1,130 @@ +/******************************************************************************* +Copyright (C) 2016 Marvell International Ltd. + +Marvell BSD License Option + +If you received this File from Marvell, you may opt to use, redistribute and/or +modify this File under the following licensing terms. +Redistribution and use in source and binary forms, with or without modification, +are permitted provided that the following conditions are met: + +* Redistributions of source code must retain the above copyright notice, + this list of conditions and the following disclaimer. + +* Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + +* Neither the name of Marvell nor the names of its contributors may be + used to endorse or promote products derived from this software without + specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR +ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON +ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +*******************************************************************************/ +#ifndef __MV_SPI_FLASH_H__ +#define __MV_SPI_FLASH_H__ + +#include <Library/IoLib.h> +#include <Library/PcdLib.h> +#include <Library/UefiLib.h> +#include <Library/DebugLib.h> +#include <Library/MemoryAllocationLib.h> +#include <Uefi/UefiBaseType.h> +#include <Library/BaseMemoryLib.h> +#include <Library/UefiBootServicesTableLib.h> + +#include <Protocol/Spi.h> +#include <Protocol/SpiFlash.h> + +#define SPI_FLASH_SIGNATURE SIGNATURE_32 ('F', 'S', 'P', 'I') + +#define CMD_READ_ID 0x9f +#define READ_STATUS_REG_CMD 0x0b +#define CMD_WRITE_ENABLE 0x06 +#define CMD_FLAG_STATUS 0x70 +#define CMD_WRITE_STATUS_REG 0x01 +#define CMD_READ_ARRAY_FAST 0x0b +#define CMD_PAGE_PROGRAM 0x02 +#define CMD_BANK_WRITE 0xc5 +#define CMD_ERASE_64K 0xd8 +#define CMD_4B_ADDR_ENABLE 0xb7 + +#define STATUS_REG_POLL_BIT (1 << 7) + +#define SPI_TRANSFER_BEGIN 0x01 // Assert CS before transfer +#define SPI_TRANSFER_END 0x02 // Deassert CS after transfers + +#define SPI_FLASH_16MB_BOUN 0x1000000 + +typedef enum { + SPI_FLASH_READ_ID, + SPI_FLASH_READ, // Read from SPI flash with address + SPI_FLASH_WRITE, // Write to SPI flash with address + SPI_FLASH_ERASE, + SPI_FLASH_UPDATE, + SPI_COMMAND_MAX +} SPI_COMMAND; + +typedef struct { + EFI_SPI_FLASH_PROTOCOL SpiFlashProtocol; + UINTN Signature; + EFI_HANDLE Handle; +} SPI_FLASH_INSTANCE; + +EFI_STATUS +EFIAPI +SpiFlashReadId ( + IN SPI_DEVICE *SpiDev, + IN UINT32 DataByteCount, + IN OUT UINT8 *Buffer + ); + +EFI_STATUS +SpiFlashRead ( + IN SPI_DEVICE *Slave, + IN UINT32 Offset, + IN UINTN Length, + IN VOID *Buf + ); + +EFI_STATUS +SpiFlashWrite ( + IN SPI_DEVICE *Slave, + IN UINT32 Offset, + IN UINTN Length, + IN VOID *Buf + ); + +EFI_STATUS +SpiFlashUpdate ( + IN SPI_DEVICE *Slave, + IN UINT32 Offset, + IN UINTN ByteCount, + IN UINT8 *Buf + ); + +EFI_STATUS +SpiFlashErase ( + IN SPI_DEVICE *SpiDev, + IN UINTN Offset, + IN UINTN Length + ); + +EFI_STATUS +EFIAPI +EfiSpiFlashInit ( + IN EFI_SPI_FLASH_PROTOCOL *This, + IN SPI_DEVICE *Slave + ); + +#endif // __MV_SPI_FLASH_H__ diff --git a/Drivers/Spi/Devices/MvSpiFlash.inf b/Drivers/Spi/Devices/MvSpiFlash.inf new file mode 100644 index 0000000..ad333a9 --- /dev/null +++ b/Drivers/Spi/Devices/MvSpiFlash.inf @@ -0,0 +1,74 @@ +#/******************************************************************************* +#Copyright (C) 2016 Marvell International Ltd. +# +#Marvell BSD License Option +# +#If you received this File from Marvell, you may opt to use, redistribute and/or +#modify this File under the following licensing terms. +#Redistribution and use in source and binary forms, with or without modification, +#are permitted provided that the following conditions are met: +# +#* Redistributions of source code must retain the above copyright notice, +# this list of conditions and the following disclaimer. +# +#* Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# +#* Neither the name of Marvell nor the names of its contributors may be +# used to endorse or promote products derived from this software without +# specific prior written permission. +# +#THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +#ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +#WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +#DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR +#ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +#(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +#LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON +#ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +#(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +#SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +# +#*******************************************************************************/ + +################################################################################ +# +# Defines Section - statements that will be processed to create a Makefile. +# +################################################################################ +[Defines] + INF_VERSION = 0x00010005 + BASE_NAME = SpiFlashDxe + FILE_GUID = 49d7fb74-306d-42bd-94c8-c0c54b181dd7 + MODULE_TYPE = DXE_DRIVER + VERSION_STRING = 1.0 + ENTRY_POINT = SpiFlashEntryPoint + +[Sources] + MvSpiFlash.c + MvSpiFlash.h + +[Packages] + MdePkg/MdePkg.dec + OpenPlatformPkg/Platforms/Marvell/Marvell.dec + +[LibraryClasses] + UefiBootServicesTableLib + UefiDriverEntryPoint + TimerLib + UefiLib + DebugLib + MemoryAllocationLib + +[FixedPcd] + gMarvellTokenSpaceGuid.PcdSpiFlashAddressCycles + gMarvellTokenSpaceGuid.PcdSpiFlashEraseSize + gMarvellTokenSpaceGuid.PcdSpiFlashPageSize + +[Protocols] + gEfiSpiMasterProtocolGuid + gEfiSpiFlashProtocolGuid + +[Depex] + TRUE diff --git a/Platforms/Marvell/Marvell.dec b/Platforms/Marvell/Marvell.dec index 97497fd..dffb749 100644 --- a/Platforms/Marvell/Marvell.dec +++ b/Platforms/Marvell/Marvell.dec @@ -118,6 +118,11 @@ gMarvellTokenSpaceGuid.PcdSpiMaxFrequency|0|UINT32|0x30000052 gMarvellTokenSpaceGuid.PcdSpiClockFrequency|0|UINT32|0x30000053
+ gMarvellTokenSpaceGuid.PcdSpiFlashAddressCycles|0|UINT32|0x3000053 + gMarvellTokenSpaceGuid.PcdSpiFlashEraseSize|0|UINT64|0x3000054 + gMarvellTokenSpaceGuid.PcdSpiFlashPageSize|0|UINT32|0x3000055 + gMarvellTokenSpaceGuid.PcdSpiFlashId|0|UINT32|0x3000056 + [Protocols] gEfiEepromProtocolGuid = { 0xcd728a1f, 0x45b5, 0x4feb, { 0x98, 0xc8, 0x31, 0x3d, 0xa8, 0x11, 0x74, 0x62 }} gEfiSpiMasterProtocolGuid = { 0x23de66a3, 0xf666, 0x4b3e, { 0xaa, 0xa2, 0x68, 0x9b, 0x18, 0xae, 0x2e, 0x19 }}
From: Jan Dąbroś jsd@semihalf.com
Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Jan Dabros jsd@semihalf.com Signed-off-by: Marcin Wojtas mw@semihalf.com --- Platforms/Marvell/Armada/Apn806.dsc | 5 +++++ Platforms/Marvell/Armada/Armada.dsc.inc | 1 + Platforms/Marvell/Armada/Armada7040.fdf | 1 + Platforms/Marvell/Armada/Armada7040_rz.dsc | 5 +++++ 4 files changed, 12 insertions(+)
diff --git a/Platforms/Marvell/Armada/Apn806.dsc b/Platforms/Marvell/Armada/Apn806.dsc index 6c7c2e9..4ec4af3 100644 --- a/Platforms/Marvell/Armada/Apn806.dsc +++ b/Platforms/Marvell/Armada/Apn806.dsc @@ -74,3 +74,8 @@ gMarvellTokenSpaceGuid.PcdSpiRegBase|0xF0510600 gMarvellTokenSpaceGuid.PcdSpiMaxFrequency|10000000 gMarvellTokenSpaceGuid.PcdSpiClockFrequency|200000000 + + gMarvellTokenSpaceGuid.PcdSpiFlashAddressCycles|4 + gMarvellTokenSpaceGuid.PcdSpiFlashEraseSize|65536 + gMarvellTokenSpaceGuid.PcdSpiFlashPageSize|256 + gMarvellTokenSpaceGuid.PcdSpiFlashId|0x20BA21 diff --git a/Platforms/Marvell/Armada/Armada.dsc.inc b/Platforms/Marvell/Armada/Armada.dsc.inc index fca1c57..1cd25cb 100644 --- a/Platforms/Marvell/Armada/Armada.dsc.inc +++ b/Platforms/Marvell/Armada/Armada.dsc.inc @@ -394,6 +394,7 @@ MdeModulePkg/Bus/I2c/I2cDxe/I2cDxe.inf OpenPlatformPkg/Drivers/I2c/Devices/MvEeprom/MvEeprom.inf OpenPlatformPkg/Drivers/Spi/SpiDxe.inf + OpenPlatformPkg/Drivers/Spi/Devices/MvSpiFlash.inf
MdeModulePkg/Core/RuntimeDxe/RuntimeDxe.inf MdeModulePkg/Universal/SecurityStubDxe/SecurityStubDxe.inf diff --git a/Platforms/Marvell/Armada/Armada7040.fdf b/Platforms/Marvell/Armada/Armada7040.fdf index 19ec16b..043c5d4 100644 --- a/Platforms/Marvell/Armada/Armada7040.fdf +++ b/Platforms/Marvell/Armada/Armada7040.fdf @@ -106,6 +106,7 @@ FvNameGuid = 5eda4200-2c5f-43cb-9da3-0baf74b1b30c INF MdeModulePkg/Bus/I2c/I2cDxe/I2cDxe.inf INF OpenPlatformPkg/Drivers/I2c/Devices/MvEeprom/MvEeprom.inf INF OpenPlatformPkg/Drivers/Spi/SpiDxe.inf + INF OpenPlatformPkg/Drivers/Spi/Devices/MvSpiFlash.inf
# Multiple Console IO support INF MdeModulePkg/Universal/Console/ConPlatformDxe/ConPlatformDxe.inf diff --git a/Platforms/Marvell/Armada/Armada7040_rz.dsc b/Platforms/Marvell/Armada/Armada7040_rz.dsc index 8e46776..8a0c2a9 100644 --- a/Platforms/Marvell/Armada/Armada7040_rz.dsc +++ b/Platforms/Marvell/Armada/Armada7040_rz.dsc @@ -86,3 +86,8 @@ gMarvellTokenSpaceGuid.PcdSpiRegBase|0xF2700680 gMarvellTokenSpaceGuid.PcdSpiMaxFrequency|10000000 gMarvellTokenSpaceGuid.PcdSpiClockFrequency|200000000 + + gMarvellTokenSpaceGuid.PcdSpiFlashAddressCycles|3 + gMarvellTokenSpaceGuid.PcdSpiFlashEraseSize|65536 + gMarvellTokenSpaceGuid.PcdSpiFlashPageSize|256 + gMarvellTokenSpaceGuid.PcdSpiFlashId|0x20BA18
From: Jan Dąbroś jsd@semihalf.com
sf command uses EFI_SPI_FLASH_PROTOCOL and EFI_SPI_MASTER_PROTOCOL. It allows read/write/erase/update operations on SPI flash.
Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Jan Dabros jsd@semihalf.com Signed-off-by: Marcin Wojtas mw@semihalf.com --- Applications/SpiTool/SpiFlashCmd.c | 529 +++++++++++++++++++++++++++++++++++ Applications/SpiTool/SpiFlashCmd.inf | 76 +++++ Applications/SpiTool/SpiFlashCmd.uni | Bin 0 -> 7216 bytes Platforms/Marvell/Marvell.dec | 1 + 4 files changed, 606 insertions(+) create mode 100644 Applications/SpiTool/SpiFlashCmd.c create mode 100644 Applications/SpiTool/SpiFlashCmd.inf create mode 100644 Applications/SpiTool/SpiFlashCmd.uni
diff --git a/Applications/SpiTool/SpiFlashCmd.c b/Applications/SpiTool/SpiFlashCmd.c new file mode 100644 index 0000000..08b5200 --- /dev/null +++ b/Applications/SpiTool/SpiFlashCmd.c @@ -0,0 +1,529 @@ +/******************************************************************************* +Copyright (C) 2016 Marvell International Ltd. + +Marvell BSD License Option + +If you received this File from Marvell, you may opt to use, redistribute and/or +modify this File under the following licensing terms. +Redistribution and use in source and binary forms, with or without modification, +are permitted provided that the following conditions are met: + +* Redistributions of source code must retain the above copyright notice, + this list of conditions and the following disclaimer. + +* Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + +* Neither the name of Marvell nor the names of its contributors may be + used to endorse or promote products derived from this software without + specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR +ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON +ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +*******************************************************************************/ +#include <Uefi.h> +#include <ShellBase.h> + +#include <Library/BaseLib.h> +#include <Library/BaseMemoryLib.h> +#include <Library/DebugLib.h> +#include <Library/MemoryAllocationLib.h> +#include <Library/ShellCommandLib.h> +#include <Library/ShellLib.h> +#include <Library/UefiLib.h> +#include <Library/UefiBootServicesTableLib.h> +#include <Library/PrintLib.h> +#include <Library/ShellCEntryLib.h> +#include <Library/HiiLib.h> +#include <Library/FileHandleLib.h> + +#include <Protocol/Spi.h> +#include <Protocol/SpiFlash.h> + +#include "../../Drivers/Spi/Devices/MvSpiFlash.h" + +EFI_SPI_FLASH_PROTOCOL *SpiFlashProtocol; +EFI_SPI_MASTER_PROTOCOL *SpiMasterProtocol; + +CONST CHAR16 gShellSpiFlashFileName[] = L"ShellCommand"; +EFI_HANDLE gShellSfHiiHandle = NULL; + +BOOLEAN InitFlag = 1; + +STATIC CONST SHELL_PARAM_ITEM ParamList[] = { + {L"read", TypeFlag}, + {L"readfile", TypeFlag}, + {L"write", TypeFlag}, + {L"writefile", TypeFlag}, + {L"erase", TypeFlag}, + {L"update", TypeFlag}, + {L"updatefile", TypeFlag}, + {L"probe", TypeFlag}, + {L"help", TypeFlag}, + {NULL , TypeMax} + }; + +typedef enum { + PROBE = 1, + READ = 2, + READ_FILE = 4, + WRITE = 8, + WRITE_FILE = 16, + ERASE = 32, + UPDATE = 64, + UPDATE_FILE = 128, +} Flags; + +/** + Return the file name of the help text file if not using HII. + + @return The string pointer to the file name. +**/ +CONST CHAR16* +EFIAPI +ShellCommandGetManFileNameSpiFlash ( + VOID + ) +{ + + return gShellSpiFlashFileName; +} + +VOID +SfUsage ( + VOID + ) +{ + Print (L"\nBasic SPI command\n" + "sf [probe | read | readfile | write | writefile | erase |" + "update | updatefile]" + "[<Address> | <FilePath>] <Offset> <Length>\n\n" + "Length - Number of bytes to send\n" + "Address - Address in RAM to store/load data\n" + "FilePath - Path to file to read/write data from/to\n" + "Offset - Offset from beggining of SPI flash to store/load data\n" + "Examples:\n" + "Check if there is response from SPI flash\n" + " sf probe\n" + "Read 32 bytes from 0xe00000 of SPI flash into RAM at address 0x100000\n" + " sf read 0x100000 0xe00000 32\n" + "Read 0x20 bytes from 0x200000 of SPI flash into RAM at address 0x300000\n" + " sf read 0x300000 0x200000 0x20\n" + "Erase 0x10000 bytes from offset 0x100000 of SPI flash\n" + " sf erase 0x100000 0x100000\n" + "Write 16 bytes from 0x200000 at RAM into SPI flash at address 0x4000000\n" + " sf write 0x200000 0x4000000 16\n" + "Update 100 bytes from 0x100000 at RAM in SPI flash at address 0xe00000\n" + " sf update 0x100000 0xe00000 100\n" + "Read 0x3000 bytes from 0x0 of SPI flash into file fs2:file.bin\n" + " sf readfile fs2:file.bin 0x0 0x3000 \n" + "Update data in SPI flash at 0x3000000 from file Linux.efi\n" + " sf updatefile Linux.efi 0x3000000\n" + ); +} + +STATIC +EFI_STATUS +OpenAndPrepareFile ( + IN CHAR16 *FilePath, + SHELL_FILE_HANDLE *FileHandle + ) +{ + EFI_STATUS Status; + UINT64 OpenMode; + + OpenMode = EFI_FILE_MODE_READ | EFI_FILE_MODE_WRITE | EFI_FILE_MODE_CREATE; + + Status = ShellOpenFileByName (FilePath, FileHandle, OpenMode, 0); + if (EFI_ERROR (Status)) { + Print (L"sf: Cannot open file\n"); + return Status; + } + + Status = FileHandleSetPosition(*FileHandle, 0); + + if (EFI_ERROR(Status)) { + Print (L"sf: Cannot set file position to first byte\n"); + ShellCloseFile (FileHandle); + return Status; + } + + return EFI_SUCCESS; +} + +STATIC +EFI_STATUS +FlashProbe ( + IN SPI_DEVICE *Slave + ) +{ + EFI_STATUS Status; + UINT8 IdBuffer[4]; + UINT32 Id, RefId; + + Id = PcdGet32 (PcdSpiFlashId); + + IdBuffer[0] = CMD_READ_ID; + + SpiFlashProtocol->ReadId ( + Slave, + 4, + IdBuffer + ); + + RefId = (IdBuffer[0] << 16) + (IdBuffer[1] << 8) + IdBuffer[2]; + + if (RefId == Id) { + Print (L"sf: Detected supported SPI flash with ID=%3x\n", RefId); + Status = SpiFlashProtocol->Init (SpiFlashProtocol, Slave); + if (EFI_ERROR(Status)) { + Print (L"sf: Cannot initialize flash device\n"); + return SHELL_ABORTED; + } + InitFlag = 0; + return EFI_SUCCESS; + } else if (RefId != 0) { + Print (L"sf: Unsupported SPI flash detected with ID=%2x\n", RefId); + return SHELL_ABORTED; + } + + Print (L"sf: No SPI flash detected"); + return SHELL_ABORTED; +} + +SHELL_STATUS +EFIAPI +ShellCommandRunSpiFlash ( + IN EFI_HANDLE ImageHandle, + IN EFI_SYSTEM_TABLE *SystemTable + ) +{ +EFI_STATUS Status; + SPI_DEVICE *Slave; + LIST_ENTRY *CheckPackage; + EFI_PHYSICAL_ADDRESS Address = 0, Offset = 0; + SHELL_FILE_HANDLE FileHandle = NULL; + UINTN ByteCount, FileSize, I; + UINT8 *Buffer = NULL, *FileBuffer = NULL; + CHAR16 *ProblemParam, *FilePath; + CONST CHAR16 *AddressStr = NULL, *OffsetStr = NULL; + CONST CHAR16 *LengthStr = NULL, *FileStr = NULL; + BOOLEAN AddrFlag = FALSE, LengthFlag = TRUE, FileFlag = FALSE; + UINT8 Flag = 0, CheckFlag = 0; + + Status = gBS->LocateProtocol ( + &gEfiSpiFlashProtocolGuid, + NULL, + (VOID **)&SpiFlashProtocol + ); + if (EFI_ERROR(Status)) { + Print (L"sf: Cannot locate SpiFlash protocol\n"); + return SHELL_ABORTED; + } + + Status = gBS->LocateProtocol ( + &gEfiSpiMasterProtocolGuid, + NULL, + (VOID **)&SpiMasterProtocol + ); + if (EFI_ERROR(Status)) { + Print (L"sf: Cannot locate SpiMaster protocol\n"); + return SHELL_ABORTED; + } + + // Parse Shell command line + Status = ShellInitialize (); + if (EFI_ERROR (Status)) { + Print (L"sf: Cannot initialize Shell\n"); + ASSERT_EFI_ERROR (Status); + return SHELL_ABORTED; + } + + Status = ShellCommandLineParse (ParamList, &CheckPackage, &ProblemParam, TRUE); + if (EFI_ERROR (Status)) { + Print (L"sf: Error while parsing command line\n"); + return SHELL_ABORTED; + } + + if (ShellCommandLineGetFlag (CheckPackage, L"help")) { + SfUsage(); + return EFI_SUCCESS; + } + + // Check flags provided by user + Flag |= (ShellCommandLineGetFlag (CheckPackage, L"probe") << 0); + Flag |= (ShellCommandLineGetFlag (CheckPackage, L"read") << 1); + Flag |= (ShellCommandLineGetFlag (CheckPackage, L"readfile") << 2); + Flag |= (ShellCommandLineGetFlag (CheckPackage, L"write") << 3); + Flag |= (ShellCommandLineGetFlag (CheckPackage, L"writefile") << 4); + Flag |= (ShellCommandLineGetFlag (CheckPackage, L"erase") << 5); + Flag |= (ShellCommandLineGetFlag (CheckPackage, L"update") << 6); + Flag |= (ShellCommandLineGetFlag (CheckPackage, L"updatefile") << 7); + + if (InitFlag && !(Flag & PROBE)) { + Print (L"Please run sf probe\n"); + return EFI_SUCCESS; + } + + CheckFlag = Flag; + for (I = 0; CheckFlag; CheckFlag >>= 1) { + I += CheckFlag & 1; + if (I > 1) { + Print (L"sf: Too many flags\n"); + SfUsage(); + return SHELL_ABORTED; + } + } + + // Setup new spi device + Slave = SpiMasterProtocol->SetupDevice (SpiMasterProtocol, 0, 0); + if (Slave == NULL) { + Print(L"sf: Cannot allocate SPI device!\n"); + return SHELL_ABORTED; + } + + switch (Flag) { + case PROBE: + // Probe spi bus + Status = FlashProbe (Slave); + if (EFI_ERROR(Status)) { + // No supported spi flash detected + return SHELL_ABORTED; + } else { + return Status; + } + break; + // Fall through + case READ: + case WRITE: + case UPDATE: + AddressStr = ShellCommandLineGetRawValue (CheckPackage, 1); + OffsetStr = ShellCommandLineGetRawValue (CheckPackage, 2); + LengthStr = ShellCommandLineGetRawValue (CheckPackage, 3); + AddrFlag = TRUE; + break; + case ERASE: + OffsetStr = ShellCommandLineGetRawValue (CheckPackage, 1); + LengthStr = ShellCommandLineGetRawValue (CheckPackage, 2); + break; + case READ_FILE: + FileStr = ShellCommandLineGetRawValue (CheckPackage, 1); + OffsetStr = ShellCommandLineGetRawValue (CheckPackage, 2); + LengthStr = ShellCommandLineGetRawValue (CheckPackage, 3); + FileFlag = TRUE; + break; + case WRITE_FILE: + case UPDATE_FILE: + FileStr = ShellCommandLineGetRawValue (CheckPackage, 1); + OffsetStr = ShellCommandLineGetRawValue (CheckPackage, 2); + LengthFlag = FALSE; + FileFlag = TRUE; + break; + } + + // Read address parameter + if ((AddressStr == NULL) & AddrFlag) { + Print (L"sf: No address parameter!\n"); + return SHELL_ABORTED; + } else if (AddrFlag) { + Address = ShellHexStrToUintn (AddressStr); + if (Address == (UINTN)(-1)) { + Print (L"sf: Wrong address parameter\n"); + return SHELL_ABORTED; + } + } + + // Read offset parameter + if (OffsetStr == NULL) { + Print (L"sf: No offset Parameter!\n"); + return SHELL_ABORTED; + } else { + Offset = ShellHexStrToUintn (OffsetStr); + if (Offset < 0) { + Print (L"sf: Wrong offset parameter: %s", OffsetStr); + return SHELL_ABORTED; + } + } + + // Read length parameter + if ((LengthStr == NULL) & LengthFlag) { + Print (L"sf: No lenght parameter!\n"); + return SHELL_ABORTED; + } else if (LengthFlag) { + ByteCount = ShellStrToUintn (LengthStr); + if (ByteCount < 0) { + Print (L"sf: Wrong length parameter %s!\n", LengthStr); + return SHELL_ABORTED; + } + } + + if (FileFlag) { + // Read FilePath parameter + if (FileStr == NULL) { + Print (L"sf: No FilePath parameter!\n"); + return SHELL_ABORTED; + } else { + FilePath = (CHAR16 *) FileStr; + Status = ShellIsFile (FilePath); + // When read file into flash, file doesn't have to exist + if (EFI_ERROR(Status && !(Flag & READ_FILE))) { + Print (L"sf: Wrong FilePath parameter!\n"); + return SHELL_ABORTED; + } + } + + Status = OpenAndPrepareFile (FilePath, &FileHandle); + if (EFI_ERROR(Status)) { + Print (L"sf: Error while preparing file\n"); + return SHELL_ABORTED; + } + + // Get file size in order to check correctness at the end of transfer + if (Flag & (WRITE_FILE | UPDATE_FILE)) { + Status = FileHandleGetSize (FileHandle, &FileSize); + if (EFI_ERROR (Status)) { + Print (L"sf: Cannot get file size\n"); + } + ByteCount = (UINTN) FileSize; + } + + FileBuffer = AllocateZeroPool ((UINTN) ByteCount); + if (FileBuffer == NULL) { + Print (L"sf: Cannot allocate memory\n"); + goto Error_Close_File; + } + + // Read file content and store it in FileBuffer + if (Flag & (WRITE_FILE | UPDATE_FILE)) { + Status = FileHandleRead (FileHandle, &ByteCount, FileBuffer); + if (EFI_ERROR (Status)) { + Print (L"sf: Read from file error\n"); + goto Error_Free_Buffer; + } else if (ByteCount != (UINTN) FileSize) { + Print (L"sf: Not whole file read. Abort\n"); + goto Error_Free_Buffer; + } + } + } + + + Buffer = (UINT8 *) Address; + if (FileFlag) { + Buffer = FileBuffer; + } + + switch (Flag) { + case READ: + case READ_FILE: + Status = SpiFlashProtocol->Read (Slave, Offset, ByteCount, Buffer); + break; + case ERASE: + Status = SpiFlashProtocol->Erase (Slave, Offset, ByteCount); + break; + case WRITE: + case WRITE_FILE: + Status = SpiFlashProtocol->Write (Slave, Offset, ByteCount, Buffer); + break; + case UPDATE: + case UPDATE_FILE: + Status = SpiFlashProtocol->Update (Slave, Offset, ByteCount, Buffer); + break; + } + + SpiMasterProtocol->FreeDevice(Slave); + + if (EFI_ERROR (Status)) { + Print (L"sf: Error while performing spi transfer\n"); + return SHELL_ABORTED; + } + + switch (Flag) { + case ERASE: + Print (L"sf: %d bytes succesfully erased at offset 0x%x\n", ByteCount, + Offset); + break; + case WRITE: + case WRITE_FILE: + Print (L"sf: Write %d bytes at offset 0x%x\n", ByteCount, Offset); + break; + case UPDATE: + case UPDATE_FILE: + Print (L"sf: Update %d bytes at offset 0x%x\n", ByteCount, Offset); + break; + case READ: + Print (L"sf: Read %d bytes from offset 0x%x\n", ByteCount, Offset); + break; + case READ_FILE: + Status = FileHandleWrite (FileHandle, &ByteCount, FileBuffer); + if (EFI_ERROR(Status)) { + Print (L"sf: Error while writing into file\n"); + goto Error_Free_Buffer; + } + break; + } + + if (FileFlag) { + FreePool (FileBuffer); + + if (FileHandle != NULL) { + ShellCloseFile (&FileHandle); + } + } + + return EFI_SUCCESS; + +Error_Free_Buffer: + FreePool (FileBuffer); +Error_Close_File: + ShellCloseFile (&FileHandle); + return SHELL_ABORTED; +} + +EFI_STATUS +EFIAPI +SpiFlashConstructor ( + IN EFI_HANDLE ImageHandle, + IN EFI_SYSTEM_TABLE *SystemTable + ) +{ + gShellSfHiiHandle = NULL; + + gShellSfHiiHandle = HiiAddPackages ( + &gShellSfHiiGuid, gImageHandle, + SpiFlashShellStrings, NULL + ); + if (gShellSfHiiHandle == NULL) { + return EFI_DEVICE_ERROR; + } + + ShellCommandRegisterCommandName ( + L"sf", ShellCommandRunSpiFlash, ShellCommandGetManFileNameSpiFlash, 0, + L"sf", TRUE , gShellSfHiiHandle, STRING_TOKEN (STR_GET_HELP_SF) + ); + + return EFI_SUCCESS; +} + +EFI_STATUS +EFIAPI +SpiFlashDestructor ( + IN EFI_HANDLE ImageHandle, + IN EFI_SYSTEM_TABLE *SystemTable + ) +{ + + if (gShellSfHiiHandle != NULL) { + HiiRemovePackages (gShellSfHiiHandle); + } + return EFI_SUCCESS; +} diff --git a/Applications/SpiTool/SpiFlashCmd.inf b/Applications/SpiTool/SpiFlashCmd.inf new file mode 100644 index 0000000..b1b7b04 --- /dev/null +++ b/Applications/SpiTool/SpiFlashCmd.inf @@ -0,0 +1,76 @@ +# Copyright (C) 2016 Marvell International Ltd. +# +# Marvell BSD License Option +# +# If you received this File from Marvell, you may opt to use, redistribute and/or +# modify this File under the following licensing terms. +# Redistribution and use in source and binary forms, with or without modification, +# are permitted provided that the following conditions are met: +# +# * Redistributions of source code must retain the above copyright notice, +# this list of conditions and the following disclaimer. +# +# * Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# +# * Neither the name of Marvell nor the names of its contributors may be +# used to endorse or promote products derived from this software without +# specific prior written permission. +# +# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +# DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR +# ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +# (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +# LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON +# ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +# SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +# + +[Defines] + INF_VERSION = 0x00010006 + BASE_NAME = SpiFlashShell + FILE_GUID = 2f2dd8c9-221f-4acf-afe5-5897264c5774 + MODULE_TYPE = UEFI_APPLICATION + VERSION_STRING = 0.1 + LIBRARY_CLASS = NULL|UEFI_APPLICATION UEFI_DRIVER + CONSTRUCTOR = SpiFlashConstructor + DESTRUCTOR = SpiFlashDestructor + +[Sources] + SpiFlashCmd.c + SpiFlashCmd.uni + +[Packages] + MdePkg/MdePkg.dec + ShellPkg/ShellPkg.dec + MdeModulePkg/MdeModulePkg.dec + OpenPlatformPkg/Platforms/Marvell/Marvell.dec + +[LibraryClasses] + UefiLib + UefiBootServicesTableLib + MemoryAllocationLib + BaseLib + BaseMemoryLib + DebugLib + ShellCommandLib + ShellLib + UefiLib + UefiRuntimeServicesTableLib + PcdLib + HiiLib + FileHandleLib + +[Pcd] + gMarvellTokenSpaceGuid.PcdSpiFlashId + +[Protocols] + gEfiSpiFlashProtocolGuid + gEfiSpiMasterProtocolGuid + +[Guids] + gShellSfHiiGuid diff --git a/Applications/SpiTool/SpiFlashCmd.uni b/Applications/SpiTool/SpiFlashCmd.uni new file mode 100644 index 0000000000000000000000000000000000000000..3f25663ed79f1e7a8f6f7ca3143864e04a506fac GIT binary patch literal 7216 zcmd6s+ix316vpQniT`1hzLcs>(iZVh#Dn8FZ6xP{?KD&rRf$uFh~`4#P%81a1K)3s zPv)|=6%a_(%GuqyocYdoE^}t{*Pm<Q(Pw>q8NLYJa2c+`r*Iw4!fE(9OhXeMs`V?~ zpM~}CG<>6{op7WPzlHbVgRUlQhYO8-ueJ;IOf~m1KGE0L`$<?0Nat72-3Y_58ONQ4 zv1D9?8~ts<o^ZG%pSv9<>iHz;x4K_z95c=$k`uK|h4@VKo3N$(hbU*FahKs-ZRN_3 z)#8%Qh5D1;(H)JadTO)=NEpXTCsFcL&u8ISedyb0-i3PBH2ykjcdjQ!PNKYdcy8ki zxH7y*nP?VFUWSjFdm-i<y(K=p%{V?6F5`1B7niZ`*j$e$N^Ue4_O2syY0Po##j5ZC zo@;S-6SW5un!pdJ{T(^5m2?Jivj5}A2r|*}N`H}wEcC!$S8BPG_0IHWEv$ot<=l)l z3*M1s+G2BG>0Gj=;l-WDHR{W+M|xYv9I`H>r<Gi>Dmc*?-vA}LO|>!>N|=x2A?U?e zX4MgOp*E1?y~a|G&!3a`;0v~%;aa3WoFo+Uyvn?IEbjs{OkHQO=_~vFK1`YB^Zlo0 z%Itk2_Ru^bUCtNL?}+ky$)ZWK=>LED@<_ry@1vLHsQmdvHXch;I3_!$xbUd6tbwnY zBw~w9WKn*mrw_9FyeRPqOboWOlf^~KyN=86*mhUgEVj#hL>33P$3dAn8|h=2z;N?! z<5T1yl{fR$JZmzO9?!YQOE|O)Y(7m!hDmruf}w*m^D45C<>cJU3<Xh3-X<cEmiB}c zW5oJI5<W^7%UI5`<+(*(coQ?*Skfo@jc0gZ-*P4ETE-(oq%3$N9cmkm!Yl2iLya41 z|Jw?qa2PtuRXw#>`@Y`x!fU;4s&!NC8{v)qGLunV_3o=>pb;<CHd5Owwe{opL6qH* z-I>YQU5#MuMmW&Zo}O8KMXPdW%@y5k1`P1TdcE+2)&bctj$|g|chuU~-LM(@L7X*; zt;4vZY)eX4;|_#_=a;e7FyNJY5jS#n^c&5jfsftTbuCu|-MsavB(^kbM^Xk__0<eb zM>=mutfQ!rv$7Re+`ZFmE3yIyjda5rXwnt-ete_#K&|^4H`FXf!V7rNZWuM~=m`Xy z%C_*dtH0<8ldtu|4p<#@eO*b*c^2K1rXYlKV}7wMH#CkaY+I5ybmz@<%IyhKP<Mp` zjzKuDt*ah954<2{>`=NhlNGE5@952Z0XE*maXC_$`d+-5B%9eta!0c|@(271d=Dd% zfA1?6FIWrhuz)dbJ~31~^(Ph`=^0OJwECW|O|?6_pdG}h>*{G3zKz)W8s*-PhaKpx z7d1r>_<<eM+Hja}G2h$q`C-)2BMIigG0=4&X2C|BQh^i6hw8&)uzgo+*s8>{doZJO z+giMUgUB__-5*i}fb~!-^t2*>EuQhy<XfFP|9~^{2L6(~tCVJ%TUHq@v?g)T6Xzhp z?qmk6V6({thUQTH@Cy(46mOP0Jf1u^kp)asEb1D2)-b;ERwTh!opWKtqmwnTaYueZ z_5}%?8=EfMasar>+>*SF{8RdQ+Mz%1)8Sg=2%gr$cj3X^+k;q3a%N$d<$T7)PW>eM zCc6o5r}0E{qnc?Yn@d&84ryl|^Qw2z4@Ti#w0vJN@J@Wg{`@N;xYgc$s@3ZCZN(Mk zUM$5K2%PKst;kYGaVKWyCX;RJK8ZSk)hd|tSglZdtZK$vA$}{wNh*08KPG$iTK$|g zjx={owS`p!AUshURbi?|)*=sf_G}|rZOL5~Ue+DT+u2L@^@L~E_?lLW>Hp)ba-srj z!XNrk_kgr~qpq>DG-Gld%J*^{6&K99>^3U1=B-c|7d|p?ahX49<ywO4kLI2w@1wn~ z+ZQstjta2$t0!vNjkP=6T<guwUB@~dQ)Aw!#q5NB_(hG)BzDwu5?Q6%D_3ESy5G)H z)Jr?r3ao@>)?|gtnSI=Q=C8Xa51vHsr`4*BqLQqY_or$YZBKQ9!(-AkZ~J3n;Gg5$ znt9Z|w5j<AUurj&-3xrp<fqPqoylx;S$V@-?osn1Z?SJt$zTntT6X9*-*rnp<3(#u zH=Y~E;TLJjsliWiXhjR2!ZRlezH?X%B`dXUQDeZ<EXM6Dgk9?~1GQPKKi8MNMqezF zZ>P1^!|ximes_5!v@zrsa1X}1oOa77K<3jsiR&$734OA2J%{XFBSVkHS~8w5n9DS! z->?5l)8}^*@2_b-$22XGxh}P~J^792+>)_HS`*zVQ<QVyYEkspD<_-fdA}{MZmH!Q zN(0WzM1p;5UhJ18C+2JJd1Nok2J<|1v0r|jS!<cS@?8*}N-VULl1!Ug+k;~7vzS<9 zshT<Bis;HUo?pQ%);5pq8e6hxnLXP$Xvrm^D^XNSOc{q6?&Hh!UFLy#zDfH7zWhwz ze!XQ?c@1Bvu_Wz0$M_8DvH3DA62X+?uO*i@E%&Eo_Q_>h4oa0FPhNxdqdvD{a8<0+ zUL#1lm6mJIEH$xJYiV9(aen5EJWyryT6-d2Z|=7v<};gOZhLP8J5_B@^82ywKhSy5 zPTicx%WD*OQX*ljSg@~YRH)=YuiUR<?Mg<WuC*R){;R42_E_s_SJyQXzMgO<^{-JS k5;8CU%b-^LC{%7O+kg4mZQuLsoWobqbfzd7=Y+-YZ<!+^rT_o{
literal 0 HcmV?d00001
diff --git a/Platforms/Marvell/Marvell.dec b/Platforms/Marvell/Marvell.dec index dffb749..690062d 100644 --- a/Platforms/Marvell/Marvell.dec +++ b/Platforms/Marvell/Marvell.dec @@ -53,6 +53,7 @@ gMarvellTokenSpaceGuid = { 0xf995c6c8, 0xbc9b, 0x4e93, { 0xbd, 0xcf, 0x49, 0x90, 0xc6, 0xe7, 0x8c, 0x7f } }
gShellEepromHiiGuid = { 0xb2f4c714, 0x147f, 0x4ff7, { 0x82, 0x1b, 0xce, 0x7b, 0x91, 0x7f, 0x5f, 0x2f } } + gShellSfHiiGuid = { 0x03a67756, 0x8cde, 0x4638, { 0x82, 0x34, 0x4a, 0x0f, 0x6d, 0x58, 0x81, 0x39 } }
[PcdsFixedAtBuild.common] #MPP
From: Jan Dąbroś jsd@semihalf.com
Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Jan Dabros jsd@semihalf.com Signed-off-by: Marcin Wojtas mw@semihalf.com --- Platforms/Marvell/Armada/Armada.dsc.inc | 1 + 1 file changed, 1 insertion(+)
diff --git a/Platforms/Marvell/Armada/Armada.dsc.inc b/Platforms/Marvell/Armada/Armada.dsc.inc index 1cd25cb..2b09db1 100644 --- a/Platforms/Marvell/Armada/Armada.dsc.inc +++ b/Platforms/Marvell/Armada/Armada.dsc.inc @@ -450,6 +450,7 @@ NULL|ShellPkg/Library/UefiShellNetwork1CommandsLib/UefiShellNetwork1CommandsLib.inf NULL|ShellPkg/Library/UefiShellTftpCommandLib/UefiShellTftpCommandLib.inf NULL|OpenPlatformPkg/Applications/EepromCmd/EepromCmd.inf + NULL|OpenPlatformPkg/Applications/SpiTool/SpiFlashCmd.inf HandleParsingLib|ShellPkg/Library/UefiHandleParsingLib/UefiHandleParsingLib.inf PrintLib|MdePkg/Library/BasePrintLib/BasePrintLib.inf BcfgCommandLib|ShellPkg/Library/UefiShellBcfgCommandLib/UefiShellBcfgCommandLib.inf
Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Jan Dabros jsd@semihalf.com Signed-off-by: Marcin Wojtas mw@semihalf.com --- Platforms/Marvell/Armada/Armada.dsc.inc | 2 ++ Platforms/Marvell/Armada/Armada7040.fdf | 1 + 2 files changed, 3 insertions(+)
diff --git a/Platforms/Marvell/Armada/Armada.dsc.inc b/Platforms/Marvell/Armada/Armada.dsc.inc index 2b09db1..44defd7 100644 --- a/Platforms/Marvell/Armada/Armada.dsc.inc +++ b/Platforms/Marvell/Armada/Armada.dsc.inc @@ -54,6 +54,7 @@ CpuLib|MdePkg/Library/BaseCpuLib/BaseCpuLib.inf PciLib|MdePkg/Library/BasePciLibCf8/BasePciLibCf8.inf PciCf8Lib|MdePkg/Library/BasePciCf8Lib/BasePciCf8Lib.inf + FileExplorerLib|MdeModulePkg/Library/FileExplorerLib/FileExplorerLib.inf
# Basic UEFI services libraries UefiLib|MdePkg/Library/UefiLib/UefiLib.inf @@ -396,6 +397,7 @@ OpenPlatformPkg/Drivers/Spi/SpiDxe.inf OpenPlatformPkg/Drivers/Spi/Devices/MvSpiFlash.inf
+ MdeModulePkg/Universal/Disk/RamDiskDxe/RamDiskDxe.inf MdeModulePkg/Core/RuntimeDxe/RuntimeDxe.inf MdeModulePkg/Universal/SecurityStubDxe/SecurityStubDxe.inf MdeModulePkg/Universal/CapsuleRuntimeDxe/CapsuleRuntimeDxe.inf diff --git a/Platforms/Marvell/Armada/Armada7040.fdf b/Platforms/Marvell/Armada/Armada7040.fdf index 043c5d4..d40b386 100644 --- a/Platforms/Marvell/Armada/Armada7040.fdf +++ b/Platforms/Marvell/Armada/Armada7040.fdf @@ -107,6 +107,7 @@ FvNameGuid = 5eda4200-2c5f-43cb-9da3-0baf74b1b30c INF OpenPlatformPkg/Drivers/I2c/Devices/MvEeprom/MvEeprom.inf INF OpenPlatformPkg/Drivers/Spi/SpiDxe.inf INF OpenPlatformPkg/Drivers/Spi/Devices/MvSpiFlash.inf + INF MdeModulePkg/Universal/Disk/RamDiskDxe/RamDiskDxe.inf
# Multiple Console IO support INF MdeModulePkg/Universal/Console/ConPlatformDxe/ConPlatformDxe.inf
From: Jan Dąbroś jsd@semihalf.com
'fupdate' command performs updating firmware from file placed on local filesystem or on TFTP server. It uses tftp and sf commands.
Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Jan Dabros jsd@semihalf.com Signed-off-by: Marcin Wojtas mw@semihalf.com --- Applications/FirmwareUpdate/FUpdate.c | 437 ++++++++++++++++++++++++++++++++ Applications/FirmwareUpdate/FUpdate.inf | 69 +++++ Applications/FirmwareUpdate/FUpdate.uni | Bin 0 -> 5838 bytes Platforms/Marvell/Marvell.dec | 1 + 4 files changed, 507 insertions(+) create mode 100644 Applications/FirmwareUpdate/FUpdate.c create mode 100644 Applications/FirmwareUpdate/FUpdate.inf create mode 100644 Applications/FirmwareUpdate/FUpdate.uni
diff --git a/Applications/FirmwareUpdate/FUpdate.c b/Applications/FirmwareUpdate/FUpdate.c new file mode 100644 index 0000000..4bdc5e3 --- /dev/null +++ b/Applications/FirmwareUpdate/FUpdate.c @@ -0,0 +1,437 @@ +/******************************************************************************* +Copyright (C) 2016 Marvell International Ltd. + +Marvell BSD License Option + +If you received this File from Marvell, you may opt to use, redistribute and/or +modify this File under the following licensing terms. +Redistribution and use in source and binary forms, with or without modification, +are permitted provided that the following conditions are met: + +* Redistributions of source code must retain the above copyright notice, + this list of conditions and the following disclaimer. + +* Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + +* Neither the name of Marvell nor the names of its contributors may be + used to endorse or promote products derived from this software without + specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR +ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON +ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +*******************************************************************************/ +#include <Uefi.h> +#include <ShellBase.h> + +#include <Library/BaseLib.h> +#include <Library/DebugLib.h> +#include <Library/MemoryAllocationLib.h> +#include <Library/ShellCommandLib.h> +#include <Library/ShellLib.h> +#include <Library/UefiLib.h> +#include <Library/PrintLib.h> +#include <Library/UefiLib.h> +#include <Library/ShellCEntryLib.h> +#include <Library/HiiLib.h> +#include <Guid/ShellLibHiiGuid.h> +#include <Library/UefiBootServicesTableLib.h> +#include <Library/FileHandleLib.h> + +#define TFTP_CMD_STRING L"tftp " +#define SPACE_STRING L" " +#define SF_PROBE_CMD_STRING L"sf probe" +#define SF_WRITE_CMD_STRING L"sf updatefile " +#define SF_LOAD_ADDR_STRING L"0x0" + +#define HEADER_SIZE 49152 +#define MAIN_HDR_MAGIC 0xB105B002 + +typedef struct { + UINT32 Magic; // 0-3 + UINT32 PrologSize; // 4-7 + UINT32 PrologChecksum; // 8-11 + UINT32 BootImageSize; // 12-15 + UINT32 BootImageChecksum; // 16-19 + UINT32 Reserved0; // 20-23 + UINT32 LoadAddr; // 24-27 + UINT32 ExecAddr; // 28-31 + UINT8 UartConfig; // 32 + UINT8 Baudrate; // 33 + UINT8 ExtCount; // 34 + UINT8 AuxFlags; // 35 + UINT32 IoArg0; // 36-39 + UINT32 IoArg1; // 40-43 + UINT32 IoArg2; // 43-47 + UINT32 IoArg3; // 48-51 + UINT32 Reserved1; // 52-55 + UINT32 Reserved2; // 56-59 + UINT32 Reserved3; // 60-63 +} MV_IMAGE_HEADER; + +STATIC +UINT32 +CountChecksum ( + UINT32 *Start, + UINT32 Length + ) +{ + UINT32 Sum = 0; + UINT32 *Startp = Start; + + do { + Sum += *Startp; + Startp++; + Length -= 4; + } while (Length > 0); + + return Sum; +} + +STATIC +EFI_STATUS +CheckImageHeader ( + IN VOID *ImageHeader + ) +{ + MV_IMAGE_HEADER *Header; + UINT32 HeaderLength, Checksum, ChecksumBackup; + + Header = (MV_IMAGE_HEADER *) ImageHeader; + HeaderLength = Header->PrologSize; + ChecksumBackup = Header->PrologChecksum; + + // Compare magic number + if (Header->Magic != MAIN_HDR_MAGIC) { + Print (L"fupdate: Bad Image magic 0x%08x != 0x%08x", Header->Magic, + MAIN_HDR_MAGIC); + return EFI_DEVICE_ERROR; + } + + // The checksum field is discarded from calculation + Header->PrologChecksum = 0; + + Checksum = CountChecksum((UINT32 *)Header, HeaderLength); + if (Checksum != ChecksumBackup) { + Print (L"fupdate: Bad Image checksum. 0x%x != 0x%x", Checksum, + ChecksumBackup); + return EFI_DEVICE_ERROR; + } + + // Restore checksum backup + Header->PrologChecksum = ChecksumBackup; + + return 0; +} + +STATIC +EFI_STATUS +CheckFirmwareImage ( + CONST CHAR16* FirmwareImage + ) +{ + EFI_STATUS Status; + VOID *FileBuffer; + UINT64 OpenMode; + UINTN HeaderSize; + SHELL_FILE_HANDLE FileHandle = NULL; + + OpenMode = EFI_FILE_MODE_READ; + HeaderSize = HEADER_SIZE; + + FileBuffer = AllocateZeroPool (HEADER_SIZE); + + Status = ShellOpenFileByName (FirmwareImage, &FileHandle, OpenMode, 0); + if (EFI_ERROR (Status)) { + Print (L"fupdate: Cannot open Image file\n"); + return SHELL_ABORTED; + } + + // Read Image header into buffer + Status = FileHandleRead (FileHandle, &HeaderSize, FileBuffer); + if (EFI_ERROR (Status)) { + Print (L"fupdate: Cannot read Image file header\n"); + ShellCloseFile (&FileHandle); + FreePool (FileBuffer); + return SHELL_ABORTED; + } + + Status = CheckImageHeader (FileBuffer); + if (EFI_ERROR(Status)) { + return EFI_DEVICE_ERROR; + } + + FreePool (FileBuffer); + + return EFI_SUCCESS; +} + +STATIC +CONST CHAR16 * +FileNameFromFilePath ( + CONST CHAR16 *RemoteFilePath + ) +{ + CONST CHAR16 *Walker; + + // Gather FileName from FilePath + Walker = RemoteFilePath + StrLen (RemoteFilePath); + while ((--Walker) >= RemoteFilePath) { + if ((*Walker == L'\') || (*Walker == L'/')) { + break; + } + } + + return (Walker + 1); +} + +STATIC +CONST CHAR16* +PrepareFile ( + LIST_ENTRY *CheckPackage + ) +{ + EFI_STATUS Status; + CONST CHAR16 *ValueStr; + + ValueStr = ShellCommandLineGetValue (CheckPackage, L"-f"); + if (ValueStr == NULL) { + Print (L"fupdate: No LocalFilePath parameter!\n"); + return NULL; + } else { + Status = ShellIsFile (ValueStr); + if (EFI_ERROR(Status)) { + Print (L"fupdate: Wrong LocalFilePath parameter!\n"); + return NULL; + } + } + return ValueStr; +} + +CONST CHAR16 gShellFUpdateFileName[] = L"ShellCommand"; +EFI_HANDLE gShellFUpdateHiiHandle = NULL; +EFI_HANDLE gShellFUpdateHiiHandle; + +STATIC CONST SHELL_PARAM_ITEM ParamList[] = { + {L"help", TypeFlag}, + {L"-t", TypeFlag}, + {L"-f", TypeValue}, + {NULL , TypeMax} + }; + +/** + Return the file name of the help text file if not using HII. + + @return The string pointer to the file name. +**/ +CONST CHAR16* +EFIAPI +ShellCommandGetManFileNameFUpdate ( + VOID + ) +{ + + return gShellFUpdateFileName; +} + +VOID +FUpdateUsage ( + VOID + ) +{ + Print (L"\nFirmware update command\n" + "fupdate [-f <LocalFilePath>] [-t <Host> <RemoteFilePath>]\n\n" + "LocalFilePath - path to local firmware image file\n" + "Host - IP number of TFTP server\n" + "RemoteFilePath - path to firmware image file on TFTP server\n" + "Examples:\n" + "Update firmware from file fs2:Uefi.img\n" + " fupdate -f fs2:Uefi.img\n" + "Update firmware from file path/Uefi.img TFTP server with IP address 10.0.0.200\n" + " fupdate -t 10.0.0.200 path/Uefi.img\n" + ); +} + +SHELL_STATUS +EFIAPI +ShellCommandRunFUpdate ( + IN EFI_HANDLE ImageHandle, + IN EFI_SYSTEM_TABLE *SystemTable + ) +{ + EFI_STATUS Status; + LIST_ENTRY *CheckPackage; + CHAR16 *ProblemParam, *TftpCmd = NULL, *SfCmd = NULL; + CONST CHAR16 *RemoteFilePath, *Host, *FileToWrite; + UINT8 CmdLen; + BOOLEAN FileFlag, TftpFlag; + + Status = ShellInitialize (); + if (EFI_ERROR (Status)) { + Print (L"fupdate: Error while initializinf Shell\n"); + ASSERT_EFI_ERROR (Status); + return SHELL_ABORTED; + } + + Status = ShellCommandLineParse (ParamList, &CheckPackage, &ProblemParam, TRUE); + if (EFI_ERROR (Status)) { + Print (L"Parse error!\n"); + } + + if (ShellCommandLineGetFlag (CheckPackage, L"help")) { + FUpdateUsage(); + return EFI_SUCCESS; + } + + FileFlag = ShellCommandLineGetFlag (CheckPackage, L"-f"); + TftpFlag = ShellCommandLineGetFlag (CheckPackage, L"-t"); + + if (!FileFlag && !TftpFlag) { + Print (L"fupdate: Please specify -f or -t flag\n"); + return SHELL_ABORTED; + } else if (FileFlag && !TftpFlag) { + // Prepare local file to be burned into flash + FileToWrite = PrepareFile (CheckPackage); + if (FileToWrite == NULL) { + Print (L"fupdate: Error while preparing file for burn\n"); + return SHELL_ABORTED; + } + } else if (TftpFlag && !FileFlag) { + Host = ShellCommandLineGetRawValue (CheckPackage, 1); + if (Host == NULL) { + Print (L"fupdate: No Host parameter!\n"); + return SHELL_ABORTED; + } + + RemoteFilePath = ShellCommandLineGetRawValue (CheckPackage, 2); + if (RemoteFilePath == NULL) { + Print (L"fupdate: No remote_file_path parameter!\n"); + return SHELL_ABORTED; + } + + // Gather firmware image name from remote filepath + FileToWrite = FileNameFromFilePath (RemoteFilePath); + + // Allocate buffer for tftp command string + CmdLen = StrSize (TFTP_CMD_STRING) + StrSize (SPACE_STRING) + StrSize (Host) + + StrSize (RemoteFilePath); + TftpCmd = (CHAR16 *) AllocateZeroPool (CmdLen + sizeof(CHAR16)); + if (TftpCmd == NULL) { + Print (L"fupdate: Cannot allocate memory\n"); + return SHELL_ABORTED; + } + + // Concatenate parameters and form tftp command string + StrCatS (TftpCmd, CmdLen / sizeof(CHAR16), TFTP_CMD_STRING); + StrCatS (TftpCmd, CmdLen / sizeof(CHAR16), (CHAR16 *)Host); + // Insert space + StrCatS (TftpCmd, CmdLen / sizeof(CHAR16), SPACE_STRING); + StrCatS (TftpCmd, CmdLen / sizeof(CHAR16), (CHAR16 *)RemoteFilePath); + + ShellExecute (ImageHandle, TftpCmd, FALSE, NULL, &Status); + FreePool (TftpCmd); + if (EFI_ERROR(Status)) { + Print (L"fupdate: Error while performing tftp command\n"); + return SHELL_ABORTED; + } + + } else { + Print (L"fupdate: Both -f and -t flag specified, please choose one\n"); + return SHELL_ABORTED; + } + + // Check image checksum and magic + Status = CheckFirmwareImage (FileToWrite); + if (EFI_ERROR(Status)) { + Print (L"fupdate: Wrong firmware Image\n"); + return SHELL_ABORTED; + } + + // Probe spi bus + ShellExecute (ImageHandle, SF_PROBE_CMD_STRING, FALSE, NULL, &Status); + if (EFI_ERROR(Status)) { + Print (L"fupdate: Error while performing sf probe\n"); + return SHELL_ABORTED; + } + + // Allocate buffer for sf command string + CmdLen = StrSize (SF_WRITE_CMD_STRING) + StrSize (FileToWrite) + + StrSize (SPACE_STRING) + StrSize (SF_LOAD_ADDR_STRING); + SfCmd = (CHAR16 *) AllocateZeroPool (CmdLen + sizeof(CHAR16)); + if (SfCmd == NULL) { + Print (L"fupdate: Cannot allocate memory\n"); + return SHELL_ABORTED; + } + + // Concatenate parameters and form command string + StrCatS (SfCmd, CmdLen / sizeof(CHAR16), SF_WRITE_CMD_STRING); + StrCatS (SfCmd, CmdLen / sizeof(CHAR16), (CHAR16 *)FileToWrite); + StrCatS (SfCmd, CmdLen / sizeof(CHAR16), SPACE_STRING); + StrCatS (SfCmd, CmdLen / sizeof(CHAR16), SF_LOAD_ADDR_STRING); + + // Update firmware image in flash + ShellExecute (ImageHandle, SfCmd, TRUE, NULL, &Status); + FreePool (SfCmd); + if (EFI_ERROR(Status)) { + Print (L"fupdate: Error while performing sf update\n"); + return SHELL_ABORTED; + } + + return EFI_SUCCESS; +} + +EFI_STATUS +EFIAPI +FUpdateConstructor ( + IN EFI_HANDLE ImageHandle, + IN EFI_SYSTEM_TABLE *SystemTable + ) +{ + EFI_STATUS Status; + + gShellFUpdateHiiHandle = NULL; + + gShellFUpdateHiiHandle = HiiAddPackages ( + &gShellFUpdateHiiGuid, gImageHandle, + FUpdateShellStrings, NULL + ); + if (gShellFUpdateHiiHandle == NULL) { + Print (L"fupdate: Cannot add Hii package\n"); + return EFI_DEVICE_ERROR; + } + + Status = ShellCommandRegisterCommandName ( + L"fupdate", ShellCommandRunFUpdate, ShellCommandGetManFileNameFUpdate, 0, + L"fupdate", TRUE , gShellFUpdateHiiHandle, STRING_TOKEN (STR_GET_HELP_FUPDATE) + ); + if (EFI_ERROR(Status)) { + Print (L"fupdate: Error while registering command\n"); + return SHELL_ABORTED; + } + + return EFI_SUCCESS; +} + +EFI_STATUS +EFIAPI +FUpdateDestructor ( + IN EFI_HANDLE ImageHandle, + IN EFI_SYSTEM_TABLE *SystemTable + ) +{ + + if (gShellFUpdateHiiHandle != NULL) { + HiiRemovePackages (gShellFUpdateHiiHandle); + } + return EFI_SUCCESS; +} diff --git a/Applications/FirmwareUpdate/FUpdate.inf b/Applications/FirmwareUpdate/FUpdate.inf new file mode 100644 index 0000000..d7cd7ed --- /dev/null +++ b/Applications/FirmwareUpdate/FUpdate.inf @@ -0,0 +1,69 @@ +# Copyright (C) 2016 Marvell International Ltd. +# +# Marvell BSD License Option +# +# If you received this File from Marvell, you may opt to use, redistribute and/or +# modify this File under the following licensing terms. +# Redistribution and use in source and binary forms, with or without modification, +# are permitted provided that the following conditions are met: +# +# * Redistributions of source code must retain the above copyright notice, +# this list of conditions and the following disclaimer. +# +# * Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# +# * Neither the name of Marvell nor the names of its contributors may be +# used to endorse or promote products derived from this software without +# specific prior written permission. +# +# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +# DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR +# ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +# (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +# LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON +# ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +# SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +# + +[Defines] + INF_VERSION = 0x00010006 + BASE_NAME = FUpdateShell + FILE_GUID = 470292b2-926b-4ed8-8080-be7a260db627 + MODULE_TYPE = UEFI_APPLICATION + VERSION_STRING = 0.1 + LIBRARY_CLASS = NULL|UEFI_APPLICATION UEFI_DRIVER + CONSTRUCTOR = FUpdateConstructor + DESTRUCTOR = FUpdateDestructor + +[Sources] + FUpdate.c + FUpdate.uni + +[Packages] + MdePkg/MdePkg.dec + ShellPkg/ShellPkg.dec + MdeModulePkg/MdeModulePkg.dec + OpenPlatformPkg/Platforms/Marvell/Marvell.dec + +[LibraryClasses] + UefiLib + UefiBootServicesTableLib + MemoryAllocationLib + BaseLib + BaseMemoryLib + DebugLib + ShellCommandLib + ShellLib + UefiLib + UefiRuntimeServicesTableLib + PcdLib + HiiLib + FileHandleLib + +[Guids] + gShellFUpdateHiiGuid diff --git a/Applications/FirmwareUpdate/FUpdate.uni b/Applications/FirmwareUpdate/FUpdate.uni new file mode 100644 index 0000000000000000000000000000000000000000..6143c0580f1d1ef8ce4fe619a1df1ce380adf2c0 GIT binary patch literal 5838 zcmd6r?N1v=5XSd&rTz~m@+FOuK&z@BXdB5G6OhbHeI_(&s)*P?EX6>LDdL}R`}}4Y z_Fim)B2|h`_TBEy&OY<Z%kJL4|E#8GU-k8E`X+VLMY>G4X_hAGEPYJ#RHUcs{Z98E z(pvgH{iLVebS#O#(@FZIt4KTPT#_g1JJ*}J#$MPH@A_(w)60Z*e$BBPsZ5(DH%TMu zI8RslFVenngr*p~lTP*KR@$$1pGl4p6GJjq&s>Nn8egO>-9MS0Q^{SVsru?OKUYs^ znhN!;+Src8b3GNB10={X)7Ui6^*l)*^bUIqjXT$yRmsoHx~ZO!JT-lb@LbynxN^K` zIn^kbyht}1doJb+wK5;k=NwOk%lRBE#O3S<wy>ix&4tFo-prWGG9T<MUWEtn%*5H1 zSq~;Gfgeyu8$Ga<Z3c1n|8rvmo!EG(e{`Y?JMh~dM@OiCW&nJZN~Bn~_GrJG$Ij zd>%7RrE8wn?<20zyXy5!t%sOH*M&t|ohxPqCl(VMpv1PhX2wGq^RXfXyO3p6Go#Mc z2Xdm<S*qfT=Nvu6g3sr;me~&{8O5Tg@+clDy1)!mvr2Bp%yEAVQ*Qa<_-Qib{vL}x zEYC<E=8NnPMAdtpMc3xp|Nrt8nS_5%EXt~=;(06|k7OwvQyp_&MAmuLAl6(HxkV-N zET8D<lf1qtOCkd^gYD|%d6DaG;EFrG-4iy??Rq_;ii11ypk6r(+2fVKanpABoH=Nv z<&j#gnvCR4)Z7mbaOf4-W15N#lkkcLM+avfRa7Cb$<-)x6l5)Rn~X$TUK4VTk?W_@ za3fp1Vg<`y=axm`l~uNpw4drXy2AteUMrc`D;^ahSHUaU(DczTZEGzpC0A<w+e*W9 zlsc+aJ@t71fm-|Njar-P-BkZZdaHj%BGuK~1N96f@mhUD^=+%KZ}J1v-I3oJiR_*v zkljd!dfL}Bv#)4Y?##KOyN`eYo|vzfe%Cx8D@~G-$nUDRue)P&^aC3;wBFKIlpSg5 zO72iNcz$iYj)AD$H{9si)o*yG4ScM|VQYOh&@Gyeoy3+#?Mll)vu@v^>B#0C!#XsJ zf|V_saqr%;En@`^3fYD?u%s*OeQVKssNMs~l^TU4ynqMmO0%@1ClG9^+QQSG{;?A# z-{^-Q@H*)Fy0VpvJi0GSK?vv0{BmDzNRD0Djx=xRPRnho`V*v}?g|GSgK$w_S8s?s z@PZWCQnoXa8N7$+=-tHvY`itODpHvGO}x1#A6ZCqN25B52jU8RPYubJ$BO3*-oiRO z;7of=l<H^yiARTeCejMczOQRj{lPA12bOhRJ(cNa!`7EnL_ZOBs8-J`#SZv^9k<$X zcx*8~`ic3{Y>Z5Td2kGL9g117k*Dmy$>bxwBVzD<S9AER<a0zY(pBGjzJP<wb;~0j zat46)NHg>_BmbVy#A%ML&V78q8Fhnr$<bBU=9YU^87}oEdC(K*Aj0od2E5>-sRWMZ zNblhn9*8MgUOOV6qBc<l+)_Lm7Dv@^zN)=wg0E)Hg^|ck=D^1t#Rb(DByjF*hHkF` z;HuY_9BtH}dYtDK`s+R&t{O-1w3>cRPwrb!Y%j@~g;kdG85b+{3yV!w6Iy3>qPfzZ zX{9ojT`eo5pLsm0-dh|D(|hxLUpeqz+>;BQS42nq$~dmIf}d&5CJLW-MHLu-u?x7? zdOVi2?;F<Cx1yOQLNu-H0}g9a>}aO8dtoo~QX}3;{+%qy`l;i@HPx)wdSBPauAx3( z>^nf%KE)1&a40S~$+4?pPs1L58H!T5z)Evq`BJvzidIjPmp|l5{Q8S>lszr`Qdr`A zePHZ;Os~?Pl0b59lG~ERx38?lX)E?;i$*TP4(h0Xk3mjUJT#X_%?n8_X0gin<(*~h zvDtgF@4S(hIi(+~mG|D+OX0buJ?&^+)>Dm0=76ngbhQ19reJ%S)<S+^oo4sxJJnmY zGY6%`kVg`g?m$uXqa?6%tocvmOTIZQvTJ!v1RCa!I0-gk(Id$@uiD7@iqnDTaIo8+ zyV>(n7Ls@DKFB<FqO7V-xpu@iN36HTd@g76i6Zb~*Ok7Rt*dfT7boHmyUtp=;i;K( zo^g-W@FnOXzE@lLs*zExG5O1n$4E0i3Vj`1la=w~d*Rw6t)*%#8qJA``utI=&gXax z|FhF$H#bn-d!tC;obk9gsE#aZW7`pd*NC^C^!K$wv6t-H-o^KX5&g~k(7qbL-AH!% z2@qzF6)k>Vp2}uwYkVd1H)P>oTCvDQf3r9rtC-mFvyX}sR8P6g7q^*ax)F|8UHrt% QHyJ;b`f6NX>FQbZ9}*T`00000
literal 0 HcmV?d00001
diff --git a/Platforms/Marvell/Marvell.dec b/Platforms/Marvell/Marvell.dec index 690062d..b17f23a 100644 --- a/Platforms/Marvell/Marvell.dec +++ b/Platforms/Marvell/Marvell.dec @@ -54,6 +54,7 @@
gShellEepromHiiGuid = { 0xb2f4c714, 0x147f, 0x4ff7, { 0x82, 0x1b, 0xce, 0x7b, 0x91, 0x7f, 0x5f, 0x2f } } gShellSfHiiGuid = { 0x03a67756, 0x8cde, 0x4638, { 0x82, 0x34, 0x4a, 0x0f, 0x6d, 0x58, 0x81, 0x39 } } + gShellFUpdateHiiGuid = { 0x9b5d2176, 0x590a, 0x49db, { 0x89, 0x5d, 0x4a, 0x70, 0xfe, 0xad, 0xbe, 0x24 } }
[PcdsFixedAtBuild.common] #MPP
From: Jan Dąbroś jsd@semihalf.com
Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Jan Dabros jsd@semihalf.com Signed-off-by: Marcin Wojtas mw@semihalf.com --- Platforms/Marvell/Armada/Armada.dsc.inc | 1 + 1 file changed, 1 insertion(+)
diff --git a/Platforms/Marvell/Armada/Armada.dsc.inc b/Platforms/Marvell/Armada/Armada.dsc.inc index 44defd7..b8f0463 100644 --- a/Platforms/Marvell/Armada/Armada.dsc.inc +++ b/Platforms/Marvell/Armada/Armada.dsc.inc @@ -453,6 +453,7 @@ NULL|ShellPkg/Library/UefiShellTftpCommandLib/UefiShellTftpCommandLib.inf NULL|OpenPlatformPkg/Applications/EepromCmd/EepromCmd.inf NULL|OpenPlatformPkg/Applications/SpiTool/SpiFlashCmd.inf + NULL|OpenPlatformPkg/Applications/FirmwareUpdate/FUpdate.inf HandleParsingLib|ShellPkg/Library/UefiHandleParsingLib/UefiHandleParsingLib.inf PrintLib|MdePkg/Library/BasePrintLib/BasePrintLib.inf BcfgCommandLib|ShellPkg/Library/UefiShellBcfgCommandLib/UefiShellBcfgCommandLib.inf
Hi Leif,
Did you have a chance to take a look?
Best regards, Marcin
2016-04-06 8:22 GMT+02:00 Marcin Wojtas mw@semihalf.com:
Hello,
Here is v2 version of the support. The patchset shrank a bit, because the custom RamDisk driver was replaced with the one already existing in a tree - yet because of lack of FAT formatting it's not functional for the platform purposes, but it's not crucial at this point. Also a custom UART driver has been replaced. Detailed list of changes is below.
For convenience purpose whole patchset is available in the github: https://github.com/MarvellEmbeddedProcessors/edk2-open-platform/commits/opp-...
Any comments or remarks are mostly welcome.
Best regards, Marcin
Changelog: v1 -> v2
- Fix "may be used uninitialized" variables issue, branch compiles both with DEBUG and RELEASE flags
- Remove I2C_FLAG_NORESTART dependency - replace it with local definition
- Remove Marvell UART Library:
Since in edk2 there is support for 16550, internal library is unnecessary.
- DW8250 IP has programming interface compatible with NS-16550.
- /Library/BaseSerialPortLib16550/BaseSerialPortLib16550.inf is used instead
- RamDisk driver:
- Remove old driver imported from EFI TOOLKIT 2.0
- Replace it with new MdeModulePkg/Universal/Disk/RamDiskDxe from edk2
- Lack of FAT formatting issue emerged
- Add explicit dependency on IoLib in Drivers/Spi/SpiDxe.inf
- Add poster's "Signed-off-by" registry to every commit message
- Move to 05.04.2016 HEAD of edk2/master
- Update CpuExceptionHandlerLib within OPP.
Bartosz Szczepanek (6): Drivers/I2c: Create MvI2cDxe driver Platforms/Marvell: Copy BdsLib to Armada7040 directory Platforms/Marvell: Add necessary BdsLibConnectAll call Drivers/I2c: Add MvEeprom driver Platforms/Marvell: Enable EEPROM driver on Armada7040 platforms Aplications/Eeprom: Add 'eeprom' command to shell
Jan Dąbroś (14): Platforms/Marvell: Create MppLib Platforms/Marvell: Armada: Enable MppLib on Armada7040 platforms Platforms/Marvell: Enable I2C driver on Armada7040 platforms Platforms/Marvell: Enable 'eeprom' command on Armada7040 platforms Platforms/Marvell: Add EFI_SPI_MASTER_PROTOCOL Drivers/Spi: Add Spi master driver Platforms/Marvell: Enable Spi master driver for Armada7040 boards Platforms/Marvell: Add EFI_SPI_FLASH_PROTOCOL Drivers/Spi: Implement Spi flash driver Platforms/Marvell: Enable Spi flash driver on Armada7040 platforms Applications/SpiTool: Add 'sf' command utility Platforms/Marvell: Enable 'sf' command on Armada7040 platforms Applications/FirmwareUpdate: Add 'fupdate' comand to shell Platforms/Marvell: Enable 'fupdate' command on Armada7040 platforms
Marcin Wojtas (1): Platforms/Marvell: Enable RamDisk usage on Armada7040 platforms
Yehuda Yitschak (2): Platforms/Marvell: Add initial support for Armada7040 SOC lib Platforms/Marvell: Add initial support for Armada7040 Platforms
Applications/EepromCmd/EepromCmd.c | 365 +++++++++++ Applications/EepromCmd/EepromCmd.inf | 74 +++ Applications/EepromCmd/EepromCmd.uni | Bin 0 -> 6816 bytes Applications/FirmwareUpdate/FUpdate.c | 437 +++++++++++++ Applications/FirmwareUpdate/FUpdate.inf | 69 +++ Applications/FirmwareUpdate/FUpdate.uni | Bin 0 -> 5838 bytes Applications/SpiTool/SpiFlashCmd.c | 529 ++++++++++++++++ Applications/SpiTool/SpiFlashCmd.inf | 76 +++ Applications/SpiTool/SpiFlashCmd.uni | Bin 0 -> 7216 bytes Documentation/Marvell/Drivers/EepromDriver.txt | 95 +++ Documentation/Marvell/Drivers/I2cDriver.txt | 64 ++ Documentation/Marvell/Drivers/SpiDriver.txt | 116 ++++ Documentation/Marvell/PortingGuide/I2c.txt | 16 + Documentation/Marvell/PortingGuide/Mpp.txt | 48 ++ Documentation/Marvell/PortingGuide/Spi.txt | 15 + Documentation/Marvell/PortingGuide/SpiFlash.txt | 19 + Drivers/I2c/Devices/MvEeprom/MvEeprom.c | 292 +++++++++ Drivers/I2c/Devices/MvEeprom/MvEeprom.h | 90 +++ Drivers/I2c/Devices/MvEeprom/MvEeprom.inf | 70 +++ Drivers/I2c/MvI2cDxe/MvI2cDxe.c | 686 +++++++++++++++++++++ Drivers/I2c/MvI2cDxe/MvI2cDxe.h | 254 ++++++++ Drivers/I2c/MvI2cDxe/MvI2cDxe.inf | 73 +++ Drivers/Spi/Devices/MvSpiFlash.c | 523 ++++++++++++++++ Drivers/Spi/Devices/MvSpiFlash.h | 130 ++++ Drivers/Spi/Devices/MvSpiFlash.inf | 74 +++ Drivers/Spi/SpiDxe.c | 378 ++++++++++++ Drivers/Spi/SpiDxe.h | 145 +++++ Drivers/Spi/SpiDxe.inf | 74 +++ Platforms/Marvell/Armada/Apn806.dsc | 81 +++ Platforms/Marvell/Armada/Armada.dsc.inc | 465 ++++++++++++++ Platforms/Marvell/Armada/Armada7040.fdf | 277 +++++++++ Platforms/Marvell/Armada/Armada7040_rz.dsc | 93 +++ .../Library/Armada7040BdsLib/Armada7040BdsLib.c | 428 +++++++++++++ .../Library/Armada7040BdsLib/Armada7040BdsLib.h | 37 ++ .../Library/Armada7040BdsLib/Armada7040BdsLib.inf | 66 ++ .../Armada7040Lib/AArch64/ArmPlatformHelper.S | 65 ++ .../Armada/Library/Armada7040Lib/Armada7040Lib.c | 156 +++++ .../Armada/Library/Armada7040Lib/Armada7040Lib.inf | 47 ++ .../Library/Armada7040Lib/Armada7040LibMem.c | 73 +++ Platforms/Marvell/Include/Library/MppLib.h | 42 ++ Platforms/Marvell/Include/Protocol/Eeprom.h | 60 ++ Platforms/Marvell/Include/Protocol/Spi.h | 105 ++++ Platforms/Marvell/Include/Protocol/SpiFlash.h | 102 +++ Platforms/Marvell/Library/MppLib/MppLib.c | 175 ++++++ Platforms/Marvell/Library/MppLib/MppLib.inf | 108 ++++ Platforms/Marvell/Marvell.dec | 132 ++++ 46 files changed, 7224 insertions(+) create mode 100644 Applications/EepromCmd/EepromCmd.c create mode 100644 Applications/EepromCmd/EepromCmd.inf create mode 100644 Applications/EepromCmd/EepromCmd.uni create mode 100644 Applications/FirmwareUpdate/FUpdate.c create mode 100644 Applications/FirmwareUpdate/FUpdate.inf create mode 100644 Applications/FirmwareUpdate/FUpdate.uni create mode 100644 Applications/SpiTool/SpiFlashCmd.c create mode 100644 Applications/SpiTool/SpiFlashCmd.inf create mode 100644 Applications/SpiTool/SpiFlashCmd.uni create mode 100644 Documentation/Marvell/Drivers/EepromDriver.txt create mode 100644 Documentation/Marvell/Drivers/I2cDriver.txt create mode 100644 Documentation/Marvell/Drivers/SpiDriver.txt create mode 100644 Documentation/Marvell/PortingGuide/I2c.txt create mode 100644 Documentation/Marvell/PortingGuide/Mpp.txt create mode 100644 Documentation/Marvell/PortingGuide/Spi.txt create mode 100644 Documentation/Marvell/PortingGuide/SpiFlash.txt create mode 100644 Drivers/I2c/Devices/MvEeprom/MvEeprom.c create mode 100644 Drivers/I2c/Devices/MvEeprom/MvEeprom.h create mode 100644 Drivers/I2c/Devices/MvEeprom/MvEeprom.inf create mode 100644 Drivers/I2c/MvI2cDxe/MvI2cDxe.c create mode 100644 Drivers/I2c/MvI2cDxe/MvI2cDxe.h create mode 100644 Drivers/I2c/MvI2cDxe/MvI2cDxe.inf create mode 100644 Drivers/Spi/Devices/MvSpiFlash.c create mode 100644 Drivers/Spi/Devices/MvSpiFlash.h create mode 100644 Drivers/Spi/Devices/MvSpiFlash.inf create mode 100644 Drivers/Spi/SpiDxe.c create mode 100644 Drivers/Spi/SpiDxe.h create mode 100644 Drivers/Spi/SpiDxe.inf create mode 100644 Platforms/Marvell/Armada/Apn806.dsc create mode 100644 Platforms/Marvell/Armada/Armada.dsc.inc create mode 100644 Platforms/Marvell/Armada/Armada7040.fdf create mode 100644 Platforms/Marvell/Armada/Armada7040_rz.dsc create mode 100644 Platforms/Marvell/Armada/Library/Armada7040BdsLib/Armada7040BdsLib.c create mode 100644 Platforms/Marvell/Armada/Library/Armada7040BdsLib/Armada7040BdsLib.h create mode 100644 Platforms/Marvell/Armada/Library/Armada7040BdsLib/Armada7040BdsLib.inf create mode 100644 Platforms/Marvell/Armada/Library/Armada7040Lib/AArch64/ArmPlatformHelper.S create mode 100644 Platforms/Marvell/Armada/Library/Armada7040Lib/Armada7040Lib.c create mode 100644 Platforms/Marvell/Armada/Library/Armada7040Lib/Armada7040Lib.inf create mode 100644 Platforms/Marvell/Armada/Library/Armada7040Lib/Armada7040LibMem.c create mode 100644 Platforms/Marvell/Include/Library/MppLib.h create mode 100644 Platforms/Marvell/Include/Protocol/Eeprom.h create mode 100644 Platforms/Marvell/Include/Protocol/Spi.h create mode 100644 Platforms/Marvell/Include/Protocol/SpiFlash.h create mode 100644 Platforms/Marvell/Library/MppLib/MppLib.c create mode 100644 Platforms/Marvell/Library/MppLib/MppLib.inf create mode 100644 Platforms/Marvell/Marvell.dec
-- 1.8.3.1
Hi Marcin,
Just had time for a cursory look so far, I'm afraid. But I can confirm the build issues are all resolved.
In general, I was pretty happy with what I saw the first time around, so unless I spot something (this week) I'd say it's good to go.
Regards,
Leif
On Mon, Apr 11, 2016 at 06:08:35PM +0200, Marcin Wojtas wrote:
Hi Leif,
Did you have a chance to take a look?
Best regards, Marcin
2016-04-06 8:22 GMT+02:00 Marcin Wojtas mw@semihalf.com:
Hello,
Here is v2 version of the support. The patchset shrank a bit, because the custom RamDisk driver was replaced with the one already existing in a tree - yet because of lack of FAT formatting it's not functional for the platform purposes, but it's not crucial at this point. Also a custom UART driver has been replaced. Detailed list of changes is below.
For convenience purpose whole patchset is available in the github: https://github.com/MarvellEmbeddedProcessors/edk2-open-platform/commits/opp-...
Any comments or remarks are mostly welcome.
Best regards, Marcin
Changelog: v1 -> v2
- Fix "may be used uninitialized" variables issue, branch compiles both with DEBUG and RELEASE flags
- Remove I2C_FLAG_NORESTART dependency - replace it with local definition
- Remove Marvell UART Library:
Since in edk2 there is support for 16550, internal library is unnecessary.
- DW8250 IP has programming interface compatible with NS-16550.
- /Library/BaseSerialPortLib16550/BaseSerialPortLib16550.inf is used instead
- RamDisk driver:
- Remove old driver imported from EFI TOOLKIT 2.0
- Replace it with new MdeModulePkg/Universal/Disk/RamDiskDxe from edk2
- Lack of FAT formatting issue emerged
- Add explicit dependency on IoLib in Drivers/Spi/SpiDxe.inf
- Add poster's "Signed-off-by" registry to every commit message
- Move to 05.04.2016 HEAD of edk2/master
- Update CpuExceptionHandlerLib within OPP.
Bartosz Szczepanek (6): Drivers/I2c: Create MvI2cDxe driver Platforms/Marvell: Copy BdsLib to Armada7040 directory Platforms/Marvell: Add necessary BdsLibConnectAll call Drivers/I2c: Add MvEeprom driver Platforms/Marvell: Enable EEPROM driver on Armada7040 platforms Aplications/Eeprom: Add 'eeprom' command to shell
Jan Dąbroś (14): Platforms/Marvell: Create MppLib Platforms/Marvell: Armada: Enable MppLib on Armada7040 platforms Platforms/Marvell: Enable I2C driver on Armada7040 platforms Platforms/Marvell: Enable 'eeprom' command on Armada7040 platforms Platforms/Marvell: Add EFI_SPI_MASTER_PROTOCOL Drivers/Spi: Add Spi master driver Platforms/Marvell: Enable Spi master driver for Armada7040 boards Platforms/Marvell: Add EFI_SPI_FLASH_PROTOCOL Drivers/Spi: Implement Spi flash driver Platforms/Marvell: Enable Spi flash driver on Armada7040 platforms Applications/SpiTool: Add 'sf' command utility Platforms/Marvell: Enable 'sf' command on Armada7040 platforms Applications/FirmwareUpdate: Add 'fupdate' comand to shell Platforms/Marvell: Enable 'fupdate' command on Armada7040 platforms
Marcin Wojtas (1): Platforms/Marvell: Enable RamDisk usage on Armada7040 platforms
Yehuda Yitschak (2): Platforms/Marvell: Add initial support for Armada7040 SOC lib Platforms/Marvell: Add initial support for Armada7040 Platforms
Applications/EepromCmd/EepromCmd.c | 365 +++++++++++ Applications/EepromCmd/EepromCmd.inf | 74 +++ Applications/EepromCmd/EepromCmd.uni | Bin 0 -> 6816 bytes Applications/FirmwareUpdate/FUpdate.c | 437 +++++++++++++ Applications/FirmwareUpdate/FUpdate.inf | 69 +++ Applications/FirmwareUpdate/FUpdate.uni | Bin 0 -> 5838 bytes Applications/SpiTool/SpiFlashCmd.c | 529 ++++++++++++++++ Applications/SpiTool/SpiFlashCmd.inf | 76 +++ Applications/SpiTool/SpiFlashCmd.uni | Bin 0 -> 7216 bytes Documentation/Marvell/Drivers/EepromDriver.txt | 95 +++ Documentation/Marvell/Drivers/I2cDriver.txt | 64 ++ Documentation/Marvell/Drivers/SpiDriver.txt | 116 ++++ Documentation/Marvell/PortingGuide/I2c.txt | 16 + Documentation/Marvell/PortingGuide/Mpp.txt | 48 ++ Documentation/Marvell/PortingGuide/Spi.txt | 15 + Documentation/Marvell/PortingGuide/SpiFlash.txt | 19 + Drivers/I2c/Devices/MvEeprom/MvEeprom.c | 292 +++++++++ Drivers/I2c/Devices/MvEeprom/MvEeprom.h | 90 +++ Drivers/I2c/Devices/MvEeprom/MvEeprom.inf | 70 +++ Drivers/I2c/MvI2cDxe/MvI2cDxe.c | 686 +++++++++++++++++++++ Drivers/I2c/MvI2cDxe/MvI2cDxe.h | 254 ++++++++ Drivers/I2c/MvI2cDxe/MvI2cDxe.inf | 73 +++ Drivers/Spi/Devices/MvSpiFlash.c | 523 ++++++++++++++++ Drivers/Spi/Devices/MvSpiFlash.h | 130 ++++ Drivers/Spi/Devices/MvSpiFlash.inf | 74 +++ Drivers/Spi/SpiDxe.c | 378 ++++++++++++ Drivers/Spi/SpiDxe.h | 145 +++++ Drivers/Spi/SpiDxe.inf | 74 +++ Platforms/Marvell/Armada/Apn806.dsc | 81 +++ Platforms/Marvell/Armada/Armada.dsc.inc | 465 ++++++++++++++ Platforms/Marvell/Armada/Armada7040.fdf | 277 +++++++++ Platforms/Marvell/Armada/Armada7040_rz.dsc | 93 +++ .../Library/Armada7040BdsLib/Armada7040BdsLib.c | 428 +++++++++++++ .../Library/Armada7040BdsLib/Armada7040BdsLib.h | 37 ++ .../Library/Armada7040BdsLib/Armada7040BdsLib.inf | 66 ++ .../Armada7040Lib/AArch64/ArmPlatformHelper.S | 65 ++ .../Armada/Library/Armada7040Lib/Armada7040Lib.c | 156 +++++ .../Armada/Library/Armada7040Lib/Armada7040Lib.inf | 47 ++ .../Library/Armada7040Lib/Armada7040LibMem.c | 73 +++ Platforms/Marvell/Include/Library/MppLib.h | 42 ++ Platforms/Marvell/Include/Protocol/Eeprom.h | 60 ++ Platforms/Marvell/Include/Protocol/Spi.h | 105 ++++ Platforms/Marvell/Include/Protocol/SpiFlash.h | 102 +++ Platforms/Marvell/Library/MppLib/MppLib.c | 175 ++++++ Platforms/Marvell/Library/MppLib/MppLib.inf | 108 ++++ Platforms/Marvell/Marvell.dec | 132 ++++ 46 files changed, 7224 insertions(+) create mode 100644 Applications/EepromCmd/EepromCmd.c create mode 100644 Applications/EepromCmd/EepromCmd.inf create mode 100644 Applications/EepromCmd/EepromCmd.uni create mode 100644 Applications/FirmwareUpdate/FUpdate.c create mode 100644 Applications/FirmwareUpdate/FUpdate.inf create mode 100644 Applications/FirmwareUpdate/FUpdate.uni create mode 100644 Applications/SpiTool/SpiFlashCmd.c create mode 100644 Applications/SpiTool/SpiFlashCmd.inf create mode 100644 Applications/SpiTool/SpiFlashCmd.uni create mode 100644 Documentation/Marvell/Drivers/EepromDriver.txt create mode 100644 Documentation/Marvell/Drivers/I2cDriver.txt create mode 100644 Documentation/Marvell/Drivers/SpiDriver.txt create mode 100644 Documentation/Marvell/PortingGuide/I2c.txt create mode 100644 Documentation/Marvell/PortingGuide/Mpp.txt create mode 100644 Documentation/Marvell/PortingGuide/Spi.txt create mode 100644 Documentation/Marvell/PortingGuide/SpiFlash.txt create mode 100644 Drivers/I2c/Devices/MvEeprom/MvEeprom.c create mode 100644 Drivers/I2c/Devices/MvEeprom/MvEeprom.h create mode 100644 Drivers/I2c/Devices/MvEeprom/MvEeprom.inf create mode 100644 Drivers/I2c/MvI2cDxe/MvI2cDxe.c create mode 100644 Drivers/I2c/MvI2cDxe/MvI2cDxe.h create mode 100644 Drivers/I2c/MvI2cDxe/MvI2cDxe.inf create mode 100644 Drivers/Spi/Devices/MvSpiFlash.c create mode 100644 Drivers/Spi/Devices/MvSpiFlash.h create mode 100644 Drivers/Spi/Devices/MvSpiFlash.inf create mode 100644 Drivers/Spi/SpiDxe.c create mode 100644 Drivers/Spi/SpiDxe.h create mode 100644 Drivers/Spi/SpiDxe.inf create mode 100644 Platforms/Marvell/Armada/Apn806.dsc create mode 100644 Platforms/Marvell/Armada/Armada.dsc.inc create mode 100644 Platforms/Marvell/Armada/Armada7040.fdf create mode 100644 Platforms/Marvell/Armada/Armada7040_rz.dsc create mode 100644 Platforms/Marvell/Armada/Library/Armada7040BdsLib/Armada7040BdsLib.c create mode 100644 Platforms/Marvell/Armada/Library/Armada7040BdsLib/Armada7040BdsLib.h create mode 100644 Platforms/Marvell/Armada/Library/Armada7040BdsLib/Armada7040BdsLib.inf create mode 100644 Platforms/Marvell/Armada/Library/Armada7040Lib/AArch64/ArmPlatformHelper.S create mode 100644 Platforms/Marvell/Armada/Library/Armada7040Lib/Armada7040Lib.c create mode 100644 Platforms/Marvell/Armada/Library/Armada7040Lib/Armada7040Lib.inf create mode 100644 Platforms/Marvell/Armada/Library/Armada7040Lib/Armada7040LibMem.c create mode 100644 Platforms/Marvell/Include/Library/MppLib.h create mode 100644 Platforms/Marvell/Include/Protocol/Eeprom.h create mode 100644 Platforms/Marvell/Include/Protocol/Spi.h create mode 100644 Platforms/Marvell/Include/Protocol/SpiFlash.h create mode 100644 Platforms/Marvell/Library/MppLib/MppLib.c create mode 100644 Platforms/Marvell/Library/MppLib/MppLib.inf create mode 100644 Platforms/Marvell/Marvell.dec
-- 1.8.3.1
Leif,
Thanks a lot. We are looking forward to your comments then. Either way, in case you don't spot anything, please let know - I'd like to issue v3 with 3 minor fixes after your review is done.
Best regards, Marcin
2016-04-11 18:37 GMT+02:00 Leif Lindholm leif.lindholm@linaro.org:
Hi Marcin,
Just had time for a cursory look so far, I'm afraid. But I can confirm the build issues are all resolved.
In general, I was pretty happy with what I saw the first time around, so unless I spot something (this week) I'd say it's good to go.
Regards,
Leif
On Mon, Apr 11, 2016 at 06:08:35PM +0200, Marcin Wojtas wrote:
Hi Leif,
Did you have a chance to take a look?
Best regards, Marcin
2016-04-06 8:22 GMT+02:00 Marcin Wojtas mw@semihalf.com:
Hello,
Here is v2 version of the support. The patchset shrank a bit, because the custom RamDisk driver was replaced with the one already existing in a tree - yet because of lack of FAT formatting it's not functional for the platform purposes, but it's not crucial at this point. Also a custom UART driver has been replaced. Detailed list of changes is below.
For convenience purpose whole patchset is available in the github: https://github.com/MarvellEmbeddedProcessors/edk2-open-platform/commits/opp-...
Any comments or remarks are mostly welcome.
Best regards, Marcin
Changelog: v1 -> v2
- Fix "may be used uninitialized" variables issue, branch compiles both with DEBUG and RELEASE flags
- Remove I2C_FLAG_NORESTART dependency - replace it with local definition
- Remove Marvell UART Library:
Since in edk2 there is support for 16550, internal library is unnecessary.
- DW8250 IP has programming interface compatible with NS-16550.
- /Library/BaseSerialPortLib16550/BaseSerialPortLib16550.inf is used instead
- RamDisk driver:
- Remove old driver imported from EFI TOOLKIT 2.0
- Replace it with new MdeModulePkg/Universal/Disk/RamDiskDxe from edk2
- Lack of FAT formatting issue emerged
- Add explicit dependency on IoLib in Drivers/Spi/SpiDxe.inf
- Add poster's "Signed-off-by" registry to every commit message
- Move to 05.04.2016 HEAD of edk2/master
- Update CpuExceptionHandlerLib within OPP.
Bartosz Szczepanek (6): Drivers/I2c: Create MvI2cDxe driver Platforms/Marvell: Copy BdsLib to Armada7040 directory Platforms/Marvell: Add necessary BdsLibConnectAll call Drivers/I2c: Add MvEeprom driver Platforms/Marvell: Enable EEPROM driver on Armada7040 platforms Aplications/Eeprom: Add 'eeprom' command to shell
Jan Dąbroś (14): Platforms/Marvell: Create MppLib Platforms/Marvell: Armada: Enable MppLib on Armada7040 platforms Platforms/Marvell: Enable I2C driver on Armada7040 platforms Platforms/Marvell: Enable 'eeprom' command on Armada7040 platforms Platforms/Marvell: Add EFI_SPI_MASTER_PROTOCOL Drivers/Spi: Add Spi master driver Platforms/Marvell: Enable Spi master driver for Armada7040 boards Platforms/Marvell: Add EFI_SPI_FLASH_PROTOCOL Drivers/Spi: Implement Spi flash driver Platforms/Marvell: Enable Spi flash driver on Armada7040 platforms Applications/SpiTool: Add 'sf' command utility Platforms/Marvell: Enable 'sf' command on Armada7040 platforms Applications/FirmwareUpdate: Add 'fupdate' comand to shell Platforms/Marvell: Enable 'fupdate' command on Armada7040 platforms
Marcin Wojtas (1): Platforms/Marvell: Enable RamDisk usage on Armada7040 platforms
Yehuda Yitschak (2): Platforms/Marvell: Add initial support for Armada7040 SOC lib Platforms/Marvell: Add initial support for Armada7040 Platforms
Applications/EepromCmd/EepromCmd.c | 365 +++++++++++ Applications/EepromCmd/EepromCmd.inf | 74 +++ Applications/EepromCmd/EepromCmd.uni | Bin 0 -> 6816 bytes Applications/FirmwareUpdate/FUpdate.c | 437 +++++++++++++ Applications/FirmwareUpdate/FUpdate.inf | 69 +++ Applications/FirmwareUpdate/FUpdate.uni | Bin 0 -> 5838 bytes Applications/SpiTool/SpiFlashCmd.c | 529 ++++++++++++++++ Applications/SpiTool/SpiFlashCmd.inf | 76 +++ Applications/SpiTool/SpiFlashCmd.uni | Bin 0 -> 7216 bytes Documentation/Marvell/Drivers/EepromDriver.txt | 95 +++ Documentation/Marvell/Drivers/I2cDriver.txt | 64 ++ Documentation/Marvell/Drivers/SpiDriver.txt | 116 ++++ Documentation/Marvell/PortingGuide/I2c.txt | 16 + Documentation/Marvell/PortingGuide/Mpp.txt | 48 ++ Documentation/Marvell/PortingGuide/Spi.txt | 15 + Documentation/Marvell/PortingGuide/SpiFlash.txt | 19 + Drivers/I2c/Devices/MvEeprom/MvEeprom.c | 292 +++++++++ Drivers/I2c/Devices/MvEeprom/MvEeprom.h | 90 +++ Drivers/I2c/Devices/MvEeprom/MvEeprom.inf | 70 +++ Drivers/I2c/MvI2cDxe/MvI2cDxe.c | 686 +++++++++++++++++++++ Drivers/I2c/MvI2cDxe/MvI2cDxe.h | 254 ++++++++ Drivers/I2c/MvI2cDxe/MvI2cDxe.inf | 73 +++ Drivers/Spi/Devices/MvSpiFlash.c | 523 ++++++++++++++++ Drivers/Spi/Devices/MvSpiFlash.h | 130 ++++ Drivers/Spi/Devices/MvSpiFlash.inf | 74 +++ Drivers/Spi/SpiDxe.c | 378 ++++++++++++ Drivers/Spi/SpiDxe.h | 145 +++++ Drivers/Spi/SpiDxe.inf | 74 +++ Platforms/Marvell/Armada/Apn806.dsc | 81 +++ Platforms/Marvell/Armada/Armada.dsc.inc | 465 ++++++++++++++ Platforms/Marvell/Armada/Armada7040.fdf | 277 +++++++++ Platforms/Marvell/Armada/Armada7040_rz.dsc | 93 +++ .../Library/Armada7040BdsLib/Armada7040BdsLib.c | 428 +++++++++++++ .../Library/Armada7040BdsLib/Armada7040BdsLib.h | 37 ++ .../Library/Armada7040BdsLib/Armada7040BdsLib.inf | 66 ++ .../Armada7040Lib/AArch64/ArmPlatformHelper.S | 65 ++ .../Armada/Library/Armada7040Lib/Armada7040Lib.c | 156 +++++ .../Armada/Library/Armada7040Lib/Armada7040Lib.inf | 47 ++ .../Library/Armada7040Lib/Armada7040LibMem.c | 73 +++ Platforms/Marvell/Include/Library/MppLib.h | 42 ++ Platforms/Marvell/Include/Protocol/Eeprom.h | 60 ++ Platforms/Marvell/Include/Protocol/Spi.h | 105 ++++ Platforms/Marvell/Include/Protocol/SpiFlash.h | 102 +++ Platforms/Marvell/Library/MppLib/MppLib.c | 175 ++++++ Platforms/Marvell/Library/MppLib/MppLib.inf | 108 ++++ Platforms/Marvell/Marvell.dec | 132 ++++ 46 files changed, 7224 insertions(+) create mode 100644 Applications/EepromCmd/EepromCmd.c create mode 100644 Applications/EepromCmd/EepromCmd.inf create mode 100644 Applications/EepromCmd/EepromCmd.uni create mode 100644 Applications/FirmwareUpdate/FUpdate.c create mode 100644 Applications/FirmwareUpdate/FUpdate.inf create mode 100644 Applications/FirmwareUpdate/FUpdate.uni create mode 100644 Applications/SpiTool/SpiFlashCmd.c create mode 100644 Applications/SpiTool/SpiFlashCmd.inf create mode 100644 Applications/SpiTool/SpiFlashCmd.uni create mode 100644 Documentation/Marvell/Drivers/EepromDriver.txt create mode 100644 Documentation/Marvell/Drivers/I2cDriver.txt create mode 100644 Documentation/Marvell/Drivers/SpiDriver.txt create mode 100644 Documentation/Marvell/PortingGuide/I2c.txt create mode 100644 Documentation/Marvell/PortingGuide/Mpp.txt create mode 100644 Documentation/Marvell/PortingGuide/Spi.txt create mode 100644 Documentation/Marvell/PortingGuide/SpiFlash.txt create mode 100644 Drivers/I2c/Devices/MvEeprom/MvEeprom.c create mode 100644 Drivers/I2c/Devices/MvEeprom/MvEeprom.h create mode 100644 Drivers/I2c/Devices/MvEeprom/MvEeprom.inf create mode 100644 Drivers/I2c/MvI2cDxe/MvI2cDxe.c create mode 100644 Drivers/I2c/MvI2cDxe/MvI2cDxe.h create mode 100644 Drivers/I2c/MvI2cDxe/MvI2cDxe.inf create mode 100644 Drivers/Spi/Devices/MvSpiFlash.c create mode 100644 Drivers/Spi/Devices/MvSpiFlash.h create mode 100644 Drivers/Spi/Devices/MvSpiFlash.inf create mode 100644 Drivers/Spi/SpiDxe.c create mode 100644 Drivers/Spi/SpiDxe.h create mode 100644 Drivers/Spi/SpiDxe.inf create mode 100644 Platforms/Marvell/Armada/Apn806.dsc create mode 100644 Platforms/Marvell/Armada/Armada.dsc.inc create mode 100644 Platforms/Marvell/Armada/Armada7040.fdf create mode 100644 Platforms/Marvell/Armada/Armada7040_rz.dsc create mode 100644 Platforms/Marvell/Armada/Library/Armada7040BdsLib/Armada7040BdsLib.c create mode 100644 Platforms/Marvell/Armada/Library/Armada7040BdsLib/Armada7040BdsLib.h create mode 100644 Platforms/Marvell/Armada/Library/Armada7040BdsLib/Armada7040BdsLib.inf create mode 100644 Platforms/Marvell/Armada/Library/Armada7040Lib/AArch64/ArmPlatformHelper.S create mode 100644 Platforms/Marvell/Armada/Library/Armada7040Lib/Armada7040Lib.c create mode 100644 Platforms/Marvell/Armada/Library/Armada7040Lib/Armada7040Lib.inf create mode 100644 Platforms/Marvell/Armada/Library/Armada7040Lib/Armada7040LibMem.c create mode 100644 Platforms/Marvell/Include/Library/MppLib.h create mode 100644 Platforms/Marvell/Include/Protocol/Eeprom.h create mode 100644 Platforms/Marvell/Include/Protocol/Spi.h create mode 100644 Platforms/Marvell/Include/Protocol/SpiFlash.h create mode 100644 Platforms/Marvell/Library/MppLib/MppLib.c create mode 100644 Platforms/Marvell/Library/MppLib/MppLib.inf create mode 100644 Platforms/Marvell/Marvell.dec
-- 1.8.3.1