Compare commits

..

47 Commits

Author SHA1 Message Date
Sean Rhodes
2dc1e51593 UefiPayloadPkg: Add Secure Boot support
Cc: Guo Dong <guo.dong@intel.com>
Cc: Ray Ni <ray.ni@intel.com>
Cc: Maurice Ma <maurice.ma@intel.com>
Cc: Benjamin You <benjamin.you@intel.com>
Signed-off-by: Sean Rhodes <sean@starlabs.systems>
Change-Id: I4f44e29bc967b7d2208193e21aeeef8b96afcc69
2022-06-03 09:03:42 -06:00
Sean Rhodes
35dde2452d MdeModulePkg/FaultTolerantWriteDxe: Don't check for address alignment
WorkSpaceAddress and SpareAreaAddress point into MMIO, which isn't
always aligned. Remove the check for block alignment to avoid
false assertions.

Signed-off-by: Sean Rhodes <sean@starlabs.systems>
Change-Id: Ia1c1f44b6a0e7f32cac0d7806e74d729e5d83a6d
2022-06-03 09:03:42 -06:00
Matt DeVillier
0f49a3fc87 Ps2KbdCtrller: Make wait for SUCCESS after BAT non-fatal
Recent model Chromebooks only return ACK, but not
BAT_SUCCESS, which causes hanging and failed ps2k init.
To mitigate this, make the absence of BAT_SUCCESS reply
non-fatal, and reduce the no-reply timeout from 4s to 1s.

Tested on google/dracia and purism/librem_14

Cc: Hao A Wu <hao.a.wu@intel.com>
Cc: Ray Ni <ray.ni@intel.com>
Signed-off-by: Matt DeVillier <matt.devillier@gmail.com>
Signed-off-by: Sean Rhodes <sean@starlabs.systems>
Change-Id: Ib644f6797eb50eb3bb75235ac48ddb6096a7bd6d
2022-06-03 09:03:42 -06:00
Patrick Rudolph
792844cb3b UefiPayloadPkg: Hook up RNG support
Hoop Up RNG from SecurityPkg.

Cc: Jiewen Yao <jiewen.yao@intel.com>
Cc: Jian J Wang <jian.j.wang@intel.com>
Cc: Guo Dong <guo.dong@intel.com>
Cc: Ray Ni <ray.ni@intel.com>
Cc: Maurice Ma <maurice.ma@intel.com>
Cc: Benjamin You <benjamin.you@intel.com>
Signed-off-by: Patrick Rudolph <patrick.rudolph@9elements.com>
Change-Id: I9fadc2f36b0601b8a2f5b8a9abc3f208e7987e6c
2022-06-03 09:03:42 -06:00
Patrick Rudolph
136138411f SecurityPkg: Add RNG support
Uses the RDRAND instruction if available and install EfiRngProtocol.
The protocol may be used by iPXE or the Linux kernel to gather entropy.

Cc: Jiewen Yao <jiewen.yao@intel.com>
Cc: Jian J Wang <jian.j.wang@intel.com>
Cc: Guo Dong <guo.dong@intel.com>
Signed-off-by: Patrick Rudolph <patrick.rudolph@9elements.com>
Change-Id: I0f74b64c6a7e8fc6fdd8ea8f2a416d8b7c0334f4
2022-06-03 09:03:42 -06:00
Sean Rhodes
1f31c0e81e UefiPayloadPkg: Add support for Firmware Volume Block Protocol
This adds support for FVB in order to support a platform independent
and non-volatile variable store on UefiPayloadPkg. The variable store
makes use the SmmStoreLib to provide an unauthenticed variable store.

Since commit bc744f5893fc4d53275ed26dd8d968011c6a09c1 coreboot supports
the SMMSTORE v2 feature. It implements a SMI handler that is able to
write, read and erase pages in the boot media (SPI flash).
The communication is done using a fixed communication buffer that is
allocated in CBMEM. The existence of this optional feature is advertised
by a coreboot table.
When the SMMSTORE feature is not available the variable emulation is used
by setting PcdEmuVariableNvModeEnable to TRUE.

The DXE component provides runtime services and takes care of virtual to
physical mapping the communication buffers between SMM and OS.

The contents of the variable store can be accessed and modified by any
priviledged application. As authentication is done by runtime services
only the store shouldn't be used to store authenticated variables.

Tested on Linux and Windows 10 on real hardware.
Currently this cannot be tested on coreboot and qemu as it doesn't support
the SMMSTORE on qemu.

Cc: Guo Dong <guo.dong@intel.com>
Cc: Ray Ni <ray.ni@intel.com>
Cc: Maurice Ma <maurice.ma@intel.com>
Cc: Benjamin You <benjamin.you@intel.com>
Signed-off-by: Patrick Rudolph <patrick.rudolph@9elements.com>
Signed-off-by: Sean Rhodes <sean@starlabs.systems>
Change-Id: I79a234275e25961869edf959cfbf4f8d17df2383
2022-06-03 09:03:42 -06:00
Patrick Rudolph
dcdfb2f083 UefiPayloadPkg: Add SmmStoreLib
Implement all of the FVB protocol functions on top of the SmmStore
as a library. The library consumes the introduced gEfiSmmStoreInfoHobGuid.

The SMI handler uses a fixed communication buffer in reserved DRAM.
To initiate a transaction you must write to the I/O APM_CNT port.

Tests on Intel(R) Xeon(R) E-2288G CPU @ 3.70G showed that the SMI isn't
triggered with a probability of 1:40 of all cases when called in a tight
loop. The CPU continues running and the SMI is triggeres asynchronously
a few clock cycles later. coreboot only handels synchronous APM request
and does nothing on asynchronous APM triggers.

As there's no livesign from SMM it's impossible to tell if the handler
has run. Just wait a bit and try again to trigger a synchronous SMI.

Tests confirmed that out of 5 million tries the SMI is now always handled.

When a synchronous SMI happens with the correct write to the APM_CNT port,
the ebx register is checked first that it doesn't point to SMRAM.
If it doesn't it's used to read in the arguments that define a SmmStore
transaction.

The SMI handler will only operate on a predefined and memory mapped region in
the boot media.

Cc: Guo Dong <guo.dong@intel.com>
Cc: Ray Ni <ray.ni@intel.com>
Cc: Maurice Ma <maurice.ma@intel.com>
Cc: Benjamin You <benjamin.you@intel.com>
Cc: Sean Rhodes <sean@starlabs.systems>
Signed-off-by: Patrick Rudolph <patrick.rudolph@9elements.com>
Change-Id: Id4182623e4198c6512d3fe6ec20adf6738586d9b
2022-06-03 09:03:42 -06:00
Patrick Rudolph
13dd54ae32 UefiPayloadPkg: Add SmmStoreInfoGuid
Add a new InfoHob that contains the SmmStore information passed from
coreboot tables when the SMMSTOREV2 feature is enabled.

This will be used to implement the FVB in top of the MM installed by
coreboot.

Cc: Guo Dong <guo.dong@intel.com>
Cc: Ray Ni <ray.ni@intel.com>
Cc: Maurice Ma <maurice.ma@intel.com>
Cc: Benjamin You <benjamin.you@intel.com>
Cc: Sean Rhodes <sean@starlabs.systems>
Signed-off-by: Patrick Rudolph <patrick.rudolph@9elements.com>
Change-Id: Ia3f7eef27d4758768c1a6736afe1cb77ee6a2f8f
2022-06-03 09:03:42 -06:00
Patrick Rudolph
bb19b4bc30 UefiPayloadPkg/Include/Coreboot: Add headers for SMMSTOREv2 table
Since commit bc744f5893fc4d53275ed26dd8d968011c6a09c1 coreboot supports
the SMMSTORE v2 feature. It implements a SMI handler that is able to
write, read and erase pages in the boot media (SPI flash).
The existence of this optional feature is advertised by a coreboot table.

Add the tag and headers to parse the table.

Cc: Guo Dong <guo.dong@intel.com>
Cc: Ray Ni <ray.ni@intel.com>
Cc: Maurice Ma <maurice.ma@intel.com>
Cc: Benjamin You <benjamin.you@intel.com>
Cc: Sean Rhodes <sean@starlabs.systems>
Signed-off-by: Patrick Rudolph <patrick.rudolph@9elements.com>
Change-Id: I02be3fa8d5d6ff47d56b81876590afef8f6c43c0
2022-06-03 09:03:42 -06:00
Patrick Rudolph
7693804ed1 UefiPayloadPkg: Increase FV size to 8MB
The following commits need additional space.

Signed-off-by: Patrick Rudolph <patrick.rudolph@9elements.com>
Change-Id: I6b757f73fe4e90282b4bfb84469545ab1af9d1bb
Reviewed-on: https://review.coreboot.org/c/edk2/+/58630
Tested-by: build bot (Jenkins) <no-reply@coreboot.org>
Reviewed-by: Matt DeVillier <matt.devillier@gmail.com>
2022-06-03 09:03:42 -06:00
Jeremy Soller
626f1a3273 UefiPayloadPkg: Add System76 Setup menu 2022-06-03 09:03:42 -06:00
Jeremy Soller
0420529401 UefiPayloadPkg: Add Intel GOP driver 2022-06-03 09:03:42 -06:00
Tim Crawford
13e6178201 UefiPayloadPkg: Add Pop!_OS Recovery to boot text
Preserve existing UI and add the note about pressing Space to go to
the systemd-boot menu for Pop!_OS Recovery.

Signed-off-by: Tim Crawford <tcrawford@system76.com>
2022-06-03 09:03:42 -06:00
Tim Crawford
cbff8f0510 MdeModulePkg/BmBootDesciption: Remove device prefixes
Remove the device prefixes to match current System76 firmware UI in the
One Time Boot menu.

Signed-off-by: Tim Crawford <tcrawford@system76.com>
2022-06-03 09:03:42 -06:00
Tim Crawford
601bcb9ce2 MdeModulePkg/BM: Update boot options on device change
Register an event to trigger when a block device is added or removed
that will update the list of boot options. Use a refreshguid to force
the form to display the changes if it already open.
2022-06-03 09:03:42 -06:00
Tim Crawford
6468032370 MdeModulePkg/Core: Signal notify events on protocol removal
In order for BootManager to maintain a valid list of boot options, it
must know when the BlockIo protocol is also removed, not just added.
2022-06-03 09:03:42 -06:00
Jeremy Soller
7b3153b1cb UiApp: Dynamically generated firmware configuration information page
Signed-off-by: Jeremy Soller <jeremy@system76.com>
Signed-off-by: Tim Crawford <tcrawford@system76.com>
2022-06-03 09:03:42 -06:00
Tim Crawford
f2e99ad7b6 MdeModulePkg/BMM: Unregister F9 and F10 hotkeys 2022-06-03 09:03:42 -06:00
Tim Crawford
ae93abfcbf MdeModulePkg/BMM: Remove Commit/Discard buttons 2022-06-03 09:03:42 -06:00
Tim Crawford
de3e52e5d3 MdeModulePkg/BMM: Save BootOrder on list update 2022-06-03 09:03:42 -06:00
Tim Crawford
260b22ed3e MdeModulePkg/BMM: Add some debug logging 2022-06-03 09:03:42 -06:00
Tim Crawford
b79d3f9599 MdeModulePkg/UiApp: Add warning if no bootable options found 2022-06-03 09:03:42 -06:00
Tim Crawford
49dad2f15d MdeModulePkg/BootMaintenanceManagerUiLib: Make it look like current BMM 2022-06-03 09:03:42 -06:00
Tim Crawford
21bbc9ae0e MdeModulePkg/UiApp: Make it look like current FrontPage
Signed-off-by: Jeremy Soller <jeremy@system76.com>
Signed-off-by: Tim Crawford <tcrawford@system76.com>
2022-06-03 09:03:42 -06:00
Tim Crawford
52d9ce76db MdeModulePkg/BM: Make it look like current BootMngr 2022-06-03 09:03:42 -06:00
Tim Crawford
0d209e3a81 UefiPayloadPkg: Disable EFI shell 2022-06-03 09:03:42 -06:00
Jeremy Soller
c418d4eb9e UefiPayloadPkg: Add library for logging to EC
Make use of the SMFI command interface to forward logs from edk2 to
System76 EC.

Signed-off-by: Jeremy Soller <jeremy@system76.com>
Signed-off-by: Tim Crawford <tcrawford@system76.com>
2022-06-03 09:03:42 -06:00
Patrick Rudolph
648620d59d UefiPayloadPkg: Scan for Option ROMs
Scanning for PCI Option ROMs on UEFI works with full PCI enumeration.
On platforms where the bootloader has done PCI enumeration a
platform specific driver needs to provide the Option ROMs.

As this is not specific to any platform, but rather to the UEFI as
payload concept, add the PCI platform driver to UefiPayloadPkg.

On coreboot the ROM BAR is part of the PCI bridge MMIO window and
can safely enabled if existing.

The Option ROMs are not passed in by bootloader in a HOB as:
- they might not fit into a HOB
- this is EDK2 specific and would just bloat the bootloader code
- would waste lot's of non reclaimable memory if placed in e820
  reserved DRAM space

Signed-off-by: Patrick Rudolph <patrick.rudolph@9elements.com>
2022-06-03 09:03:42 -06:00
Patrick Rudolph
6284b7fe6f UefiPayloadPkg: Use new filesystem drivers
Signed-off-by: Patrick Rudolph <patrick.rudolph@9elements.com>
2022-06-03 09:03:42 -06:00
CoolStar
e3ac04f774 Add filesystem drivers
Add EXT2/EXT4, exFAT, NTFS filesystem drivers.
Do not add ISO9115 drivers as it breaks El Torito boot.
2022-06-03 09:03:42 -06:00
Tim Crawford
5f7a6fe58b UefiPayloadPkg: Stall before connecting devices
USB devices are not being detected when booting. Pause a bit for them to
be initialized and detected by EfiBootManagerConnectAll().
2022-06-03 09:03:42 -06:00
Tim Crawford
4f9743107d MdeModulePkg/BdsDxe: Forward any key for booting
Pressing escape will bring a user to the boot manager. Pressing any
other key will continue booting, forwarding the key to systemd-boot.
2022-06-03 09:03:42 -06:00
Matt DeVillier
f300ed8297 MdeModulePkg: Wait for input after boot failure
Signed-off-by: Matt DeVillier <matt.devillier@gmail.com>
2022-06-03 09:03:42 -06:00
Tim Crawford
1fd1cf3dfb UefiPayloadPkg: Clear screen on boot error 2022-06-03 09:03:42 -06:00
Tim Crawford
053e8aed4d UefiPayloadPkg: Copy PlatformBootManagerUnableToBoot() from OvmfPkg 2022-06-03 09:03:42 -06:00
Matt DeVillier
b219d5c94f UefiPayloadPkg: Set ResetOnMemoryTypeInformationChange to FALSE
the default value, TRUE, causes reboots if a device boots to the
shell, exits, and then attempts to boot from another source.

Signed-off-by: Matt DeVillier <matt.devillier@gmail.com>
2022-06-03 09:03:42 -06:00
Matt DeVillier
20a7334a96 MdeModulePkg/GraphicsConsole: don't draw cursor at 0,0
Prevents cursor from flashing on screen when
changing modes or clearing the screen.

Signed-off-by: Matt DeVillier <matt.devillier@gmail.com>
2022-06-03 09:03:42 -06:00
Matt DeVillier
a8abddc10a MdeModulePkg/BmBootDesciption: Improve device descriptions
Add device type prefixes for USB, IDE, SATA, and NVMe drives.
Remove UEFI prefix, remove serial numbers.

Signed-off-by: Matt DeVillier <matt.devillier@gmail.com>
2022-06-03 09:03:42 -06:00
Matt DeVillier
93688ae1e5 MdeModulePkg/BmBoot: skip secondary eMMC entries
Internal eMMC devices often show multiple entries, so skip
any after the initial entry.

Signed-off-by: Matt DeVillier <matt.devillier@gmail.com>
2022-06-03 09:03:42 -06:00
Matt DeVillier
38a3b6f58d MdeModulePkg/Frontpage: get SMBIOS Data from table directly
rather than getting it from the EFI SMBIOS protocol

Signed-off-by: Matt DeVillier <matt.devillier@gmail.com>
2022-06-03 09:03:41 -06:00
Tim Crawford
85f616be1b UefiPayloadPkg: Disable Device Manager 2022-06-03 09:03:41 -06:00
Matt DeVillier
1aed3a3e36 BmpSupportLib: fix BMP validation
BMP files by tools other than MS paint can have a
variable number of padding bytes, which results in
the DataSize being less than (ImageSize - HeaderSize).
Fix the check to be less stringent.

Test: use BMP created by/saved by Photoshop

Signed-off-by: Matt DeVillier <matt.devillier@gmail.com>
2022-06-03 09:03:41 -06:00
Matt DeVillier
f8d5dcd99b MdeModulePkg: load boot logo into BGRT table
This is a shoehorned-in implementation of an ACPI BGRT
table, ported pretty much directly from the version used
under CorebootPayloadPkg.

EDK2 provides a facility to do this already, but it assumes
the ACPI tables already exist as EFI structures, so would need
to write code to populate those using the tables already in RAM
created by coreboot. This seemed like the easier option ATM.

Signed-off-by: Matt DeVillier <matt.devillier@gmail.com>
2022-06-03 09:03:41 -06:00
Tim Crawford
2046be8d5e MdeModulePkg/BootLogoLib: Center logo 38.2% from top of screen
Use Microsoft's recommended positioning [1] for the boot logo.

> We recommend that the logo is placed with its center at 38.2% from the
> screen's top edge. This positioning is based on the golden ratio's
> visual aesthetics and matches the Windows 10 design proportions.

[1]: https://docs.microsoft.com/en-us/windows-hardware/drivers/bringup/boot-screen-components#position-the-logo-during-post
2022-06-03 09:03:41 -06:00
Tim Crawford
57ed7e7151 MdeModulePkg/Logo: Use System76 boot logo 2022-06-03 09:03:41 -06:00
Tim Crawford
a8285c29d8 UefiPayloadPkg: Enable boot logo
Signed-off-by: Tim Crawford <tcrawford@system76.com>
2022-06-03 09:03:41 -06:00
Tim Crawford
be10ebabba UefiPayloadPkg: Show boot message as progress text
Signed-off-by: Tim Crawford <tcrawford@system76.com>
2022-06-03 09:03:41 -06:00
1841 changed files with 31817 additions and 167157 deletions

View File

@@ -3,7 +3,6 @@
# #
# Copyright (c) Microsoft Corporation. # Copyright (c) Microsoft Corporation.
# Copyright (c) 2020, Hewlett Packard Enterprise Development LP. All rights reserved.<BR> # Copyright (c) 2020, Hewlett Packard Enterprise Development LP. All rights reserved.<BR>
# Copyright (c) 2022, Loongson Technology Corporation Limited. All rights reserved.<BR>
# SPDX-License-Identifier: BSD-2-Clause-Patent # SPDX-License-Identifier: BSD-2-Clause-Patent
## ##
trigger: trigger:
@@ -13,14 +12,10 @@ pr:
- master - master
- stable/* - stable/*
variables:
- template: templates/defaults.yml
jobs: jobs:
- template: templates/pr-gate-build-job.yml - template: templates/pr-gate-build-job.yml
parameters: parameters:
tool_chain_tag: 'GCC5' tool_chain_tag: 'GCC5'
vm_image: 'ubuntu-22.04' vm_image: 'ubuntu-latest'
container: ${{ variables.default_linux_image }} arch_list: "IA32,X64,ARM,AARCH64,RISCV64"
arch_list: "IA32,X64,ARM,AARCH64,RISCV64,LOONGARCH64"
usePythonVersion: '' # use Python from the container image

View File

@@ -27,7 +27,7 @@ steps:
- task: UsePythonVersion@0 - task: UsePythonVersion@0
inputs: inputs:
versionSpec: '>=3.10.6' versionSpec: '3.8.x'
architecture: 'x64' architecture: 'x64'
- script: | - script: |

View File

@@ -12,18 +12,9 @@ pr:
- master - master
- stable/* - stable/*
variables:
- template: templates/defaults.yml
jobs: jobs:
- template: templates/pr-gate-build-job.yml - template: templates/pr-gate-build-job.yml
parameters: parameters:
tool_chain_tag: 'VS2019' tool_chain_tag: 'VS2019'
vm_image: 'windows-2019' vm_image: 'windows-2019'
arch_list: "IA32,X64" arch_list: "IA32,X64"
usePythonVersion: ${{ variables.default_python_version }}
extra_install_step:
- powershell: choco install opencppcoverage; Write-Host "##vso[task.prependpath]C:\Program Files\OpenCppCoverage"
displayName: Install Code Coverage Tool
condition: and(gt(variables.pkg_count, 0), succeeded())

View File

@@ -10,6 +10,15 @@ parameters:
tool_chain_tag: '' tool_chain_tag: ''
steps: steps:
- ${{ if contains(parameters.tool_chain_tag, 'GCC') }}:
- bash: sudo apt-get update
displayName: Update apt
condition: and(gt(variables.pkg_count, 0), succeeded())
- bash: sudo apt-get install gcc g++ make uuid-dev
displayName: Install required tools
condition: and(gt(variables.pkg_count, 0), succeeded())
- task: CmdLine@1 - task: CmdLine@1
displayName: Build Base Tools from source displayName: Build Base Tools from source
inputs: inputs:

View File

@@ -1,12 +0,0 @@
## @file
# File templates/default.yml
#
# template file containing common default values
#
# Copyright (c) Red Hat, Inc.
# SPDX-License-Identifier: BSD-2-Clause-Patent
##
variables:
default_python_version: ">=3.10.6"
default_linux_image: "ghcr.io/tianocore/containers/fedora-37-test:3b3eb8f"

View File

@@ -34,26 +34,16 @@ parameters:
- name: extra_install_step - name: extra_install_step
type: stepList type: stepList
default: [] default: []
- name: usePythonVersion
type: string
default: ''
steps: steps:
- bash: |
echo "##vso[task.prependpath]${HOME}/.local/bin"
echo "new PATH=${PATH}"
displayName: Set PATH
condition: eq('${{ parameters.tool_chain_tag }}', 'GCC5')
- checkout: self - checkout: self
clean: true clean: true
fetchDepth: 1 fetchDepth: 1
- task: UsePythonVersion@0 - task: UsePythonVersion@0
inputs: inputs:
versionSpec: ${{ parameters.usePythonVersion }} versionSpec: "3.8.x"
architecture: "x64" architecture: "x64"
condition: ne('${{ parameters.usePythonVersion }}', '')
- script: pip install -r pip-requirements.txt --upgrade - script: pip install -r pip-requirements.txt --upgrade
displayName: 'Install/Upgrade pip modules' displayName: 'Install/Upgrade pip modules'
@@ -116,7 +106,7 @@ steps:
filename: stuart_build filename: stuart_build
arguments: -c ${{ parameters.build_file }} TOOL_CHAIN_TAG=${{ parameters.tool_chain_tag}} TARGET=${{ parameters.build_target}} -a ${{ parameters.build_arch}} ${{ parameters.build_flags}} ${{ parameters.run_flags }} --FlashOnly arguments: -c ${{ parameters.build_file }} TOOL_CHAIN_TAG=${{ parameters.tool_chain_tag}} TARGET=${{ parameters.build_target}} -a ${{ parameters.build_arch}} ${{ parameters.build_flags}} ${{ parameters.run_flags }} --FlashOnly
condition: and(and(gt(variables.pkg_count, 0), succeeded()), eq(variables['Run'], true)) condition: and(and(gt(variables.pkg_count, 0), succeeded()), eq(variables['Run'], true))
timeoutInMinutes: 2 timeoutInMinutes: 1
# Copy the build logs to the artifact staging directory # Copy the build logs to the artifact staging directory
- task: CopyFiles@2 - task: CopyFiles@2

View File

@@ -12,9 +12,6 @@ parameters:
tool_chain_tag: '' tool_chain_tag: ''
vm_image: '' vm_image: ''
arch_list: '' arch_list: ''
extra_install_step: []
usePythonVersion: ''
container: ''
# Build step # Build step
jobs: jobs:
@@ -24,10 +21,6 @@ jobs:
#Use matrix to speed up the build process #Use matrix to speed up the build process
strategy: strategy:
matrix: matrix:
${{ if eq(parameters.tool_chain_tag, 'GCC5') }}:
TARGET_GCC_ONLY:
Build.Pkgs: 'EmbeddedPkg'
Build.Targets: 'DEBUG,RELEASE,NO-TARGET,NOOPT'
TARGET_ARM_ARMPLATFORM: TARGET_ARM_ARMPLATFORM:
Build.Pkgs: 'ArmPkg,ArmPlatformPkg' Build.Pkgs: 'ArmPkg,ArmPlatformPkg'
Build.Targets: 'DEBUG,RELEASE,NO-TARGET,NOOPT' Build.Targets: 'DEBUG,RELEASE,NO-TARGET,NOOPT'
@@ -44,19 +37,13 @@ jobs:
Build.Pkgs: 'NetworkPkg,RedfishPkg' Build.Pkgs: 'NetworkPkg,RedfishPkg'
Build.Targets: 'DEBUG,RELEASE,NO-TARGET,NOOPT' Build.Targets: 'DEBUG,RELEASE,NO-TARGET,NOOPT'
TARGET_OTHER: TARGET_OTHER:
Build.Pkgs: 'PcAtChipsetPkg,PrmPkg,ShellPkg,SourceLevelDebugPkg,StandaloneMmPkg,SignedCapsulePkg' Build.Pkgs: 'PcAtChipsetPkg,PrmPkg,ShellPkg,StandaloneMmPkg'
Build.Targets: 'DEBUG,RELEASE,NO-TARGET,NOOPT' Build.Targets: 'DEBUG,RELEASE,NO-TARGET,NOOPT'
TARGET_FMP_FAT_TEST: TARGET_FMP_FAT_TEST:
Build.Pkgs: 'FmpDevicePkg,FatPkg,UnitTestFrameworkPkg,DynamicTablesPkg' Build.Pkgs: 'FmpDevicePkg,FatPkg,UnitTestFrameworkPkg,DynamicTablesPkg'
Build.Targets: 'DEBUG,RELEASE,NO-TARGET,NOOPT' Build.Targets: 'DEBUG,RELEASE,NO-TARGET,NOOPT'
TARGET_CRYPTO_DEBUG: TARGET_CRYPTO:
Build.Pkgs: 'CryptoPkg' Build.Pkgs: 'CryptoPkg'
Build.Targets: 'DEBUG,NOOPT'
TARGET_CRYPTO_RELEASE:
Build.Pkgs: 'CryptoPkg'
Build.Targets: 'RELEASE,NO-TARGET'
TARGET_FSP:
Build.Pkgs: 'IntelFsp2Pkg,IntelFsp2WrapperPkg'
Build.Targets: 'DEBUG,RELEASE,NO-TARGET,NOOPT' Build.Targets: 'DEBUG,RELEASE,NO-TARGET,NOOPT'
TARGET_SECURITY: TARGET_SECURITY:
Build.Pkgs: 'SecurityPkg' Build.Pkgs: 'SecurityPkg'
@@ -76,9 +63,6 @@ jobs:
pool: pool:
vmImage: ${{ parameters.vm_image }} vmImage: ${{ parameters.vm_image }}
${{ if not(eq(parameters.container, '')) }}:
container: ${{ parameters.container }}
steps: steps:
- template: pr-gate-steps.yml - template: pr-gate-steps.yml
parameters: parameters:
@@ -86,47 +70,3 @@ jobs:
build_pkgs: $(Build.Pkgs) build_pkgs: $(Build.Pkgs)
build_targets: $(Build.Targets) build_targets: $(Build.Targets)
build_archs: ${{ parameters.arch_list }} build_archs: ${{ parameters.arch_list }}
usePythonVersion: ${{ parameters.usePythonVersion }}
extra_install_step: ${{ parameters.extra_install_step }}
- job: Build_${{ parameters.tool_chain_tag }}_TARGET_CODE_COVERAGE
dependsOn: Build_${{ parameters.tool_chain_tag }}
workspace:
clean: all
pool:
vmImage: 'windows-2019'
steps:
- checkout: self
clean: true
fetchDepth: 1
submodules: true
- task: DownloadPipelineArtifact@2
displayName: 'Download Build Artifacts'
inputs:
buildType: 'current'
targetPath: '$(Build.ArtifactStagingDirectory)'
- powershell: Write-Host "##vso[task.setvariable variable=is_code_coverage]0"
displayName: Give default value for whether CodeCoverage or not
- powershell: if (Test-Path -Path $(Build.ArtifactStagingDirectory)/**/coverage.xml) {Write-Host "##vso[task.setvariable variable=is_code_coverage]1"}
displayName: Check coverage.xml exist or not
- task: CmdLine@2
displayName: Create code coverage report
inputs:
script: |
dotnet tool install -g dotnet-reportgenerator-globaltool
reportgenerator -reports:$(Build.ArtifactStagingDirectory)/**/coverage.xml -targetdir:$(Build.ArtifactStagingDirectory)/Coverage -reporttypes:Cobertura -filefilters:-*Build*;-*UnitTest*;-*Mock*;-*usr*
condition: eq(variables.is_code_coverage, 1)
- task: PublishCodeCoverageResults@1
displayName: 'Publish code coverage'
inputs:
codeCoverageTool: Cobertura
summaryFileLocation: '$(Build.ArtifactStagingDirectory)/Coverage/Cobertura.xml'
condition: eq(variables.is_code_coverage, 1)

View File

@@ -12,25 +12,16 @@ parameters:
build_pkgs: '' build_pkgs: ''
build_targets: '' build_targets: ''
build_archs: '' build_archs: ''
usePythonVersion: ''
extra_install_step: []
steps: steps:
- bash: |
echo "##vso[task.prependpath]${HOME}/.local/bin"
echo "new PATH=${PATH}"
displayName: Set PATH
condition: eq('${{ parameters.tool_chain_tag }}', 'GCC5')
- checkout: self - checkout: self
clean: true clean: true
fetchDepth: 1 fetchDepth: 1
- task: UsePythonVersion@0 - task: UsePythonVersion@0
inputs: inputs:
versionSpec: ${{ parameters.usePythonVersion }} versionSpec: '3.8.x'
architecture: "x64" architecture: 'x64'
condition: ne('${{ parameters.usePythonVersion }}', '')
- script: pip install -r pip-requirements.txt --upgrade - script: pip install -r pip-requirements.txt --upgrade
displayName: 'Install/Upgrade pip modules' displayName: 'Install/Upgrade pip modules'
@@ -46,8 +37,6 @@ steps:
displayName: fetch target branch displayName: fetch target branch
condition: eq(variables['Build.Reason'], 'PullRequest') condition: eq(variables['Build.Reason'], 'PullRequest')
- ${{ parameters.extra_install_step }}
# trim the package list if this is a PR # trim the package list if this is a PR
- task: CmdLine@1 - task: CmdLine@1
displayName: Check if ${{ parameters.build_pkgs }} need testing displayName: Check if ${{ parameters.build_pkgs }} need testing
@@ -136,7 +125,6 @@ steps:
TestSuites.xml TestSuites.xml
**/BUILD_TOOLS_REPORT.html **/BUILD_TOOLS_REPORT.html
**/OVERRIDELOG.TXT **/OVERRIDELOG.TXT
coverage.xml
flattenFolders: true flattenFolders: true
condition: succeededOrFailed() condition: succeededOrFailed()

View File

@@ -1,16 +0,0 @@
{
"image": "ghcr.io/tianocore/containers/fedora-35-dev:latest",
"postCreateCommand": "git config --global --add safe.directory * && pip install --upgrade -r pip-requirements.txt",
"customizations": {
"vscode": {
"extensions": [
"DavidAnson.vscode-markdownlint",
"ms-azuretools.vscode-docker",
"ms-vscode-remote.remote-containers",
"ms-vscode.cpptools",
"walonli.edk2-vscode",
"zachflower.uncrustify"
]
}
}
}

View File

@@ -1,52 +0,0 @@
# PrmPkg: Apply uncrustify changes
a298a84478053872ed9da660a75f182ce81b8ddc
# UnitTestFrameworkPkg: Apply uncrustify changes
7c0ad2c33810ead45b7919f8f8d0e282dae52e71
# UefiPayloadPkg: Apply uncrustify changes
e5efcf8be8a1bf59aa98875787475e3144ee4cef
# UefiCpuPkg: Apply uncrustify changes
053e878bfb5c9d5eca779789b62891add30b14ba
# StandaloneMmPkg: Apply uncrustify changes
91415a36ae7aaeabb2bbab3762f39544f9aed683
# SourceLevelDebugPkg: Apply uncrustify changes
c1e126b1196de75e0a4cda21e4551ea9bb05e059
# SignedCapsulePkg: Apply uncrustify changes
b87864896714cf3062a7bc6d577d8fbd62d105e5
# ShellPkg: Apply uncrustify changes
47d20b54f9a65b08aa602a1866c1b59a69088dfc
# SecurityPkg: Apply uncrustify changes
c411b485b63a671a1e276700cff025c73997233c
# RedfishPkg: Apply uncrustify changes
39de741e2dcb8f11e9b4438e37224797643d8451
# PcAtChipsetPkg: Apply uncrustify changes
5220bd211df890f2672c23c050082862cd1e82d6
# OvmfPkg: Apply uncrustify changes
ac0a286f4d747a4c6c603a7b225917293cbe1e9f
# NetworkPkg: Apply uncrustify changes
d1050b9dff1cace252aff86630bfdb59dff5f507
# MdePkg: Apply uncrustify changes
2f88bd3a1296c522317f1c21377876de63de5be7
# MdeModulePkg: Apply uncrustify changes
1436aea4d5707e672672a11bda72be2c63c936c3
# IntelFsp2WrapperPkg: Apply uncrustify changes
7c7184e201a90a1d2376e615e55e3f4074731468
# IntelFsp2Pkg: Apply uncrustify changes
111f2228ddf487b0ac3491e416bb3dcdcfa4f979
# FmpDevicePkg: Apply uncrustify changes
45ce0a67bb4ee80f27da93777c623f51f344f23b
# FatPkg: Apply uncrustify changes
bcdcc4160d7460c46c08c9395aae81be44ef23a9
# EmulatorPkg: Apply uncrustify changes
a550d468a6ca577d9e9c57a0eafcf2fc9fbb8c97
# EmbeddedPkg: Apply uncrustify changes
e7108d0e9655b1795c94ac372b0449f28dd907df
# DynamicTablesPkg: Apply uncrustify changes
731c67e1d77b7741a91762d17659fc9fbcb9e305
# CryptoPkg: Apply uncrustify changes
7c342378317039e632d9a1a5d4cf7c21aec8cb7a
# ArmVirtPkg: Apply uncrustify changes
2b16a4fb91b9b31c0d152588f5ac51080c6c0763
# ArmPlatformPkg: Apply uncrustify changes
40b0b23ed34f48c26d711d3e4613a4bb35eeadff
# ArmPkg: Apply uncrustify changes
429309e0c6b74792d679681a8edd0d5ae0ff850c

View File

@@ -1,24 +0,0 @@
## @file
# GitHub issue configuration file.
#
# This file is meant to direct contributors familiar with GitHub's issue tracker
# to the external resources used by TianoCore.
#
# Copyright (c) Microsoft Corporation.
# SPDX-License-Identifier: BSD-2-Clause-Patent
##
blank_issues_enabled: false
contact_links:
- name: Bugs and Feature Requests
url: https://bugzilla.tianocore.org/
about: Submit bug reports and feature requests here
- name: Reporting Security Issues
url: https://github.com/tianocore/tianocore.github.io/wiki/Reporting-Security-Issues
about: Read the wiki page that describes the process here
- name: EDK II Development Mailing List
url: https://edk2.groups.io/g/devel
about: Submit code patches and ask questions on the mailing list (devel@edk2.groups.io)
- name: EDK II Discussions
url: https://github.com/tianocore/edk2/discussions
about: You can also reach out on the Discussion section of this repository

View File

@@ -1,29 +0,0 @@
## @file
# CodeQL configuration file for edk2.
#
# Copyright (c) Microsoft Corporation.
# SPDX-License-Identifier: BSD-2-Clause-Patent
##
name: "CodeQL config"
# The following line disables the default queries. This is used because we want to enable on query at a time by
# explicitly specifying each query in a "queries" array as they are enabled.
#
# See the following for more information about adding custom queries:
# https://docs.github.com/en/code-security/code-scanning/automatically-scanning-your-code-for-vulnerabilities-and-errors/configuring-code-scanning#using-a-custom-configuration-file
#disable-default-queries: true
queries:
- name: EDK2 CodeQL Query List
uses: ./.github/codeql/edk2.qls
# We must specify a query for CodeQL to run. Until the first query is enabled, enable the security query suite but
# exclude all problem levels from impacting the results. After the first query is enabled, this filter can be relaxed
# to find the level of problems desired from the query.
query-filters:
- exclude:
problem.severity:
- warning
- recommendation

View File

@@ -1,24 +0,0 @@
---
- description: EDK2 (C++) queries
# Bring in all queries from the official cpp-queries suite so individual queries can be explicitly enabled.
- queries: '.'
from: codeql/cpp-queries
# Enable individual queries below.
- include:
id: cpp/conditionallyuninitializedvariable
- include:
id: cpp/infinite-loop-with-unsatisfiable-exit-condition
- include:
id: cpp/overflow-buffer
- include:
id: cpp/overrunning-write
- include:
id: cpp/overrunning-write-with-float
- include:
id: cpp/pointer-overflow-check
- include:
id: cpp/very-likely-overrunning-write

View File

@@ -1,36 +0,0 @@
## @file
# Dependabot configuration file to enable GitHub services for managing and updating
# dependencies.
#
# Copyright (c) Microsoft Corporation.
# SPDX-License-Identifier: BSD-2-Clause-Patent
#
# Please see the documentation for all configuration options:
# https://docs.github.com/github/administering-a-repository/configuration-options-for-dependency-updates
##
version: 2
updates:
- package-ecosystem: "pip"
directory: "/"
schedule:
interval: "daily"
commit-message:
prefix: "pip"
reviewers:
- "makubacki"
- "mdkinney"
- "spbrogan"
rebase-strategy: "disabled"
- package-ecosystem: "github-actions"
directory: "/"
schedule:
interval: "weekly"
day: "monday"
commit-message:
prefix: "GitHub Action"
reviewers:
- "makubacki"
- "mdkinney"
- "spbrogan"
rebase-strategy: "disabled"

View File

@@ -1,118 +0,0 @@
# @file
# GitHub Workflow for CodeQL Analysis
#
# Copyright (c) Microsoft Corporation.
#
# SPDX-License-Identifier: BSD-2-Clause-Patent
##
name: "CodeQL"
on:
push:
branches:
- master
pull_request:
branches:
- master
paths-ignore:
- '**/*.bat'
- '**/*.md'
- '**/*.py'
- '**/*.rst'
- '**/*.sh'
- '**/*.txt'
schedule:
# https://crontab.guru/#20_23_*_*_4
- cron: '20 23 * * 4'
jobs:
analyze:
name: Analyze
runs-on: windows-2019
permissions:
actions: read
contents: read
security-events: write
strategy:
fail-fast: false
matrix:
include:
- Package: "ArmPkg"
ArchList: "IA32,X64"
- Package: "CryptoPkg"
ArchList: "IA32"
- Package: "CryptoPkg"
ArchList: "X64"
- Package: "DynamicTablesPkg"
ArchList: "IA32,X64"
- Package: "FatPkg"
ArchList: "IA32,X64"
- Package: "FmpDevicePkg"
ArchList: "IA32,X64"
- Package: "IntelFsp2Pkg"
ArchList: "IA32,X64"
- Package: "IntelFsp2WrapperPkg"
ArchList: "IA32,X64"
- Package: "MdeModulePkg"
ArchList: "IA32"
- Package: "MdeModulePkg"
ArchList: "X64"
- Package: "MdePkg"
ArchList: "IA32,X64"
- Package: "PcAtChipsetPkg"
ArchList: "IA32,X64"
- Package: "PrmPkg"
ArchList: "IA32,X64"
- Package: "SecurityPkg"
ArchList: "IA32,X64"
- Package: "ShellPkg"
ArchList: "IA32,X64"
- Package: "SourceLevelDebugPkg"
ArchList: "IA32,X64"
- Package: "StandaloneMmPkg"
ArchList: "IA32,X64"
- Package: "UefiCpuPkg"
ArchList: "IA32,X64"
- Package: "UnitTestFrameworkPkg"
ArchList: "IA32,X64"
steps:
- name: Checkout repository
uses: actions/checkout@v3
- name: Install Python
uses: actions/setup-python@v4
with:
python-version: '3.10.6'
cache: 'pip'
cache-dependency-path: 'pip-requirements.txt'
# Initializes the CodeQL tools for scanning.
- name: Initialize CodeQL
uses: github/codeql-action/init@v2
with:
languages: 'cpp'
# CodeQL supports [ 'cpp', 'csharp', 'go', 'java', 'javascript', 'python', 'ruby' ]
# Learn more about CodeQL language support at https://codeql.github.com/docs/codeql-overview/supported-languages-and-frameworks/
config-file: ./.github/codeql/codeql-config.yml
# Note: Add new queries to codeql-config.yml file as they are enabled.
- name: Install/Upgrade pip Modules
run: pip install -r pip-requirements.txt --upgrade
- name: Setup
run: stuart_setup -c .pytool/CISettings.py -t DEBUG -a ${{ matrix.ArchList }} TOOL_CHAIN_TAG=VS2019
- name: Update
run: stuart_update -c .pytool/CISettings.py -t DEBUG -a ${{ matrix.ArchList }} TOOL_CHAIN_TAG=VS2019
- name: Build Tools From Source
run: python BaseTools/Edk2ToolsBuild.py -t VS2019
- name: CI Build
run: stuart_ci_build -c .pytool/CISettings.py -p ${{ matrix.Package }} -t DEBUG -a ${{ matrix.ArchList }} TOOL_CHAIN_TAG=VS2019
- name: Perform CodeQL Analysis
uses: github/codeql-action/analyze@v2

12
.gitmodules vendored
View File

@@ -20,15 +20,3 @@
[submodule "RedfishPkg/Library/JsonLib/jansson"] [submodule "RedfishPkg/Library/JsonLib/jansson"]
path = RedfishPkg/Library/JsonLib/jansson path = RedfishPkg/Library/JsonLib/jansson
url = https://github.com/akheron/jansson url = https://github.com/akheron/jansson
[submodule "UnitTestFrameworkPkg/Library/GoogleTestLib/googletest"]
path = UnitTestFrameworkPkg/Library/GoogleTestLib/googletest
url = https://github.com/google/googletest.git
[submodule "UnitTestFrameworkPkg/Library/SubhookLib/subhook"]
path = UnitTestFrameworkPkg/Library/SubhookLib/subhook
url = https://github.com/Zeex/subhook.git
[submodule "MdePkg/Library/BaseFdtLib/libfdt"]
path = MdePkg/Library/BaseFdtLib/libfdt
url = https://github.com/devicetree-org/pylibfdt.git
[submodule "MdePkg/Library/MipiSysTLib/mipisyst"]
path = MdePkg/Library/MipiSysTLib/mipisyst
url = https://github.com/MIPI-Alliance/public-mipi-sys-t.git

View File

@@ -38,6 +38,7 @@ pull_request_rules:
actions: actions:
queue: queue:
method: rebase method: rebase
rebase_fallback: none
name: default name: default
- name: Post a comment on a PR that can not be merged due to a merge conflict - name: Post a comment on a PR that can not be merged due to a merge conflict

View File

@@ -53,10 +53,7 @@ class Settings(CiBuildSettingsManager, UpdateSettingsManager, SetupSettingsManag
"ArmPlatformPkg", "ArmPlatformPkg",
"ArmVirtPkg", "ArmVirtPkg",
"DynamicTablesPkg", "DynamicTablesPkg",
"EmbeddedPkg",
"EmulatorPkg", "EmulatorPkg",
"IntelFsp2Pkg",
"IntelFsp2WrapperPkg",
"MdePkg", "MdePkg",
"MdeModulePkg", "MdeModulePkg",
"NetworkPkg", "NetworkPkg",
@@ -65,7 +62,6 @@ class Settings(CiBuildSettingsManager, UpdateSettingsManager, SetupSettingsManag
"UefiCpuPkg", "UefiCpuPkg",
"FmpDevicePkg", "FmpDevicePkg",
"ShellPkg", "ShellPkg",
"SignedCapsulePkg",
"StandaloneMmPkg", "StandaloneMmPkg",
"FatPkg", "FatPkg",
"CryptoPkg", "CryptoPkg",
@@ -73,7 +69,6 @@ class Settings(CiBuildSettingsManager, UpdateSettingsManager, SetupSettingsManag
"UnitTestFrameworkPkg", "UnitTestFrameworkPkg",
"OvmfPkg", "OvmfPkg",
"RedfishPkg", "RedfishPkg",
"SourceLevelDebugPkg",
"UefiPayloadPkg" "UefiPayloadPkg"
) )
@@ -84,8 +79,7 @@ class Settings(CiBuildSettingsManager, UpdateSettingsManager, SetupSettingsManag
"X64", "X64",
"ARM", "ARM",
"AARCH64", "AARCH64",
"RISCV64", "RISCV64")
"LOONGARCH64")
def GetTargetsSupported(self): def GetTargetsSupported(self):
''' return iterable of edk2 target tags supported by this build ''' ''' return iterable of edk2 target tags supported by this build '''
@@ -169,6 +163,13 @@ class Settings(CiBuildSettingsManager, UpdateSettingsManager, SetupSettingsManag
else: else:
logging.warning("Falling back to using in-tree BaseTools") logging.warning("Falling back to using in-tree BaseTools")
if is_linux and self.ActualToolChainTag.upper().startswith("GCC"):
if "AARCH64" in self.ActualArchitectures:
scopes += ("gcc_aarch64_linux",)
if "ARM" in self.ActualArchitectures:
scopes += ("gcc_arm_linux",)
if "RISCV64" in self.ActualArchitectures:
scopes += ("gcc_riscv64_unknown",)
self.ActualScopes = scopes self.ActualScopes = scopes
return self.ActualScopes return self.ActualScopes
@@ -183,8 +184,6 @@ class Settings(CiBuildSettingsManager, UpdateSettingsManager, SetupSettingsManag
"CryptoPkg/Library/OpensslLib/openssl", False)) "CryptoPkg/Library/OpensslLib/openssl", False))
rs.append(RequiredSubmodule( rs.append(RequiredSubmodule(
"UnitTestFrameworkPkg/Library/CmockaLib/cmocka", False)) "UnitTestFrameworkPkg/Library/CmockaLib/cmocka", False))
rs.append(RequiredSubmodule(
"UnitTestFrameworkPkg/Library/GoogleTestLib/googletest", False))
rs.append(RequiredSubmodule( rs.append(RequiredSubmodule(
"MdeModulePkg/Universal/RegularExpressionDxe/oniguruma", False)) "MdeModulePkg/Universal/RegularExpressionDxe/oniguruma", False))
rs.append(RequiredSubmodule( rs.append(RequiredSubmodule(
@@ -193,12 +192,6 @@ class Settings(CiBuildSettingsManager, UpdateSettingsManager, SetupSettingsManag
"BaseTools/Source/C/BrotliCompress/brotli", False)) "BaseTools/Source/C/BrotliCompress/brotli", False))
rs.append(RequiredSubmodule( rs.append(RequiredSubmodule(
"RedfishPkg/Library/JsonLib/jansson", False)) "RedfishPkg/Library/JsonLib/jansson", False))
rs.append(RequiredSubmodule(
"UnitTestFrameworkPkg/Library/SubhookLib/subhook", False))
rs.append(RequiredSubmodule(
"MdePkg/Library/BaseFdtLib/libfdt", False))
rs.append(RequiredSubmodule(
"MdePkg/Library/MipiSysTLib/mipisyst", False))
return rs return rs
def GetName(self): def GetName(self):

View File

@@ -69,13 +69,6 @@ class EccCheck(ICiBuildPlugin):
env.set_shell_var('PACKAGES_PATH', os.pathsep.join(Edk2pathObj.PackagePathList)) env.set_shell_var('PACKAGES_PATH', os.pathsep.join(Edk2pathObj.PackagePathList))
self.ECC_PASS = True self.ECC_PASS = True
abs_pkg_path = Edk2pathObj.GetAbsolutePathOnThisSystemFromEdk2RelativePath(packagename)
if abs_pkg_path is None:
tc.SetSkipped()
tc.LogStdError("No Package folder {0}".format(abs_pkg_path))
return 0
# Create temp directory # Create temp directory
temp_path = os.path.join(workspace_path, 'Build', '.pytool', 'Plugin', 'EccCheck') temp_path = os.path.join(workspace_path, 'Build', '.pytool', 'Plugin', 'EccCheck')
try: try:
@@ -84,7 +77,7 @@ class EccCheck(ICiBuildPlugin):
shutil.rmtree(temp_path) shutil.rmtree(temp_path)
# Copy package being scanned to temp_path # Copy package being scanned to temp_path
shutil.copytree ( shutil.copytree (
abs_pkg_path, os.path.join(workspace_path, packagename),
os.path.join(temp_path, packagename), os.path.join(temp_path, packagename),
symlinks=True symlinks=True
) )

View File

@@ -289,8 +289,6 @@
"unrecovered", "unrecovered",
"cmocka", "cmocka",
"unenrolling", "unenrolling",
"unconfigure", "unconfigure"
"Loongson",
"LOONGARCH"
] ]
} }

View File

@@ -290,7 +290,7 @@ class UncrustifyCheck(ICiBuildPlugin):
# This information is only used for reporting (not used here) and # This information is only used for reporting (not used here) and
# the ignore lines are being passed directly as they are given to # the ignore lines are being passed directly as they are given to
# this plugin. # this plugin.
return parse_gitignore_lines(ignored_files, "Package configuration file", self._abs_package_path) return parse_gitignore_lines(ignored_files, "Package configuration file", self._abs_workspace_path)
def _get_git_ignored_paths(self) -> List[str]: def _get_git_ignored_paths(self) -> List[str]:
"""" """"

View File

@@ -1,12 +1,5 @@
# Edk2 Continuous Integration # Edk2 Continuous Integration
This file focuses on information for those working with the `.pytools` directory
directly or interested in lower-level details about how CI works.
If you just want to get started building code, visit
[Build Instructions](https://github.com/tianocore/tianocore.github.io/wiki/Build-Instruction)
on the TianoCore wiki.
## Basic Status ## Basic Status
| Package | Windows VS2019 (IA32/X64)| Ubuntu GCC (IA32/X64/ARM/AARCH64) | Known Issues | | Package | Windows VS2019 (IA32/X64)| Ubuntu GCC (IA32/X64/ARM/AARCH64) | Known Issues |
@@ -89,18 +82,43 @@ easily and consistently running locally and in a cloud ci environment. To do
that a few steps should be followed. Details of EDKII Tools can be found in the that a few steps should be followed. Details of EDKII Tools can be found in the
[docs folder here](https://github.com/tianocore/edk2-pytool-extensions/tree/master/docs) [docs folder here](https://github.com/tianocore/edk2-pytool-extensions/tree/master/docs)
### Prerequisites
1. A supported toolchain (others might work but this is what is tested and validated)
* Windows 10:
* VS 2017 or VS 2019
* Windows SDK (for rc)
* Windows WDK (for capsules)
* Ubuntu 18.04 or Fedora
* GCC5
* Easy to add more but this is the current state
2. Python 3.7.x or newer on path
3. git on path
4. Recommended to setup and activate a python virtual environment
5. Install the requirements `pip install --upgrade -r pip-requirements.txt`
### Running CI ### Running CI
Quick notes: 1. clone your edk2 repo
2. Activate your python virtual environment in cmd window
* By default all CI plugins are opted in. 3. Get code dependencies (done only when submodules change)
* Setting the plugin to `skip` as an argument will skip running the plugin. * `stuart_setup -c .pytool/CISettings.py TOOL_CHAIN_TAG=<your tag here>`
Examples: 4. Update other dependencies (done more often)
* `stuart_update -c .pytool/CISettings.py TOOL_CHAIN_TAG=<your tag here>`
5. Run CI build (--help will give you options)
* `stuart_ci_build -c .pytool/CISettings.py TOOL_CHAIN_TAG=<your tag here>`
* -p <pkg1,pkg2,pkg3> : To build only certain packages use a CSV list
* -a <arch1,arch2,arch3>: To run only certain architectures use a CSV list
* -t <target1,target2>: To run only tests related to certain targets use a
CSV list
* By default all tests are opted in. Then given a package.ci.yaml file those
tests can be configured for a package. Finally setting the check to the
value `skip` will skip that plugin. Examples:
* `CompilerPlugin=skip` skip the build test * `CompilerPlugin=skip` skip the build test
* `GuidCheck=skip` skip the Guid check * `GuidCheck=skip` skip the Guid check
* `SpellCheck=skip` skip the spell checker * `SpellCheck=skip` skip the spell checker
* etc. * etc
* Detailed reports and logs per package are captured in the `Build` directory. 6. Detailed reports and logs per package are captured in the `Build` directory
## Current PyTool Test Capabilities ## Current PyTool Test Capabilities

File diff suppressed because it is too large Load Diff

View File

@@ -1,31 +0,0 @@
## @file
# Application to present AArch64 cpu information.
#
# Based on HelloWorld:
# Copyright (c) 2008 - 2018, Intel Corporation. All rights reserved.<BR>
# Copyright (c) 2023, Linaro Ltd. All rights reserved.<BR>
#
# SPDX-License-Identifier: BSD-2-Clause-Patent
#
##
[Defines]
INF_VERSION = 0x00010019
BASE_NAME = ArmCpuInfo
FILE_GUID = b3134491-6502-4faf-a9da-007184e32163
MODULE_TYPE = UEFI_APPLICATION
VERSION_STRING = 1.0
ENTRY_POINT = UefiMain
[Sources]
ArmCpuInfo.c
[Packages]
ArmPkg/ArmPkg.dec
MdePkg/MdePkg.dec
MdeModulePkg/MdeModulePkg.dec
[LibraryClasses]
ArmLib
UefiApplicationEntryPoint
UefiLib

View File

@@ -87,7 +87,7 @@
## options defined .pytool/Plugin/SpellCheck ## options defined .pytool/Plugin/SpellCheck
"SpellCheck": { "SpellCheck": {
"AuditOnly": True, "AuditOnly": False,
"IgnoreFiles": [ "IgnoreFiles": [
"Library/ArmSoftFloatLib/berkeley-softfloat-3/**" "Library/ArmSoftFloatLib/berkeley-softfloat-3/**"
], # use gitignore syntax to ignore errors ], # use gitignore syntax to ignore errors

View File

@@ -2,7 +2,7 @@
# ARM processor package. # ARM processor package.
# #
# Copyright (c) 2009 - 2010, Apple Inc. All rights reserved.<BR> # Copyright (c) 2009 - 2010, Apple Inc. All rights reserved.<BR>
# Copyright (c) 2011 - 2023, ARM Limited. All rights reserved. # Copyright (c) 2011 - 2021, ARM Limited. All rights reserved.
# Copyright (c) 2021, Ampere Computing LLC. All rights reserved. # Copyright (c) 2021, Ampere Computing LLC. All rights reserved.
# #
# SPDX-License-Identifier: BSD-2-Clause-Patent # SPDX-License-Identifier: BSD-2-Clause-Patent
@@ -71,11 +71,6 @@
# #
ArmSvcLib|Include/Library/ArmSvcLib.h ArmSvcLib|Include/Library/ArmSvcLib.h
## @libraryclass Provides a Monitor Call interface that will use the
# default conduit (HVC or SMC).
#
ArmMonitorLib|Include/Library/ArmMonitorLib.h
## @libraryclass Provides a default exception handler. ## @libraryclass Provides a default exception handler.
# #
DefaultExceptionHandlerLib|Include/Library/DefaultExceptionHandlerLib.h DefaultExceptionHandlerLib|Include/Library/DefaultExceptionHandlerLib.h
@@ -104,8 +99,6 @@
# Include/Guid/ArmMpCoreInfo.h # Include/Guid/ArmMpCoreInfo.h
gArmMpCoreInfoGuid = { 0xa4ee0728, 0xe5d7, 0x4ac5, {0xb2, 0x1e, 0x65, 0x8e, 0xd8, 0x57, 0xe8, 0x34} } gArmMpCoreInfoGuid = { 0xa4ee0728, 0xe5d7, 0x4ac5, {0xb2, 0x1e, 0x65, 0x8e, 0xd8, 0x57, 0xe8, 0x34} }
gArmMmuReplaceLiveTranslationEntryFuncGuid = { 0xa8b50ff3, 0x08ec, 0x4dd3, {0xbf, 0x04, 0x28, 0xbf, 0x71, 0x75, 0xc7, 0x4a} }
[Protocols.common] [Protocols.common]
## Arm System Control and Management Interface(SCMI) Base protocol ## Arm System Control and Management Interface(SCMI) Base protocol
## ArmPkg/Include/Protocol/ArmScmiBaseProtocol.h ## ArmPkg/Include/Protocol/ArmScmiBaseProtocol.h
@@ -139,11 +132,6 @@
# Define if the GICv3 controller should use the GICv2 legacy # Define if the GICv3 controller should use the GICv2 legacy
gArmTokenSpaceGuid.PcdArmGicV3WithV2Legacy|FALSE|BOOLEAN|0x00000042 gArmTokenSpaceGuid.PcdArmGicV3WithV2Legacy|FALSE|BOOLEAN|0x00000042
## Define the conduit to use for monitor calls.
# Default PcdMonitorConduitHvc = FALSE, conduit = SMC
# If PcdMonitorConduitHvc = TRUE, conduit = HVC
gArmTokenSpaceGuid.PcdMonitorConduitHvc|FALSE|BOOLEAN|0x00000047
[PcdsFeatureFlag.ARM] [PcdsFeatureFlag.ARM]
# Whether to map normal memory as non-shareable. FALSE is the safe choice, but # Whether to map normal memory as non-shareable. FALSE is the safe choice, but
# TRUE may be appropriate to fix performance problems if you don't care about # TRUE may be appropriate to fix performance problems if you don't care about
@@ -221,13 +209,6 @@
# #
gArmTokenSpaceGuid.PcdArmDmaDeviceOffset|0x0|UINT64|0x0000044 gArmTokenSpaceGuid.PcdArmDmaDeviceOffset|0x0|UINT64|0x0000044
#
# Boot the Uefi Shell instead of UiApp when no valid boot option is found.
# This is useful in CI environment so that startup.nsh can be launched.
# The default value is FALSE.
#
gArmTokenSpaceGuid.PcdUefiShellDefaultBootEnable|FALSE|BOOLEAN|0x0000052
[PcdsFixedAtBuild.common, PcdsPatchableInModule.common] [PcdsFixedAtBuild.common, PcdsPatchableInModule.common]
gArmTokenSpaceGuid.PcdFdBaseAddress|0|UINT64|0x0000002B gArmTokenSpaceGuid.PcdFdBaseAddress|0|UINT64|0x0000002B
gArmTokenSpaceGuid.PcdFvBaseAddress|0|UINT64|0x0000002D gArmTokenSpaceGuid.PcdFvBaseAddress|0|UINT64|0x0000002D

View File

@@ -113,6 +113,7 @@
ArmPkg/Library/DebugAgentSymbolsBaseLib/DebugAgentSymbolsBaseLib.inf ArmPkg/Library/DebugAgentSymbolsBaseLib/DebugAgentSymbolsBaseLib.inf
ArmPkg/Library/DebugPeCoffExtraActionLib/DebugPeCoffExtraActionLib.inf ArmPkg/Library/DebugPeCoffExtraActionLib/DebugPeCoffExtraActionLib.inf
ArmPkg/Library/DefaultExceptionHandlerLib/DefaultExceptionHandlerLib.inf ArmPkg/Library/DefaultExceptionHandlerLib/DefaultExceptionHandlerLib.inf
ArmPkg/Library/RvdPeCoffExtraActionLib/RvdPeCoffExtraActionLib.inf
ArmPkg/Library/SemiHostingDebugLib/SemiHostingDebugLib.inf ArmPkg/Library/SemiHostingDebugLib/SemiHostingDebugLib.inf
ArmPkg/Library/SemiHostingSerialPortLib/SemiHostingSerialPortLib.inf ArmPkg/Library/SemiHostingSerialPortLib/SemiHostingSerialPortLib.inf
ArmPkg/Library/SemihostLib/SemihostLib.inf ArmPkg/Library/SemihostLib/SemihostLib.inf
@@ -130,12 +131,9 @@
ArmPkg/Library/ArmGenericTimerPhyCounterLib/ArmGenericTimerPhyCounterLib.inf ArmPkg/Library/ArmGenericTimerPhyCounterLib/ArmGenericTimerPhyCounterLib.inf
ArmPkg/Library/ArmGenericTimerVirtCounterLib/ArmGenericTimerVirtCounterLib.inf ArmPkg/Library/ArmGenericTimerVirtCounterLib/ArmGenericTimerVirtCounterLib.inf
ArmPkg/Library/ArmTrngLib/ArmTrngLib.inf
ArmPkg/Library/ArmHvcLib/ArmHvcLib.inf
ArmPkg/Library/ArmHvcLibNull/ArmHvcLibNull.inf
ArmPkg/Library/ArmMonitorLib/ArmMonitorLib.inf
ArmPkg/Library/ArmSmcLib/ArmSmcLib.inf ArmPkg/Library/ArmSmcLib/ArmSmcLib.inf
ArmPkg/Library/ArmSmcLibNull/ArmSmcLibNull.inf ArmPkg/Library/ArmSmcLibNull/ArmSmcLibNull.inf
ArmPkg/Library/ArmHvcLib/ArmHvcLib.inf
ArmPkg/Library/ArmSvcLib/ArmSvcLib.inf ArmPkg/Library/ArmSvcLib/ArmSvcLib.inf
ArmPkg/Library/OpteeLib/OpteeLib.inf ArmPkg/Library/OpteeLib/OpteeLib.inf
@@ -163,10 +161,8 @@
ArmPkg/Universal/Smbios/OemMiscLibNull/OemMiscLibNull.inf ArmPkg/Universal/Smbios/OemMiscLibNull/OemMiscLibNull.inf
[Components.AARCH64] [Components.AARCH64]
ArmPkg/Drivers/ArmPsciMpServicesDxe/ArmPsciMpServicesDxe.inf
ArmPkg/Drivers/MmCommunicationDxe/MmCommunication.inf ArmPkg/Drivers/MmCommunicationDxe/MmCommunication.inf
ArmPkg/Library/ArmMmuLib/ArmMmuPeiLib.inf ArmPkg/Library/ArmMmuLib/ArmMmuPeiLib.inf
ArmPkg/Application/ArmCpuInfo/ArmCpuInfo.inf
[Components.AARCH64, Components.ARM] [Components.AARCH64, Components.ARM]
ArmPkg/Library/StandaloneMmMmuLib/ArmMmuStandaloneMmLib.inf ArmPkg/Library/StandaloneMmMmuLib/ArmMmuStandaloneMmLib.inf

View File

@@ -137,7 +137,7 @@ CpuArchEventProtocolNotify (
DEBUG (( DEBUG ((
DEBUG_ERROR, DEBUG_ERROR,
"%a: Cpu->RegisterInterruptHandler() - %r\n", "%a: Cpu->RegisterInterruptHandler() - %r\n",
__func__, __FUNCTION__,
Status Status
)); ));
return; return;
@@ -153,7 +153,7 @@ CpuArchEventProtocolNotify (
DEBUG (( DEBUG ((
DEBUG_ERROR, DEBUG_ERROR,
"%a: Cpu->RegisterInterruptHandler() - %r\n", "%a: Cpu->RegisterInterruptHandler() - %r\n",
__func__, __FUNCTION__,
Status Status
)); ));
} }

View File

@@ -366,9 +366,10 @@ ArmGicIsInterruptEnabled (
FeaturePcdGet (PcdArmGicV3WithV2Legacy) || FeaturePcdGet (PcdArmGicV3WithV2Legacy) ||
SourceIsSpi (Source)) SourceIsSpi (Source))
{ {
Interrupts = MmioRead32 ( Interrupts = ((MmioRead32 (
GicDistributorBase + ARM_GIC_ICDISER + (4 * RegOffset) GicDistributorBase + ARM_GIC_ICDISER + (4 * RegOffset)
); )
& (1 << RegShift)) != 0);
} else { } else {
GicCpuRedistributorBase = GicGetCpuRedistributorBase ( GicCpuRedistributorBase = GicGetCpuRedistributorBase (
GicRedistributorBase, GicRedistributorBase,

File diff suppressed because it is too large Load Diff

View File

@@ -1,56 +0,0 @@
## @file
# ARM MP services protocol driver
#
# Copyright (c) 2022, Qualcomm Innovation Center, Inc. All rights reserved.<BR>
#
# SPDX-License-Identifier: BSD-2-Clause-Patent
#
##
[Defines]
INF_VERSION = 1.27
BASE_NAME = ArmPsciMpServicesDxe
FILE_GUID = 007ab472-dc4a-4df8-a5c2-abb4a327278c
MODULE_TYPE = DXE_DRIVER
VERSION_STRING = 1.0
ENTRY_POINT = ArmPsciMpServicesDxeInitialize
[Sources.Common]
ArmPsciMpServicesDxe.c
MpFuncs.S
MpServicesInternal.h
[Packages]
ArmPkg/ArmPkg.dec
ArmPlatformPkg/ArmPlatformPkg.dec
EmbeddedPkg/EmbeddedPkg.dec
MdePkg/MdePkg.dec
MdeModulePkg/MdeModulePkg.dec
[LibraryClasses]
ArmLib
ArmMmuLib
ArmSmcLib
BaseMemoryLib
CacheMaintenanceLib
CpuExceptionHandlerLib
DebugLib
HobLib
MemoryAllocationLib
UefiBootServicesTableLib
UefiDriverEntryPoint
UefiLib
[Protocols]
gEfiMpServiceProtocolGuid ## PRODUCES
gEfiLoadedImageProtocolGuid ## CONSUMES
[Guids]
gArmMpCoreInfoGuid
[Depex]
TRUE
[BuildOptions]
GCC:*_*_*_CC_FLAGS = -mstrict-align

View File

@@ -1,74 +0,0 @@
#===============================================================================
# Copyright (c) 2022 Qualcomm Innovation Center, Inc. All rights reserved.
#
# SPDX-License-Identifier: BSD-2-Clause-Patent
#===============================================================================
.text
.align 3
#include <AsmMacroIoLibV8.h>
#include <IndustryStandard/ArmStdSmc.h>
#include <Library/ArmLib.h>
#include "MpServicesInternal.h"
GCC_ASM_IMPORT (gApStacksBase)
GCC_ASM_IMPORT (gProcessorIDs)
GCC_ASM_IMPORT (ApProcedure)
GCC_ASM_IMPORT (gApStackSize)
GCC_ASM_IMPORT (gTcr)
GCC_ASM_IMPORT (gTtbr0)
GCC_ASM_IMPORT (gMair)
GCC_ASM_EXPORT (ApEntryPoint)
// Entry-point for the AP
// VOID
// ApEntryPoint (
// VOID
// );
ASM_PFX(ApEntryPoint):
// Configure the MMU and caches
ldr x0, gTcr
bl ArmSetTCR
ldr x0, gTtbr0
bl ArmSetTTBR0
ldr x0, gMair
bl ArmSetMAIR
bl ArmDisableAlignmentCheck
bl ArmEnableStackAlignmentCheck
bl ArmEnableInstructionCache
bl ArmEnableDataCache
bl ArmEnableMmu
mrs x0, mpidr_el1
// Mask the non-affinity bits
bic x0, x0, 0x00ff000000
and x0, x0, 0xffffffffff
ldr x1, gProcessorIDs
mov x2, 0 // x2 = processor index
// Find index in gProcessorIDs for current processor
1:
ldr x3, [x1, x2, lsl #3] // x4 = gProcessorIDs + x2 * 8
cmp x3, #-1 // check if we've reached the end of gProcessorIDs
beq ProcessorNotFound
add x2, x2, 1 // x2++
cmp x0, x3 // if mpidr_el1 != gProcessorIDs[x] then loop
bne 1b
// Calculate stack address
// x2 contains the index for the current processor plus 1
ldr x0, gApStacksBase
ldr x1, gApStackSize
mul x3, x2, x1 // x3 = (ProcessorIndex + 1) * gApStackSize
add sp, x0, x3 // sp = gApStacksBase + x3
mov x29, xzr
bl ApProcedure // doesn't return
ProcessorNotFound:
// Turn off the processor
MOV32 (w0, ARM_SMC_ID_PSCI_CPU_OFF)
smc #0
b .

View File

@@ -1,345 +0,0 @@
/** @file
Copyright (c) 2022, Qualcomm Innovation Center, Inc. All rights reserved.<BR>
Copyright (c) 2006 - 2011, Intel Corporation. All rights reserved.<BR>
Portions copyright (c) 2011, Apple Inc. All rights reserved.
SPDX-License-Identifier: BSD-2-Clause-Patent
**/
#ifndef MP_SERVICES_INTERNAL_H_
#define MP_SERVICES_INTERNAL_H_
#include <Protocol/Cpu.h>
#include <Protocol/MpService.h>
#include <Library/BaseLib.h>
#include <Library/UefiLib.h>
#define AP_STACK_SIZE 0x1000
//
// Internal Data Structures
//
//
// AP state
//
// The state transitions for an AP when it processes a procedure are:
// Idle ----> Ready ----> Busy ----> Finished ----> Idle
// [BSP] [BSP] [AP] [BSP]
//
typedef enum {
CpuStateIdle,
CpuStateReady,
CpuStateBlocked,
CpuStateBusy,
CpuStateFinished,
CpuStateDisabled
} CPU_STATE;
//
// Define Individual Processor Data block.
//
typedef struct {
EFI_PROCESSOR_INFORMATION Info;
EFI_AP_PROCEDURE Procedure;
VOID *Parameter;
CPU_STATE State;
EFI_EVENT CheckThisAPEvent;
EFI_EVENT WaitEvent;
UINTN Timeout;
UINTN TimeTaken;
BOOLEAN TimeoutActive;
BOOLEAN *SingleApFinished;
} CPU_AP_DATA;
//
// Define MP data block which consumes individual processor block.
//
typedef struct {
UINTN NumberOfProcessors;
UINTN NumberOfEnabledProcessors;
EFI_EVENT CheckAllAPsEvent;
EFI_EVENT AllWaitEvent;
UINTN FinishCount;
UINTN StartCount;
EFI_AP_PROCEDURE Procedure;
VOID *ProcedureArgument;
BOOLEAN SingleThread;
UINTN StartedNumber;
CPU_AP_DATA *CpuData;
UINTN *FailedList;
UINTN FailedListIndex;
UINTN AllTimeout;
UINTN AllTimeTaken;
BOOLEAN AllTimeoutActive;
} CPU_MP_DATA;
/** Secondary core entry point.
**/
VOID
ApEntryPoint (
VOID
);
/** C entry-point for the AP.
This function gets called from the assembly function ApEntryPoint.
**/
VOID
ApProcedure (
VOID
);
/** Turns on the specified core using PSCI and executes the user-supplied
function that's been configured via a previous call to SetApProcedure.
@param ProcessorIndex The index of the core to turn on.
@retval EFI_SUCCESS The processor was successfully turned on.
@retval EFI_DEVICE_ERROR An error occurred turning the processor on.
**/
STATIC
EFI_STATUS
EFIAPI
DispatchCpu (
IN UINTN ProcessorIndex
);
/** Returns whether the specified processor is the BSP.
@param[in] ProcessorIndex The index the processor to check.
@return TRUE if the processor is the BSP, FALSE otherwise.
**/
STATIC
BOOLEAN
IsProcessorBSP (
UINTN ProcessorIndex
);
/** Returns whether the processor executing this function is the BSP.
@return Whether the current processor is the BSP.
**/
STATIC
BOOLEAN
IsCurrentProcessorBSP (
VOID
);
/** Returns whether the specified processor is enabled.
@param[in] ProcessorIndex The index of the processor to check.
@return TRUE if the processor is enabled, FALSE otherwise.
**/
STATIC
BOOLEAN
IsProcessorEnabled (
UINTN ProcessorIndex
);
/** Configures the processor context with the user-supplied procedure and
argument.
@param CpuData The processor context.
@param Procedure The user-supplied procedure.
@param ProcedureArgument The user-supplied procedure argument.
**/
STATIC
VOID
SetApProcedure (
IN CPU_AP_DATA *CpuData,
IN EFI_AP_PROCEDURE Procedure,
IN VOID *ProcedureArgument
);
/**
Get the Application Processors state.
@param[in] CpuData The pointer to CPU_AP_DATA of specified AP
@return The AP status
**/
CPU_STATE
GetApState (
IN CPU_AP_DATA *CpuData
);
/** Returns the index of the next processor that is blocked.
@param[out] NextNumber The index of the next blocked processor.
@retval EFI_SUCCESS Successfully found the next blocked processor.
@retval EFI_NOT_FOUND There are no blocked processors.
**/
STATIC
EFI_STATUS
GetNextBlockedNumber (
OUT UINTN *NextNumber
);
/** Stalls the BSP for the minimum of gPollInterval and Timeout.
@param[in] Timeout The time limit in microseconds remaining for
APs to return from Procedure.
@retval StallTime Time of execution stall.
**/
STATIC
UINTN
CalculateAndStallInterval (
IN UINTN Timeout
);
/** Sets up the state for the StartupAllAPs function.
@param SingleThread Whether the APs will execute sequentially.
**/
STATIC
VOID
StartupAllAPsPrepareState (
IN BOOLEAN SingleThread
);
/** Handles execution of StartupAllAPs when a WaitEvent has been specified.
@param Procedure The user-supplied procedure.
@param ProcedureArgument The user-supplied procedure argument.
@param WaitEvent The wait event to be signaled when the work is
complete or a timeout has occurred.
@param TimeoutInMicroseconds The timeout for the work to be completed. Zero
indicates an infinite timeout.
@param SingleThread Whether the APs will execute sequentially.
@param FailedCpuList User-supplied pointer for list of failed CPUs.
@return EFI_SUCCESS on success.
**/
STATIC
EFI_STATUS
StartupAllAPsWithWaitEvent (
IN EFI_AP_PROCEDURE Procedure,
IN VOID *ProcedureArgument,
IN EFI_EVENT WaitEvent,
IN UINTN TimeoutInMicroseconds,
IN BOOLEAN SingleThread,
IN UINTN **FailedCpuList
);
/** Handles execution of StartupAllAPs when no wait event has been specified.
@param Procedure The user-supplied procedure.
@param ProcedureArgument The user-supplied procedure argument.
@param TimeoutInMicroseconds The timeout for the work to be completed. Zero
indicates an infinite timeout.
@param SingleThread Whether the APs will execute sequentially.
@param FailedCpuList User-supplied pointer for list of failed CPUs.
@return EFI_SUCCESS on success.
**/
STATIC
EFI_STATUS
StartupAllAPsNoWaitEvent (
IN EFI_AP_PROCEDURE Procedure,
IN VOID *ProcedureArgument,
IN UINTN TimeoutInMicroseconds,
IN BOOLEAN SingleThread,
IN UINTN **FailedCpuList
);
/** Adds the specified processor the list of failed processors.
@param ProcessorIndex The processor index to add.
@param ApState Processor state.
**/
STATIC
VOID
AddProcessorToFailedList (
UINTN ProcessorIndex,
CPU_STATE ApState
);
/** Handles the StartupAllAPs case where the timeout has occurred.
**/
STATIC
VOID
ProcessStartupAllAPsTimeout (
VOID
);
/**
If a timeout is specified in StartupAllAps(), a timer is set, which invokes
this procedure periodically to check whether all APs have finished.
@param[in] Event The WaitEvent the user supplied.
@param[in] Context The event context.
**/
STATIC
VOID
EFIAPI
CheckAllAPsStatus (
IN EFI_EVENT Event,
IN VOID *Context
);
/** Invoked periodically via a timer to check the state of the processor.
@param Event The event supplied by the timer expiration.
@param Context The processor context.
**/
STATIC
VOID
EFIAPI
CheckThisAPStatus (
IN EFI_EVENT Event,
IN VOID *Context
);
/**
This function is called by all processors (both BSP and AP) once and collects
MP related data.
@param BSP TRUE if the processor is the BSP.
@param Mpidr The MPIDR for the specified processor. This should be
the full MPIDR and not only the affinity bits.
@param ProcessorIndex The index of the processor.
@return EFI_SUCCESS if the data for the processor collected and filled in.
**/
STATIC
EFI_STATUS
FillInProcessorInformation (
IN BOOLEAN BSP,
IN UINTN Mpidr,
IN UINTN ProcessorIndex
);
/**
Event notification function called when the EFI_EVENT_GROUP_READY_TO_BOOT is
signaled. After this point, non-blocking mode is no longer allowed.
@param Event Event whose notification function is being invoked.
@param Context The pointer to the notification function's context,
which is implementation-dependent.
**/
STATIC
VOID
EFIAPI
ReadyToBootSignaled (
IN EFI_EVENT Event,
IN VOID *Context
);
#endif /* MP_SERVICES_INTERNAL_H_ */

View File

@@ -145,8 +145,8 @@ ScmiCommandExecute (
/** Internal common function useful for common protocol discovery messages. /** Internal common function useful for common protocol discovery messages.
@param[in] ProtocolId Protocol Id of the protocol. @param[in] ProtocolId Protocol Id of the the protocol.
@param[in] MessageId Message Id of the message. @param[in] MesaageId Message Id of the message.
@param[out] ReturnValues SCMI response return values. @param[out] ReturnValues SCMI response return values.

View File

@@ -236,7 +236,12 @@ ClockDescribeRates (
*TotalRates = NUM_RATES (DescribeRates->NumRatesFlags) *TotalRates = NUM_RATES (DescribeRates->NumRatesFlags)
+ NUM_REMAIN_RATES (DescribeRates->NumRatesFlags); + NUM_REMAIN_RATES (DescribeRates->NumRatesFlags);
if (*Format == ScmiClockRateFormatDiscrete) {
RequiredArraySize = (*TotalRates) * sizeof (UINT64); RequiredArraySize = (*TotalRates) * sizeof (UINT64);
} else {
// We need to return triplet of 64 bit value for each rate
RequiredArraySize = (*TotalRates) * 3 * sizeof (UINT64);
}
if (RequiredArraySize > (*RateArraySize)) { if (RequiredArraySize > (*RateArraySize)) {
*RateArraySize = RequiredArraySize; *RateArraySize = RequiredArraySize;
@@ -254,6 +259,7 @@ ClockDescribeRates (
ConvertTo64Bit (Rate->Low, Rate->High); ConvertTo64Bit (Rate->Low, Rate->High);
} }
} else { } else {
for (RateNo = 0; RateNo < NUM_RATES (DescribeRates->NumRatesFlags); RateNo++) {
// Linear clock rates from minimum to maximum in steps // Linear clock rates from minimum to maximum in steps
// Minimum clock rate. // Minimum clock rate.
Rate = &DescribeRates->Rates[RateOffset++]; Rate = &DescribeRates->Rates[RateOffset++];
@@ -270,6 +276,7 @@ ClockDescribeRates (
RateArray[RateIndex++].ContinuousRate.Step = RateArray[RateIndex++].ContinuousRate.Step =
ConvertTo64Bit (Rate->Low, Rate->High); ConvertTo64Bit (Rate->Low, Rate->High);
} }
}
} while (NUM_REMAIN_RATES (DescribeRates->NumRatesFlags) != 0); } while (NUM_REMAIN_RATES (DescribeRates->NumRatesFlags) != 0);
// Update RateArraySize with RequiredArraySize. // Update RateArraySize with RequiredArraySize.

View File

@@ -64,10 +64,6 @@ PageAttributeToGcdAttribute (
} }
// Determine protection attributes // Determine protection attributes
if ((PageAttributes & TT_AF) == 0) {
GcdAttributes |= EFI_MEMORY_RP;
}
if (((PageAttributes & TT_AP_MASK) == TT_AP_NO_RO) || if (((PageAttributes & TT_AP_MASK) == TT_AP_NO_RO) ||
((PageAttributes & TT_AP_MASK) == TT_AP_RO_RO)) ((PageAttributes & TT_AP_MASK) == TT_AP_RO_RO))
{ {
@@ -83,23 +79,6 @@ PageAttributeToGcdAttribute (
return GcdAttributes; return GcdAttributes;
} }
/**
Convert an arch specific set of page attributes into a mask
of EFI_MEMORY_xx constants.
@param PageAttributes The set of page attributes.
@retval The mask of EFI_MEMORY_xx constants.
**/
UINT64
RegionAttributeToGcdAttribute (
IN UINTN PageAttributes
)
{
return PageAttributeToGcdAttribute (PageAttributes);
}
STATIC STATIC
UINT64 UINT64
GetFirstPageAttribute ( GetFirstPageAttribute (
@@ -322,9 +301,7 @@ EfiAttributeToArmAttribute (
} }
// Set the access flag to match the block attributes // Set the access flag to match the block attributes
if ((EfiAttributes & EFI_MEMORY_RP) == 0) {
ArmAttributes |= TT_AF; ArmAttributes |= TT_AF;
}
// Determine protection attributes // Determine protection attributes
if ((EfiAttributes & EFI_MEMORY_RO) != 0) { if ((EfiAttributes & EFI_MEMORY_RO) != 0) {

View File

@@ -13,15 +13,6 @@ SPDX-License-Identifier: BSD-2-Clause-Patent
#include <Library/MemoryAllocationLib.h> #include <Library/MemoryAllocationLib.h>
#include "CpuDxe.h" #include "CpuDxe.h"
/**
Convert a set of ARM short descriptor section attributes into a mask
of EFI_MEMORY_xx constants.
@param SectionAttributes The set of page attributes.
@param GcdAttributes Pointer to the return value.
**/
STATIC
EFI_STATUS EFI_STATUS
SectionToGcdAttributes ( SectionToGcdAttributes (
IN UINT32 SectionAttributes, IN UINT32 SectionAttributes,
@@ -59,16 +50,23 @@ SectionToGcdAttributes (
// determine protection attributes // determine protection attributes
switch (SectionAttributes & TT_DESCRIPTOR_SECTION_AP_MASK) { switch (SectionAttributes & TT_DESCRIPTOR_SECTION_AP_MASK) {
case TT_DESCRIPTOR_SECTION_AP_NO_RW: case TT_DESCRIPTOR_SECTION_AP_NO_NO: // no read, no write
// *GcdAttributes |= EFI_MEMORY_RO | EFI_MEMORY_RP;
break;
case TT_DESCRIPTOR_SECTION_AP_RW_NO:
case TT_DESCRIPTOR_SECTION_AP_RW_RW: case TT_DESCRIPTOR_SECTION_AP_RW_RW:
// normal read/write access, do not add additional attributes // normal read/write access, do not add additional attributes
break; break;
// read only cases map to write-protect // read only cases map to write-protect
case TT_DESCRIPTOR_SECTION_AP_NO_RO: case TT_DESCRIPTOR_SECTION_AP_RO_NO:
case TT_DESCRIPTOR_SECTION_AP_RO_RO: case TT_DESCRIPTOR_SECTION_AP_RO_RO:
*GcdAttributes |= EFI_MEMORY_RO; *GcdAttributes |= EFI_MEMORY_RO;
break; break;
default:
return EFI_UNSUPPORTED;
} }
// now process eXectue Never attribute // now process eXectue Never attribute
@@ -76,42 +74,9 @@ SectionToGcdAttributes (
*GcdAttributes |= EFI_MEMORY_XP; *GcdAttributes |= EFI_MEMORY_XP;
} }
if ((SectionAttributes & TT_DESCRIPTOR_SECTION_AF) == 0) {
*GcdAttributes |= EFI_MEMORY_RP;
}
return EFI_SUCCESS; return EFI_SUCCESS;
} }
/**
Convert an arch specific set of page attributes into a mask
of EFI_MEMORY_xx constants.
@param PageAttributes The set of page attributes.
@retval The mask of EFI_MEMORY_xx constants.
**/
UINT64
RegionAttributeToGcdAttribute (
IN UINTN PageAttributes
)
{
UINT64 Result;
SectionToGcdAttributes (PageAttributes, &Result);
return Result;
}
/**
Convert a set of ARM short descriptor page attributes into a mask
of EFI_MEMORY_xx constants.
@param PageAttributes The set of page attributes.
@param GcdAttributes Pointer to the return value.
**/
STATIC
EFI_STATUS EFI_STATUS
PageToGcdAttributes ( PageToGcdAttributes (
IN UINT32 PageAttributes, IN UINT32 PageAttributes,
@@ -149,16 +114,23 @@ PageToGcdAttributes (
// determine protection attributes // determine protection attributes
switch (PageAttributes & TT_DESCRIPTOR_PAGE_AP_MASK) { switch (PageAttributes & TT_DESCRIPTOR_PAGE_AP_MASK) {
case TT_DESCRIPTOR_PAGE_AP_NO_RW: case TT_DESCRIPTOR_PAGE_AP_NO_NO: // no read, no write
// *GcdAttributes |= EFI_MEMORY_RO | EFI_MEMORY_RP;
break;
case TT_DESCRIPTOR_PAGE_AP_RW_NO:
case TT_DESCRIPTOR_PAGE_AP_RW_RW: case TT_DESCRIPTOR_PAGE_AP_RW_RW:
// normal read/write access, do not add additional attributes // normal read/write access, do not add additional attributes
break; break;
// read only cases map to write-protect // read only cases map to write-protect
case TT_DESCRIPTOR_PAGE_AP_NO_RO: case TT_DESCRIPTOR_PAGE_AP_RO_NO:
case TT_DESCRIPTOR_PAGE_AP_RO_RO: case TT_DESCRIPTOR_PAGE_AP_RO_RO:
*GcdAttributes |= EFI_MEMORY_RO; *GcdAttributes |= EFI_MEMORY_RO;
break; break;
default:
return EFI_UNSUPPORTED;
} }
// now process eXectue Never attribute // now process eXectue Never attribute
@@ -166,10 +138,6 @@ PageToGcdAttributes (
*GcdAttributes |= EFI_MEMORY_XP; *GcdAttributes |= EFI_MEMORY_XP;
} }
if ((PageAttributes & TT_DESCRIPTOR_PAGE_AF) == 0) {
*GcdAttributes |= EFI_MEMORY_RP;
}
return EFI_SUCCESS; return EFI_SUCCESS;
} }
@@ -197,8 +165,7 @@ SyncCacheConfigPage (
// Convert SectionAttributes into PageAttributes // Convert SectionAttributes into PageAttributes
NextPageAttributes = NextPageAttributes =
TT_DESCRIPTOR_CONVERT_TO_PAGE_CACHE_POLICY (*NextSectionAttributes) | TT_DESCRIPTOR_CONVERT_TO_PAGE_CACHE_POLICY (*NextSectionAttributes, 0) |
TT_DESCRIPTOR_CONVERT_TO_PAGE_AF (*NextSectionAttributes) |
TT_DESCRIPTOR_CONVERT_TO_PAGE_AP (*NextSectionAttributes); TT_DESCRIPTOR_CONVERT_TO_PAGE_AP (*NextSectionAttributes);
// obtain page table base // obtain page table base
@@ -207,7 +174,7 @@ SyncCacheConfigPage (
for (i = 0; i < TRANSLATION_TABLE_PAGE_COUNT; i++) { for (i = 0; i < TRANSLATION_TABLE_PAGE_COUNT; i++) {
if ((SecondLevelTable[i] & TT_DESCRIPTOR_PAGE_TYPE_MASK) == TT_DESCRIPTOR_PAGE_TYPE_PAGE) { if ((SecondLevelTable[i] & TT_DESCRIPTOR_PAGE_TYPE_MASK) == TT_DESCRIPTOR_PAGE_TYPE_PAGE) {
// extract attributes (cacheability and permissions) // extract attributes (cacheability and permissions)
PageAttributes = SecondLevelTable[i] & (TT_DESCRIPTOR_PAGE_CACHE_POLICY_MASK | TT_DESCRIPTOR_PAGE_AP_MASK | TT_DESCRIPTOR_PAGE_AF); PageAttributes = SecondLevelTable[i] & (TT_DESCRIPTOR_PAGE_CACHE_POLICY_MASK | TT_DESCRIPTOR_PAGE_AP_MASK);
if (NextPageAttributes == 0) { if (NextPageAttributes == 0) {
// start on a new region // start on a new region
@@ -245,8 +212,7 @@ SyncCacheConfigPage (
// Convert back PageAttributes into SectionAttributes // Convert back PageAttributes into SectionAttributes
*NextSectionAttributes = *NextSectionAttributes =
TT_DESCRIPTOR_CONVERT_TO_SECTION_CACHE_POLICY (NextPageAttributes) | TT_DESCRIPTOR_CONVERT_TO_SECTION_CACHE_POLICY (NextPageAttributes, 0) |
TT_DESCRIPTOR_CONVERT_TO_SECTION_AF (NextPageAttributes) |
TT_DESCRIPTOR_CONVERT_TO_SECTION_AP (NextPageAttributes); TT_DESCRIPTOR_CONVERT_TO_SECTION_AP (NextPageAttributes);
return EFI_SUCCESS; return EFI_SUCCESS;
@@ -290,14 +256,14 @@ SyncCacheConfig (
FirstLevelTable = (ARM_FIRST_LEVEL_DESCRIPTOR *)(ArmGetTTBR0BaseAddress ()); FirstLevelTable = (ARM_FIRST_LEVEL_DESCRIPTOR *)(ArmGetTTBR0BaseAddress ());
// Get the first region // Get the first region
NextSectionAttributes = FirstLevelTable[0] & (TT_DESCRIPTOR_SECTION_CACHE_POLICY_MASK | TT_DESCRIPTOR_SECTION_AP_MASK | TT_DESCRIPTOR_SECTION_AF); NextSectionAttributes = FirstLevelTable[0] & (TT_DESCRIPTOR_SECTION_CACHE_POLICY_MASK | TT_DESCRIPTOR_SECTION_AP_MASK);
// iterate through each 1MB descriptor // iterate through each 1MB descriptor
NextRegionBase = NextRegionLength = 0; NextRegionBase = NextRegionLength = 0;
for (i = 0; i < TRANSLATION_TABLE_SECTION_COUNT; i++) { for (i = 0; i < TRANSLATION_TABLE_SECTION_COUNT; i++) {
if ((FirstLevelTable[i] & TT_DESCRIPTOR_SECTION_TYPE_MASK) == TT_DESCRIPTOR_SECTION_TYPE_SECTION) { if ((FirstLevelTable[i] & TT_DESCRIPTOR_SECTION_TYPE_MASK) == TT_DESCRIPTOR_SECTION_TYPE_SECTION) {
// extract attributes (cacheability and permissions) // extract attributes (cacheability and permissions)
SectionAttributes = FirstLevelTable[i] & (TT_DESCRIPTOR_SECTION_CACHE_POLICY_MASK | TT_DESCRIPTOR_SECTION_AP_MASK | TT_DESCRIPTOR_SECTION_AF); SectionAttributes = FirstLevelTable[i] & (TT_DESCRIPTOR_SECTION_CACHE_POLICY_MASK | TT_DESCRIPTOR_SECTION_AP_MASK);
if (NextSectionAttributes == 0) { if (NextSectionAttributes == 0) {
// start on a new region // start on a new region
@@ -417,10 +383,6 @@ EfiAttributeToArmAttribute (
ArmAttributes |= TT_DESCRIPTOR_SECTION_XN_MASK; ArmAttributes |= TT_DESCRIPTOR_SECTION_XN_MASK;
} }
if ((EfiAttributes & EFI_MEMORY_RP) == 0) {
ArmAttributes |= TT_DESCRIPTOR_SECTION_AF;
}
return ArmAttributes; return ArmAttributes;
} }
@@ -437,7 +399,7 @@ GetMemoryRegionPage (
UINT32 PageDescriptor; UINT32 PageDescriptor;
// Convert the section attributes into page attributes // Convert the section attributes into page attributes
PageAttributes = ConvertSectionAttributesToPageAttributes (*RegionAttributes); PageAttributes = ConvertSectionAttributesToPageAttributes (*RegionAttributes, 0);
// Calculate index into first level translation table for start of modification // Calculate index into first level translation table for start of modification
TableIndex = ((*BaseAddress) & TT_DESCRIPTOR_PAGE_INDEX_MASK) >> TT_DESCRIPTOR_PAGE_BASE_SHIFT; TableIndex = ((*BaseAddress) & TT_DESCRIPTOR_PAGE_INDEX_MASK) >> TT_DESCRIPTOR_PAGE_BASE_SHIFT;
@@ -517,10 +479,7 @@ GetMemoryRegion (
ASSERT (PageTableIndex < TRANSLATION_TABLE_PAGE_COUNT); ASSERT (PageTableIndex < TRANSLATION_TABLE_PAGE_COUNT);
PageAttributes = PageTable[PageTableIndex] & TT_DESCRIPTOR_PAGE_ATTRIBUTE_MASK; PageAttributes = PageTable[PageTableIndex] & TT_DESCRIPTOR_PAGE_ATTRIBUTE_MASK;
*RegionAttributes = TT_DESCRIPTOR_CONVERT_TO_SECTION_CACHE_POLICY (PageAttributes) | *RegionAttributes = TT_DESCRIPTOR_CONVERT_TO_SECTION_CACHE_POLICY (PageAttributes, 0) |
TT_DESCRIPTOR_CONVERT_TO_SECTION_S (PageAttributes) |
TT_DESCRIPTOR_CONVERT_TO_SECTION_XN (PageAttributes) |
TT_DESCRIPTOR_CONVERT_TO_SECTION_AF (PageAttributes) |
TT_DESCRIPTOR_CONVERT_TO_SECTION_AP (PageAttributes); TT_DESCRIPTOR_CONVERT_TO_SECTION_AP (PageAttributes);
} }
@@ -535,7 +494,6 @@ GetMemoryRegion (
// Scan the page table to find the end of the region. // Scan the page table to find the end of the region.
Status = GetMemoryRegionPage (PageTable, BaseAddress, RegionLength, RegionAttributes); Status = GetMemoryRegionPage (PageTable, BaseAddress, RegionLength, RegionAttributes);
ASSERT (*RegionLength > 0);
// If we have found the end of the region (Status == EFI_SUCCESS) then we exit the for-loop // If we have found the end of the region (Status == EFI_SUCCESS) then we exit the for-loop
if (Status == EFI_SUCCESS) { if (Status == EFI_SUCCESS) {

View File

@@ -244,8 +244,6 @@ CpuDxeInitialize (
&mCpuHandle, &mCpuHandle,
&gEfiCpuArchProtocolGuid, &gEfiCpuArchProtocolGuid,
&mCpu, &mCpu,
&gEfiMemoryAttributeProtocolGuid,
&mMemoryAttribute,
NULL NULL
); );
@@ -258,6 +256,12 @@ CpuDxeInitialize (
SyncCacheConfig (&mCpu); SyncCacheConfig (&mCpu);
mIsFlushingGCD = FALSE; mIsFlushingGCD = FALSE;
// If the platform is a MPCore system then install the Configuration Table describing the
// secondary core states
if (ArmIsMpCore ()) {
PublishArmProcessorTable ();
}
// //
// Setup a callback for idle events // Setup a callback for idle events
// //

View File

@@ -30,12 +30,9 @@
#include <Protocol/Cpu.h> #include <Protocol/Cpu.h>
#include <Protocol/DebugSupport.h> #include <Protocol/DebugSupport.h>
#include <Protocol/LoadedImage.h> #include <Protocol/LoadedImage.h>
#include <Protocol/MemoryAttribute.h>
extern BOOLEAN mIsFlushingGCD; extern BOOLEAN mIsFlushingGCD;
extern EFI_MEMORY_ATTRIBUTE_PROTOCOL mMemoryAttribute;
/** /**
This function registers and enables the handler specified by InterruptHandler for a processor This function registers and enables the handler specified by InterruptHandler for a processor
interrupt or exception type specified by InterruptType. If InterruptHandler is NULL, then the interrupt or exception type specified by InterruptType. If InterruptHandler is NULL, then the
@@ -107,6 +104,21 @@ SyncCacheConfig (
IN EFI_CPU_ARCH_PROTOCOL *CpuProtocol IN EFI_CPU_ARCH_PROTOCOL *CpuProtocol
); );
/**
* Publish ARM Processor Data table in UEFI SYSTEM Table.
* @param HobStart Pointer to the beginning of the HOB List from PEI.
*
* Description : This function iterates through HOB list and finds ARM processor Table Entry HOB.
* If the ARM processor Table Entry HOB is found, the HOB data is copied to run-time memory
* and a pointer is assigned to it in ARM processor table. Then the ARM processor table is
* installed in EFI configuration table.
**/
VOID
EFIAPI
PublishArmProcessorTable (
VOID
);
// The ARM Attributes might be defined on 64-bit (case of the long format description table) // The ARM Attributes might be defined on 64-bit (case of the long format description table)
UINT64 UINT64
EfiAttributeToArmAttribute ( EfiAttributeToArmAttribute (
@@ -129,18 +141,4 @@ SetGcdMemorySpaceAttributes (
IN UINT64 Attributes IN UINT64 Attributes
); );
/**
Convert an arch specific set of page attributes into a mask
of EFI_MEMORY_xx constants.
@param PageAttributes The set of page attributes.
@retval The mask of EFI_MEMORY_xx constants.
**/
UINT64
RegionAttributeToGcdAttribute (
IN UINTN PageAttributes
);
#endif // CPU_DXE_H_ #endif // CPU_DXE_H_

View File

@@ -21,9 +21,9 @@
[Sources.Common] [Sources.Common]
CpuDxe.c CpuDxe.c
CpuDxe.h CpuDxe.h
CpuMpCore.c
CpuMmuCommon.c CpuMmuCommon.c
Exception.c Exception.c
MemoryAttribute.c
[Sources.ARM] [Sources.ARM]
Arm/Mmu.c Arm/Mmu.c
@@ -54,7 +54,6 @@
[Protocols] [Protocols]
gEfiCpuArchProtocolGuid gEfiCpuArchProtocolGuid
gEfiMemoryAttributeProtocolGuid
[Guids] [Guids]
gEfiDebugImageInfoTableGuid gEfiDebugImageInfoTableGuid

View File

@@ -0,0 +1,98 @@
/** @file
*
* Copyright (c) 2011-2021, Arm Limited. All rights reserved.<BR>
*
* SPDX-License-Identifier: BSD-2-Clause-Patent
*
**/
#include <Library/UefiBootServicesTableLib.h>
#include <Library/BaseMemoryLib.h>
#include <Library/HobLib.h>
#include <Library/DebugLib.h>
#include <Library/MemoryAllocationLib.h>
#include <Guid/ArmMpCoreInfo.h>
ARM_PROCESSOR_TABLE mArmProcessorTableTemplate = {
{
EFI_ARM_PROCESSOR_TABLE_SIGNATURE,
0,
EFI_ARM_PROCESSOR_TABLE_REVISION,
EFI_ARM_PROCESSOR_TABLE_OEM_ID,
EFI_ARM_PROCESSOR_TABLE_OEM_TABLE_ID,
EFI_ARM_PROCESSOR_TABLE_OEM_REVISION,
EFI_ARM_PROCESSOR_TABLE_CREATOR_ID,
EFI_ARM_PROCESSOR_TABLE_CREATOR_REVISION,
{ 0 },
0
}, // ARM Processor table header
0, // Number of entries in ARM processor Table
NULL // ARM Processor Table
};
/** Publish ARM Processor Data table in UEFI SYSTEM Table.
* @param HobStart Pointer to the beginning of the HOB List from PEI.
*
* Description : This function iterates through HOB list and finds ARM processor Table Entry HOB.
* If the ARM processor Table Entry HOB is found, the HOB data is copied to run-time memory
* and a pointer is assigned to it in ARM processor table. Then the ARM processor table is
* installed in EFI configuration table.
**/
VOID
EFIAPI
PublishArmProcessorTable (
VOID
)
{
EFI_PEI_HOB_POINTERS Hob;
Hob.Raw = GetHobList ();
// Iterate through the HOBs and find if there is ARM PROCESSOR ENTRY HOB
for ( ; !END_OF_HOB_LIST (Hob); Hob.Raw = GET_NEXT_HOB (Hob)) {
// Check for Correct HOB type
if ((GET_HOB_TYPE (Hob)) == EFI_HOB_TYPE_GUID_EXTENSION) {
// Check for correct GUID type
if (CompareGuid (&(Hob.Guid->Name), &gArmMpCoreInfoGuid)) {
ARM_PROCESSOR_TABLE *ArmProcessorTable;
EFI_STATUS Status;
// Allocate Runtime memory for ARM processor table
ArmProcessorTable = (ARM_PROCESSOR_TABLE *)AllocateRuntimePool (sizeof (ARM_PROCESSOR_TABLE));
// Check if the memory allocation is successful or not
ASSERT (NULL != ArmProcessorTable);
// Set ARM processor table to default values
CopyMem (ArmProcessorTable, &mArmProcessorTableTemplate, sizeof (ARM_PROCESSOR_TABLE));
// Fill in Length fields of ARM processor table
ArmProcessorTable->Header.Length = sizeof (ARM_PROCESSOR_TABLE);
ArmProcessorTable->Header.DataLen = GET_GUID_HOB_DATA_SIZE (Hob);
// Fill in Identifier(ARM processor table GUID)
ArmProcessorTable->Header.Identifier = gArmMpCoreInfoGuid;
// Set Number of ARM core entries in the Table
ArmProcessorTable->NumberOfEntries = GET_GUID_HOB_DATA_SIZE (Hob)/sizeof (ARM_CORE_INFO);
// Allocate runtime memory for ARM processor Table entries
ArmProcessorTable->ArmCpus = (ARM_CORE_INFO *)AllocateRuntimePool (
ArmProcessorTable->NumberOfEntries * sizeof (ARM_CORE_INFO)
);
// Check if the memory allocation is successful or not
ASSERT (NULL != ArmProcessorTable->ArmCpus);
// Copy ARM Processor Table data from HOB list to newly allocated memory
CopyMem (ArmProcessorTable->ArmCpus, GET_GUID_HOB_DATA (Hob), ArmProcessorTable->Header.DataLen);
// Install the ARM Processor table into EFI system configuration table
Status = gBS->InstallConfigurationTable (&gArmMpCoreInfoGuid, ArmProcessorTable);
ASSERT_EFI_ERROR (Status);
}
}
}
}

View File

@@ -1,319 +0,0 @@
/** @file
Copyright (c) 2023, Google LLC. All rights reserved.
SPDX-License-Identifier: BSD-2-Clause-Patent
**/
#include "CpuDxe.h"
/**
Check whether the provided memory range is covered by a single entry of type
EfiGcdSystemMemory in the GCD memory map.
@param BaseAddress The physical address that is the start address of
a memory region.
@param Length The size in bytes of the memory region.
@return Whether the region is system memory or not.
**/
STATIC
BOOLEAN
RegionIsSystemMemory (
IN EFI_PHYSICAL_ADDRESS BaseAddress,
IN UINT64 Length
)
{
EFI_GCD_MEMORY_SPACE_DESCRIPTOR GcdDescriptor;
EFI_PHYSICAL_ADDRESS GcdEndAddress;
EFI_STATUS Status;
Status = gDS->GetMemorySpaceDescriptor (BaseAddress, &GcdDescriptor);
if (EFI_ERROR (Status) ||
(GcdDescriptor.GcdMemoryType != EfiGcdMemoryTypeSystemMemory))
{
return FALSE;
}
GcdEndAddress = GcdDescriptor.BaseAddress + GcdDescriptor.Length;
//
// Return TRUE if the GCD descriptor covers the range entirely
//
return GcdEndAddress >= (BaseAddress + Length);
}
/**
This function retrieves the attributes of the memory region specified by
BaseAddress and Length. If different attributes are obtained from different
parts of the memory region, EFI_NO_MAPPING will be returned.
@param This The EFI_MEMORY_ATTRIBUTE_PROTOCOL instance.
@param BaseAddress The physical address that is the start address of
a memory region.
@param Length The size in bytes of the memory region.
@param Attributes Pointer to attributes returned.
@retval EFI_SUCCESS The attributes got for the memory region.
@retval EFI_INVALID_PARAMETER Length is zero.
Attributes is NULL.
@retval EFI_NO_MAPPING Attributes are not consistent cross the memory
region.
@retval EFI_UNSUPPORTED The processor does not support one or more
bytes of the memory resource range specified
by BaseAddress and Length.
**/
STATIC
EFI_STATUS
GetMemoryAttributes (
IN EFI_MEMORY_ATTRIBUTE_PROTOCOL *This,
IN EFI_PHYSICAL_ADDRESS BaseAddress,
IN UINT64 Length,
OUT UINT64 *Attributes
)
{
UINTN RegionAddress;
UINTN RegionLength;
UINTN RegionAttributes;
UINTN Union;
UINTN Intersection;
EFI_STATUS Status;
if ((Length == 0) || (Attributes == NULL)) {
return EFI_INVALID_PARAMETER;
}
if (!RegionIsSystemMemory (BaseAddress, Length)) {
return EFI_UNSUPPORTED;
}
DEBUG ((
DEBUG_VERBOSE,
"%a: BaseAddress == 0x%lx, Length == 0x%lx\n",
__func__,
BaseAddress,
Length
));
Union = 0;
Intersection = MAX_UINTN;
for (RegionAddress = (UINTN)BaseAddress;
RegionAddress < (UINTN)(BaseAddress + Length);
RegionAddress += RegionLength)
{
Status = GetMemoryRegion (
&RegionAddress,
&RegionLength,
&RegionAttributes
);
DEBUG ((
DEBUG_VERBOSE,
"%a: RegionAddress == 0x%lx, RegionLength == 0x%lx, RegionAttributes == 0x%lx\n",
__func__,
(UINT64)RegionAddress,
(UINT64)RegionLength,
(UINT64)RegionAttributes
));
if (EFI_ERROR (Status)) {
return EFI_NO_MAPPING;
}
Union |= RegionAttributes;
Intersection &= RegionAttributes;
}
DEBUG ((
DEBUG_VERBOSE,
"%a: Union == %lx, Intersection == %lx\n",
__func__,
(UINT64)Union,
(UINT64)Intersection
));
if (Union != Intersection) {
return EFI_NO_MAPPING;
}
*Attributes = RegionAttributeToGcdAttribute (Union);
*Attributes &= EFI_MEMORY_RP | EFI_MEMORY_RO | EFI_MEMORY_XP;
return EFI_SUCCESS;
}
/**
This function set given attributes of the memory region specified by
BaseAddress and Length.
The valid Attributes is EFI_MEMORY_RP, EFI_MEMORY_XP, and EFI_MEMORY_RO.
@param This The EFI_MEMORY_ATTRIBUTE_PROTOCOL instance.
@param BaseAddress The physical address that is the start address of
a memory region.
@param Length The size in bytes of the memory region.
@param Attributes The bit mask of attributes to set for the memory
region.
@retval EFI_SUCCESS The attributes were set for the memory region.
@retval EFI_INVALID_PARAMETER Length is zero.
Attributes specified an illegal combination of
attributes that cannot be set together.
@retval EFI_UNSUPPORTED The processor does not support one or more
bytes of the memory resource range specified
by BaseAddress and Length.
The bit mask of attributes is not supported for
the memory resource range specified by
BaseAddress and Length.
@retval EFI_OUT_OF_RESOURCES Requested attributes cannot be applied due to
lack of system resources.
@retval EFI_ACCESS_DENIED Attributes for the requested memory region are
controlled by system firmware and cannot be
updated via the protocol.
**/
STATIC
EFI_STATUS
SetMemoryAttributes (
IN EFI_MEMORY_ATTRIBUTE_PROTOCOL *This,
IN EFI_PHYSICAL_ADDRESS BaseAddress,
IN UINT64 Length,
IN UINT64 Attributes
)
{
EFI_STATUS Status;
DEBUG ((
DEBUG_INFO,
"%a: BaseAddress == 0x%lx, Length == 0x%lx, Attributes == 0x%lx\n",
__func__,
(UINTN)BaseAddress,
(UINTN)Length,
(UINTN)Attributes
));
if ((Length == 0) ||
((Attributes & ~(EFI_MEMORY_RO | EFI_MEMORY_RP | EFI_MEMORY_XP)) != 0))
{
return EFI_INVALID_PARAMETER;
}
if (!RegionIsSystemMemory (BaseAddress, Length)) {
return EFI_UNSUPPORTED;
}
if ((Attributes & EFI_MEMORY_RP) != 0) {
Status = ArmSetMemoryRegionNoAccess (BaseAddress, Length);
if (EFI_ERROR (Status)) {
return EFI_UNSUPPORTED;
}
}
if ((Attributes & EFI_MEMORY_RO) != 0) {
Status = ArmSetMemoryRegionReadOnly (BaseAddress, Length);
if (EFI_ERROR (Status)) {
return EFI_UNSUPPORTED;
}
}
if ((Attributes & EFI_MEMORY_XP) != 0) {
Status = ArmSetMemoryRegionNoExec (BaseAddress, Length);
if (EFI_ERROR (Status)) {
return EFI_UNSUPPORTED;
}
}
return EFI_SUCCESS;
}
/**
This function clears given attributes of the memory region specified by
BaseAddress and Length.
The valid Attributes is EFI_MEMORY_RP, EFI_MEMORY_XP, and EFI_MEMORY_RO.
@param This The EFI_MEMORY_ATTRIBUTE_PROTOCOL instance.
@param BaseAddress The physical address that is the start address of
a memory region.
@param Length The size in bytes of the memory region.
@param Attributes The bit mask of attributes to clear for the memory
region.
@retval EFI_SUCCESS The attributes were cleared for the memory region.
@retval EFI_INVALID_PARAMETER Length is zero.
Attributes specified an illegal combination of
attributes that cannot be cleared together.
@retval EFI_UNSUPPORTED The processor does not support one or more
bytes of the memory resource range specified
by BaseAddress and Length.
The bit mask of attributes is not supported for
the memory resource range specified by
BaseAddress and Length.
@retval EFI_OUT_OF_RESOURCES Requested attributes cannot be applied due to
lack of system resources.
@retval EFI_ACCESS_DENIED Attributes for the requested memory region are
controlled by system firmware and cannot be
updated via the protocol.
**/
STATIC
EFI_STATUS
ClearMemoryAttributes (
IN EFI_MEMORY_ATTRIBUTE_PROTOCOL *This,
IN EFI_PHYSICAL_ADDRESS BaseAddress,
IN UINT64 Length,
IN UINT64 Attributes
)
{
EFI_STATUS Status;
DEBUG ((
DEBUG_INFO,
"%a: BaseAddress == 0x%lx, Length == 0x%lx, Attributes == 0x%lx\n",
__func__,
(UINTN)BaseAddress,
(UINTN)Length,
(UINTN)Attributes
));
if ((Length == 0) ||
((Attributes & ~(EFI_MEMORY_RO | EFI_MEMORY_RP | EFI_MEMORY_XP)) != 0))
{
return EFI_INVALID_PARAMETER;
}
if (!RegionIsSystemMemory (BaseAddress, Length)) {
return EFI_UNSUPPORTED;
}
if ((Attributes & EFI_MEMORY_RP) != 0) {
Status = ArmClearMemoryRegionNoAccess (BaseAddress, Length);
if (EFI_ERROR (Status)) {
return EFI_UNSUPPORTED;
}
}
if ((Attributes & EFI_MEMORY_RO) != 0) {
Status = ArmClearMemoryRegionReadOnly (BaseAddress, Length);
if (EFI_ERROR (Status)) {
return EFI_UNSUPPORTED;
}
}
if ((Attributes & EFI_MEMORY_XP) != 0) {
Status = ArmClearMemoryRegionNoExec (BaseAddress, Length);
if (EFI_ERROR (Status)) {
return EFI_UNSUPPORTED;
}
}
return EFI_SUCCESS;
}
EFI_MEMORY_ATTRIBUTE_PROTOCOL mMemoryAttribute = {
GetMemoryAttributes,
SetMemoryAttributes,
ClearMemoryAttributes
};

View File

@@ -574,7 +574,7 @@ ExtendFile (
} }
Remaining = Size; Remaining = Size;
ZeroMem (WriteBuffer, sizeof (WriteBuffer)); SetMem (WriteBuffer, 0, sizeof (WriteBuffer));
while (Remaining > 0) { while (Remaining > 0) {
WriteNb = MIN (Remaining, sizeof (WriteBuffer)); WriteNb = MIN (Remaining, sizeof (WriteBuffer));
WriteSize = WriteNb; WriteSize = WriteNb;

View File

@@ -38,22 +38,10 @@
.global Name ; \ .global Name ; \
.section #Section, "ax" ; \ .section #Section, "ax" ; \
.type Name, %function ; \ .type Name, %function ; \
Name: ; \ Name:
AARCH64_BTI(c)
#define _ASM_FUNC_ALIGN(Name, Section, Align) \
.global Name ; \
.section #Section, "ax" ; \
.type Name, %function ; \
.balign Align ; \
Name: ; \
AARCH64_BTI(c)
#define ASM_FUNC(Name) _ASM_FUNC(ASM_PFX(Name), .text. ## Name) #define ASM_FUNC(Name) _ASM_FUNC(ASM_PFX(Name), .text. ## Name)
#define ASM_FUNC_ALIGN(Name, Align) \
_ASM_FUNC_ALIGN(ASM_PFX(Name), .text. ## Name, Align)
#define MOV32(Reg, Val) \ #define MOV32(Reg, Val) \
movz Reg, (Val) >> 16, lsl #16 ; \ movz Reg, (Val) >> 16, lsl #16 ; \
movk Reg, (Val) & 0xffff movk Reg, (Val) & 0xffff

View File

@@ -112,10 +112,6 @@
#define ARM_VECTOR_LOW_A32_FIQ 0x700 #define ARM_VECTOR_LOW_A32_FIQ 0x700
#define ARM_VECTOR_LOW_A32_SERR 0x780 #define ARM_VECTOR_LOW_A32_SERR 0x780
// The ID_AA64ISAR2_EL1 register is not recognized by older
// assemblers, we need to define it here.
#define ID_AA64ISAR2_EL1 S3_0_C0_C6_2
// The ID_AA64MMFR2_EL1 register was added in ARMv8.2. Since we // The ID_AA64MMFR2_EL1 register was added in ARMv8.2. Since we
// build for ARMv8.0, we need to define the register here. // build for ARMv8.0, we need to define the register here.
#define ID_AA64MMFR2_EL1 S3_0_C0_C7_2 #define ID_AA64MMFR2_EL1 S3_0_C0_C7_2

View File

@@ -54,9 +54,11 @@
#define TT_DESCRIPTOR_SECTION_TYPE_IS_PAGE_TABLE(Desc) (((Desc) & 3UL) == TT_DESCRIPTOR_SECTION_TYPE_PAGE_TABLE) #define TT_DESCRIPTOR_SECTION_TYPE_IS_PAGE_TABLE(Desc) (((Desc) & 3UL) == TT_DESCRIPTOR_SECTION_TYPE_PAGE_TABLE)
// Translation table descriptor types // Translation table descriptor types
#define TT_DESCRIPTOR_PAGE_TYPE_MASK (1UL << 1) #define TT_DESCRIPTOR_PAGE_TYPE_MASK (3UL << 0)
#define TT_DESCRIPTOR_PAGE_TYPE_FAULT (0UL << 1) #define TT_DESCRIPTOR_PAGE_TYPE_FAULT (0UL << 0)
#define TT_DESCRIPTOR_PAGE_TYPE_PAGE (1UL << 1) #define TT_DESCRIPTOR_PAGE_TYPE_PAGE (2UL << 0)
#define TT_DESCRIPTOR_PAGE_TYPE_PAGE_XN (3UL << 0)
#define TT_DESCRIPTOR_PAGE_TYPE_LARGEPAGE (1UL << 0)
// Section descriptor definitions // Section descriptor definitions
#define TT_DESCRIPTOR_SECTION_SIZE (0x00100000) #define TT_DESCRIPTOR_SECTION_SIZE (0x00100000)
@@ -80,24 +82,25 @@
#define TT_DESCRIPTOR_PAGE_S_NOT_SHARED (0UL << 10) #define TT_DESCRIPTOR_PAGE_S_NOT_SHARED (0UL << 10)
#define TT_DESCRIPTOR_PAGE_S_SHARED (1UL << 10) #define TT_DESCRIPTOR_PAGE_S_SHARED (1UL << 10)
#define TT_DESCRIPTOR_SECTION_AP_MASK ((1UL << 15) | (1UL << 11)) #define TT_DESCRIPTOR_SECTION_AP_MASK ((1UL << 15) | (3UL << 10))
#define TT_DESCRIPTOR_SECTION_AP_NO_RW ((0UL << 15) | (0UL << 11)) #define TT_DESCRIPTOR_SECTION_AP_NO_NO ((0UL << 15) | (0UL << 10))
#define TT_DESCRIPTOR_SECTION_AP_RW_RW ((0UL << 15) | (1UL << 11)) #define TT_DESCRIPTOR_SECTION_AP_RW_NO ((0UL << 15) | (1UL << 10))
#define TT_DESCRIPTOR_SECTION_AP_NO_RO ((1UL << 15) | (0UL << 11)) #define TT_DESCRIPTOR_SECTION_AP_RW_RO ((0UL << 15) | (2UL << 10))
#define TT_DESCRIPTOR_SECTION_AP_RO_RO ((1UL << 15) | (1UL << 11)) #define TT_DESCRIPTOR_SECTION_AP_RW_RW ((0UL << 15) | (3UL << 10))
#define TT_DESCRIPTOR_SECTION_AP_RO_NO ((1UL << 15) | (1UL << 10))
#define TT_DESCRIPTOR_SECTION_AP_RO_RO ((1UL << 15) | (3UL << 10))
#define TT_DESCRIPTOR_SECTION_AF (1UL << 10) #define TT_DESCRIPTOR_PAGE_AP_MASK ((1UL << 9) | (3UL << 4))
#define TT_DESCRIPTOR_PAGE_AP_NO_NO ((0UL << 9) | (0UL << 4))
#define TT_DESCRIPTOR_PAGE_AP_MASK ((1UL << 9) | (1UL << 5)) #define TT_DESCRIPTOR_PAGE_AP_RW_NO ((0UL << 9) | (1UL << 4))
#define TT_DESCRIPTOR_PAGE_AP_NO_RW ((0UL << 9) | (0UL << 5)) #define TT_DESCRIPTOR_PAGE_AP_RW_RO ((0UL << 9) | (2UL << 4))
#define TT_DESCRIPTOR_PAGE_AP_RW_RW ((0UL << 9) | (1UL << 5)) #define TT_DESCRIPTOR_PAGE_AP_RW_RW ((0UL << 9) | (3UL << 4))
#define TT_DESCRIPTOR_PAGE_AP_NO_RO ((1UL << 9) | (0UL << 5)) #define TT_DESCRIPTOR_PAGE_AP_RO_NO ((1UL << 9) | (1UL << 4))
#define TT_DESCRIPTOR_PAGE_AP_RO_RO ((1UL << 9) | (1UL << 5)) #define TT_DESCRIPTOR_PAGE_AP_RO_RO ((1UL << 9) | (3UL << 4))
#define TT_DESCRIPTOR_PAGE_AF (1UL << 4)
#define TT_DESCRIPTOR_SECTION_XN_MASK (0x1UL << 4) #define TT_DESCRIPTOR_SECTION_XN_MASK (0x1UL << 4)
#define TT_DESCRIPTOR_PAGE_XN_MASK (0x1UL << 0) #define TT_DESCRIPTOR_PAGE_XN_MASK (0x1UL << 0)
#define TT_DESCRIPTOR_LARGEPAGE_XN_MASK (0x1UL << 15)
#define TT_DESCRIPTOR_SECTION_CACHE_POLICY_MASK ((3UL << 12) | (1UL << 3) | (1UL << 2)) #define TT_DESCRIPTOR_SECTION_CACHE_POLICY_MASK ((3UL << 12) | (1UL << 3) | (1UL << 2))
#define TT_DESCRIPTOR_SECTION_CACHEABLE_MASK (1UL << 3) #define TT_DESCRIPTOR_SECTION_CACHEABLE_MASK (1UL << 3)
@@ -121,27 +124,37 @@
#define TT_DESCRIPTOR_PAGE_CACHE_POLICY_WRITE_BACK_ALLOC ((1UL << 6) | (1UL << 3) | (1UL << 2)) #define TT_DESCRIPTOR_PAGE_CACHE_POLICY_WRITE_BACK_ALLOC ((1UL << 6) | (1UL << 3) | (1UL << 2))
#define TT_DESCRIPTOR_PAGE_CACHE_POLICY_NON_SHAREABLE_DEVICE ((2UL << 6) | (0UL << 3) | (0UL << 2)) #define TT_DESCRIPTOR_PAGE_CACHE_POLICY_NON_SHAREABLE_DEVICE ((2UL << 6) | (0UL << 3) | (0UL << 2))
#define TT_DESCRIPTOR_LARGEPAGE_CACHE_POLICY_MASK ((3UL << 12) | (1UL << 3) | (1UL << 2))
#define TT_DESCRIPTOR_LARGEPAGE_CACHE_POLICY_STRONGLY_ORDERED ((0UL << 12) | (0UL << 3) | (0UL << 2))
#define TT_DESCRIPTOR_LARGEPAGE_CACHE_POLICY_SHAREABLE_DEVICE ((0UL << 12) | (0UL << 3) | (1UL << 2))
#define TT_DESCRIPTOR_LARGEPAGE_CACHE_POLICY_WRITE_THROUGH_NO_ALLOC ((0UL << 12) | (1UL << 3) | (0UL << 2))
#define TT_DESCRIPTOR_LARGEPAGE_CACHE_POLICY_WRITE_BACK_NO_ALLOC ((0UL << 12) | (1UL << 3) | (1UL << 2))
#define TT_DESCRIPTOR_LARGEPAGE_CACHE_POLICY_NON_CACHEABLE ((1UL << 12) | (0UL << 3) | (0UL << 2))
#define TT_DESCRIPTOR_LARGEPAGE_CACHE_POLICY_WRITE_BACK_ALLOC ((1UL << 12) | (1UL << 3) | (1UL << 2))
#define TT_DESCRIPTOR_LARGEPAGE_CACHE_POLICY_NON_SHAREABLE_DEVICE ((2UL << 12) | (0UL << 3) | (0UL << 2))
#define TT_DESCRIPTOR_CONVERT_TO_PAGE_AP(Desc) ((((Desc) & TT_DESCRIPTOR_SECTION_AP_MASK) >> 6) & TT_DESCRIPTOR_PAGE_AP_MASK) #define TT_DESCRIPTOR_CONVERT_TO_PAGE_AP(Desc) ((((Desc) & TT_DESCRIPTOR_SECTION_AP_MASK) >> 6) & TT_DESCRIPTOR_PAGE_AP_MASK)
#define TT_DESCRIPTOR_CONVERT_TO_PAGE_NG(Desc) ((((Desc) & TT_DESCRIPTOR_SECTION_NG_MASK) >> 6) & TT_DESCRIPTOR_PAGE_NG_MASK) #define TT_DESCRIPTOR_CONVERT_TO_PAGE_NG(Desc) ((((Desc) & TT_DESCRIPTOR_SECTION_NG_MASK) >> 6) & TT_DESCRIPTOR_PAGE_NG_MASK)
#define TT_DESCRIPTOR_CONVERT_TO_PAGE_S(Desc) ((((Desc) & TT_DESCRIPTOR_SECTION_S_MASK) >> 6) & TT_DESCRIPTOR_PAGE_S_MASK) #define TT_DESCRIPTOR_CONVERT_TO_PAGE_S(Desc) ((((Desc) & TT_DESCRIPTOR_SECTION_S_MASK) >> 6) & TT_DESCRIPTOR_PAGE_S_MASK)
#define TT_DESCRIPTOR_CONVERT_TO_PAGE_AF(Desc) ((((Desc) & TT_DESCRIPTOR_SECTION_AF) >> 6) & TT_DESCRIPTOR_PAGE_AF) #define TT_DESCRIPTOR_CONVERT_TO_PAGE_XN(Desc, IsLargePage) ((IsLargePage)?\
#define TT_DESCRIPTOR_CONVERT_TO_PAGE_XN(Desc) ((((Desc) & TT_DESCRIPTOR_SECTION_XN_MASK) >> 4) & TT_DESCRIPTOR_PAGE_XN_MASK) ((((Desc) & TT_DESCRIPTOR_SECTION_XN_MASK) << 11) & TT_DESCRIPTOR_LARGEPAGE_XN_MASK): \
#define TT_DESCRIPTOR_CONVERT_TO_PAGE_CACHE_POLICY(Desc) ((((Desc) & (0x3 << 12)) >> 6) | (Desc & (0x3 << 2))) ((((Desc) & TT_DESCRIPTOR_SECTION_XN_MASK) >> 4) & TT_DESCRIPTOR_PAGE_XN_MASK))
#define TT_DESCRIPTOR_CONVERT_TO_PAGE_CACHE_POLICY(Desc, IsLargePage) (IsLargePage? \
(((Desc) & TT_DESCRIPTOR_SECTION_CACHE_POLICY_MASK) & TT_DESCRIPTOR_LARGEPAGE_CACHE_POLICY_MASK): \
(((((Desc) & (0x3 << 12)) >> 6) | (Desc & (0x3 << 2)))))
#define TT_DESCRIPTOR_CONVERT_TO_SECTION_AP(Desc) ((((Desc) & TT_DESCRIPTOR_PAGE_AP_MASK) << 6) & TT_DESCRIPTOR_SECTION_AP_MASK) #define TT_DESCRIPTOR_CONVERT_TO_SECTION_AP(Desc) ((((Desc) & TT_DESCRIPTOR_PAGE_AP_MASK) << 6) & TT_DESCRIPTOR_SECTION_AP_MASK)
#define TT_DESCRIPTOR_CONVERT_TO_SECTION_S(Desc) ((((Desc) & TT_DESCRIPTOR_PAGE_S_MASK) << 6) & TT_DESCRIPTOR_SECTION_S_MASK)
#define TT_DESCRIPTOR_CONVERT_TO_SECTION_AF(Desc) ((((Desc) & TT_DESCRIPTOR_PAGE_AF) << 6) & TT_DESCRIPTOR_SECTION_AF) #define TT_DESCRIPTOR_CONVERT_TO_SECTION_CACHE_POLICY(Desc, IsLargePage) (IsLargePage? \
#define TT_DESCRIPTOR_CONVERT_TO_SECTION_XN(Desc) ((((Desc) & TT_DESCRIPTOR_PAGE_XN_MASK) << 4) & TT_DESCRIPTOR_SECTION_XN_MASK) (((Desc) & TT_DESCRIPTOR_LARGEPAGE_CACHE_POLICY_MASK) & TT_DESCRIPTOR_SECTION_CACHE_POLICY_MASK): \
#define TT_DESCRIPTOR_CONVERT_TO_SECTION_CACHE_POLICY(Desc) ((((Desc) & (0x3 << 6)) << 6) | (Desc & (0x3 << 2))) (((((Desc) & (0x3 << 6)) << 6) | (Desc & (0x3 << 2)))))
#define TT_DESCRIPTOR_SECTION_ATTRIBUTE_MASK (TT_DESCRIPTOR_SECTION_NS_MASK | TT_DESCRIPTOR_SECTION_NG_MASK | \ #define TT_DESCRIPTOR_SECTION_ATTRIBUTE_MASK (TT_DESCRIPTOR_SECTION_NS_MASK | TT_DESCRIPTOR_SECTION_NG_MASK | \
TT_DESCRIPTOR_SECTION_S_MASK | TT_DESCRIPTOR_SECTION_AP_MASK | \ TT_DESCRIPTOR_SECTION_S_MASK | TT_DESCRIPTOR_SECTION_AP_MASK | \
TT_DESCRIPTOR_SECTION_AF | \
TT_DESCRIPTOR_SECTION_XN_MASK | TT_DESCRIPTOR_SECTION_CACHE_POLICY_MASK) TT_DESCRIPTOR_SECTION_XN_MASK | TT_DESCRIPTOR_SECTION_CACHE_POLICY_MASK)
#define TT_DESCRIPTOR_PAGE_ATTRIBUTE_MASK (TT_DESCRIPTOR_PAGE_NG_MASK | TT_DESCRIPTOR_PAGE_S_MASK | \ #define TT_DESCRIPTOR_PAGE_ATTRIBUTE_MASK (TT_DESCRIPTOR_PAGE_NG_MASK | TT_DESCRIPTOR_PAGE_S_MASK | \
TT_DESCRIPTOR_PAGE_AP_MASK | TT_DESCRIPTOR_PAGE_XN_MASK | \ TT_DESCRIPTOR_PAGE_AP_MASK | TT_DESCRIPTOR_PAGE_XN_MASK | \
TT_DESCRIPTOR_PAGE_AF | \
TT_DESCRIPTOR_PAGE_CACHE_POLICY_MASK) TT_DESCRIPTOR_PAGE_CACHE_POLICY_MASK)
#define TT_DESCRIPTOR_SECTION_DOMAIN_MASK (0x0FUL << 5) #define TT_DESCRIPTOR_SECTION_DOMAIN_MASK (0x0FUL << 5)
@@ -157,49 +170,56 @@
#define TT_DESCRIPTOR_PAGE_BASE_ADDRESS(a) ((a) & TT_DESCRIPTOR_PAGE_BASE_ADDRESS_MASK) #define TT_DESCRIPTOR_PAGE_BASE_ADDRESS(a) ((a) & TT_DESCRIPTOR_PAGE_BASE_ADDRESS_MASK)
#define TT_DESCRIPTOR_PAGE_BASE_SHIFT 12 #define TT_DESCRIPTOR_PAGE_BASE_SHIFT 12
#define TT_DESCRIPTOR_SECTION_DEFAULT (TT_DESCRIPTOR_SECTION_TYPE_SECTION | \ #define TT_DESCRIPTOR_SECTION_WRITE_BACK(NonSecure) (TT_DESCRIPTOR_SECTION_TYPE_SECTION | \
((NonSecure) ? TT_DESCRIPTOR_SECTION_NS : 0) | \
TT_DESCRIPTOR_SECTION_NG_GLOBAL | \ TT_DESCRIPTOR_SECTION_NG_GLOBAL | \
TT_DESCRIPTOR_SECTION_S_SHARED | \ TT_DESCRIPTOR_SECTION_S_SHARED | \
TT_DESCRIPTOR_SECTION_DOMAIN(0) | \ TT_DESCRIPTOR_SECTION_DOMAIN(0) | \
TT_DESCRIPTOR_SECTION_AP_RW_RW | \ TT_DESCRIPTOR_SECTION_AP_RW_RW | \
TT_DESCRIPTOR_SECTION_AF)
#define TT_DESCRIPTOR_SECTION_WRITE_BACK (TT_DESCRIPTOR_SECTION_DEFAULT | \
TT_DESCRIPTOR_SECTION_CACHE_POLICY_WRITE_BACK_ALLOC) TT_DESCRIPTOR_SECTION_CACHE_POLICY_WRITE_BACK_ALLOC)
#define TT_DESCRIPTOR_SECTION_WRITE_THROUGH(NonSecure) (TT_DESCRIPTOR_SECTION_TYPE_SECTION | \
#define TT_DESCRIPTOR_SECTION_WRITE_THROUGH (TT_DESCRIPTOR_SECTION_DEFAULT | \ ((NonSecure) ? TT_DESCRIPTOR_SECTION_NS : 0) | \
TT_DESCRIPTOR_SECTION_NG_GLOBAL | \
TT_DESCRIPTOR_SECTION_S_SHARED | \
TT_DESCRIPTOR_SECTION_DOMAIN(0) | \
TT_DESCRIPTOR_SECTION_AP_RW_RW | \
TT_DESCRIPTOR_SECTION_CACHE_POLICY_WRITE_THROUGH_NO_ALLOC) TT_DESCRIPTOR_SECTION_CACHE_POLICY_WRITE_THROUGH_NO_ALLOC)
#define TT_DESCRIPTOR_SECTION_DEVICE(NonSecure) (TT_DESCRIPTOR_SECTION_TYPE_SECTION | \
#define TT_DESCRIPTOR_SECTION_DEVICE (TT_DESCRIPTOR_SECTION_DEFAULT | \ ((NonSecure) ? TT_DESCRIPTOR_SECTION_NS : 0) | \
TT_DESCRIPTOR_SECTION_NG_GLOBAL | \
TT_DESCRIPTOR_SECTION_S_NOT_SHARED | \
TT_DESCRIPTOR_SECTION_DOMAIN(0) | \
TT_DESCRIPTOR_SECTION_AP_RW_RW | \
TT_DESCRIPTOR_SECTION_XN_MASK | \
TT_DESCRIPTOR_SECTION_CACHE_POLICY_SHAREABLE_DEVICE) TT_DESCRIPTOR_SECTION_CACHE_POLICY_SHAREABLE_DEVICE)
#define TT_DESCRIPTOR_SECTION_UNCACHED(NonSecure) (TT_DESCRIPTOR_SECTION_TYPE_SECTION | \
#define TT_DESCRIPTOR_SECTION_UNCACHED (TT_DESCRIPTOR_SECTION_DEFAULT | \ ((NonSecure) ? TT_DESCRIPTOR_SECTION_NS : 0) | \
TT_DESCRIPTOR_SECTION_NG_GLOBAL | \
TT_DESCRIPTOR_SECTION_S_NOT_SHARED | \
TT_DESCRIPTOR_SECTION_DOMAIN(0) | \
TT_DESCRIPTOR_SECTION_AP_RW_RW | \
TT_DESCRIPTOR_SECTION_CACHE_POLICY_NON_CACHEABLE) TT_DESCRIPTOR_SECTION_CACHE_POLICY_NON_CACHEABLE)
#define TT_DESCRIPTOR_PAGE_WRITE_BACK (TT_DESCRIPTOR_PAGE_TYPE_PAGE | \ #define TT_DESCRIPTOR_PAGE_WRITE_BACK (TT_DESCRIPTOR_PAGE_TYPE_PAGE | \
TT_DESCRIPTOR_PAGE_NG_GLOBAL | \ TT_DESCRIPTOR_PAGE_NG_GLOBAL | \
TT_DESCRIPTOR_PAGE_S_SHARED | \ TT_DESCRIPTOR_PAGE_S_SHARED | \
TT_DESCRIPTOR_PAGE_AP_RW_RW | \ TT_DESCRIPTOR_PAGE_AP_RW_RW | \
TT_DESCRIPTOR_PAGE_AF | \
TT_DESCRIPTOR_PAGE_CACHE_POLICY_WRITE_BACK_ALLOC) TT_DESCRIPTOR_PAGE_CACHE_POLICY_WRITE_BACK_ALLOC)
#define TT_DESCRIPTOR_PAGE_WRITE_THROUGH (TT_DESCRIPTOR_PAGE_TYPE_PAGE | \ #define TT_DESCRIPTOR_PAGE_WRITE_THROUGH (TT_DESCRIPTOR_PAGE_TYPE_PAGE | \
TT_DESCRIPTOR_PAGE_NG_GLOBAL | \ TT_DESCRIPTOR_PAGE_NG_GLOBAL | \
TT_DESCRIPTOR_PAGE_S_SHARED | \ TT_DESCRIPTOR_PAGE_S_SHARED | \
TT_DESCRIPTOR_PAGE_AP_RW_RW | \ TT_DESCRIPTOR_PAGE_AP_RW_RW | \
TT_DESCRIPTOR_PAGE_AF | \
TT_DESCRIPTOR_PAGE_CACHE_POLICY_WRITE_THROUGH_NO_ALLOC) TT_DESCRIPTOR_PAGE_CACHE_POLICY_WRITE_THROUGH_NO_ALLOC)
#define TT_DESCRIPTOR_PAGE_DEVICE (TT_DESCRIPTOR_PAGE_TYPE_PAGE | \ #define TT_DESCRIPTOR_PAGE_DEVICE (TT_DESCRIPTOR_PAGE_TYPE_PAGE | \
TT_DESCRIPTOR_PAGE_NG_GLOBAL | \ TT_DESCRIPTOR_PAGE_NG_GLOBAL | \
TT_DESCRIPTOR_PAGE_S_NOT_SHARED | \ TT_DESCRIPTOR_PAGE_S_NOT_SHARED | \
TT_DESCRIPTOR_PAGE_AP_RW_RW | \ TT_DESCRIPTOR_PAGE_AP_RW_RW | \
TT_DESCRIPTOR_PAGE_AF | \
TT_DESCRIPTOR_PAGE_XN_MASK | \ TT_DESCRIPTOR_PAGE_XN_MASK | \
TT_DESCRIPTOR_PAGE_CACHE_POLICY_SHAREABLE_DEVICE) TT_DESCRIPTOR_PAGE_CACHE_POLICY_SHAREABLE_DEVICE)
#define TT_DESCRIPTOR_PAGE_UNCACHED (TT_DESCRIPTOR_PAGE_TYPE_PAGE | \ #define TT_DESCRIPTOR_PAGE_UNCACHED (TT_DESCRIPTOR_PAGE_TYPE_PAGE | \
TT_DESCRIPTOR_PAGE_NG_GLOBAL | \ TT_DESCRIPTOR_PAGE_NG_GLOBAL | \
TT_DESCRIPTOR_PAGE_S_NOT_SHARED | \ TT_DESCRIPTOR_PAGE_S_NOT_SHARED | \
TT_DESCRIPTOR_PAGE_AP_RW_RW | \ TT_DESCRIPTOR_PAGE_AP_RW_RW | \
TT_DESCRIPTOR_PAGE_AF | \
TT_DESCRIPTOR_PAGE_CACHE_POLICY_NON_CACHEABLE) TT_DESCRIPTOR_PAGE_CACHE_POLICY_NON_CACHEABLE)
// First Level Descriptors // First Level Descriptors
@@ -210,7 +230,8 @@ typedef UINT32 ARM_PAGE_TABLE_ENTRY;
UINT32 UINT32
ConvertSectionAttributesToPageAttributes ( ConvertSectionAttributesToPageAttributes (
IN UINT32 SectionAttributes IN UINT32 SectionAttributes,
IN BOOLEAN IsLargePage
); );
#endif // ARMV7_MMU_H_ #endif // ARMV7_MMU_H_

View File

@@ -23,9 +23,36 @@ typedef struct {
UINT64 MailboxClearValue; UINT64 MailboxClearValue;
} ARM_CORE_INFO; } ARM_CORE_INFO;
typedef struct {
UINT64 Signature;
UINT32 Length;
UINT32 Revision;
UINT64 OemId;
UINT64 OemTableId;
UINTN OemRevision;
UINTN CreatorId;
UINTN CreatorRevision;
EFI_GUID Identifier;
UINTN DataLen;
} ARM_PROCESSOR_TABLE_HEADER;
typedef struct {
ARM_PROCESSOR_TABLE_HEADER Header;
UINTN NumberOfEntries;
ARM_CORE_INFO *ArmCpus;
} ARM_PROCESSOR_TABLE;
#define ARM_MP_CORE_INFO_GUID \ #define ARM_MP_CORE_INFO_GUID \
{ 0xa4ee0728, 0xe5d7, 0x4ac5, {0xb2, 0x1e, 0x65, 0x8e, 0xd8, 0x57, 0xe8, 0x34} } { 0xa4ee0728, 0xe5d7, 0x4ac5, {0xb2, 0x1e, 0x65, 0x8e, 0xd8, 0x57, 0xe8, 0x34} }
#define EFI_ARM_PROCESSOR_TABLE_SIGNATURE SIGNATURE_64 ('C', 'P', 'U', 'T', 'A', 'B', 'L', 'E')
#define EFI_ARM_PROCESSOR_TABLE_REVISION 0x00010000// 1.0
#define EFI_ARM_PROCESSOR_TABLE_OEM_ID SIGNATURE_64('A','R','M',' ', 'L', 't', 'd', ' ')
#define EFI_ARM_PROCESSOR_TABLE_OEM_TABLE_ID SIGNATURE_64('V', 'E', 'R', 'S', 'A', 'T', 'I', 'L')
#define EFI_ARM_PROCESSOR_TABLE_OEM_REVISION 0x00000001
#define EFI_ARM_PROCESSOR_TABLE_CREATOR_ID 0xA5A5A5A5
#define EFI_ARM_PROCESSOR_TABLE_CREATOR_REVISION 0x01000001
extern EFI_GUID gArmMpCoreInfoGuid; extern EFI_GUID gArmMpCoreInfoGuid;
#endif /* ARM_MP_CORE_INFO_GUID_H_ */ #endif /* ARM_MP_CORE_INFO_GUID_H_ */

View File

@@ -1,20 +1,13 @@
/** @file /** @file
* *
* Copyright (c) 2020, NUVIA Inc. All rights reserved.<BR> * Copyright (c) 2020, NUVIA Inc. All rights reserved.<BR>
* Copyright (c) 2012 - 2022, Arm Limited. All rights reserved. * Copyright (c) 2012-2017, ARM Limited. All rights reserved.
* *
* SPDX-License-Identifier: BSD-2-Clause-Patent * SPDX-License-Identifier: BSD-2-Clause-Patent
* *
* @par Revision Reference: * @par Revision Reference:
* - [1] SMC Calling Convention version 1.2 * - SMC Calling Convention version 1.2
* (https://developer.arm.com/documentation/den0028/c/?lang=en) * (https://developer.arm.com/documentation/den0028/c/?lang=en)
* - [2] Arm True Random Number Generator Firmware, Interface 1.0,
* Platform Design Document.
* (https://developer.arm.com/documentation/den0098/latest/)
*
* @par Glossary:
* - TRNG - True Random Number Generator
*
**/ **/
#ifndef ARM_STD_SMC_H_ #ifndef ARM_STD_SMC_H_
@@ -100,8 +93,6 @@
#define ARM_SMC_ID_PSCI_MIGRATE_AARCH32 0x84000005 #define ARM_SMC_ID_PSCI_MIGRATE_AARCH32 0x84000005
#define ARM_SMC_ID_PSCI_SYSTEM_OFF 0x84000008 #define ARM_SMC_ID_PSCI_SYSTEM_OFF 0x84000008
#define ARM_SMC_ID_PSCI_SYSTEM_RESET 0x84000009 #define ARM_SMC_ID_PSCI_SYSTEM_RESET 0x84000009
#define ARM_SMC_ID_PSCI_FEATURES 0x8400000A
#define ARM_SMC_ID_PSCI_SYSTEM_RESET2_AARCH64 0xC4000012
/* The current PSCI version is: 0.2 */ /* The current PSCI version is: 0.2 */
#define ARM_SMC_PSCI_VERSION_MAJOR 0 #define ARM_SMC_PSCI_VERSION_MAJOR 0
@@ -146,102 +137,4 @@
/* 0xbf00ff02 is reserved */ /* 0xbf00ff02 is reserved */
#define ARM_SMC_ID_TOS_REVISION 0xbf00ff03 #define ARM_SMC_ID_TOS_REVISION 0xbf00ff03
// Firmware TRNG interface Function IDs
/*
SMC/HVC call to get the version of the TRNG backend,
Cf. [2], 2.1 TRNG_VERSION
Input values:
W0 0x8400_0050
W1-W7 Reserved (MBZ)
Return values:
Success (W0 > 0) W0[31] MBZ
W0[30:16] Major revision
W0[15:0] Minor revision
W1 - W3 Reserved (MBZ)
Error (W0 < 0)
NOT_SUPPORTED Function not implemented
*/
#define ARM_SMC_ID_TRNG_VERSION 0x84000050
/*
SMC/HVC call to check if a TRNG function ID is implemented by the backend,
Cf. [2], Section 2.2 TRNG_FEATURES
Input Values
W0 0x8400_0051
W1 trng_func_id
W2-W7 Reserved (MBZ)
Return values:
Success (W0 >= 0):
SUCCESS Function is implemented.
> 0 Function is implemented and
has specific capabilities,
see function definition.
Error (W0 < 0)
NOT_SUPPORTED Function with FID=trng_func_id
is not implemented
*/
#define ARM_SMC_ID_TRNG_FEATURES 0x84000051
/*
SMC/HVC call to get the UUID of the TRNG backend,
Cf. [2], Section 2.3 TRNG_GET_UUID
Input Values:
W0 0x8400_0052
W1-W7 Reserved (MBZ)
Return Values:
Success (W0 != -1)
W0 UUID[31:0]
W1 UUID[63:32]
W2 UUID[95:64]
W3 UUID[127:96]
Error (W0 = -1)
W0 NOT_SUPPORTED
*/
#define ARM_SMC_ID_TRNG_GET_UUID 0x84000052
/*
AARCH32 SMC/HVC call to get entropy bits, Cf. [2], Section 2.4 TRNG_RND.
Input values:
W0 0x8400_0053
W2-W7 Reserved (MBZ)
Return values:
Success (W0 = 0):
W0 MBZ
W1 Entropy[95:64]
W2 Entropy[63:32]
W3 Entropy[31:0]
Error (W0 < 0)
W0 NOT_SUPPORTED
NO_ENTROPY
INVALID_PARAMETERS
W1 - W3 Reserved (MBZ)
*/
#define ARM_SMC_ID_TRNG_RND_AARCH32 0x84000053
/*
AARCH64 SMC/HVC call to get entropy bits, Cf. [2], Section 2.4 TRNG_RND.
Input values:
X0 0xC400_0053
X2-X7 Reserved (MBZ)
Return values:
Success (X0 = 0):
X0 MBZ
X1 Entropy[191:128]
X2 Entropy[127:64]
X3 Entropy[63:0]
Error (X0 < 0)
X0 NOT_SUPPORTED
NO_ENTROPY
INVALID_PARAMETERS
X1 - X3 Reserved (MBZ)
*/
#define ARM_SMC_ID_TRNG_RND_AARCH64 0xC4000053
// Firmware TRNG status codes
#define TRNG_STATUS_SUCCESS (INT32)(0)
#define TRNG_STATUS_NOT_SUPPORTED (INT32)(-1)
#define TRNG_STATUS_INVALID_PARAMETER (INT32)(-2)
#define TRNG_STATUS_NO_ENTROPY (INT32)(-3)
#endif // ARM_STD_SMC_H_ #endif // ARM_STD_SMC_H_

View File

@@ -25,24 +25,29 @@
EFI_MEMORY_WT | EFI_MEMORY_WB | \ EFI_MEMORY_WT | EFI_MEMORY_WB | \
EFI_MEMORY_UCE) EFI_MEMORY_UCE)
/**
* The UEFI firmware must not use the ARM_MEMORY_REGION_ATTRIBUTE_NONSECURE_* attributes.
*
* The Non Secure memory attribute (ARM_MEMORY_REGION_ATTRIBUTE_NONSECURE_*) should only
* be used in Secure World to distinguished Secure to Non-Secure memory.
*/
typedef enum { typedef enum {
ARM_MEMORY_REGION_ATTRIBUTE_UNCACHED_UNBUFFERED = 0, ARM_MEMORY_REGION_ATTRIBUTE_UNCACHED_UNBUFFERED = 0,
ARM_MEMORY_REGION_ATTRIBUTE_NONSECURE_UNCACHED_UNBUFFERED,
ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK, ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK,
ARM_MEMORY_REGION_ATTRIBUTE_NONSECURE_WRITE_BACK,
// On some platforms, memory mapped flash region is designed as not supporting // On some platforms, memory mapped flash region is designed as not supporting
// shareable attribute, so WRITE_BACK_NONSHAREABLE is added for such special // shareable attribute, so WRITE_BACK_NONSHAREABLE is added for such special
// need. // need.
// Do NOT use below two attributes if you are not sure. // Do NOT use below two attributes if you are not sure.
ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK_NONSHAREABLE, ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK_NONSHAREABLE,
ARM_MEMORY_REGION_ATTRIBUTE_NONSECURE_WRITE_BACK_NONSHAREABLE,
// Special region types for memory that must be mapped with read-only or
// non-execute permissions from the very start, e.g., to support the use
// of the WXN virtual memory control.
ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK_RO,
ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK_XP,
ARM_MEMORY_REGION_ATTRIBUTE_WRITE_THROUGH, ARM_MEMORY_REGION_ATTRIBUTE_WRITE_THROUGH,
ARM_MEMORY_REGION_ATTRIBUTE_NONSECURE_WRITE_THROUGH,
ARM_MEMORY_REGION_ATTRIBUTE_DEVICE, ARM_MEMORY_REGION_ATTRIBUTE_DEVICE,
ARM_MEMORY_REGION_ATTRIBUTE_NONSECURE_DEVICE
} ARM_MEMORY_REGION_ATTRIBUTES; } ARM_MEMORY_REGION_ATTRIBUTES;
#define IS_ARM_MEMORY_REGION_ATTRIBUTES_SECURE(attr) ((UINT32)(attr) & 1) #define IS_ARM_MEMORY_REGION_ATTRIBUTES_SECURE(attr) ((UINT32)(attr) & 1)
@@ -110,9 +115,7 @@ typedef enum {
#define GET_MPIDR_AFF1(MpId) (((MpId) & ARM_CORE_AFF1) >> 8) #define GET_MPIDR_AFF1(MpId) (((MpId) & ARM_CORE_AFF1) >> 8)
#define GET_MPIDR_AFF2(MpId) (((MpId) & ARM_CORE_AFF2) >> 16) #define GET_MPIDR_AFF2(MpId) (((MpId) & ARM_CORE_AFF2) >> 16)
#define GET_MPIDR_AFF3(MpId) (((MpId) & ARM_CORE_AFF3) >> 32) #define GET_MPIDR_AFF3(MpId) (((MpId) & ARM_CORE_AFF3) >> 32)
#define GET_MPIDR_AFFINITY_BITS(MpId) ((MpId) & 0xFF00FFFFFF)
#define PRIMARY_CORE_ID (PcdGet32(PcdArmPrimaryCore) & ARM_CORE_MASK) #define PRIMARY_CORE_ID (PcdGet32(PcdArmPrimaryCore) & ARM_CORE_MASK)
#define MPIDR_MT_BIT BIT24
/** Reads the CCSIDR register for the specified cache. /** Reads the CCSIDR register for the specified cache.

View File

@@ -21,40 +21,6 @@ ArmConfigureMmu (
OUT UINTN *TranslationTableSize OPTIONAL OUT UINTN *TranslationTableSize OPTIONAL
); );
/**
Convert a region of memory to read-protected, by clearing the access flag.
@param BaseAddress The start of the region.
@param Length The size of the region.
@retval EFI_SUCCESS The attributes were set successfully.
@retval EFI_OUT_OF_RESOURCES The operation failed due to insufficient memory.
**/
EFI_STATUS
EFIAPI
ArmSetMemoryRegionNoAccess (
IN EFI_PHYSICAL_ADDRESS BaseAddress,
IN UINT64 Length
);
/**
Convert a region of memory to read-enabled, by setting the access flag.
@param BaseAddress The start of the region.
@param Length The size of the region.
@retval EFI_SUCCESS The attributes were set successfully.
@retval EFI_OUT_OF_RESOURCES The operation failed due to insufficient memory.
**/
EFI_STATUS
EFIAPI
ArmClearMemoryRegionNoAccess (
IN EFI_PHYSICAL_ADDRESS BaseAddress,
IN UINT64 Length
);
EFI_STATUS EFI_STATUS
EFIAPI EFIAPI
ArmSetMemoryRegionNoExec ( ArmSetMemoryRegionNoExec (
@@ -88,8 +54,7 @@ EFIAPI
ArmReplaceLiveTranslationEntry ( ArmReplaceLiveTranslationEntry (
IN UINT64 *Entry, IN UINT64 *Entry,
IN UINT64 Value, IN UINT64 Value,
IN UINT64 RegionStart, IN UINT64 RegionStart
IN BOOLEAN DisableMmu
); );
EFI_STATUS EFI_STATUS

View File

@@ -1,42 +0,0 @@
/** @file
Copyright (c) 2022, Arm Limited. All rights reserved.<BR>
SPDX-License-Identifier: BSD-2-Clause-Patent
**/
#ifndef ARM_MONITOR_LIB_H_
#define ARM_MONITOR_LIB_H_
/** The size of the SMC arguments is different between AArch64 and AArch32.
The native size is used for the arguments.
It will be casted to either HVC or SMC args.
*/
typedef struct {
UINTN Arg0;
UINTN Arg1;
UINTN Arg2;
UINTN Arg3;
UINTN Arg4;
UINTN Arg5;
UINTN Arg6;
UINTN Arg7;
} ARM_MONITOR_ARGS;
/** Monitor call.
An HyperVisor Call (HVC) or System Monitor Call (SMC) will be issued
depending on the default conduit. PcdMonitorConduitHvc determines the type
of the call: if true, do an HVC.
@param [in,out] Args Arguments for the HVC/SMC.
**/
VOID
EFIAPI
ArmMonitorCall (
IN OUT ARM_MONITOR_ARGS *Args
);
#endif // ARM_MONITOR_LIB_H_

View File

@@ -1,6 +1,5 @@
/** @file /** @file
* *
* Copyright (c) 2022, Ampere Computing LLC. All rights reserved.
* Copyright (c) 2021, NUVIA Inc. All rights reserved. * Copyright (c) 2021, NUVIA Inc. All rights reserved.
* Copyright (c) 2015, Hisilicon Limited. All rights reserved. * Copyright (c) 2015, Hisilicon Limited. All rights reserved.
* Copyright (c) 2015, Linaro Limited. All rights reserved. * Copyright (c) 2015, Linaro Limited. All rights reserved.
@@ -37,7 +36,6 @@ typedef struct {
} OEM_MISC_PROCESSOR_DATA; } OEM_MISC_PROCESSOR_DATA;
typedef enum { typedef enum {
BiosVersionType00,
ProductNameType01, ProductNameType01,
SerialNumType01, SerialNumType01,
UuidType01, UuidType01,
@@ -45,7 +43,7 @@ typedef enum {
VersionType01, VersionType01,
SkuNumberType01, SkuNumberType01,
FamilyType01, FamilyType01,
AssetTagType02, AssertTagType02,
SerialNumberType02, SerialNumberType02,
BoardManufacturerType02, BoardManufacturerType02,
ProductNameType02, ProductNameType02,
@@ -60,7 +58,6 @@ typedef enum {
SkuNumberType03, SkuNumberType03,
ProcessorPartNumType04, ProcessorPartNumType04,
ProcessorSerialNumType04, ProcessorSerialNumType04,
ProcessorVersionType04,
SmbiosHiiStringFieldMax SmbiosHiiStringFieldMax
} OEM_MISC_SMBIOS_HII_STRING_FIELD; } OEM_MISC_SMBIOS_HII_STRING_FIELD;
@@ -236,36 +233,4 @@ OemGetChassisNumPowerCords (
VOID VOID
); );
/**
Fetches the system UUID.
@param[out] SystemUuid The pointer to the buffer to store the System UUID.
**/
VOID
EFIAPI
OemGetSystemUuid (
OUT GUID *SystemUuid
);
/** Fetches the BIOS release.
@return The BIOS release.
**/
UINT16
EFIAPI
OemGetBiosRelease (
VOID
);
/** Fetches the embedded controller firmware release.
@return The embedded controller firmware release.
**/
UINT16
EFIAPI
OemGetEmbeddedControllerFirmwareRelease (
VOID
);
#endif // OEM_MISC_LIB_H_ #endif // OEM_MISC_LIB_H_

View File

@@ -94,6 +94,7 @@
GCC_ASM_EXPORT(ExceptionHandlersEnd) GCC_ASM_EXPORT(ExceptionHandlersEnd)
GCC_ASM_EXPORT(CommonCExceptionHandler) GCC_ASM_EXPORT(CommonCExceptionHandler)
GCC_ASM_EXPORT(RegisterEl0Stack)
.text .text
@@ -386,6 +387,6 @@ ASM_PFX(CommonExceptionEntry):
eret eret
ASM_FUNC(RegisterEl0Stack) ASM_PFX(RegisterEl0Stack):
msr sp_el0, x0 msr sp_el0, x0
ret ret

View File

@@ -4,7 +4,6 @@
* Copyright (c) 2008 - 2009, Apple Inc. All rights reserved.<BR> * Copyright (c) 2008 - 2009, Apple Inc. All rights reserved.<BR>
* Copyright (c) 2011-2021, Arm Limited. All rights reserved.<BR> * Copyright (c) 2011-2021, Arm Limited. All rights reserved.<BR>
* Copyright (c) 2016 HP Development Company, L.P. * Copyright (c) 2016 HP Development Company, L.P.
* Copyright (c) 2022, Intel Corporation. All rights reserved.<BR>
* *
* SPDX-License-Identifier: BSD-2-Clause-Patent * SPDX-License-Identifier: BSD-2-Clause-Patent
* *
@@ -195,6 +194,32 @@ CopyExceptionHandlers (
return RETURN_SUCCESS; return RETURN_SUCCESS;
} }
/**
Initializes all CPU interrupt/exceptions entries and provides the default interrupt/exception handlers.
Caller should try to get an array of interrupt and/or exception vectors that are in use and need to
persist by EFI_VECTOR_HANDOFF_INFO defined in PI 1.3 specification.
If caller cannot get reserved vector list or it does not exists, set VectorInfo to NULL.
If VectorInfo is not NULL, the exception vectors will be initialized per vector attribute accordingly.
@param[in] VectorInfo Pointer to reserved vector list.
@retval EFI_SUCCESS All CPU interrupt/exception entries have been successfully initialized
with default interrupt/exception handlers.
@retval EFI_INVALID_PARAMETER VectorInfo includes the invalid content if VectorInfo is not NULL.
@retval EFI_UNSUPPORTED This function is not supported.
**/
EFI_STATUS
EFIAPI
InitializeCpuInterruptHandlers (
IN EFI_VECTOR_HANDOFF_INFO *VectorInfo OPTIONAL
)
{
// not needed, this is what the CPU driver is for
return EFI_UNSUPPORTED;
}
/** /**
Registers a function to be called from the processor exception handler. (On ARM/AArch64 this only Registers a function to be called from the processor exception handler. (On ARM/AArch64 this only
provides exception handlers, not interrupt handling which is provided through the Hardware Interrupt provides exception handlers, not interrupt handling which is provided through the Hardware Interrupt
@@ -204,8 +229,8 @@ This function registers and enables the handler specified by ExceptionHandler fo
interrupt or exception type specified by ExceptionType. If ExceptionHandler is NULL, then the interrupt or exception type specified by ExceptionType. If ExceptionHandler is NULL, then the
handler for the processor interrupt or exception type specified by ExceptionType is uninstalled. handler for the processor interrupt or exception type specified by ExceptionType is uninstalled.
The installed handler is called once for each processor interrupt or exception. The installed handler is called once for each processor interrupt or exception.
NOTE: This function should be invoked after InitializeCpuExceptionHandlers() is invoked, NOTE: This function should be invoked after InitializeCpuExceptionHandlers() or
otherwise EFI_UNSUPPORTED returned. InitializeCpuInterruptHandlers() invoked, otherwise EFI_UNSUPPORTED returned.
@param[in] ExceptionType Defines which interrupt or exception to hook. @param[in] ExceptionType Defines which interrupt or exception to hook.
@param[in] ExceptionHandler A pointer to a function of type EFI_CPU_INTERRUPT_HANDLER that is called @param[in] ExceptionHandler A pointer to a function of type EFI_CPU_INTERRUPT_HANDLER that is called
@@ -287,25 +312,33 @@ CommonCExceptionHandler (
} }
/** /**
Setup separate stacks for certain exception handlers. Initializes all CPU exceptions entries with optional extra initializations.
If the input Buffer and BufferSize are both NULL, use global variable if possible.
@param[in] Buffer Point to buffer used to separate exception stack. By default, this method should include all functionalities implemented by
@param[in, out] BufferSize On input, it indicates the byte size of Buffer. InitializeCpuExceptionHandlers(), plus extra initialization works, if any.
If the size is not enough, the return status will This could be done by calling InitializeCpuExceptionHandlers() directly
be EFI_BUFFER_TOO_SMALL, and output BufferSize in this method besides the extra works.
will be the size it needs.
InitData is optional and its use and content are processor arch dependent.
The typical usage of it is to convey resources which have to be reserved
elsewhere and are necessary for the extra initializations of exception.
@param[in] VectorInfo Pointer to reserved vector list.
@param[in] InitData Pointer to data optional for extra initializations
of exception.
@retval EFI_SUCCESS The exceptions have been successfully
initialized.
@retval EFI_INVALID_PARAMETER VectorInfo or InitData contains invalid
content.
@retval EFI_SUCCESS The stacks are assigned successfully.
@retval EFI_UNSUPPORTED This function is not supported.
@retval EFI_BUFFER_TOO_SMALL This BufferSize is too small.
**/ **/
EFI_STATUS EFI_STATUS
EFIAPI EFIAPI
InitializeSeparateExceptionStacks ( InitializeCpuExceptionHandlersEx (
IN VOID *Buffer, IN EFI_VECTOR_HANDOFF_INFO *VectorInfo OPTIONAL,
IN OUT UINTN *BufferSize IN CPU_EXCEPTION_INIT_DATA *InitData OPTIONAL
) )
{ {
return EFI_SUCCESS; return InitializeCpuExceptionHandlers (VectorInfo);
} }

View File

@@ -1,29 +0,0 @@
/** @file
Arm HyperVisor Call (HVC) Null Library.
Copyright (c) 2022, Arm Limited. All rights reserved.<BR>
SPDX-License-Identifier: BSD-2-Clause-Patent
**/
#include <Library/ArmHvcLib.h>
#include <Library/DebugLib.h>
/**
Trigger an HVC call
HVC calls can take up to 8 arguments and return up to 4 return values.
Therefore, the 4 first fields in the ARM_HVC_ARGS structure are used
for both input and output values.
@param [in,out] Args Arguments for the HVC call.
**/
VOID
ArmCallHvc (
IN OUT ARM_HVC_ARGS *Args
)
{
ASSERT (FALSE);
return;
}

View File

@@ -1,22 +0,0 @@
## @file
# Arm Hvc Null Library
#
# Copyright (c) 2022, Arm Limited. All rights reserved.<BR>
#
# SPDX-License-Identifier: BSD-2-Clause-Patent
##
[Defines]
INF_VERSION = 1.29
BASE_NAME = ArmHvcLibNull
FILE_GUID = 02076A46-D6DB-48DD-8E5F-153172DD73A1
MODULE_TYPE = BASE
VERSION_STRING = 1.0
LIBRARY_CLASS = ArmHvcLib
[Sources]
ArmHvcLibNull.c
[Packages]
ArmPkg/ArmPkg.dec
MdePkg/MdePkg.dec

View File

@@ -40,43 +40,7 @@ ArmCleanInvalidateDataCacheEntryBySetWay (
UINTN UINTN
EFIAPI EFIAPI
ArmReadIdAA64Dfr0 ( ArmReadIdAA64Pfr0 (
VOID
);
UINTN
EFIAPI
ArmReadIdAA64Dfr1 (
VOID
);
UINTN
EFIAPI
ArmReadIdAA64Isar0 (
VOID
);
UINTN
EFIAPI
ArmReadIdAA64Isar1 (
VOID
);
UINTN
EFIAPI
ArmReadIdAA64Isar2 (
VOID
);
UINTN
EFIAPI
ArmReadIdAA64Mmfr0 (
VOID
);
UINTN
EFIAPI
ArmReadIdAA64Mmfr1 (
VOID VOID
); );
@@ -90,16 +54,4 @@ ArmReadIdAA64Mmfr2 (
VOID VOID
); );
UINTN
EFIAPI
ArmReadIdAA64Pfr0 (
VOID
);
UINTN
EFIAPI
ArmReadIdAA64Pfr1 (
VOID
);
#endif // AARCH64_LIB_H_ #endif // AARCH64_LIB_H_

View File

@@ -425,6 +425,10 @@ ASM_FUNC(ArmCallWFI)
wfi wfi
ret ret
ASM_FUNC(ArmReadIdAA64Mmfr2)
mrs x0, ID_AA64MMFR2_EL1 // read EL1 MMFR2
ret
ASM_FUNC(ArmReadMpidr) ASM_FUNC(ArmReadMpidr)
mrs x0, mpidr_el1 // read EL1 MPIDR mrs x0, mpidr_el1 // read EL1 MPIDR
ret ret
@@ -448,6 +452,10 @@ ASM_FUNC(ArmIsArchTimerImplemented)
ret ret
ASM_FUNC(ArmReadIdAA64Pfr0)
mrs x0, id_aa64pfr0_el1 // Read ID_AA64PFR0 Register
ret
// VOID ArmWriteHcr(UINTN Hcr) // VOID ArmWriteHcr(UINTN Hcr)
ASM_FUNC(ArmWriteHcr) ASM_FUNC(ArmWriteHcr)
@@ -474,54 +482,4 @@ ASM_FUNC(ArmWriteCntHctl)
msr cnthctl_el2, x0 msr cnthctl_el2, x0
ret ret
ASM_FUNC(ArmReadIdAA64Dfr0)
mrs x0, ID_AA64DFR0_EL1
ret
ASM_FUNC(ArmReadIdAA64Dfr1)
mrs x0, ID_AA64DFR1_EL1
ret
ASM_FUNC(ArmReadIdAA64Isar0)
mrs x0, ID_AA64ISAR0_EL1
ret
ASM_FUNC(ArmReadIdAA64Isar1)
mrs x0, ID_AA64ISAR1_EL1
ret
ASM_FUNC(ArmReadIdAA64Isar2)
mrs x0, ID_AA64ISAR2_EL1
ret
ASM_FUNC(ArmReadIdAA64Mmfr0)
mrs x0, ID_AA64MMFR0_EL1
ret
ASM_FUNC(ArmReadIdAA64Mmfr1)
mrs x0, ID_AA64MMFR1_EL1
ret
ASM_FUNC(ArmReadIdAA64Mmfr2)
mrs x0, ID_AA64MMFR2_EL1
ret
ASM_FUNC(ArmReadIdAA64Pfr0)
mrs x0, ID_AA64PFR0_EL1
ret
ASM_FUNC(ArmReadIdAA64Pfr1)
mrs x0, ID_AA64PFR1_EL1
ret
ASM_FUNCTION_REMOVE_IF_UNREFERENCED ASM_FUNCTION_REMOVE_IF_UNREFERENCED

View File

@@ -16,7 +16,6 @@
.set CTRL_C_BIT, (1 << 2) .set CTRL_C_BIT, (1 << 2)
.set CTRL_B_BIT, (1 << 7) .set CTRL_B_BIT, (1 << 7)
.set CTRL_I_BIT, (1 << 12) .set CTRL_I_BIT, (1 << 12)
.set CTRL_AFE_BIT,(1 << 29)
ASM_FUNC(ArmInvalidateDataCacheEntryByMVA) ASM_FUNC(ArmInvalidateDataCacheEntryByMVA)
@@ -65,7 +64,6 @@ ASM_FUNC(ArmInvalidateInstructionCache)
ASM_FUNC(ArmEnableMmu) ASM_FUNC(ArmEnableMmu)
mrc p15,0,R0,c1,c0,0 mrc p15,0,R0,c1,c0,0
orr R0,R0,#1 orr R0,R0,#1
orr R0,R0,#CTRL_AFE_BIT
mcr p15,0,R0,c1,c0,0 mcr p15,0,R0,c1,c0,0
dsb dsb
isb isb

View File

@@ -10,7 +10,6 @@
**/ **/
#include <Uefi.h> #include <Uefi.h>
#include <Pi/PiMultiPhase.h>
#include <Chipset/AArch64.h> #include <Chipset/AArch64.h>
#include <Library/BaseMemoryLib.h> #include <Library/BaseMemoryLib.h>
#include <Library/CacheMaintenanceLib.h> #include <Library/CacheMaintenanceLib.h>
@@ -19,17 +18,6 @@
#include <Library/ArmMmuLib.h> #include <Library/ArmMmuLib.h>
#include <Library/BaseLib.h> #include <Library/BaseLib.h>
#include <Library/DebugLib.h> #include <Library/DebugLib.h>
#include <Library/HobLib.h>
STATIC
VOID (
EFIAPI *mReplaceLiveEntryFunc
)(
IN UINT64 *Entry,
IN UINT64 Value,
IN UINT64 RegionStart,
IN BOOLEAN DisableMmu
) = ArmReplaceLiveTranslationEntry;
STATIC STATIC
UINT64 UINT64
@@ -37,47 +25,33 @@ ArmMemoryAttributeToPageAttribute (
IN ARM_MEMORY_REGION_ATTRIBUTES Attributes IN ARM_MEMORY_REGION_ATTRIBUTES Attributes
) )
{ {
UINT64 Permissions;
switch (Attributes) {
case ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK_RO:
Permissions = TT_AP_NO_RO;
break;
case ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK_XP:
case ARM_MEMORY_REGION_ATTRIBUTE_DEVICE:
if (ArmReadCurrentEL () == AARCH64_EL2) {
Permissions = TT_XN_MASK;
} else {
Permissions = TT_UXN_MASK | TT_PXN_MASK;
}
break;
default:
Permissions = 0;
break;
}
switch (Attributes) { switch (Attributes) {
case ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK_NONSHAREABLE: case ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK_NONSHAREABLE:
case ARM_MEMORY_REGION_ATTRIBUTE_NONSECURE_WRITE_BACK_NONSHAREABLE:
return TT_ATTR_INDX_MEMORY_WRITE_BACK; return TT_ATTR_INDX_MEMORY_WRITE_BACK;
case ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK: case ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK:
case ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK_RO: case ARM_MEMORY_REGION_ATTRIBUTE_NONSECURE_WRITE_BACK:
case ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK_XP: return TT_ATTR_INDX_MEMORY_WRITE_BACK | TT_SH_INNER_SHAREABLE;
return TT_ATTR_INDX_MEMORY_WRITE_BACK | TT_SH_INNER_SHAREABLE | Permissions;
case ARM_MEMORY_REGION_ATTRIBUTE_WRITE_THROUGH: case ARM_MEMORY_REGION_ATTRIBUTE_WRITE_THROUGH:
case ARM_MEMORY_REGION_ATTRIBUTE_NONSECURE_WRITE_THROUGH:
return TT_ATTR_INDX_MEMORY_WRITE_THROUGH | TT_SH_INNER_SHAREABLE; return TT_ATTR_INDX_MEMORY_WRITE_THROUGH | TT_SH_INNER_SHAREABLE;
// Uncached and device mappings are treated as outer shareable by default, // Uncached and device mappings are treated as outer shareable by default,
case ARM_MEMORY_REGION_ATTRIBUTE_UNCACHED_UNBUFFERED: case ARM_MEMORY_REGION_ATTRIBUTE_UNCACHED_UNBUFFERED:
case ARM_MEMORY_REGION_ATTRIBUTE_NONSECURE_UNCACHED_UNBUFFERED:
return TT_ATTR_INDX_MEMORY_NON_CACHEABLE; return TT_ATTR_INDX_MEMORY_NON_CACHEABLE;
default: default:
ASSERT (0); ASSERT (0);
case ARM_MEMORY_REGION_ATTRIBUTE_DEVICE: case ARM_MEMORY_REGION_ATTRIBUTE_DEVICE:
return TT_ATTR_INDX_DEVICE_MEMORY | Permissions; case ARM_MEMORY_REGION_ATTRIBUTE_NONSECURE_DEVICE:
if (ArmReadCurrentEL () == AARCH64_EL2) {
return TT_ATTR_INDX_DEVICE_MEMORY | TT_XN_MASK;
} else {
return TT_ATTR_INDX_DEVICE_MEMORY | TT_UXN_MASK | TT_PXN_MASK;
}
} }
} }
@@ -109,40 +83,14 @@ ReplaceTableEntry (
IN UINT64 *Entry, IN UINT64 *Entry,
IN UINT64 Value, IN UINT64 Value,
IN UINT64 RegionStart, IN UINT64 RegionStart,
IN UINT64 BlockMask,
IN BOOLEAN IsLiveBlockMapping IN BOOLEAN IsLiveBlockMapping
) )
{ {
BOOLEAN DisableMmu; if (!ArmMmuEnabled () || !IsLiveBlockMapping) {
//
// Replacing a live block entry with a table entry (or vice versa) requires a
// break-before-make sequence as per the architecture. This means the mapping
// must be made invalid and cleaned from the TLBs first, and this is a bit of
// a hassle if the mapping in question covers the code that is actually doing
// the mapping and the unmapping, and so we only bother with this if actually
// necessary.
//
if (!IsLiveBlockMapping || !ArmMmuEnabled ()) {
// If the mapping is not a live block mapping, or the MMU is not on yet, we
// can simply overwrite the entry.
*Entry = Value; *Entry = Value;
ArmUpdateTranslationTableEntry (Entry, (VOID *)(UINTN)RegionStart); ArmUpdateTranslationTableEntry (Entry, (VOID *)(UINTN)RegionStart);
} else { } else {
// If the mapping in question does not cover the code that updates the ArmReplaceLiveTranslationEntry (Entry, Value, RegionStart);
// entry in memory, or the entry that we are intending to update, we can
// use an ordinary break before make. Otherwise, we will need to
// temporarily disable the MMU.
DisableMmu = FALSE;
if ((((RegionStart ^ (UINTN)mReplaceLiveEntryFunc) & ~BlockMask) == 0) ||
(((RegionStart ^ (UINTN)Entry) & ~BlockMask) == 0))
{
DisableMmu = TRUE;
DEBUG ((DEBUG_WARN, "%a: splitting block entry with MMU disabled\n", __func__));
}
mReplaceLiveEntryFunc (Entry, Value, RegionStart, DisableMmu);
} }
} }
@@ -212,8 +160,7 @@ UpdateRegionMappingRecursive (
IN UINT64 AttributeSetMask, IN UINT64 AttributeSetMask,
IN UINT64 AttributeClearMask, IN UINT64 AttributeClearMask,
IN UINT64 *PageTable, IN UINT64 *PageTable,
IN UINTN Level, IN UINTN Level
IN BOOLEAN TableIsLive
) )
{ {
UINTN BlockShift; UINTN BlockShift;
@@ -223,7 +170,6 @@ UpdateRegionMappingRecursive (
UINT64 EntryValue; UINT64 EntryValue;
VOID *TranslationTable; VOID *TranslationTable;
EFI_STATUS Status; EFI_STATUS Status;
BOOLEAN NextTableIsLive;
ASSERT (((RegionStart | RegionEnd) & EFI_PAGE_MASK) == 0); ASSERT (((RegionStart | RegionEnd) & EFI_PAGE_MASK) == 0);
@@ -233,7 +179,7 @@ UpdateRegionMappingRecursive (
DEBUG (( DEBUG ((
DEBUG_VERBOSE, DEBUG_VERBOSE,
"%a(%d): %llx - %llx set %lx clr %lx\n", "%a(%d): %llx - %llx set %lx clr %lx\n",
__func__, __FUNCTION__,
Level, Level,
RegionStart, RegionStart,
RegionEnd, RegionEnd,
@@ -251,30 +197,16 @@ UpdateRegionMappingRecursive (
// than a block, and recurse to create the block or page entries at // than a block, and recurse to create the block or page entries at
// the next level. No block mappings are allowed at all at level 0, // the next level. No block mappings are allowed at all at level 0,
// so in that case, we have to recurse unconditionally. // so in that case, we have to recurse unconditionally.
// // If we are changing a table entry and the AttributeClearMask is non-zero,
// One special case to take into account is any region that covers the page // we cannot replace it with a block entry without potentially losing
// table itself: if we'd cover such a region with block mappings, we are // attribute information, so keep the table entry in that case.
// more likely to end up in the situation later where we need to disable
// the MMU in order to update page table entries safely, so prefer page
// mappings in that particular case.
// //
if ((Level == 0) || (((RegionStart | BlockEnd) & BlockMask) != 0) || if ((Level == 0) || (((RegionStart | BlockEnd) & BlockMask) != 0) ||
((Level < 3) && (((UINT64)PageTable & ~BlockMask) == RegionStart)) || (IsTableEntry (*Entry, Level) && (AttributeClearMask != 0)))
IsTableEntry (*Entry, Level))
{ {
ASSERT (Level < 3); ASSERT (Level < 3);
if (!IsTableEntry (*Entry, Level)) { if (!IsTableEntry (*Entry, Level)) {
//
// If the region we are trying to map is already covered by a block
// entry with the right attributes, don't bother splitting it up.
//
if (IsBlockEntry (*Entry, Level) &&
((*Entry & TT_ATTRIBUTES_MASK & ~AttributeClearMask) == AttributeSetMask))
{
continue;
}
// //
// No table entry exists yet, so we need to allocate a page table // No table entry exists yet, so we need to allocate a page table
// for the next level. // for the next level.
@@ -305,8 +237,7 @@ UpdateRegionMappingRecursive (
*Entry & TT_ATTRIBUTES_MASK, *Entry & TT_ATTRIBUTES_MASK,
0, 0,
TranslationTable, TranslationTable,
Level + 1, Level + 1
FALSE
); );
if (EFI_ERROR (Status)) { if (EFI_ERROR (Status)) {
// //
@@ -318,11 +249,8 @@ UpdateRegionMappingRecursive (
return Status; return Status;
} }
} }
NextTableIsLive = FALSE;
} else { } else {
TranslationTable = (VOID *)(UINTN)(*Entry & TT_ADDRESS_MASK_BLOCK_ENTRY); TranslationTable = (VOID *)(UINTN)(*Entry & TT_ADDRESS_MASK_BLOCK_ENTRY);
NextTableIsLive = TableIsLive;
} }
// //
@@ -334,8 +262,7 @@ UpdateRegionMappingRecursive (
AttributeSetMask, AttributeSetMask,
AttributeClearMask, AttributeClearMask,
TranslationTable, TranslationTable,
Level + 1, Level + 1
NextTableIsLive
); );
if (EFI_ERROR (Status)) { if (EFI_ERROR (Status)) {
if (!IsTableEntry (*Entry, Level)) { if (!IsTableEntry (*Entry, Level)) {
@@ -358,8 +285,7 @@ UpdateRegionMappingRecursive (
Entry, Entry,
EntryValue, EntryValue,
RegionStart, RegionStart,
BlockMask, IsBlockEntry (*Entry, Level)
TableIsLive && IsBlockEntry (*Entry, Level)
); );
} }
} else { } else {
@@ -368,7 +294,20 @@ UpdateRegionMappingRecursive (
EntryValue |= (Level == 3) ? TT_TYPE_BLOCK_ENTRY_LEVEL3 EntryValue |= (Level == 3) ? TT_TYPE_BLOCK_ENTRY_LEVEL3
: TT_TYPE_BLOCK_ENTRY; : TT_TYPE_BLOCK_ENTRY;
ReplaceTableEntry (Entry, EntryValue, RegionStart, BlockMask, FALSE); if (IsTableEntry (*Entry, Level)) {
//
// We are replacing a table entry with a block entry. This is only
// possible if we are keeping none of the original attributes.
// We can free the table entry's page table, and all the ones below
// it, since we are dropping the only possible reference to it.
//
ASSERT (AttributeClearMask == 0);
TranslationTable = (VOID *)(UINTN)(*Entry & TT_ADDRESS_MASK_BLOCK_ENTRY);
ReplaceTableEntry (Entry, EntryValue, RegionStart, TRUE);
FreePageTablesRecursive (TranslationTable, Level + 1);
} else {
ReplaceTableEntry (Entry, EntryValue, RegionStart, FALSE);
}
} }
} }
@@ -381,9 +320,7 @@ UpdateRegionMapping (
IN UINT64 RegionStart, IN UINT64 RegionStart,
IN UINT64 RegionLength, IN UINT64 RegionLength,
IN UINT64 AttributeSetMask, IN UINT64 AttributeSetMask,
IN UINT64 AttributeClearMask, IN UINT64 AttributeClearMask
IN UINT64 *RootTable,
IN BOOLEAN TableIsLive
) )
{ {
UINTN T0SZ; UINTN T0SZ;
@@ -399,9 +336,8 @@ UpdateRegionMapping (
RegionStart + RegionLength, RegionStart + RegionLength,
AttributeSetMask, AttributeSetMask,
AttributeClearMask, AttributeClearMask,
RootTable, ArmGetTTBR0BaseAddress (),
GetRootTableLevel (T0SZ), GetRootTableLevel (T0SZ)
TableIsLive
); );
} }
@@ -416,9 +352,7 @@ FillTranslationTable (
MemoryRegion->VirtualBase, MemoryRegion->VirtualBase,
MemoryRegion->Length, MemoryRegion->Length,
ArmMemoryAttributeToPageAttribute (MemoryRegion->Attributes) | TT_AF, ArmMemoryAttributeToPageAttribute (MemoryRegion->Attributes) | TT_AF,
0, 0
RootTable,
FALSE
); );
} }
@@ -462,11 +396,7 @@ GcdAttributeToPageAttribute (
PageAttributes |= TT_AP_NO_RO; PageAttributes |= TT_AP_NO_RO;
} }
if ((GcdAttributes & EFI_MEMORY_RP) == 0) { return PageAttributes | TT_AF;
PageAttributes |= TT_AF;
}
return PageAttributes;
} }
EFI_STATUS EFI_STATUS
@@ -487,18 +417,16 @@ ArmSetMemoryAttributes (
// No memory type was set in Attributes, so we are going to update the // No memory type was set in Attributes, so we are going to update the
// permissions only. // permissions only.
// //
PageAttributes &= TT_AP_MASK | TT_UXN_MASK | TT_PXN_MASK | TT_AF; PageAttributes &= TT_AP_MASK | TT_UXN_MASK | TT_PXN_MASK;
PageAttributeMask = ~(TT_ADDRESS_MASK_BLOCK_ENTRY | TT_AP_MASK | PageAttributeMask = ~(TT_ADDRESS_MASK_BLOCK_ENTRY | TT_AP_MASK |
TT_PXN_MASK | TT_XN_MASK | TT_AF); TT_PXN_MASK | TT_XN_MASK);
} }
return UpdateRegionMapping ( return UpdateRegionMapping (
BaseAddress, BaseAddress,
Length, Length,
PageAttributes, PageAttributes,
PageAttributeMask, PageAttributeMask
ArmGetTTBR0BaseAddress (),
TRUE
); );
} }
@@ -511,14 +439,7 @@ SetMemoryRegionAttribute (
IN UINT64 BlockEntryMask IN UINT64 BlockEntryMask
) )
{ {
return UpdateRegionMapping ( return UpdateRegionMapping (BaseAddress, Length, Attributes, BlockEntryMask);
BaseAddress,
Length,
Attributes,
BlockEntryMask,
ArmGetTTBR0BaseAddress (),
TRUE
);
} }
EFI_STATUS EFI_STATUS
@@ -562,54 +483,6 @@ ArmClearMemoryRegionNoExec (
); );
} }
/**
Convert a region of memory to read-protected, by clearing the access flag.
@param BaseAddress The start of the region.
@param Length The size of the region.
@retval EFI_SUCCESS The attributes were set successfully.
@retval EFI_OUT_OF_RESOURCES The operation failed due to insufficient memory.
**/
EFI_STATUS
ArmSetMemoryRegionNoAccess (
IN EFI_PHYSICAL_ADDRESS BaseAddress,
IN UINT64 Length
)
{
return SetMemoryRegionAttribute (
BaseAddress,
Length,
0,
~(TT_ADDRESS_MASK_BLOCK_ENTRY | TT_AF)
);
}
/**
Convert a region of memory to read-enabled, by setting the access flag.
@param BaseAddress The start of the region.
@param Length The size of the region.
@retval EFI_SUCCESS The attributes were set successfully.
@retval EFI_OUT_OF_RESOURCES The operation failed due to insufficient memory.
**/
EFI_STATUS
ArmClearMemoryRegionNoAccess (
IN EFI_PHYSICAL_ADDRESS BaseAddress,
IN UINT64 Length
)
{
return SetMemoryRegionAttribute (
BaseAddress,
Length,
TT_AF,
~TT_ADDRESS_MASK_BLOCK_ENTRY
);
}
EFI_STATUS EFI_STATUS
ArmSetMemoryRegionReadOnly ( ArmSetMemoryRegionReadOnly (
IN EFI_PHYSICAL_ADDRESS BaseAddress, IN EFI_PHYSICAL_ADDRESS BaseAddress,
@@ -740,7 +613,7 @@ ArmConfigureMmu (
// loss of coherency when using mismatched attributes, and given that memory // loss of coherency when using mismatched attributes, and given that memory
// is mapped cacheable except for extraordinary cases (such as non-coherent // is mapped cacheable except for extraordinary cases (such as non-coherent
// DMA), have the page table walker perform cached accesses as well, and // DMA), have the page table walker perform cached accesses as well, and
// assert below that matches the attributes we use for CPU accesses to // assert below that that matches the attributes we use for CPU accesses to
// the region. // the region.
// //
TCR |= TCR_SH_INNER_SHAREABLE | TCR |= TCR_SH_INNER_SHAREABLE |
@@ -756,6 +629,14 @@ ArmConfigureMmu (
return EFI_OUT_OF_RESOURCES; return EFI_OUT_OF_RESOURCES;
} }
//
// We set TTBR0 just after allocating the table to retrieve its location from
// the subsequent functions without needing to pass this value across the
// functions. The MMU is only enabled after the translation tables are
// populated.
//
ArmSetTTBR0 (TranslationTable);
if (TranslationTableBase != NULL) { if (TranslationTableBase != NULL) {
*TranslationTableBase = TranslationTable; *TranslationTableBase = TranslationTable;
} }
@@ -764,7 +645,6 @@ ArmConfigureMmu (
*TranslationTableSize = RootTableEntryCount * sizeof (UINT64); *TranslationTableSize = RootTableEntryCount * sizeof (UINT64);
} }
if (!ArmMmuEnabled ()) {
// //
// Make sure we are not inadvertently hitting in the caches // Make sure we are not inadvertently hitting in the caches
// when populating the page tables. // when populating the page tables.
@@ -773,8 +653,6 @@ ArmConfigureMmu (
TranslationTable, TranslationTable,
RootTableEntryCount * sizeof (UINT64) RootTableEntryCount * sizeof (UINT64)
); );
}
ZeroMem (TranslationTable, RootTableEntryCount * sizeof (UINT64)); ZeroMem (TranslationTable, RootTableEntryCount * sizeof (UINT64));
while (MemoryTable->Length != 0) { while (MemoryTable->Length != 0) {
@@ -799,17 +677,12 @@ ArmConfigureMmu (
MAIR_ATTR (TT_ATTR_INDX_MEMORY_WRITE_BACK, MAIR_ATTR_NORMAL_MEMORY_WRITE_BACK) MAIR_ATTR (TT_ATTR_INDX_MEMORY_WRITE_BACK, MAIR_ATTR_NORMAL_MEMORY_WRITE_BACK)
); );
ArmSetTTBR0 (TranslationTable);
if (!ArmMmuEnabled ()) {
ArmDisableAlignmentCheck (); ArmDisableAlignmentCheck ();
ArmEnableStackAlignmentCheck (); ArmEnableStackAlignmentCheck ();
ArmEnableInstructionCache (); ArmEnableInstructionCache ();
ArmEnableDataCache (); ArmEnableDataCache ();
ArmEnableMmu (); ArmEnableMmu ();
}
return EFI_SUCCESS; return EFI_SUCCESS;
FreeTranslationTable: FreeTranslationTable:
@@ -824,12 +697,7 @@ ArmMmuBaseLibConstructor (
) )
{ {
extern UINT32 ArmReplaceLiveTranslationEntrySize; extern UINT32 ArmReplaceLiveTranslationEntrySize;
VOID *Hob;
Hob = GetFirstGuidHob (&gArmMmuReplaceLiveTranslationEntryFuncGuid);
if (Hob != NULL) {
mReplaceLiveEntryFunc = *(VOID **)GET_GUID_HOB_DATA (Hob);
} else {
// //
// The ArmReplaceLiveTranslationEntry () helper function may be invoked // The ArmReplaceLiveTranslationEntry () helper function may be invoked
// with the MMU off so we have to ensure that it gets cleaned to the PoC // with the MMU off so we have to ensure that it gets cleaned to the PoC
@@ -838,7 +706,6 @@ ArmMmuBaseLibConstructor (
(VOID *)(UINTN)ArmReplaceLiveTranslationEntry, (VOID *)(UINTN)ArmReplaceLiveTranslationEntry,
ArmReplaceLiveTranslationEntrySize ArmReplaceLiveTranslationEntrySize
); );
}
return RETURN_SUCCESS; return RETURN_SUCCESS;
} }

View File

@@ -12,14 +12,6 @@
.macro __replace_entry, el .macro __replace_entry, el
// check whether we should disable the MMU
cbz x3, .L1_\@
// clean and invalidate first so that we don't clobber
// adjacent entries that are dirty in the caches
dc civac, x0
dsb nsh
// disable the MMU // disable the MMU
mrs x8, sctlr_el\el mrs x8, sctlr_el\el
bic x9, x8, #CTRL_M_BIT bic x9, x8, #CTRL_M_BIT
@@ -46,28 +38,6 @@
// re-enable the MMU // re-enable the MMU
msr sctlr_el\el, x8 msr sctlr_el\el, x8
isb isb
b .L2_\@
.L1_\@:
// write invalid entry
str xzr, [x0]
dsb nshst
// flush translations for the target address from the TLBs
lsr x2, x2, #12
.if \el == 1
tlbi vaae1, x2
.else
tlbi vae\el, x2
.endif
dsb nsh
// write updated entry
str x1, [x0]
dsb nshst
isb
.L2_\@:
.endm .endm
//VOID //VOID
@@ -76,17 +46,19 @@
// IN UINT64 Value, // IN UINT64 Value,
// IN UINT64 Address // IN UINT64 Address
// ) // )
// ASM_FUNC(ArmReplaceLiveTranslationEntry)
// Align this routine to a log2 upper bound of its size, so that it is
// guaranteed not to cross a page or block boundary.
ASM_FUNC_ALIGN(ArmReplaceLiveTranslationEntry, 0x200)
// disable interrupts // disable interrupts
mrs x4, daif mrs x4, daif
msr daifset, #0xf msr daifset, #0xf
isb isb
EL1_OR_EL2_OR_EL3(x5) // clean and invalidate first so that we don't clobber
// adjacent entries that are dirty in the caches
dc civac, x0
dsb nsh
EL1_OR_EL2_OR_EL3(x3)
1:__replace_entry 1 1:__replace_entry 1
b 4f b 4f
2:__replace_entry 2 2:__replace_entry 2
@@ -100,9 +72,3 @@ ASM_GLOBAL ASM_PFX(ArmReplaceLiveTranslationEntrySize)
ASM_PFX(ArmReplaceLiveTranslationEntrySize): ASM_PFX(ArmReplaceLiveTranslationEntrySize):
.long . - ArmReplaceLiveTranslationEntry .long . - ArmReplaceLiveTranslationEntry
// Double check that we did not overrun the assumed maximum size or cross a
// 0x200 boundary (and thus implicitly not any larger power of two, including
// the page size).
.balign 0x200
.org ArmReplaceLiveTranslationEntry + 0x200

View File

@@ -12,7 +12,6 @@
#include <Library/ArmMmuLib.h> #include <Library/ArmMmuLib.h>
#include <Library/CacheMaintenanceLib.h> #include <Library/CacheMaintenanceLib.h>
#include <Library/DebugLib.h> #include <Library/DebugLib.h>
#include <Library/HobLib.h>
EFI_STATUS EFI_STATUS
EFIAPI EFIAPI
@@ -22,8 +21,6 @@ ArmMmuPeiLibConstructor (
) )
{ {
extern UINT32 ArmReplaceLiveTranslationEntrySize; extern UINT32 ArmReplaceLiveTranslationEntrySize;
VOID *ArmReplaceLiveTranslationEntryFunc;
VOID *Hob;
EFI_FV_FILE_INFO FileInfo; EFI_FV_FILE_INFO FileInfo;
EFI_STATUS Status; EFI_STATUS Status;
@@ -45,20 +42,6 @@ ArmMmuPeiLibConstructor (
(UINTN)ArmReplaceLiveTranslationEntry + ArmReplaceLiveTranslationEntrySize)) (UINTN)ArmReplaceLiveTranslationEntry + ArmReplaceLiveTranslationEntrySize))
{ {
DEBUG ((DEBUG_INFO, "ArmMmuLib: skipping cache maintenance on XIP PEIM\n")); DEBUG ((DEBUG_INFO, "ArmMmuLib: skipping cache maintenance on XIP PEIM\n"));
//
// Expose the XIP version of the ArmReplaceLiveTranslationEntry() routine
// via a HOB so we can fall back to it later when we need to split block
// mappings in a way that adheres to break-before-make requirements.
//
ArmReplaceLiveTranslationEntryFunc = ArmReplaceLiveTranslationEntry;
Hob = BuildGuidDataHob (
&gArmMmuReplaceLiveTranslationEntryFuncGuid,
&ArmReplaceLiveTranslationEntryFunc,
sizeof ArmReplaceLiveTranslationEntryFunc
);
ASSERT (Hob != NULL);
} else { } else {
DEBUG ((DEBUG_INFO, "ArmMmuLib: performing cache maintenance on shadowed PEIM\n")); DEBUG ((DEBUG_INFO, "ArmMmuLib: performing cache maintenance on shadowed PEIM\n"));
// //

View File

@@ -15,16 +15,16 @@
UINT32 UINT32
ConvertSectionAttributesToPageAttributes ( ConvertSectionAttributesToPageAttributes (
IN UINT32 SectionAttributes IN UINT32 SectionAttributes,
IN BOOLEAN IsLargePage
) )
{ {
UINT32 PageAttributes; UINT32 PageAttributes;
PageAttributes = 0; PageAttributes = 0;
PageAttributes |= TT_DESCRIPTOR_CONVERT_TO_PAGE_CACHE_POLICY (SectionAttributes); PageAttributes |= TT_DESCRIPTOR_CONVERT_TO_PAGE_CACHE_POLICY (SectionAttributes, IsLargePage);
PageAttributes |= TT_DESCRIPTOR_CONVERT_TO_PAGE_AP (SectionAttributes); PageAttributes |= TT_DESCRIPTOR_CONVERT_TO_PAGE_AP (SectionAttributes);
PageAttributes |= TT_DESCRIPTOR_CONVERT_TO_PAGE_AF (SectionAttributes); PageAttributes |= TT_DESCRIPTOR_CONVERT_TO_PAGE_XN (SectionAttributes, IsLargePage);
PageAttributes |= TT_DESCRIPTOR_CONVERT_TO_PAGE_XN (SectionAttributes);
PageAttributes |= TT_DESCRIPTOR_CONVERT_TO_PAGE_NG (SectionAttributes); PageAttributes |= TT_DESCRIPTOR_CONVERT_TO_PAGE_NG (SectionAttributes);
PageAttributes |= TT_DESCRIPTOR_CONVERT_TO_PAGE_S (SectionAttributes); PageAttributes |= TT_DESCRIPTOR_CONVERT_TO_PAGE_S (SectionAttributes);

View File

@@ -100,27 +100,24 @@ PopulateLevel2PageTable (
switch (Attributes) { switch (Attributes) {
case ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK: case ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK:
case ARM_MEMORY_REGION_ATTRIBUTE_NONSECURE_WRITE_BACK:
PageAttributes = TT_DESCRIPTOR_PAGE_WRITE_BACK; PageAttributes = TT_DESCRIPTOR_PAGE_WRITE_BACK;
break; break;
case ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK_NONSHAREABLE: case ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK_NONSHAREABLE:
case ARM_MEMORY_REGION_ATTRIBUTE_NONSECURE_WRITE_BACK_NONSHAREABLE:
PageAttributes = TT_DESCRIPTOR_PAGE_WRITE_BACK; PageAttributes = TT_DESCRIPTOR_PAGE_WRITE_BACK;
PageAttributes &= ~TT_DESCRIPTOR_PAGE_S_SHARED; PageAttributes &= ~TT_DESCRIPTOR_PAGE_S_SHARED;
break; break;
case ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK_RO:
PageAttributes = TT_DESCRIPTOR_PAGE_WRITE_BACK;
PageAttributes |= TT_DESCRIPTOR_PAGE_AP_NO_RO;
break;
case ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK_XP:
PageAttributes = TT_DESCRIPTOR_PAGE_WRITE_BACK;
PageAttributes |= TT_DESCRIPTOR_PAGE_XN_MASK;
break;
case ARM_MEMORY_REGION_ATTRIBUTE_WRITE_THROUGH: case ARM_MEMORY_REGION_ATTRIBUTE_WRITE_THROUGH:
case ARM_MEMORY_REGION_ATTRIBUTE_NONSECURE_WRITE_THROUGH:
PageAttributes = TT_DESCRIPTOR_PAGE_WRITE_THROUGH; PageAttributes = TT_DESCRIPTOR_PAGE_WRITE_THROUGH;
break; break;
case ARM_MEMORY_REGION_ATTRIBUTE_DEVICE: case ARM_MEMORY_REGION_ATTRIBUTE_DEVICE:
case ARM_MEMORY_REGION_ATTRIBUTE_NONSECURE_DEVICE:
PageAttributes = TT_DESCRIPTOR_PAGE_DEVICE; PageAttributes = TT_DESCRIPTOR_PAGE_DEVICE;
break; break;
case ARM_MEMORY_REGION_ATTRIBUTE_UNCACHED_UNBUFFERED: case ARM_MEMORY_REGION_ATTRIBUTE_UNCACHED_UNBUFFERED:
case ARM_MEMORY_REGION_ATTRIBUTE_NONSECURE_UNCACHED_UNBUFFERED:
PageAttributes = TT_DESCRIPTOR_PAGE_UNCACHED; PageAttributes = TT_DESCRIPTOR_PAGE_UNCACHED;
break; break;
default: default:
@@ -148,7 +145,7 @@ PopulateLevel2PageTable (
); );
// Translate the Section Descriptor into Page Descriptor // Translate the Section Descriptor into Page Descriptor
SectionDescriptor = TT_DESCRIPTOR_PAGE_TYPE_PAGE | ConvertSectionAttributesToPageAttributes (*SectionEntry); SectionDescriptor = TT_DESCRIPTOR_PAGE_TYPE_PAGE | ConvertSectionAttributesToPageAttributes (*SectionEntry, FALSE);
BaseSectionAddress = TT_DESCRIPTOR_SECTION_BASE_ADDRESS (*SectionEntry); BaseSectionAddress = TT_DESCRIPTOR_SECTION_BASE_ADDRESS (*SectionEntry);
@@ -242,31 +239,39 @@ FillTranslationTable (
switch (MemoryRegion->Attributes) { switch (MemoryRegion->Attributes) {
case ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK: case ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK:
Attributes = TT_DESCRIPTOR_SECTION_WRITE_BACK; Attributes = TT_DESCRIPTOR_SECTION_WRITE_BACK (0);
break; break;
case ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK_NONSHAREABLE: case ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK_NONSHAREABLE:
Attributes = TT_DESCRIPTOR_SECTION_WRITE_BACK; Attributes = TT_DESCRIPTOR_SECTION_WRITE_BACK (0);
Attributes &= ~TT_DESCRIPTOR_SECTION_S_SHARED; Attributes &= ~TT_DESCRIPTOR_SECTION_S_SHARED;
break; break;
case ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK_RO:
Attributes = TT_DESCRIPTOR_SECTION_WRITE_BACK;
Attributes |= TT_DESCRIPTOR_SECTION_AP_NO_RO;
break;
case ARM_MEMORY_REGION_ATTRIBUTE_WRITE_BACK_XP:
Attributes = TT_DESCRIPTOR_SECTION_WRITE_BACK;
Attributes |= TT_DESCRIPTOR_SECTION_XN_MASK;
break;
case ARM_MEMORY_REGION_ATTRIBUTE_WRITE_THROUGH: case ARM_MEMORY_REGION_ATTRIBUTE_WRITE_THROUGH:
Attributes = TT_DESCRIPTOR_SECTION_WRITE_THROUGH; Attributes = TT_DESCRIPTOR_SECTION_WRITE_THROUGH (0);
break; break;
case ARM_MEMORY_REGION_ATTRIBUTE_DEVICE: case ARM_MEMORY_REGION_ATTRIBUTE_DEVICE:
Attributes = TT_DESCRIPTOR_SECTION_DEVICE; Attributes = TT_DESCRIPTOR_SECTION_DEVICE (0);
break; break;
case ARM_MEMORY_REGION_ATTRIBUTE_UNCACHED_UNBUFFERED: case ARM_MEMORY_REGION_ATTRIBUTE_UNCACHED_UNBUFFERED:
Attributes = TT_DESCRIPTOR_SECTION_UNCACHED; Attributes = TT_DESCRIPTOR_SECTION_UNCACHED (0);
break;
case ARM_MEMORY_REGION_ATTRIBUTE_NONSECURE_WRITE_BACK:
Attributes = TT_DESCRIPTOR_SECTION_WRITE_BACK (1);
break;
case ARM_MEMORY_REGION_ATTRIBUTE_NONSECURE_WRITE_BACK_NONSHAREABLE:
Attributes = TT_DESCRIPTOR_SECTION_WRITE_BACK (1);
Attributes &= ~TT_DESCRIPTOR_SECTION_S_SHARED;
break;
case ARM_MEMORY_REGION_ATTRIBUTE_NONSECURE_WRITE_THROUGH:
Attributes = TT_DESCRIPTOR_SECTION_WRITE_THROUGH (1);
break;
case ARM_MEMORY_REGION_ATTRIBUTE_NONSECURE_DEVICE:
Attributes = TT_DESCRIPTOR_SECTION_DEVICE (1);
break;
case ARM_MEMORY_REGION_ATTRIBUTE_NONSECURE_UNCACHED_UNBUFFERED:
Attributes = TT_DESCRIPTOR_SECTION_UNCACHED (1);
break; break;
default: default:
Attributes = TT_DESCRIPTOR_SECTION_UNCACHED; Attributes = TT_DESCRIPTOR_SECTION_UNCACHED (0);
break; break;
} }

View File

@@ -53,7 +53,7 @@ ConvertSectionToPages (
// Get section attributes and convert to page attributes // Get section attributes and convert to page attributes
SectionDescriptor = FirstLevelTable[FirstLevelIdx]; SectionDescriptor = FirstLevelTable[FirstLevelIdx];
PageDescriptor = TT_DESCRIPTOR_PAGE_TYPE_PAGE | ConvertSectionAttributesToPageAttributes (SectionDescriptor); PageDescriptor = TT_DESCRIPTOR_PAGE_TYPE_PAGE | ConvertSectionAttributesToPageAttributes (SectionDescriptor, FALSE);
// Allocate a page table for the 4KB entries (we use up a full page even though we only need 1KB) // Allocate a page table for the 4KB entries (we use up a full page even though we only need 1KB)
PageTable = (volatile ARM_PAGE_TABLE_ENTRY *)AllocatePages (1); PageTable = (volatile ARM_PAGE_TABLE_ENTRY *)AllocatePages (1);
@@ -81,12 +81,12 @@ UpdatePageEntries (
IN EFI_PHYSICAL_ADDRESS BaseAddress, IN EFI_PHYSICAL_ADDRESS BaseAddress,
IN UINT64 Length, IN UINT64 Length,
IN UINT64 Attributes, IN UINT64 Attributes,
IN UINT32 EntryMask,
OUT BOOLEAN *FlushTlbs OPTIONAL OUT BOOLEAN *FlushTlbs OPTIONAL
) )
{ {
EFI_STATUS Status; EFI_STATUS Status;
UINT32 EntryValue; UINT32 EntryValue;
UINT32 EntryMask;
UINT32 FirstLevelIdx; UINT32 FirstLevelIdx;
UINT32 Offset; UINT32 Offset;
UINT32 NumPageEntries; UINT32 NumPageEntries;
@@ -104,7 +104,12 @@ UpdatePageEntries (
// EntryMask: bitmask of values to change (1 = change this value, 0 = leave alone) // EntryMask: bitmask of values to change (1 = change this value, 0 = leave alone)
// EntryValue: values at bit positions specified by EntryMask // EntryValue: values at bit positions specified by EntryMask
EntryMask = TT_DESCRIPTOR_PAGE_TYPE_MASK | TT_DESCRIPTOR_PAGE_AP_MASK;
if ((Attributes & EFI_MEMORY_XP) != 0) {
EntryValue = TT_DESCRIPTOR_PAGE_TYPE_PAGE_XN;
} else {
EntryValue = TT_DESCRIPTOR_PAGE_TYPE_PAGE; EntryValue = TT_DESCRIPTOR_PAGE_TYPE_PAGE;
}
// Although the PI spec is unclear on this, the GCD guarantees that only // Although the PI spec is unclear on this, the GCD guarantees that only
// one Attribute bit is set at a time, so the order of the conditionals below // one Attribute bit is set at a time, so the order of the conditionals below
@@ -137,20 +142,12 @@ UpdatePageEntries (
return EFI_UNSUPPORTED; return EFI_UNSUPPORTED;
} }
if ((Attributes & EFI_MEMORY_RP) == 0) {
EntryValue |= TT_DESCRIPTOR_PAGE_AF;
}
if ((Attributes & EFI_MEMORY_RO) != 0) { if ((Attributes & EFI_MEMORY_RO) != 0) {
EntryValue |= TT_DESCRIPTOR_PAGE_AP_RO_RO; EntryValue |= TT_DESCRIPTOR_PAGE_AP_RO_RO;
} else { } else {
EntryValue |= TT_DESCRIPTOR_PAGE_AP_RW_RW; EntryValue |= TT_DESCRIPTOR_PAGE_AP_RW_RW;
} }
if ((Attributes & EFI_MEMORY_XP) != 0) {
EntryValue |= TT_DESCRIPTOR_PAGE_XN_MASK;
}
// Obtain page table base // Obtain page table base
FirstLevelTable = (ARM_FIRST_LEVEL_DESCRIPTOR *)ArmGetTTBR0BaseAddress (); FirstLevelTable = (ARM_FIRST_LEVEL_DESCRIPTOR *)ArmGetTTBR0BaseAddress ();
@@ -170,17 +167,6 @@ UpdatePageEntries (
// Does this descriptor need to be converted from section entry to 4K pages? // Does this descriptor need to be converted from section entry to 4K pages?
if (!TT_DESCRIPTOR_SECTION_TYPE_IS_PAGE_TABLE (Descriptor)) { if (!TT_DESCRIPTOR_SECTION_TYPE_IS_PAGE_TABLE (Descriptor)) {
//
// If the section mapping covers the requested region with the expected
// attributes, splitting it is unnecessary, and should be avoided as it
// may result in unbounded recursion when using a strict NX policy.
//
if ((EntryValue & ~TT_DESCRIPTOR_PAGE_TYPE_MASK & EntryMask) ==
(ConvertSectionAttributesToPageAttributes (Descriptor) & EntryMask))
{
continue;
}
Status = ConvertSectionToPages (FirstLevelIdx << TT_DESCRIPTOR_SECTION_BASE_SHIFT); Status = ConvertSectionToPages (FirstLevelIdx << TT_DESCRIPTOR_SECTION_BASE_SHIFT);
if (EFI_ERROR (Status)) { if (EFI_ERROR (Status)) {
// Exit for loop // Exit for loop
@@ -230,11 +216,11 @@ EFI_STATUS
UpdateSectionEntries ( UpdateSectionEntries (
IN EFI_PHYSICAL_ADDRESS BaseAddress, IN EFI_PHYSICAL_ADDRESS BaseAddress,
IN UINT64 Length, IN UINT64 Length,
IN UINT64 Attributes, IN UINT64 Attributes
IN UINT32 EntryMask
) )
{ {
EFI_STATUS Status; EFI_STATUS Status;
UINT32 EntryMask;
UINT32 EntryValue; UINT32 EntryValue;
UINT32 FirstLevelIdx; UINT32 FirstLevelIdx;
UINT32 NumSections; UINT32 NumSections;
@@ -250,6 +236,8 @@ UpdateSectionEntries (
// EntryValue: values at bit positions specified by EntryMask // EntryValue: values at bit positions specified by EntryMask
// Make sure we handle a section range that is unmapped // Make sure we handle a section range that is unmapped
EntryMask = TT_DESCRIPTOR_SECTION_TYPE_MASK | TT_DESCRIPTOR_SECTION_XN_MASK |
TT_DESCRIPTOR_SECTION_AP_MASK;
EntryValue = TT_DESCRIPTOR_SECTION_TYPE_SECTION; EntryValue = TT_DESCRIPTOR_SECTION_TYPE_SECTION;
// Although the PI spec is unclear on this, the GCD guarantees that only // Although the PI spec is unclear on this, the GCD guarantees that only
@@ -293,10 +281,6 @@ UpdateSectionEntries (
EntryValue |= TT_DESCRIPTOR_SECTION_XN_MASK; EntryValue |= TT_DESCRIPTOR_SECTION_XN_MASK;
} }
if ((Attributes & EFI_MEMORY_RP) == 0) {
EntryValue |= TT_DESCRIPTOR_SECTION_AF;
}
// obtain page table base // obtain page table base
FirstLevelTable = (ARM_FIRST_LEVEL_DESCRIPTOR *)ArmGetTTBR0BaseAddress (); FirstLevelTable = (ARM_FIRST_LEVEL_DESCRIPTOR *)ArmGetTTBR0BaseAddress ();
@@ -318,7 +302,6 @@ UpdateSectionEntries (
(FirstLevelIdx + i) << TT_DESCRIPTOR_SECTION_BASE_SHIFT, (FirstLevelIdx + i) << TT_DESCRIPTOR_SECTION_BASE_SHIFT,
TT_DESCRIPTOR_SECTION_SIZE, TT_DESCRIPTOR_SECTION_SIZE,
Attributes, Attributes,
ConvertSectionAttributesToPageAttributes (EntryMask),
NULL NULL
); );
} else { } else {
@@ -349,26 +332,11 @@ UpdateSectionEntries (
return Status; return Status;
} }
/**
Update the permission or memory type attributes on a range of memory.
@param BaseAddress The start of the region.
@param Length The size of the region.
@param Attributes A mask of EFI_MEMORY_xx constants.
@param SectionMask A mask of short descriptor section attributes
describing which descriptor bits to update.
@retval EFI_SUCCESS The attributes were set successfully.
@retval EFI_OUT_OF_RESOURCES The operation failed due to insufficient memory.
**/
STATIC
EFI_STATUS EFI_STATUS
SetMemoryAttributes ( ArmSetMemoryAttributes (
IN EFI_PHYSICAL_ADDRESS BaseAddress, IN EFI_PHYSICAL_ADDRESS BaseAddress,
IN UINT64 Length, IN UINT64 Length,
IN UINT64 Attributes, IN UINT64 Attributes
IN UINT32 SectionMask
) )
{ {
EFI_STATUS Status; EFI_STATUS Status;
@@ -399,12 +367,7 @@ SetMemoryAttributes (
Attributes Attributes
)); ));
Status = UpdateSectionEntries ( Status = UpdateSectionEntries (BaseAddress, ChunkLength, Attributes);
BaseAddress,
ChunkLength,
Attributes,
SectionMask
);
FlushTlbs = TRUE; FlushTlbs = TRUE;
} else { } else {
@@ -430,7 +393,6 @@ SetMemoryAttributes (
BaseAddress, BaseAddress,
ChunkLength, ChunkLength,
Attributes, Attributes,
ConvertSectionAttributesToPageAttributes (SectionMask),
&FlushTlbs &FlushTlbs
); );
} }
@@ -450,47 +412,13 @@ SetMemoryAttributes (
return Status; return Status;
} }
/**
Update the permission or memory type attributes on a range of memory.
@param BaseAddress The start of the region.
@param Length The size of the region.
@param Attributes A mask of EFI_MEMORY_xx constants.
@retval EFI_SUCCESS The attributes were set successfully.
@retval EFI_OUT_OF_RESOURCES The operation failed due to insufficient memory.
**/
EFI_STATUS
ArmSetMemoryAttributes (
IN EFI_PHYSICAL_ADDRESS BaseAddress,
IN UINT64 Length,
IN UINT64 Attributes
)
{
return SetMemoryAttributes (
BaseAddress,
Length,
Attributes,
TT_DESCRIPTOR_SECTION_TYPE_MASK |
TT_DESCRIPTOR_SECTION_XN_MASK |
TT_DESCRIPTOR_SECTION_AP_MASK |
TT_DESCRIPTOR_SECTION_AF
);
}
EFI_STATUS EFI_STATUS
ArmSetMemoryRegionNoExec ( ArmSetMemoryRegionNoExec (
IN EFI_PHYSICAL_ADDRESS BaseAddress, IN EFI_PHYSICAL_ADDRESS BaseAddress,
IN UINT64 Length IN UINT64 Length
) )
{ {
return SetMemoryAttributes ( return ArmSetMemoryAttributes (BaseAddress, Length, EFI_MEMORY_XP);
BaseAddress,
Length,
EFI_MEMORY_XP,
TT_DESCRIPTOR_SECTION_XN_MASK
);
} }
EFI_STATUS EFI_STATUS
@@ -499,12 +427,7 @@ ArmClearMemoryRegionNoExec (
IN UINT64 Length IN UINT64 Length
) )
{ {
return SetMemoryAttributes ( return ArmSetMemoryAttributes (BaseAddress, Length, __EFI_MEMORY_RWX);
BaseAddress,
Length,
0,
TT_DESCRIPTOR_SECTION_XN_MASK
);
} }
EFI_STATUS EFI_STATUS
@@ -513,12 +436,7 @@ ArmSetMemoryRegionReadOnly (
IN UINT64 Length IN UINT64 Length
) )
{ {
return SetMemoryAttributes ( return ArmSetMemoryAttributes (BaseAddress, Length, EFI_MEMORY_RO);
BaseAddress,
Length,
EFI_MEMORY_RO,
TT_DESCRIPTOR_SECTION_AP_MASK
);
} }
EFI_STATUS EFI_STATUS
@@ -527,58 +445,5 @@ ArmClearMemoryRegionReadOnly (
IN UINT64 Length IN UINT64 Length
) )
{ {
return SetMemoryAttributes ( return ArmSetMemoryAttributes (BaseAddress, Length, __EFI_MEMORY_RWX);
BaseAddress,
Length,
0,
TT_DESCRIPTOR_SECTION_AP_MASK
);
}
/**
Convert a region of memory to read-protected, by clearing the access flag.
@param BaseAddress The start of the region.
@param Length The size of the region.
@retval EFI_SUCCESS The attributes were set successfully.
@retval EFI_OUT_OF_RESOURCES The operation failed due to insufficient memory.
**/
EFI_STATUS
ArmSetMemoryRegionNoAccess (
IN EFI_PHYSICAL_ADDRESS BaseAddress,
IN UINT64 Length
)
{
return SetMemoryAttributes (
BaseAddress,
Length,
EFI_MEMORY_RP,
TT_DESCRIPTOR_SECTION_AF
);
}
/**
Convert a region of memory to read-enabled, by setting the access flag.
@param BaseAddress The start of the region.
@param Length The size of the region.
@retval EFI_SUCCESS The attributes were set successfully.
@retval EFI_OUT_OF_RESOURCES The operation failed due to insufficient memory.
**/
EFI_STATUS
ArmClearMemoryRegionNoAccess (
IN EFI_PHYSICAL_ADDRESS BaseAddress,
IN UINT64 Length
)
{
return SetMemoryAttributes (
BaseAddress,
Length,
0,
TT_DESCRIPTOR_SECTION_AF
);
} }

View File

@@ -36,11 +36,7 @@
[LibraryClasses] [LibraryClasses]
ArmLib ArmLib
CacheMaintenanceLib CacheMaintenanceLib
HobLib
MemoryAllocationLib MemoryAllocationLib
[Guids]
gArmMmuReplaceLiveTranslationEntryFuncGuid
[Pcd.ARM] [Pcd.ARM]
gArmTokenSpaceGuid.PcdNormalMemoryNonshareableOverride gArmTokenSpaceGuid.PcdNormalMemoryNonshareableOverride

View File

@@ -29,8 +29,4 @@
[LibraryClasses] [LibraryClasses]
ArmLib ArmLib
CacheMaintenanceLib CacheMaintenanceLib
HobLib
MemoryAllocationLib MemoryAllocationLib
[Guids]
gArmMmuReplaceLiveTranslationEntryFuncGuid

View File

@@ -1,34 +0,0 @@
/** @file
Arm Monitor Library.
Copyright (c) 2022, Arm Limited. All rights reserved.<BR>
SPDX-License-Identifier: BSD-2-Clause-Patent
**/
#include <Library/ArmHvcLib.h>
#include <Library/ArmMonitorLib.h>
#include <Library/ArmSmcLib.h>
#include <Library/PcdLib.h>
/** Monitor call.
An HyperVisor Call (HVC) or System Monitor Call (SMC) will be issued
depending on the default conduit. PcdMonitorConduitHvc determines the type
of the call: if true, do an HVC.
@param [in,out] Args Arguments for the HVC/SMC.
**/
VOID
EFIAPI
ArmMonitorCall (
IN OUT ARM_MONITOR_ARGS *Args
)
{
if (FeaturePcdGet (PcdMonitorConduitHvc)) {
ArmCallHvc ((ARM_HVC_ARGS *)Args);
} else {
ArmCallSmc ((ARM_SMC_ARGS *)Args);
}
}

View File

@@ -1,29 +0,0 @@
## @file
# Arm Monitor Library
#
# Copyright (c) 2022, Arm Limited. All rights reserved.<BR>
#
# SPDX-License-Identifier: BSD-2-Clause-Patent
##
[Defines]
INF_VERSION = 1.29
BASE_NAME = ArmMonitorLib
FILE_GUID = F918DACB-FBB8-4CB6-A61D-08E75AF0E7CD
MODULE_TYPE = BASE
VERSION_STRING = 1.0
LIBRARY_CLASS = ArmMonitorLib
[Sources]
ArmMonitorLib.c
[Packages]
ArmPkg/ArmPkg.dec
MdePkg/MdePkg.dec
[LibraryClasses]
ArmHvcLib
ArmSmcLib
[Pcd]
gArmTokenSpaceGuid.PcdMonitorConduitHvc

View File

@@ -65,7 +65,7 @@ LibResetSystem (
ArmCallSmc (&ArmSmcArgs); ArmCallSmc (&ArmSmcArgs);
// We should never be here // We should never be here
DEBUG ((DEBUG_ERROR, "%a: PSCI Reset failed\n", __func__)); DEBUG ((DEBUG_ERROR, "%a: PSCI Reset failed\n", __FUNCTION__));
CpuDeadLoop (); CpuDeadLoop ();
return EFI_UNSUPPORTED; return EFI_UNSUPPORTED;
} }

View File

@@ -3,7 +3,6 @@
Copyright (c) 2017 - 2018, Linaro Ltd. All rights reserved.<BR> Copyright (c) 2017 - 2018, Linaro Ltd. All rights reserved.<BR>
Copyright (c) 2019, Intel Corporation. All rights reserved.<BR> Copyright (c) 2019, Intel Corporation. All rights reserved.<BR>
Copyright (c) 2022, Arm Limited. All rights reserved.<BR>
SPDX-License-Identifier: BSD-2-Clause-Patent SPDX-License-Identifier: BSD-2-Clause-Patent
@@ -48,25 +47,9 @@ ResetWarm (
VOID VOID
) )
{ {
UINTN Arg1;
UINTN Ret;
Arg1 = ARM_SMC_ID_PSCI_SYSTEM_RESET2_AARCH64;
// Is SYSTEM_RESET2 supported?
Ret = ArmCallSmc0 (ARM_SMC_ID_PSCI_FEATURES, &Arg1, NULL, NULL);
if (Ret == ARM_SMC_PSCI_RET_SUCCESS) {
// Send PSCI SYSTEM_RESET2 command
ArmCallSmc0 (Arg1, NULL, NULL, NULL);
} else {
// Map a warm reset into a cold reset // Map a warm reset into a cold reset
DEBUG ((
DEBUG_INFO,
"Warm reboot not supported by platform, issuing cold reboot\n"
));
ResetCold (); ResetCold ();
} }
}
/** /**
This function causes the system to enter a power state equivalent This function causes the system to enter a power state equivalent

View File

@@ -5,12 +5,12 @@
// //
// //
#include <AsmMacroIoLibV8.h>
.text .text
.align 3 .align 3
ASM_FUNC(ArmCallSvc) GCC_ASM_EXPORT(ArmCallSvc)
ASM_PFX(ArmCallSvc):
// Push frame pointer and return address on the stack // Push frame pointer and return address on the stack
stp x29, x30, [sp, #-32]! stp x29, x30, [sp, #-32]!
mov x29, sp mov x29, sp

View File

@@ -1,50 +0,0 @@
/** @file
Arm Firmware TRNG definitions.
Copyright (c) 2021 - 2022, Arm Limited. All rights reserved.<BR>
SPDX-License-Identifier: BSD-2-Clause-Patent
@par Reference(s):
- [1] Arm True Random Number Generator Firmware, Interface 1.0,
Platform Design Document.
(https://developer.arm.com/documentation/den0098/latest/)
@par Glossary:
- TRNG - True Random Number Generator
- FID - Function ID
**/
#ifndef ARM_FW_TRNG_DEFS_H_
#define ARM_FW_TRNG_DEFS_H_
#include <IndustryStandard/ArmStdSmc.h>
// Firmware TRNG revision mask and shift
#define TRNG_REV_MAJOR_MASK 0x7FFF
#define TRNG_REV_MINOR_MASK 0xFFFF
#define TRNG_REV_MAJOR_SHIFT 16
#if defined (MDE_CPU_ARM)
/** FID to use on AArch32 platform to request entropy.
*/
#define ARM_SMC_ID_TRNG_RND ARM_SMC_ID_TRNG_RND_AARCH32
/** Maximum bits of entropy supported on AArch32.
*/
#define MAX_ENTROPY_BITS 96
#elif defined (MDE_CPU_AARCH64)
/** FID to use on AArch64 platform to request entropy.
*/
#define ARM_SMC_ID_TRNG_RND ARM_SMC_ID_TRNG_RND_AARCH64
/** Maximum bits of entropy supported on AArch64.
*/
#define MAX_ENTROPY_BITS 192
#else
#error "Firmware TRNG not supported. Unknown chipset."
#endif
#endif // ARM_FW_TRNG_DEFS_H_

View File

@@ -1,382 +0,0 @@
/** @file
Arm Firmware TRNG interface library.
Copyright (c) 2021 - 2022, Arm Limited. All rights reserved.<BR>
SPDX-License-Identifier: BSD-2-Clause-Patent
@par Reference(s):
- [1] Arm True Random Number Generator Firmware, Interface 1.0,
Platform Design Document.
(https://developer.arm.com/documentation/den0098/latest/)
- [2] NIST Special Publication 800-90B, Recommendation for the Entropy
Sources Used for Random Bit Generation.
(https://csrc.nist.gov/publications/detail/sp/800-90b/final)
@par Glossary:
- TRNG - True Random Number Generator
- FID - Function ID
**/
#include <Base.h>
#include <Library/ArmLib.h>
#include <Library/ArmMonitorLib.h>
#include <Library/BaseMemoryLib.h>
#include <Library/DebugLib.h>
#include "ArmTrngDefs.h"
/** Convert TRNG status codes to RETURN status codes.
@param [in] TrngStatus TRNG status code.
@retval RETURN_SUCCESS Success.
@retval RETURN_UNSUPPORTED Function not implemented or
negative return code.
@retval RETURN_INVALID_PARAMETER A parameter is invalid.
@retval RETURN_NOT_READY No Entropy available.
**/
STATIC
RETURN_STATUS
TrngStatusToReturnStatus (
IN INT32 TrngStatus
)
{
switch (TrngStatus) {
case TRNG_STATUS_NOT_SUPPORTED:
return RETURN_UNSUPPORTED;
case TRNG_STATUS_INVALID_PARAMETER:
return RETURN_INVALID_PARAMETER;
case TRNG_STATUS_NO_ENTROPY:
return RETURN_NOT_READY;
case TRNG_STATUS_SUCCESS:
return RETURN_SUCCESS;
default:
if (TrngStatus < 0) {
return RETURN_UNSUPPORTED;
}
return RETURN_SUCCESS;
}
}
/** Get the version of the Arm TRNG backend.
A TRNG may be implemented by the system firmware, in which case this
function shall return the version of the Arm TRNG backend.
The implementation must return NOT_SUPPORTED if a Back end is not present.
@param [out] MajorRevision Major revision.
@param [out] MinorRevision Minor revision.
@retval RETURN_SUCCESS The function completed successfully.
@retval RETURN_INVALID_PARAMETER Invalid parameter.
@retval RETURN_UNSUPPORTED Backend not present.
**/
RETURN_STATUS
EFIAPI
GetArmTrngVersion (
OUT UINT16 *MajorRevision,
OUT UINT16 *MinorRevision
)
{
RETURN_STATUS Status;
ARM_MONITOR_ARGS Parameters;
INT32 Revision;
if ((MajorRevision == NULL) || (MinorRevision == NULL)) {
return RETURN_INVALID_PARAMETER;
}
ZeroMem (&Parameters, sizeof (Parameters));
Parameters.Arg0 = ARM_SMC_ID_TRNG_VERSION;
ArmMonitorCall (&Parameters);
Revision = (INT32)Parameters.Arg0;
Status = TrngStatusToReturnStatus (Revision);
if (RETURN_ERROR (Status)) {
return Status;
}
*MinorRevision = (Revision & TRNG_REV_MINOR_MASK);
*MajorRevision = ((Revision >> TRNG_REV_MAJOR_SHIFT) & TRNG_REV_MAJOR_MASK);
return RETURN_SUCCESS;
}
/** Get the features supported by the Arm TRNG backend.
The caller can determine if functions defined in the Arm TRNG ABI are
present in the ABI implementation.
@param [in] FunctionId Function Id.
@param [out] Capability Function specific capability if present.
@retval RETURN_SUCCESS The function completed successfully.
@retval RETURN_INVALID_PARAMETER Invalid parameter.
@retval RETURN_UNSUPPORTED Function not implemented.
**/
STATIC
RETURN_STATUS
EFIAPI
GetArmTrngFeatures (
IN CONST UINT32 FunctionId,
OUT UINT32 *Capability OPTIONAL
)
{
ARM_MONITOR_ARGS Parameters;
RETURN_STATUS Status;
ZeroMem (&Parameters, sizeof (Parameters));
Parameters.Arg0 = ARM_SMC_ID_TRNG_FEATURES;
Parameters.Arg1 = FunctionId;
ArmMonitorCall (&Parameters);
Status = TrngStatusToReturnStatus (Parameters.Arg0);
if (RETURN_ERROR (Status)) {
return Status;
}
if (Capability != NULL) {
*Capability = (UINT32)Parameters.Arg0;
}
return RETURN_SUCCESS;
}
/** Get the UUID of the Arm TRNG backend.
A TRNG may be implemented by the system firmware, in which case this
function shall return the UUID of the TRNG backend.
Returning the Arm TRNG UUID is optional and if not implemented,
RETURN_UNSUPPORTED shall be returned.
Note: The caller must not rely on the returned UUID as a trustworthy Arm TRNG
Back end identity
@param [out] Guid UUID of the Arm TRNG backend.
@retval RETURN_SUCCESS The function completed successfully.
@retval RETURN_INVALID_PARAMETER Invalid parameter.
@retval RETURN_UNSUPPORTED Function not implemented.
**/
RETURN_STATUS
EFIAPI
GetArmTrngUuid (
OUT GUID *Guid
)
{
ARM_MONITOR_ARGS Parameters;
if (Guid == NULL) {
return RETURN_INVALID_PARAMETER;
}
ZeroMem (&Parameters, sizeof (Parameters));
Parameters.Arg0 = ARM_SMC_ID_TRNG_GET_UUID;
ArmMonitorCall (&Parameters);
// Only invalid value is TRNG_STATUS_NOT_SUPPORTED (-1).
if ((INT32)Parameters.Arg0 == TRNG_STATUS_NOT_SUPPORTED) {
return TrngStatusToReturnStatus ((INT32)Parameters.Arg0);
}
Guid->Data1 = (Parameters.Arg0 & MAX_UINT32);
Guid->Data2 = (Parameters.Arg1 & MAX_UINT16);
Guid->Data3 = ((Parameters.Arg1 >> 16) & MAX_UINT16);
Guid->Data4[0] = (Parameters.Arg2 & MAX_UINT8);
Guid->Data4[1] = ((Parameters.Arg2 >> 8) & MAX_UINT8);
Guid->Data4[2] = ((Parameters.Arg2 >> 16) & MAX_UINT8);
Guid->Data4[3] = ((Parameters.Arg2 >> 24) & MAX_UINT8);
Guid->Data4[4] = (Parameters.Arg3 & MAX_UINT8);
Guid->Data4[5] = ((Parameters.Arg3 >> 8) & MAX_UINT8);
Guid->Data4[6] = ((Parameters.Arg3 >> 16) & MAX_UINT8);
Guid->Data4[7] = ((Parameters.Arg3 >> 24) & MAX_UINT8);
DEBUG ((DEBUG_INFO, "FW-TRNG: UUID %g\n", Guid));
return RETURN_SUCCESS;
}
/** Returns maximum number of entropy bits that can be returned in a single
call.
@return Returns the maximum number of Entropy bits that can be returned
in a single call to GetArmTrngEntropy().
**/
UINTN
EFIAPI
GetArmTrngMaxSupportedEntropyBits (
VOID
)
{
return MAX_ENTROPY_BITS;
}
/** Returns N bits of conditioned entropy.
See [2] Section 2.3.1 GetEntropy: An Interface to the Entropy Source
GetEntropy
Input:
bits_of_entropy: the requested amount of entropy
Output:
entropy_bitstring: The string that provides the requested entropy.
status: A Boolean value that is TRUE if the request has been satisfied,
and is FALSE otherwise.
@param [in] EntropyBits Number of entropy bits requested.
@param [in] BufferSize Size of the Buffer in bytes.
@param [out] Buffer Buffer to return the entropy bits.
@retval RETURN_SUCCESS The function completed successfully.
@retval RETURN_INVALID_PARAMETER Invalid parameter.
@retval RETURN_UNSUPPORTED Function not implemented.
@retval RETURN_BAD_BUFFER_SIZE Buffer size is too small.
@retval RETURN_NOT_READY No Entropy available.
**/
RETURN_STATUS
EFIAPI
GetArmTrngEntropy (
IN UINTN EntropyBits,
IN UINTN BufferSize,
OUT UINT8 *Buffer
)
{
RETURN_STATUS Status;
ARM_MONITOR_ARGS Parameters;
UINTN EntropyBytes;
UINTN LastValidBits;
UINTN BytesToClear;
UINTN EntropyData[3];
if ((EntropyBits == 0) ||
(EntropyBits > MAX_ENTROPY_BITS) ||
(Buffer == NULL))
{
return RETURN_INVALID_PARAMETER;
}
EntropyBytes = (EntropyBits + 7) >> 3;
if (EntropyBytes > BufferSize) {
return RETURN_BAD_BUFFER_SIZE;
}
ZeroMem (Buffer, BufferSize);
ZeroMem (&Parameters, sizeof (Parameters));
Parameters.Arg0 = ARM_SMC_ID_TRNG_RND;
Parameters.Arg1 = EntropyBits;
ArmMonitorCall (&Parameters);
Status = TrngStatusToReturnStatus ((INT32)Parameters.Arg0);
if (RETURN_ERROR (Status)) {
return Status;
}
// The entropy data is returned in the Parameters.Arg<3..1>
// With the lower order bytes in Parameters.Arg3 and the higher
// order bytes being stored in Parameters.Arg1.
EntropyData[0] = Parameters.Arg3;
EntropyData[1] = Parameters.Arg2;
EntropyData[2] = Parameters.Arg1;
CopyMem (Buffer, EntropyData, EntropyBytes);
// Mask off any unused top bytes, in accordance with specification.
BytesToClear = BufferSize - EntropyBytes;
if (BytesToClear != 0) {
ZeroMem (&Buffer[EntropyBytes], BytesToClear);
}
// Clear the unused MSB bits of the last byte.
LastValidBits = EntropyBits & 0x7;
if (LastValidBits != 0) {
Buffer[EntropyBytes - 1] &= (0xFF >> (8 - LastValidBits));
}
return Status;
}
/** The constructor checks that the FW-TRNG interface is supported
by the host firmware.
It will ASSERT() if FW-TRNG is not supported.
It will always return RETURN_SUCCESS.
@retval RETURN_SUCCESS The constructor always returns RETURN_SUCCESS.
**/
RETURN_STATUS
EFIAPI
ArmTrngLibConstructor (
VOID
)
{
ARM_MONITOR_ARGS Parameters;
RETURN_STATUS Status;
UINT16 MajorRev;
UINT16 MinorRev;
GUID Guid;
ZeroMem (&Parameters, sizeof (Parameters));
Parameters.Arg0 = SMCCC_VERSION;
ArmMonitorCall (&Parameters);
Status = TrngStatusToReturnStatus ((INT32)Parameters.Arg0);
if (RETURN_ERROR (Status)) {
goto ErrorHandler;
}
// Cf [1] s2.1.3 'Caller responsibilities',
// SMCCC version must be greater or equal than 1.1
if ((INT32)Parameters.Arg0 < 0x10001) {
goto ErrorHandler;
}
Status = GetArmTrngVersion (&MajorRev, &MinorRev);
if (RETURN_ERROR (Status)) {
goto ErrorHandler;
}
// Check that the required features are present.
Status = GetArmTrngFeatures (ARM_SMC_ID_TRNG_RND, NULL);
if (RETURN_ERROR (Status)) {
goto ErrorHandler;
}
// Check if TRNG UUID is supported and if so trace the GUID.
Status = GetArmTrngFeatures (ARM_SMC_ID_TRNG_GET_UUID, NULL);
if (RETURN_ERROR (Status)) {
goto ErrorHandler;
}
DEBUG_CODE_BEGIN ();
Status = GetArmTrngUuid (&Guid);
if (RETURN_ERROR (Status)) {
goto ErrorHandler;
}
DEBUG ((
DEBUG_INFO,
"FW-TRNG: Version %d.%d, GUID {%g}\n",
MajorRev,
MinorRev,
&Guid
));
DEBUG_CODE_END ();
return RETURN_SUCCESS;
ErrorHandler:
DEBUG ((DEBUG_ERROR, "ArmTrngLib could not be correctly initialized.\n"));
return RETURN_SUCCESS;
}

View File

@@ -1,29 +0,0 @@
## @file
# Arm Firmware TRNG interface library.
#
# Copyright (c) 2021 - 2022, Arm Limited. All rights reserved.<BR>
#
# SPDX-License-Identifier: BSD-2-Clause-Patent
##
[Defines]
INF_VERSION = 1.29
BASE_NAME = ArmTrngLib
FILE_GUID = 10DE97C9-28E4-4C9B-A53E-8D7D1B0DD4E0
VERSION_STRING = 1.0
MODULE_TYPE = BASE
LIBRARY_CLASS = ArmTrngLib
CONSTRUCTOR = ArmTrngLibConstructor
[Sources]
ArmTrngDefs.h
ArmTrngLib.c
[Packages]
ArmPkg/ArmPkg.dec
MdePkg/MdePkg.dec
[LibraryClasses]
ArmMonitorLib
BaseLib
BaseMemoryLib

View File

@@ -77,8 +77,13 @@ PeCoffLoaderRelocateImageExtraAction (
if (ImageContext->PdbPointer) { if (ImageContext->PdbPointer) {
#ifdef __CC_ARM #ifdef __CC_ARM
#if (__ARMCC_VERSION < 500000)
// Print out the command for the RVD debugger to load symbols for this image
DEBUG ((DEBUG_LOAD | DEBUG_INFO, "load /a /ni /np %a &0x%p\n", DeCygwinPathIfNeeded (ImageContext->PdbPointer, Temp, sizeof (Temp)), (UINTN)(ImageContext->ImageAddress + ImageContext->SizeOfHeaders)));
#else
// Print out the command for the DS-5 to load symbols for this image // Print out the command for the DS-5 to load symbols for this image
DEBUG ((DEBUG_LOAD | DEBUG_INFO, "add-symbol-file %a 0x%p\n", DeCygwinPathIfNeeded (ImageContext->PdbPointer, Temp, sizeof (Temp)), (UINTN)(ImageContext->ImageAddress + ImageContext->SizeOfHeaders))); DEBUG ((DEBUG_LOAD | DEBUG_INFO, "add-symbol-file %a 0x%p\n", DeCygwinPathIfNeeded (ImageContext->PdbPointer, Temp, sizeof (Temp)), (UINTN)(ImageContext->ImageAddress + ImageContext->SizeOfHeaders)));
#endif
#elif __GNUC__ #elif __GNUC__
// This may not work correctly if you generate PE/COFF directly as then the Offset would not be required // This may not work correctly if you generate PE/COFF directly as then the Offset would not be required
DEBUG ((DEBUG_LOAD | DEBUG_INFO, "add-symbol-file %a 0x%p\n", DeCygwinPathIfNeeded (ImageContext->PdbPointer, Temp, sizeof (Temp)), (UINTN)(ImageContext->ImageAddress + ImageContext->SizeOfHeaders))); DEBUG ((DEBUG_LOAD | DEBUG_INFO, "add-symbol-file %a 0x%p\n", DeCygwinPathIfNeeded (ImageContext->PdbPointer, Temp, sizeof (Temp)), (UINTN)(ImageContext->ImageAddress + ImageContext->SizeOfHeaders)));

Binary file not shown.

View File

@@ -151,7 +151,7 @@ PlatformBootManagerAfterConsole (
LOAD_OPTION_ACTIVE LOAD_OPTION_ACTIVE
); );
} else { } else {
DEBUG ((DEBUG_ERROR, "%a: PcdLinuxBootFileGuid was not set!\n", __func__)); DEBUG ((DEBUG_ERROR, "%a: PcdLinuxBootFileGuid was not set!\n", __FUNCTION__));
} }
} }

View File

@@ -2,7 +2,7 @@
Implementation for PlatformBootManagerLib library class interfaces. Implementation for PlatformBootManagerLib library class interfaces.
Copyright (C) 2015-2016, Red Hat, Inc. Copyright (C) 2015-2016, Red Hat, Inc.
Copyright (c) 2014 - 2023, Arm Ltd. All rights reserved.<BR> Copyright (c) 2014 - 2021, ARM Ltd. All rights reserved.<BR>
Copyright (c) 2004 - 2018, Intel Corporation. All rights reserved.<BR> Copyright (c) 2004 - 2018, Intel Corporation. All rights reserved.<BR>
Copyright (c) 2016, Linaro Ltd. All rights reserved.<BR> Copyright (c) 2016, Linaro Ltd. All rights reserved.<BR>
Copyright (c) 2021, Semihalf All rights reserved.<BR> Copyright (c) 2021, Semihalf All rights reserved.<BR>
@@ -195,7 +195,7 @@ FilterAndProcess (
DEBUG (( DEBUG ((
DEBUG_VERBOSE, DEBUG_VERBOSE,
"%a: %g: %r\n", "%a: %g: %r\n",
__func__, __FUNCTION__,
ProtocolGuid, ProtocolGuid,
Status Status
)); ));
@@ -266,7 +266,7 @@ IsPciDisplay (
&Pci &Pci
); );
if (EFI_ERROR (Status)) { if (EFI_ERROR (Status)) {
DEBUG ((DEBUG_ERROR, "%a: %s: %r\n", __func__, ReportText, Status)); DEBUG ((DEBUG_ERROR, "%a: %s: %r\n", __FUNCTION__, ReportText, Status));
return FALSE; return FALSE;
} }
@@ -330,7 +330,7 @@ Connect (
DEBUG (( DEBUG ((
EFI_ERROR (Status) ? DEBUG_ERROR : DEBUG_VERBOSE, EFI_ERROR (Status) ? DEBUG_ERROR : DEBUG_VERBOSE,
"%a: %s: %r\n", "%a: %s: %r\n",
__func__, __FUNCTION__,
ReportText, ReportText,
Status Status
)); ));
@@ -356,7 +356,7 @@ AddOutput (
DEBUG (( DEBUG ((
DEBUG_ERROR, DEBUG_ERROR,
"%a: %s: handle %p: device path not found\n", "%a: %s: handle %p: device path not found\n",
__func__, __FUNCTION__,
ReportText, ReportText,
Handle Handle
)); ));
@@ -368,7 +368,7 @@ AddOutput (
DEBUG (( DEBUG ((
DEBUG_ERROR, DEBUG_ERROR,
"%a: %s: adding to ConOut: %r\n", "%a: %s: adding to ConOut: %r\n",
__func__, __FUNCTION__,
ReportText, ReportText,
Status Status
)); ));
@@ -380,7 +380,7 @@ AddOutput (
DEBUG (( DEBUG ((
DEBUG_ERROR, DEBUG_ERROR,
"%a: %s: adding to ErrOut: %r\n", "%a: %s: adding to ErrOut: %r\n",
__func__, __FUNCTION__,
ReportText, ReportText,
Status Status
)); ));
@@ -390,7 +390,7 @@ AddOutput (
DEBUG (( DEBUG ((
DEBUG_VERBOSE, DEBUG_VERBOSE,
"%a: %s: added to ConOut and ErrOut\n", "%a: %s: added to ConOut and ErrOut\n",
__func__, __FUNCTION__,
ReportText ReportText
)); ));
} }
@@ -470,64 +470,6 @@ PlatformRegisterFvBootOption (
EfiBootManagerFreeLoadOptions (BootOptions, BootOptionCount); EfiBootManagerFreeLoadOptions (BootOptions, BootOptionCount);
} }
/** Boot a Fv Boot Option.
This function is useful for booting the UEFI Shell as it is loaded
as a non active boot option.
@param[in] FileGuid The File GUID.
@param[in] Description String describing the Boot Option.
**/
STATIC
VOID
PlatformBootFvBootOption (
IN CONST EFI_GUID *FileGuid,
IN CHAR16 *Description
)
{
EFI_STATUS Status;
EFI_BOOT_MANAGER_LOAD_OPTION NewOption;
MEDIA_FW_VOL_FILEPATH_DEVICE_PATH FileNode;
EFI_LOADED_IMAGE_PROTOCOL *LoadedImage;
EFI_DEVICE_PATH_PROTOCOL *DevicePath;
Status = gBS->HandleProtocol (
gImageHandle,
&gEfiLoadedImageProtocolGuid,
(VOID **)&LoadedImage
);
ASSERT_EFI_ERROR (Status);
//
// The UEFI Shell was registered in PlatformRegisterFvBootOption ()
// previously, thus it must still be available in this FV.
//
EfiInitializeFwVolDevicepathNode (&FileNode, FileGuid);
DevicePath = DevicePathFromHandle (LoadedImage->DeviceHandle);
ASSERT (DevicePath != NULL);
DevicePath = AppendDevicePathNode (
DevicePath,
(EFI_DEVICE_PATH_PROTOCOL *)&FileNode
);
ASSERT (DevicePath != NULL);
Status = EfiBootManagerInitializeLoadOption (
&NewOption,
LoadOptionNumberUnassigned,
LoadOptionTypeBoot,
LOAD_OPTION_ACTIVE,
Description,
DevicePath,
NULL,
0
);
ASSERT_EFI_ERROR (Status);
FreePool (DevicePath);
EfiBootManagerBoot (&NewOption);
}
STATIC STATIC
VOID VOID
GetPlatformOptions ( GetPlatformOptions (
@@ -605,7 +547,7 @@ GetPlatformOptions (
DEBUG (( DEBUG ((
DEBUG_ERROR, DEBUG_ERROR,
"%a: failed to register \"%s\": %r\n", "%a: failed to register \"%s\": %r\n",
__func__, __FUNCTION__,
BootOptions[Index].Description, BootOptions[Index].Description,
Status Status
)); ));
@@ -633,7 +575,7 @@ GetPlatformOptions (
DEBUG (( DEBUG ((
DEBUG_ERROR, DEBUG_ERROR,
"%a: failed to register hotkey for \"%s\": %r\n", "%a: failed to register hotkey for \"%s\": %r\n",
__func__, __FUNCTION__,
BootOptions[Index].Description, BootOptions[Index].Description,
Status Status
)); ));
@@ -815,7 +757,7 @@ HandleCapsules (
BOOLEAN NeedReset; BOOLEAN NeedReset;
EFI_STATUS Status; EFI_STATUS Status;
DEBUG ((DEBUG_INFO, "%a: processing capsules ...\n", __func__)); DEBUG ((DEBUG_INFO, "%a: processing capsules ...\n", __FUNCTION__));
Status = gBS->LocateProtocol ( Status = gBS->LocateProtocol (
&gEsrtManagementProtocolGuid, &gEsrtManagementProtocolGuid,
@@ -843,7 +785,7 @@ HandleCapsules (
DEBUG (( DEBUG ((
DEBUG_ERROR, DEBUG_ERROR,
"%a: failed to process capsule %p - %r\n", "%a: failed to process capsule %p - %r\n",
__func__, __FUNCTION__,
CapsuleHeader, CapsuleHeader,
Status Status
)); ));
@@ -858,7 +800,7 @@ HandleCapsules (
DEBUG (( DEBUG ((
DEBUG_WARN, DEBUG_WARN,
"%a: capsule update successful, resetting ...\n", "%a: capsule update successful, resetting ...\n",
__func__ __FUNCTION__
)); ));
gRT->ResetSystem (EfiResetCold, EFI_SUCCESS, 0, NULL); gRT->ResetSystem (EfiResetCold, EFI_SUCCESS, 0, NULL);
@@ -926,7 +868,7 @@ BootDiscoveryPolicyHandler (
DEBUG (( DEBUG ((
DEBUG_INFO, DEBUG_INFO,
"%a - Unexpected DiscoveryPolicy (0x%x). Run Minimal Discovery Policy\n", "%a - Unexpected DiscoveryPolicy (0x%x). Run Minimal Discovery Policy\n",
__func__, __FUNCTION__,
DiscoveryPolicy DiscoveryPolicy
)); ));
return EFI_SUCCESS; return EFI_SUCCESS;
@@ -942,14 +884,14 @@ BootDiscoveryPolicyHandler (
DEBUG_INFO, DEBUG_INFO,
"%a - Failed to locate gEfiBootManagerPolicyProtocolGuid." "%a - Failed to locate gEfiBootManagerPolicyProtocolGuid."
"Driver connect will be skipped.\n", "Driver connect will be skipped.\n",
__func__ __FUNCTION__
)); ));
return Status; return Status;
} }
Status = BMPolicy->ConnectDeviceClass (BMPolicy, Class); Status = BMPolicy->ConnectDeviceClass (BMPolicy, Class);
if (EFI_ERROR (Status)) { if (EFI_ERROR (Status)) {
DEBUG ((DEBUG_ERROR, "%a - ConnectDeviceClass returns - %r\n", __func__, Status)); DEBUG ((DEBUG_ERROR, "%a - ConnectDeviceClass returns - %r\n", __FUNCTION__, Status));
return Status; return Status;
} }
@@ -1133,18 +1075,6 @@ PlatformBootManagerUnableToBoot (
EfiBootManagerConnectAll (); EfiBootManagerConnectAll ();
EfiBootManagerRefreshAllBootOption (); EfiBootManagerRefreshAllBootOption ();
//
// Boot the 'UEFI Shell'. If the Pcd is not set, the UEFI Shell is not
// an active boot option and must be manually selected through UiApp
// (at least during the fist boot).
//
if (FixedPcdGetBool (PcdUefiShellDefaultBootEnable)) {
PlatformBootFvBootOption (
&gUefiShellFileGuid,
L"UEFI Shell (default)"
);
}
// //
// Record the updated number of boot configured boot options // Record the updated number of boot configured boot options
// //
@@ -1166,7 +1096,7 @@ PlatformBootManagerUnableToBoot (
DEBUG (( DEBUG ((
DEBUG_WARN, DEBUG_WARN,
"%a: rebooting after refreshing all boot options\n", "%a: rebooting after refreshing all boot options\n",
__func__ __FUNCTION__
)); ));
gRT->ResetSystem (EfiResetCold, EFI_SUCCESS, 0, NULL); gRT->ResetSystem (EfiResetCold, EFI_SUCCESS, 0, NULL);
} }

View File

@@ -2,7 +2,7 @@
# Implementation for PlatformBootManagerLib library class interfaces. # Implementation for PlatformBootManagerLib library class interfaces.
# #
# Copyright (C) 2015-2016, Red Hat, Inc. # Copyright (C) 2015-2016, Red Hat, Inc.
# Copyright (c) 2014 - 2023, Arm Ltd. All rights reserved.<BR> # Copyright (c) 2014, ARM Ltd. All rights reserved.<BR>
# Copyright (c) 2007 - 2014, Intel Corporation. All rights reserved.<BR> # Copyright (c) 2007 - 2014, Intel Corporation. All rights reserved.<BR>
# Copyright (c) 2016, Linaro Ltd. All rights reserved.<BR> # Copyright (c) 2016, Linaro Ltd. All rights reserved.<BR>
# #
@@ -29,7 +29,6 @@
PlatformBm.h PlatformBm.h
[Packages] [Packages]
ArmPkg/ArmPkg.dec
EmbeddedPkg/EmbeddedPkg.dec EmbeddedPkg/EmbeddedPkg.dec
MdeModulePkg/MdeModulePkg.dec MdeModulePkg/MdeModulePkg.dec
MdePkg/MdePkg.dec MdePkg/MdePkg.dec
@@ -56,7 +55,6 @@
gEfiMdePkgTokenSpaceGuid.PcdUgaConsumeSupport gEfiMdePkgTokenSpaceGuid.PcdUgaConsumeSupport
[FixedPcd] [FixedPcd]
gArmTokenSpaceGuid.PcdUefiShellDefaultBootEnable
gEfiMdeModulePkgTokenSpaceGuid.PcdEmuVariableNvModeEnable gEfiMdeModulePkgTokenSpaceGuid.PcdEmuVariableNvModeEnable
gEfiMdeModulePkgTokenSpaceGuid.PcdFirmwareVersionString gEfiMdeModulePkgTokenSpaceGuid.PcdFirmwareVersionString
gEfiMdePkgTokenSpaceGuid.PcdUartDefaultBaudRate gEfiMdePkgTokenSpaceGuid.PcdUartDefaultBaudRate

View File

@@ -0,0 +1,147 @@
/**@file
Copyright (c) 2006 - 2009, Intel Corporation. All rights reserved.<BR>
Portions copyright (c) 2008 - 2010, Apple Inc. All rights reserved.<BR>
Portions copyright (c) 2011 - 2012, ARM Ltd. All rights reserved.<BR>
SPDX-License-Identifier: BSD-2-Clause-Patent
**/
#include <PiDxe.h>
#include <Library/PeCoffLib.h>
#include <Library/BaseLib.h>
#include <Library/DebugLib.h>
#include <Library/BaseMemoryLib.h>
#include <Library/PeCoffExtraActionLib.h>
#include <Library/SemihostLib.h>
#include <Library/PrintLib.h>
/**
Append string to debugger script file, create file if needed.
This library can show up in multiple places so we need to append the file every time we write to it.
For example Sec can use this to load the DXE core, and the DXE core would use this to load all the
other modules. So we have two instances of the library in the system.
@param Buffer Buffer to write to file.
@param Length Length of Buffer in bytes.
**/
VOID
WriteStringToFile (
IN VOID *Buffer,
IN UINT32 Length
)
{
// Working around and issue with the code that is commented out. For now send it to the console.
// You can copy the console into a file and source the file as a script and you get symbols.
// This gets you all the symbols except for SEC. To get SEC symbols you need to copy the
// debug print in the SEC into the debugger manually
SemihostWriteString (Buffer);
/*
I'm currently having issues with this code crashing the debugger. Seems like it should work.
UINT32 SemihostHandle;
UINT32 SemihostMode = SEMIHOST_FILE_MODE_WRITE | SEMIHOST_FILE_MODE_BINARY | SEMIHOST_FILE_MODE_UPDATE;
SemihostFileOpen ("c:\rvi_symbols.inc", SemihostMode, &SemihostHandle);
SemihostFileWrite (SemihostHandle, &Length, Buffer);
SemihostFileClose (SemihostHandle);
*/
}
/**
If the build is done on cygwin the paths are cygpaths.
/cygdrive/c/tmp.txt vs c:\tmp.txt so we need to convert
them to work with RVD commands
@param Name Path to convert if needed
**/
CHAR8 *
DeCygwinPathIfNeeded (
IN CHAR8 *Name
)
{
CHAR8 *Ptr;
UINTN Index;
UINTN Len;
Ptr = AsciiStrStr (Name, "/cygdrive/");
if (Ptr == NULL) {
return Name;
}
Len = AsciiStrLen (Ptr);
// convert "/cygdrive" to spaces
for (Index = 0; Index < 9; Index++) {
Ptr[Index] = ' ';
}
// convert /c to c:
Ptr[9] = Ptr[10];
Ptr[10] = ':';
// switch path separators
for (Index = 11; Index < Len; Index++) {
if (Ptr[Index] == '/') {
Ptr[Index] = '\\';
}
}
return Name;
}
/**
Performs additional actions after a PE/COFF image has been loaded and relocated.
If ImageContext is NULL, then ASSERT().
@param ImageContext Pointer to the image context structure that describes the
PE/COFF image that has already been loaded and relocated.
**/
VOID
EFIAPI
PeCoffLoaderRelocateImageExtraAction (
IN OUT PE_COFF_LOADER_IMAGE_CONTEXT *ImageContext
)
{
CHAR8 Buffer[256];
#if (__ARMCC_VERSION < 500000)
AsciiSPrint (Buffer, sizeof (Buffer), "load /a /ni /np \"%a\" &0x%08x\n", ImageContext->PdbPointer, (UINTN)(ImageContext->ImageAddress + ImageContext->SizeOfHeaders));
#else
AsciiSPrint (Buffer, sizeof (Buffer), "add-symbol-file %a 0x%08x\n", ImageContext->PdbPointer, (UINTN)(ImageContext->ImageAddress + ImageContext->SizeOfHeaders));
#endif
DeCygwinPathIfNeeded (&Buffer[16]);
WriteStringToFile (Buffer, AsciiStrSize (Buffer));
}
/**
Performs additional actions just before a PE/COFF image is unloaded. Any resources
that were allocated by PeCoffLoaderRelocateImageExtraAction() must be freed.
If ImageContext is NULL, then ASSERT().
@param ImageContext Pointer to the image context structure that describes the
PE/COFF image that is being unloaded.
**/
VOID
EFIAPI
PeCoffLoaderUnloadImageExtraAction (
IN OUT PE_COFF_LOADER_IMAGE_CONTEXT *ImageContext
)
{
CHAR8 Buffer[256];
AsciiSPrint (Buffer, sizeof (Buffer), "unload symbols_only \"%a\"\n", ImageContext->PdbPointer);
DeCygwinPathIfNeeded (Buffer);
WriteStringToFile (Buffer, AsciiStrSize (Buffer));
}

View File

@@ -0,0 +1,35 @@
#/** @file
# PeCoff extra action library for DXE phase that run Unix emulator.
#
# Lib to provide memory journal status code reporting Routines
# Copyright (c) 2007 - 2010, Intel Corporation. All rights reserved.<BR>
# Portions copyright (c) 2010, Apple Inc. All rights reserved.<BR>
# SPDX-License-Identifier: BSD-2-Clause-Patent
#
#
#**/
[Defines]
INF_VERSION = 0x00010005
BASE_NAME = RvdUnixPeCoffExtraActionLib
FILE_GUID = 5EDEB7E7-EA55-4E92-8216-335AC98A3B11
MODULE_TYPE = BASE
VERSION_STRING = 1.0
LIBRARY_CLASS = PeCoffExtraActionLib
#
# The following information is for reference only and not required by the build tools.
#
# VALID_ARCHITECTURES = ARM
#
[Sources.common]
RvdPeCoffExtraActionLib.c
[Packages]
MdePkg/MdePkg.dec
ArmPkg/ArmPkg.dec
[LibraryClasses]
DebugLib
SemihostLib

View File

@@ -1,7 +1,6 @@
/** @file /** @file
* OemMiscLib.c * OemMiscLib.c
* *
* Copyright (c) 2022, Ampere Computing LLC. All rights reserved.
* Copyright (c) 2021, NUVIA Inc. All rights reserved. * Copyright (c) 2021, NUVIA Inc. All rights reserved.
* Copyright (c) 2018, Hisilicon Limited. All rights reserved. * Copyright (c) 2018, Hisilicon Limited. All rights reserved.
* Copyright (c) 2018, Linaro Limited. All rights reserved. * Copyright (c) 2018, Linaro Limited. All rights reserved.
@@ -11,12 +10,10 @@
**/ **/
#include <Uefi.h> #include <Uefi.h>
#include <Guid/ZeroGuid.h>
#include <Library/BaseMemoryLib.h> #include <Library/BaseMemoryLib.h>
#include <Library/DebugLib.h> #include <Library/DebugLib.h>
#include <Library/HiiLib.h> #include <Library/HiiLib.h>
#include <Library/OemMiscLib.h> #include <Library/OemMiscLib.h>
#include <Library/PcdLib.h>
/** Gets the CPU frequency of the specified processor. /** Gets the CPU frequency of the specified processor.
@@ -239,47 +236,3 @@ OemGetChassisNumPowerCords (
ASSERT (FALSE); ASSERT (FALSE);
return 1; return 1;
} }
/**
Fetches the system UUID.
@param[out] SystemUuid The pointer to the buffer to store the System UUID.
**/
VOID
EFIAPI
OemGetSystemUuid (
OUT GUID *SystemUuid
)
{
ASSERT (FALSE);
CopyGuid (SystemUuid, &gZeroGuid);
}
/** Fetches the BIOS release.
@return The BIOS release.
**/
UINT16
EFIAPI
OemGetBiosRelease (
VOID
)
{
ASSERT (FALSE);
return PcdGet16 (PcdSystemBiosRelease);
}
/** Fetches the embedded controller firmware release.
@return The embedded controller firmware release.
**/
UINT16
EFIAPI
OemGetEmbeddedControllerFirmwareRelease (
VOID
)
{
ASSERT (FALSE);
return PcdGet16 (PcdEmbeddedControllerFirmwareRelease);
}

View File

@@ -1,7 +1,6 @@
#/** @file #/** @file
# OemMiscLib.inf # OemMiscLib.inf
# #
# Copyright (c) 2022, Ampere Computing LLC. All rights reserved.
# Copyright (c) 2021, NUVIA Inc. All rights reserved. # Copyright (c) 2021, NUVIA Inc. All rights reserved.
# Copyright (c) 2018, Hisilicon Limited. All rights reserved. # Copyright (c) 2018, Hisilicon Limited. All rights reserved.
# Copyright (c) 2018, Linaro Limited. All rights reserved. # Copyright (c) 2018, Linaro Limited. All rights reserved.
@@ -30,11 +29,3 @@
[LibraryClasses] [LibraryClasses]
BaseMemoryLib BaseMemoryLib
DebugLib DebugLib
PcdLib
[Guids]
gZeroGuid
[Pcd]
gArmTokenSpaceGuid.PcdEmbeddedControllerFirmwareRelease
gArmTokenSpaceGuid.PcdSystemBiosRelease

View File

@@ -1,7 +1,6 @@
/** @file /** @file
ProcessorSubClass.c ProcessorSubClass.c
Copyright (c) 2022, Ampere Computing LLC. All rights reserved.
Copyright (c) 2021, NUVIA Inc. All rights reserved.<BR> Copyright (c) 2021, NUVIA Inc. All rights reserved.<BR>
Copyright (c) 2015, Hisilicon Limited. All rights reserved. Copyright (c) 2015, Hisilicon Limited. All rights reserved.
Copyright (c) 2015, Linaro Limited. All rights reserved. Copyright (c) 2015, Linaro Limited. All rights reserved.
@@ -513,6 +512,7 @@ AllocateType4AndSetProcessorInformationStrings (
PartNumber = STRING_TOKEN (STR_PROCESSOR_PART_NUMBER); PartNumber = STRING_TOKEN (STR_PROCESSOR_PART_NUMBER);
SET_HII_STRING_IF_PCD_NOT_EMPTY (PcdProcessorManufacturer, ProcessorManu); SET_HII_STRING_IF_PCD_NOT_EMPTY (PcdProcessorManufacturer, ProcessorManu);
SET_HII_STRING_IF_PCD_NOT_EMPTY (PcdProcessorVersion, ProcessorVersion);
SET_HII_STRING_IF_PCD_NOT_EMPTY (PcdProcessorAssetTag, AssetTag); SET_HII_STRING_IF_PCD_NOT_EMPTY (PcdProcessorAssetTag, AssetTag);
if (StrLen ((CHAR16 *)FixedPcdGetPtr (PcdProcessorSerialNumber)) > 0) { if (StrLen ((CHAR16 *)FixedPcdGetPtr (PcdProcessorSerialNumber)) > 0) {
@@ -527,12 +527,6 @@ AllocateType4AndSetProcessorInformationStrings (
OemUpdateSmbiosInfo (mHiiHandle, PartNumber, ProcessorPartNumType04); OemUpdateSmbiosInfo (mHiiHandle, PartNumber, ProcessorPartNumType04);
} }
if (StrLen ((CHAR16 *)FixedPcdGetPtr (PcdProcessorVersion)) > 0) {
HiiSetString (mHiiHandle, ProcessorVersion, (CHAR16 *)FixedPcdGetPtr (PcdProcessorVersion), NULL);
} else {
OemUpdateSmbiosInfo (mHiiHandle, ProcessorVersion, ProcessorVersionType04);
}
// Processor Designation // Processor Designation
StringBufferSize = sizeof (CHAR16) * SMBIOS_STRING_MAX_LENGTH; StringBufferSize = sizeof (CHAR16) * SMBIOS_STRING_MAX_LENGTH;
ProcessorStr = AllocateZeroPool (StringBufferSize); ProcessorStr = AllocateZeroPool (StringBufferSize);
@@ -741,7 +735,7 @@ AddSmbiosProcessorTypeTable (
DEBUG (( DEBUG ((
DEBUG_ERROR, DEBUG_ERROR,
"[%a]:[%dL] Smbios Type04 Table Log Failed! %r \n", "[%a]:[%dL] Smbios Type04 Table Log Failed! %r \n",
__func__, __FUNCTION__,
DEBUG_LINE_NUMBER, DEBUG_LINE_NUMBER,
Status Status
)); ));

View File

@@ -2,7 +2,7 @@
Functions for processor information common to ARM and AARCH64. Functions for processor information common to ARM and AARCH64.
Copyright (c) 2021, NUVIA Inc. All rights reserved.<BR> Copyright (c) 2021, NUVIA Inc. All rights reserved.<BR>
Copyright (c) 2021 - 2022, Ampere Computing LLC. All rights reserved.<BR> Copyright (c) 2021, Ampere Computing LLC. All rights reserved.<BR>
SPDX-License-Identifier: BSD-2-Clause-Patent SPDX-License-Identifier: BSD-2-Clause-Patent
@@ -131,7 +131,7 @@ SmbiosGetSmcArm64SocId (
SmcCallStatus = ArmCallSmc1 (SMCCC_ARCH_SOC_ID, &SmcParam, NULL, NULL); SmcCallStatus = ArmCallSmc1 (SMCCC_ARCH_SOC_ID, &SmcParam, NULL, NULL);
if (SmcCallStatus >= 0) { if (SmcCallStatus >= 0) {
*Jep106Code = SmcCallStatus; *Jep106Code = (INT32)SmcParam;
} else { } else {
Status = EFI_UNSUPPORTED; Status = EFI_UNSUPPORTED;
} }
@@ -140,7 +140,7 @@ SmbiosGetSmcArm64SocId (
SmcCallStatus = ArmCallSmc1 (SMCCC_ARCH_SOC_ID, &SmcParam, NULL, NULL); SmcCallStatus = ArmCallSmc1 (SMCCC_ARCH_SOC_ID, &SmcParam, NULL, NULL);
if (SmcCallStatus >= 0) { if (SmcCallStatus >= 0) {
*SocRevision = SmcCallStatus; *SocRevision = (INT32)SmcParam;
} else { } else {
Status = EFI_UNSUPPORTED; Status = EFI_UNSUPPORTED;
} }

View File

@@ -1,6 +1,5 @@
/** @file /** @file
Copyright (c) 2022 - 2023, Ampere Computing LLC. All rights reserved.<BR>
Copyright (c) 2021, NUVIA Inc. All rights reserved.<BR> Copyright (c) 2021, NUVIA Inc. All rights reserved.<BR>
Copyright (c) 2009, Intel Corporation. All rights reserved.<BR> Copyright (c) 2009, Intel Corporation. All rights reserved.<BR>
Copyright (c) 2015, Hisilicon Limited. All rights reserved.<BR> Copyright (c) 2015, Hisilicon Limited. All rights reserved.<BR>
@@ -14,7 +13,6 @@
#include <Library/DebugLib.h> #include <Library/DebugLib.h>
#include <Library/HiiLib.h> #include <Library/HiiLib.h>
#include <Library/MemoryAllocationLib.h> #include <Library/MemoryAllocationLib.h>
#include <Library/OemMiscLib.h>
#include <Library/PrintLib.h> #include <Library/PrintLib.h>
#include <Library/UefiBootServicesTableLib.h> #include <Library/UefiBootServicesTableLib.h>
@@ -124,47 +122,22 @@ GetBiosReleaseDate (
return ReleaseDate; return ReleaseDate;
} }
/** Fetches the Firmware version string for SMBIOS type 0 /**
Fetches the firmware ('BIOS') version from the
This function first acquires the firmware version string from OemMiscLib; FirmwareVersionInfo HOB.
if it is invalid, PcdFirmwareVersionString is used as a fallback,
and then sets it in SMBIOS type 0.
@return The version as a UTF-16 string
**/ **/
VOID CHAR16 *
SetBiosVersion ( GetBiosVersion (
VOID VOID
) )
{ {
CHAR16 *DefaultVersionString; CHAR16 *ReleaseString;
CHAR16 *Version;
EFI_STRING_ID TokenToUpdate;
DefaultVersionString = HiiGetString ( ReleaseString = (CHAR16 *)FixedPcdGetPtr (PcdFirmwareVersionString);
mSmbiosMiscHiiHandle,
STRING_TOKEN (STR_MISC_BIOS_VERSION),
NULL
);
OemUpdateSmbiosInfo ( return ReleaseString;
mSmbiosMiscHiiHandle,
STRING_TOKEN (STR_MISC_BIOS_VERSION),
BiosVersionType00
);
Version = HiiGetString (
mSmbiosMiscHiiHandle,
STRING_TOKEN (STR_MISC_BIOS_VERSION),
NULL
);
if (((StrCmp (Version, DefaultVersionString) == 0) || (StrLen (Version) == 0))) {
Version = (CHAR16 *)FixedPcdGetPtr (PcdFirmwareVersionString);
if (StrLen (Version) > 0) {
TokenToUpdate = STRING_TOKEN (STR_MISC_BIOS_VERSION);
HiiSetString (mSmbiosMiscHiiHandle, TokenToUpdate, Version, NULL);
}
}
} }
/** /**
@@ -212,7 +185,18 @@ SMBIOS_MISC_TABLE_FUNCTION (MiscBiosVendor) {
HiiSetString (mSmbiosMiscHiiHandle, TokenToUpdate, Vendor, NULL); HiiSetString (mSmbiosMiscHiiHandle, TokenToUpdate, Vendor, NULL);
} }
SetBiosVersion (); Version = GetBiosVersion ();
if (StrLen (Version) > 0) {
TokenToUpdate = STRING_TOKEN (STR_MISC_BIOS_VERSION);
HiiSetString (mSmbiosMiscHiiHandle, TokenToUpdate, Version, NULL);
} else {
Version = (CHAR16 *)PcdGetPtr (PcdFirmwareVersionString);
if (StrLen (Version) > 0) {
TokenToUpdate = STRING_TOKEN (STR_MISC_BIOS_VERSION);
HiiSetString (mSmbiosMiscHiiHandle, TokenToUpdate, Version, NULL);
}
}
Char16String = GetBiosReleaseDate (); Char16String = GetBiosReleaseDate ();
if (StrLen (Char16String) > 0) { if (StrLen (Char16String) > 0) {
@@ -267,11 +251,13 @@ SMBIOS_MISC_TABLE_FUNCTION (MiscBiosVendor) {
} }
} }
SmbiosRecord->SystemBiosMajorRelease = (UINT8)(OemGetBiosRelease () >> 8); SmbiosRecord->SystemBiosMajorRelease = (UINT8)(PcdGet16 (PcdSystemBiosRelease) >> 8);
SmbiosRecord->SystemBiosMinorRelease = (UINT8)(OemGetBiosRelease () & 0xFF); SmbiosRecord->SystemBiosMinorRelease = (UINT8)(PcdGet16 (PcdSystemBiosRelease) & 0xFF);
SmbiosRecord->EmbeddedControllerFirmwareMajorRelease = (UINT16)(OemGetEmbeddedControllerFirmwareRelease () >> 8); SmbiosRecord->EmbeddedControllerFirmwareMajorRelease = (UINT16)
SmbiosRecord->EmbeddedControllerFirmwareMinorRelease = (UINT16)(OemGetEmbeddedControllerFirmwareRelease () & 0xFF); (PcdGet16 (PcdEmbeddedControllerFirmwareRelease) >> 8);
SmbiosRecord->EmbeddedControllerFirmwareMinorRelease = (UINT16)
(PcdGet16 (PcdEmbeddedControllerFirmwareRelease) & 0xFF);
OptionalStrStart = (CHAR8 *)(SmbiosRecord + 1); OptionalStrStart = (CHAR8 *)(SmbiosRecord + 1);
UnicodeStrToAsciiStrS (Vendor, OptionalStrStart, VendorStrLen + 1); UnicodeStrToAsciiStrS (Vendor, OptionalStrStart, VendorStrLen + 1);
@@ -287,7 +273,7 @@ SMBIOS_MISC_TABLE_FUNCTION (MiscBiosVendor) {
DEBUG (( DEBUG ((
DEBUG_ERROR, DEBUG_ERROR,
"[%a]:[%dL] Smbios Type00 Table Log Failed! %r \n", "[%a]:[%dL] Smbios Type00 Table Log Failed! %r \n",
__func__, __FUNCTION__,
DEBUG_LINE_NUMBER, DEBUG_LINE_NUMBER,
Status Status
)); ));

View File

@@ -4,7 +4,6 @@
Based on files under Nt32Pkg/MiscSubClassPlatformDxe/ Based on files under Nt32Pkg/MiscSubClassPlatformDxe/
Copyright (c) 2022, Ampere Computing LLC. All rights reserved.<BR>
Copyright (c) 2021, NUVIA Inc. All rights reserved.<BR> Copyright (c) 2021, NUVIA Inc. All rights reserved.<BR>
Copyright (c) 2006 - 2011, Intel Corporation. All rights reserved.<BR> Copyright (c) 2006 - 2011, Intel Corporation. All rights reserved.<BR>
Copyright (c) 2015, Hisilicon Limited. All rights reserved.<BR> Copyright (c) 2015, Hisilicon Limited. All rights reserved.<BR>
@@ -161,7 +160,7 @@ SMBIOS_MISC_TABLE_FUNCTION (MiscSystemManufacturer) {
SmbiosRecord->Hdr.Length = sizeof (SMBIOS_TABLE_TYPE1); SmbiosRecord->Hdr.Length = sizeof (SMBIOS_TABLE_TYPE1);
OemGetSystemUuid (&SmbiosRecord->Uuid); CopyGuid (&SmbiosRecord->Uuid, &InputData->Uuid);
OptionalStrStart = (CHAR8 *)(SmbiosRecord + 1); OptionalStrStart = (CHAR8 *)(SmbiosRecord + 1);
UnicodeStrToAsciiStrS (Manufacturer, OptionalStrStart, ManuStrLen + 1); UnicodeStrToAsciiStrS (Manufacturer, OptionalStrStart, ManuStrLen + 1);
@@ -184,7 +183,7 @@ SMBIOS_MISC_TABLE_FUNCTION (MiscSystemManufacturer) {
DEBUG (( DEBUG ((
DEBUG_ERROR, DEBUG_ERROR,
"[%a]:[%dL] Smbios Type01 Table Log Failed! %r \n", "[%a]:[%dL] Smbios Type01 Table Log Failed! %r \n",
__func__, __FUNCTION__,
DEBUG_LINE_NUMBER, DEBUG_LINE_NUMBER,
Status Status
)); ));

View File

@@ -4,7 +4,6 @@
Based on files under Nt32Pkg/MiscSubClassPlatformDxe/ Based on files under Nt32Pkg/MiscSubClassPlatformDxe/
Copyright (c) 2022, Ampere Computing LLC. All rights reserved.<BR>
Copyright (c) 2021, NUVIA Inc. All rights reserved.<BR> Copyright (c) 2021, NUVIA Inc. All rights reserved.<BR>
Copyright (c) 2009 - 2011, Intel Corporation. All rights reserved.<BR> Copyright (c) 2009 - 2011, Intel Corporation. All rights reserved.<BR>
Copyright (c) 2015, Hisilicon Limited. All rights reserved.<BR> Copyright (c) 2015, Hisilicon Limited. All rights reserved.<BR>
@@ -113,7 +112,17 @@ SMBIOS_MISC_TABLE_FUNCTION (MiscBaseBoardManufacturer) {
OemUpdateSmbiosInfo ( OemUpdateSmbiosInfo (
mSmbiosMiscHiiHandle, mSmbiosMiscHiiHandle,
STRING_TOKEN (STR_MISC_BASE_BOARD_ASSET_TAG), STRING_TOKEN (STR_MISC_BASE_BOARD_ASSET_TAG),
AssetTagType02 AssertTagType02
);
OemUpdateSmbiosInfo (
mSmbiosMiscHiiHandle,
STRING_TOKEN (STR_MISC_BASE_BOARD_SERIAL_NUMBER),
SerialNumberType02
);
OemUpdateSmbiosInfo (
mSmbiosMiscHiiHandle,
STRING_TOKEN (STR_MISC_BASE_BOARD_MANUFACTURER),
BoardManufacturerType02
); );
OemUpdateSmbiosInfo ( OemUpdateSmbiosInfo (
mSmbiosMiscHiiHandle, mSmbiosMiscHiiHandle,
@@ -214,7 +223,7 @@ SMBIOS_MISC_TABLE_FUNCTION (MiscBaseBoardManufacturer) {
DEBUG (( DEBUG ((
DEBUG_ERROR, DEBUG_ERROR,
"[%a]:[%dL] Smbios Type02 Table Log Failed! %r \n", "[%a]:[%dL] Smbios Type02 Table Log Failed! %r \n",
__func__, __FUNCTION__,
DEBUG_LINE_NUMBER, DEBUG_LINE_NUMBER,
Status Status
)); ));

View File

@@ -179,7 +179,7 @@ SMBIOS_MISC_TABLE_FUNCTION (MiscChassisManufacturer) {
DEBUG (( DEBUG ((
DEBUG_ERROR, DEBUG_ERROR,
"[%a]:[%dL] Smbios Type03 Table Log Failed! %r \n", "[%a]:[%dL] Smbios Type03 Table Log Failed! %r \n",
__func__, __FUNCTION__,
DEBUG_LINE_NUMBER, DEBUG_LINE_NUMBER,
Status Status
)); ));

View File

@@ -161,7 +161,7 @@ SMBIOS_MISC_TABLE_FUNCTION (MiscNumberOfInstallableLanguages) {
DEBUG (( DEBUG ((
DEBUG_ERROR, DEBUG_ERROR,
"[%a]:[%dL] Smbios Type13 Table Log Failed! %r \n", "[%a]:[%dL] Smbios Type13 Table Log Failed! %r \n",
__func__, __FUNCTION__,
DEBUG_LINE_NUMBER, DEBUG_LINE_NUMBER,
Status Status
)); ));

View File

@@ -69,7 +69,7 @@ SMBIOS_MISC_TABLE_FUNCTION (MiscBootInformation) {
DEBUG (( DEBUG ((
DEBUG_ERROR, DEBUG_ERROR,
"[%a]:[%dL] Smbios Type32 Table Log Failed! %r \n", "[%a]:[%dL] Smbios Type32 Table Log Failed! %r \n",
__func__, __FUNCTION__,
DEBUG_LINE_NUMBER, DEBUG_LINE_NUMBER,
Status Status
)); ));

View File

@@ -38,6 +38,10 @@
# #
LcdPlatformLib|Include/Library/LcdPlatformLib.h LcdPlatformLib|Include/Library/LcdPlatformLib.h
## @libraryclass Provides a Nor flash interface.
#
NorFlashPlatformLib|Include/Library/NorFlashPlatformLib.h
## @libraryclass Provides an interface to the clock of a PL011 device. ## @libraryclass Provides an interface to the clock of a PL011 device.
# #
PL011UartClockLib|Include/Library/PL011UartClockLib.h PL011UartClockLib|Include/Library/PL011UartClockLib.h
@@ -52,6 +56,8 @@
[PcdsFeatureFlag.common] [PcdsFeatureFlag.common]
gArmPlatformTokenSpaceGuid.PcdSendSgiToBringUpSecondaryCores|FALSE|BOOLEAN|0x00000004 gArmPlatformTokenSpaceGuid.PcdSendSgiToBringUpSecondaryCores|FALSE|BOOLEAN|0x00000004
gArmPlatformTokenSpaceGuid.PcdNorFlashCheckBlockLocked|FALSE|BOOLEAN|0x0000003C
# Disable the GOP controller on ExitBootServices(). By default the value is FALSE, # Disable the GOP controller on ExitBootServices(). By default the value is FALSE,
# we assume the OS will handle the FrameBuffer from the UEFI GOP information. # we assume the OS will handle the FrameBuffer from the UEFI GOP information.
gArmPlatformTokenSpaceGuid.PcdGopDisableOnExitBootServices|FALSE|BOOLEAN|0x0000003D gArmPlatformTokenSpaceGuid.PcdGopDisableOnExitBootServices|FALSE|BOOLEAN|0x0000003D
@@ -88,7 +94,6 @@
gArmPlatformTokenSpaceGuid.PcdSerialDbgRegisterBase|0x00000000|UINT64|0x00000030 gArmPlatformTokenSpaceGuid.PcdSerialDbgRegisterBase|0x00000000|UINT64|0x00000030
gArmPlatformTokenSpaceGuid.PcdSerialDbgUartBaudRate|0x00000000|UINT64|0x00000031 gArmPlatformTokenSpaceGuid.PcdSerialDbgUartBaudRate|0x00000000|UINT64|0x00000031
gArmPlatformTokenSpaceGuid.PcdSerialDbgUartClkInHz|0x00000000|UINT32|0x00000032 gArmPlatformTokenSpaceGuid.PcdSerialDbgUartClkInHz|0x00000000|UINT32|0x00000032
gArmPlatformTokenSpaceGuid.PcdSerialDbgInterrupt|0x00000000|UINT32|0x00000041
## PL061 GPIO ## PL061 GPIO
gArmPlatformTokenSpaceGuid.PcdPL061GpioBase|0x0|UINT32|0x00000025 gArmPlatformTokenSpaceGuid.PcdPL061GpioBase|0x0|UINT32|0x00000025

View File

@@ -55,6 +55,7 @@
LzmaDecompressLib|MdeModulePkg/Library/LzmaCustomDecompressLib/LzmaCustomDecompressLib.inf LzmaDecompressLib|MdeModulePkg/Library/LzmaCustomDecompressLib/LzmaCustomDecompressLib.inf
MemoryAllocationLib|MdePkg/Library/UefiMemoryAllocationLib/UefiMemoryAllocationLib.inf MemoryAllocationLib|MdePkg/Library/UefiMemoryAllocationLib/UefiMemoryAllocationLib.inf
MemoryInitPeiLib|ArmPlatformPkg/MemoryInitPei/MemoryInitPeiLib.inf MemoryInitPeiLib|ArmPlatformPkg/MemoryInitPei/MemoryInitPeiLib.inf
NorFlashPlatformLib|ArmPlatformPkg/Library/NorFlashPlatformNullLib/NorFlashPlatformNullLib.inf
PcdLib|MdePkg/Library/BasePcdLibNull/BasePcdLibNull.inf PcdLib|MdePkg/Library/BasePcdLibNull/BasePcdLibNull.inf
PeCoffExtraActionLib|MdePkg/Library/BasePeCoffExtraActionLibNull/BasePeCoffExtraActionLibNull.inf PeCoffExtraActionLib|MdePkg/Library/BasePeCoffExtraActionLibNull/BasePeCoffExtraActionLibNull.inf
PeCoffLib|MdePkg/Library/BasePeCoffLib/BasePeCoffLib.inf PeCoffLib|MdePkg/Library/BasePeCoffLib/BasePeCoffLib.inf
@@ -99,6 +100,7 @@
[Components.common] [Components.common]
ArmPlatformPkg/Drivers/LcdGraphicsOutputDxe/LcdGraphicsOutputDxe.inf ArmPlatformPkg/Drivers/LcdGraphicsOutputDxe/LcdGraphicsOutputDxe.inf
ArmPlatformPkg/Drivers/NorFlashDxe/NorFlashDxe.inf
ArmPlatformPkg/Drivers/PL061GpioDxe/PL061GpioDxe.inf ArmPlatformPkg/Drivers/PL061GpioDxe/PL061GpioDxe.inf
ArmPlatformPkg/Drivers/SP805WatchdogDxe/SP805WatchdogDxe.inf ArmPlatformPkg/Drivers/SP805WatchdogDxe/SP805WatchdogDxe.inf
@@ -107,6 +109,7 @@
ArmPlatformPkg/Library/HdLcd/HdLcd.inf ArmPlatformPkg/Library/HdLcd/HdLcd.inf
ArmPlatformPkg/Library/LcdHwNullLib/LcdHwNullLib.inf ArmPlatformPkg/Library/LcdHwNullLib/LcdHwNullLib.inf
ArmPlatformPkg/Library/LcdPlatformNullLib/LcdPlatformNullLib.inf ArmPlatformPkg/Library/LcdPlatformNullLib/LcdPlatformNullLib.inf
ArmPlatformPkg/Library/NorFlashPlatformNullLib/NorFlashPlatformNullLib.inf
ArmPlatformPkg/Library/PL011SerialPortLib/PL011SerialPortLib.inf ArmPlatformPkg/Library/PL011SerialPortLib/PL011SerialPortLib.inf
ArmPlatformPkg/Library/PL011UartClockLib/PL011UartClockLib.inf ArmPlatformPkg/Library/PL011UartClockLib/PL011UartClockLib.inf
ArmPlatformPkg/Library/PL011UartLib/PL011UartLib.inf ArmPlatformPkg/Library/PL011UartLib/PL011UartLib.inf
@@ -127,3 +130,6 @@
ArmPlatformPkg/PrePi/PeiUniCore.inf ArmPlatformPkg/PrePi/PeiUniCore.inf
ArmPlatformPkg/Library/ArmMaliDp/ArmMaliDp.inf ArmPlatformPkg/Library/ArmMaliDp/ArmMaliDp.inf
[Components.AARCH64]
ArmPlatformPkg/Drivers/NorFlashDxe/NorFlashStandaloneMm.inf

View File

@@ -815,6 +815,18 @@ LcdGraphicsBlt (
HorizontalResolution = This->Mode->Info->HorizontalResolution; HorizontalResolution = This->Mode->Info->HorizontalResolution;
VerticalResolution = This->Mode->Info->VerticalResolution; VerticalResolution = This->Mode->Info->VerticalResolution;
DEBUG ((
DEBUG_INFO,
"LcdGraphicsBlt (BltOperation:%d,DestX:%d,DestY:%d,Width:%d,Height:%d) res(%d,%d)\n",
BltOperation,
DestinationX,
DestinationY,
Width,
Height,
HorizontalResolution,
VerticalResolution
));
// Check we have reasonable parameters // Check we have reasonable parameters
if ((Width == 0) || (Height == 0)) { if ((Width == 0) || (Height == 0)) {
DEBUG ((DEBUG_ERROR, "LcdGraphicsBlt: ERROR - Invalid dimension: Zero size area.\n")); DEBUG ((DEBUG_ERROR, "LcdGraphicsBlt: ERROR - Invalid dimension: Zero size area.\n"));

View File

@@ -9,7 +9,7 @@
#include <Library/BaseMemoryLib.h> #include <Library/BaseMemoryLib.h>
#include "VirtNorFlash.h" #include "NorFlash.h"
// //
// Global variable declarations // Global variable declarations
@@ -65,6 +65,24 @@ NorFlashUnlockSingleBlock (
// Raise the Task Priority Level to TPL_NOTIFY to serialise all its operations // Raise the Task Priority Level to TPL_NOTIFY to serialise all its operations
// and to protect shared data structures. // and to protect shared data structures.
if (FeaturePcdGet (PcdNorFlashCheckBlockLocked) == TRUE) {
do {
// Request a lock setup
SEND_NOR_COMMAND (BlockAddress, 0, P30_CMD_LOCK_BLOCK_SETUP);
// Request an unlock
SEND_NOR_COMMAND (BlockAddress, 0, P30_CMD_UNLOCK_BLOCK);
// Send command for reading device id
SEND_NOR_COMMAND (BlockAddress, 2, P30_CMD_READ_DEVICE_ID);
// Read block lock status
LockStatus = MmioRead32 (CREATE_NOR_ADDRESS (BlockAddress, 2));
// Decode block lock status
LockStatus = FOLD_32BIT_INTO_16BIT (LockStatus);
} while ((LockStatus & 0x1) == 1);
} else {
// Request a lock setup // Request a lock setup
SEND_NOR_COMMAND (BlockAddress, 0, P30_CMD_LOCK_BLOCK_SETUP); SEND_NOR_COMMAND (BlockAddress, 0, P30_CMD_LOCK_BLOCK_SETUP);
@@ -75,6 +93,7 @@ NorFlashUnlockSingleBlock (
do { do {
LockStatus = NorFlashReadStatusRegister (Instance, BlockAddress); LockStatus = NorFlashReadStatusRegister (Instance, BlockAddress);
} while ((LockStatus & P30_SR_BIT_WRITE) != P30_SR_BIT_WRITE); } while ((LockStatus & P30_SR_BIT_WRITE) != P30_SR_BIT_WRITE);
}
// Put device back into Read Array mode // Put device back into Read Array mode
SEND_NOR_COMMAND (BlockAddress, 0, P30_CMD_READ_ARRAY); SEND_NOR_COMMAND (BlockAddress, 0, P30_CMD_READ_ARRAY);
@@ -205,6 +224,9 @@ NorFlashWriteSingleWord (
SEND_NOR_COMMAND (Instance->DeviceBaseAddress, 0, P30_CMD_CLEAR_STATUS_REGISTER); SEND_NOR_COMMAND (Instance->DeviceBaseAddress, 0, P30_CMD_CLEAR_STATUS_REGISTER);
} }
// Put device back into Read Array mode
SEND_NOR_COMMAND (Instance->DeviceBaseAddress, 0, P30_CMD_READ_ARRAY);
return Status; return Status;
} }
@@ -283,7 +305,8 @@ NorFlashWriteBuffer (
// The buffer was not available for writing // The buffer was not available for writing
if (WaitForBuffer == 0) { if (WaitForBuffer == 0) {
return EFI_DEVICE_ERROR; Status = EFI_DEVICE_ERROR;
goto EXIT;
} }
// From now on we work in 32-bit words // From now on we work in 32-bit words
@@ -333,6 +356,10 @@ NorFlashWriteBuffer (
SEND_NOR_COMMAND (Instance->DeviceBaseAddress, 0, P30_CMD_CLEAR_STATUS_REGISTER); SEND_NOR_COMMAND (Instance->DeviceBaseAddress, 0, P30_CMD_CLEAR_STATUS_REGISTER);
} }
EXIT:
// Put device back into Read Array mode
SEND_NOR_COMMAND (Instance->DeviceBaseAddress, 0, P30_CMD_READ_ARRAY);
return Status; return Status;
} }
@@ -358,6 +385,10 @@ NorFlashWriteBlocks (
return EFI_INVALID_PARAMETER; return EFI_INVALID_PARAMETER;
} }
if (Instance->Media.ReadOnly == TRUE) {
return EFI_WRITE_PROTECTED;
}
// We must have some bytes to read // We must have some bytes to read
DEBUG ((DEBUG_BLKIO, "NorFlashWriteBlocks: BufferSizeInBytes=0x%x\n", BufferSizeInBytes)); DEBUG ((DEBUG_BLKIO, "NorFlashWriteBlocks: BufferSizeInBytes=0x%x\n", BufferSizeInBytes));
if (BufferSizeInBytes == 0) { if (BufferSizeInBytes == 0) {
@@ -365,22 +396,22 @@ NorFlashWriteBlocks (
} }
// The size of the buffer must be a multiple of the block size // The size of the buffer must be a multiple of the block size
DEBUG ((DEBUG_BLKIO, "NorFlashWriteBlocks: BlockSize in bytes =0x%x\n", Instance->BlockSize)); DEBUG ((DEBUG_BLKIO, "NorFlashWriteBlocks: BlockSize in bytes =0x%x\n", Instance->Media.BlockSize));
if ((BufferSizeInBytes % Instance->BlockSize) != 0) { if ((BufferSizeInBytes % Instance->Media.BlockSize) != 0) {
return EFI_BAD_BUFFER_SIZE; return EFI_BAD_BUFFER_SIZE;
} }
// All blocks must be within the device // All blocks must be within the device
NumBlocks = ((UINT32)BufferSizeInBytes) / Instance->BlockSize; NumBlocks = ((UINT32)BufferSizeInBytes) / Instance->Media.BlockSize;
DEBUG ((DEBUG_BLKIO, "NorFlashWriteBlocks: NumBlocks=%d, LastBlock=%ld, Lba=%ld.\n", NumBlocks, Instance->LastBlock, Lba)); DEBUG ((DEBUG_BLKIO, "NorFlashWriteBlocks: NumBlocks=%d, LastBlock=%ld, Lba=%ld.\n", NumBlocks, Instance->Media.LastBlock, Lba));
if ((Lba + NumBlocks) > (Instance->LastBlock + 1)) { if ((Lba + NumBlocks) > (Instance->Media.LastBlock + 1)) {
DEBUG ((DEBUG_ERROR, "NorFlashWriteBlocks: ERROR - Write will exceed last block.\n")); DEBUG ((DEBUG_ERROR, "NorFlashWriteBlocks: ERROR - Write will exceed last block.\n"));
return EFI_INVALID_PARAMETER; return EFI_INVALID_PARAMETER;
} }
BlockSizeInWords = Instance->BlockSize / 4; BlockSizeInWords = Instance->Media.BlockSize / 4;
// Because the target *Buffer is a pointer to VOID, we must put all the data into a pointer // Because the target *Buffer is a pointer to VOID, we must put all the data into a pointer
// to a proper data type, so use *ReadBuffer // to a proper data type, so use *ReadBuffer
@@ -401,6 +432,67 @@ NorFlashWriteBlocks (
return Status; return Status;
} }
#define BOTH_ALIGNED(a, b, align) ((((UINTN)(a) | (UINTN)(b)) & ((align) - 1)) == 0)
/**
Copy Length bytes from Source to Destination, using aligned accesses only.
Note that this implementation uses memcpy() semantics rather then memmove()
semantics, i.e., SourceBuffer and DestinationBuffer should not overlap.
@param DestinationBuffer The target of the copy request.
@param SourceBuffer The place to copy from.
@param Length The number of bytes to copy.
@return Destination
**/
STATIC
VOID *
AlignedCopyMem (
OUT VOID *DestinationBuffer,
IN CONST VOID *SourceBuffer,
IN UINTN Length
)
{
UINT8 *Destination8;
CONST UINT8 *Source8;
UINT32 *Destination32;
CONST UINT32 *Source32;
UINT64 *Destination64;
CONST UINT64 *Source64;
if (BOTH_ALIGNED (DestinationBuffer, SourceBuffer, 8) && (Length >= 8)) {
Destination64 = DestinationBuffer;
Source64 = SourceBuffer;
while (Length >= 8) {
*Destination64++ = *Source64++;
Length -= 8;
}
Destination8 = (UINT8 *)Destination64;
Source8 = (CONST UINT8 *)Source64;
} else if (BOTH_ALIGNED (DestinationBuffer, SourceBuffer, 4) && (Length >= 4)) {
Destination32 = DestinationBuffer;
Source32 = SourceBuffer;
while (Length >= 4) {
*Destination32++ = *Source32++;
Length -= 4;
}
Destination8 = (UINT8 *)Destination32;
Source8 = (CONST UINT8 *)Source32;
} else {
Destination8 = DestinationBuffer;
Source8 = SourceBuffer;
}
while (Length-- != 0) {
*Destination8++ = *Source8++;
}
return DestinationBuffer;
}
EFI_STATUS EFI_STATUS
NorFlashReadBlocks ( NorFlashReadBlocks (
IN NOR_FLASH_INSTANCE *Instance, IN NOR_FLASH_INSTANCE *Instance,
@@ -416,8 +508,8 @@ NorFlashReadBlocks (
DEBUG_BLKIO, DEBUG_BLKIO,
"NorFlashReadBlocks: BufferSize=0x%xB BlockSize=0x%xB LastBlock=%ld, Lba=%ld.\n", "NorFlashReadBlocks: BufferSize=0x%xB BlockSize=0x%xB LastBlock=%ld, Lba=%ld.\n",
BufferSizeInBytes, BufferSizeInBytes,
Instance->BlockSize, Instance->Media.BlockSize,
Instance->LastBlock, Instance->Media.LastBlock,
Lba Lba
)); ));
@@ -432,14 +524,14 @@ NorFlashReadBlocks (
} }
// The size of the buffer must be a multiple of the block size // The size of the buffer must be a multiple of the block size
if ((BufferSizeInBytes % Instance->BlockSize) != 0) { if ((BufferSizeInBytes % Instance->Media.BlockSize) != 0) {
return EFI_BAD_BUFFER_SIZE; return EFI_BAD_BUFFER_SIZE;
} }
// All blocks must be within the device // All blocks must be within the device
NumBlocks = ((UINT32)BufferSizeInBytes) / Instance->BlockSize; NumBlocks = ((UINT32)BufferSizeInBytes) / Instance->Media.BlockSize;
if ((Lba + NumBlocks) > (Instance->LastBlock + 1)) { if ((Lba + NumBlocks) > (Instance->Media.LastBlock + 1)) {
DEBUG ((DEBUG_ERROR, "NorFlashReadBlocks: ERROR - Read will exceed last block\n")); DEBUG ((DEBUG_ERROR, "NorFlashReadBlocks: ERROR - Read will exceed last block\n"));
return EFI_INVALID_PARAMETER; return EFI_INVALID_PARAMETER;
} }
@@ -448,14 +540,14 @@ NorFlashReadBlocks (
StartAddress = GET_NOR_BLOCK_ADDRESS ( StartAddress = GET_NOR_BLOCK_ADDRESS (
Instance->RegionBaseAddress, Instance->RegionBaseAddress,
Lba, Lba,
Instance->BlockSize Instance->Media.BlockSize
); );
// Put the device into Read Array mode // Put the device into Read Array mode
SEND_NOR_COMMAND (Instance->DeviceBaseAddress, 0, P30_CMD_READ_ARRAY); SEND_NOR_COMMAND (Instance->DeviceBaseAddress, 0, P30_CMD_READ_ARRAY);
// Readout the data // Readout the data
CopyMem (Buffer, (VOID *)StartAddress, BufferSizeInBytes); AlignedCopyMem (Buffer, (VOID *)StartAddress, BufferSizeInBytes);
return EFI_SUCCESS; return EFI_SUCCESS;
} }
@@ -481,7 +573,7 @@ NorFlashRead (
return EFI_SUCCESS; return EFI_SUCCESS;
} }
if (((Lba * Instance->BlockSize) + Offset + BufferSizeInBytes) > Instance->Size) { if (((Lba * Instance->Media.BlockSize) + Offset + BufferSizeInBytes) > Instance->Size) {
DEBUG ((DEBUG_ERROR, "NorFlashRead: ERROR - Read will exceed device size.\n")); DEBUG ((DEBUG_ERROR, "NorFlashRead: ERROR - Read will exceed device size.\n"));
return EFI_INVALID_PARAMETER; return EFI_INVALID_PARAMETER;
} }
@@ -490,21 +582,21 @@ NorFlashRead (
StartAddress = GET_NOR_BLOCK_ADDRESS ( StartAddress = GET_NOR_BLOCK_ADDRESS (
Instance->RegionBaseAddress, Instance->RegionBaseAddress,
Lba, Lba,
Instance->BlockSize Instance->Media.BlockSize
); );
// Put the device into Read Array mode // Put the device into Read Array mode
SEND_NOR_COMMAND (Instance->DeviceBaseAddress, 0, P30_CMD_READ_ARRAY); SEND_NOR_COMMAND (Instance->DeviceBaseAddress, 0, P30_CMD_READ_ARRAY);
// Readout the data // Readout the data
CopyMem (Buffer, (VOID *)(StartAddress + Offset), BufferSizeInBytes); AlignedCopyMem (Buffer, (VOID *)(StartAddress + Offset), BufferSizeInBytes);
return EFI_SUCCESS; return EFI_SUCCESS;
} }
/* /*
Write a full or portion of a block. It must not span block boundaries; that is, Write a full or portion of a block. It must not span block boundaries; that is,
Offset + *NumBytes <= Instance->BlockSize. Offset + *NumBytes <= Instance->Media.BlockSize.
*/ */
EFI_STATUS EFI_STATUS
NorFlashWriteSingleBlock ( NorFlashWriteSingleBlock (
@@ -515,22 +607,32 @@ NorFlashWriteSingleBlock (
IN UINT8 *Buffer IN UINT8 *Buffer
) )
{ {
EFI_STATUS Status; EFI_STATUS TempStatus;
UINT32 Tmp;
UINT32 TmpBuf;
UINT32 WordToWrite;
UINT32 Mask;
BOOLEAN DoErase;
UINTN BytesToWrite;
UINTN CurOffset; UINTN CurOffset;
UINTN WordAddr;
UINTN BlockSize; UINTN BlockSize;
UINTN BlockAddress; UINTN BlockAddress;
UINT8 *OrigData; UINTN PrevBlockAddress;
PrevBlockAddress = 0;
DEBUG ((DEBUG_BLKIO, "NorFlashWriteSingleBlock(Parameters: Lba=%ld, Offset=0x%x, *NumBytes=0x%x, Buffer @ 0x%08x)\n", Lba, Offset, *NumBytes, Buffer)); DEBUG ((DEBUG_BLKIO, "NorFlashWriteSingleBlock(Parameters: Lba=%ld, Offset=0x%x, *NumBytes=0x%x, Buffer @ 0x%08x)\n", Lba, Offset, *NumBytes, Buffer));
// Check we did get some memory. Buffer is BlockSize. // Detect WriteDisabled state
if (Instance->ShadowBuffer == NULL) { if (Instance->Media.ReadOnly == TRUE) {
DEBUG ((DEBUG_ERROR, "FvbWrite: ERROR - Buffer not ready\n")); DEBUG ((DEBUG_ERROR, "NorFlashWriteSingleBlock: ERROR - Can not write: Device is in WriteDisabled state.\n"));
return EFI_DEVICE_ERROR; // It is in WriteDisabled state, return an error right away
return EFI_ACCESS_DENIED;
} }
// Cache the block size to avoid de-referencing pointers all the time // Cache the block size to avoid de-referencing pointers all the time
BlockSize = Instance->BlockSize; BlockSize = Instance->Media.BlockSize;
// The write must not span block boundaries. // The write must not span block boundaries.
// We need to check each variable individually because adding two large values together overflows. // We need to check each variable individually because adding two large values together overflows.
@@ -548,89 +650,146 @@ NorFlashWriteSingleBlock (
return EFI_BAD_BUFFER_SIZE; return EFI_BAD_BUFFER_SIZE;
} }
// Pick P30_MAX_BUFFER_SIZE_IN_BYTES (== 128 bytes) as a good start for word // Pick 128bytes as a good start for word operations as opposed to erasing the
// operations as opposed to erasing the block and writing the data regardless // block and writing the data regardless if an erase is really needed.
// if an erase is really needed. It looks like most individual NV variable // It looks like most individual NV variable writes are smaller than 128bytes.
// writes are smaller than 128 bytes. if (*NumBytes <= 128) {
// To avoid pathological cases were a 2 byte write is disregarded because it
// occurs right at a 128 byte buffered write alignment boundary, permit up to
// twice the max buffer size, and perform two writes if needed.
if ((*NumBytes + (Offset & BOUNDARY_OF_32_WORDS)) <= (2 * P30_MAX_BUFFER_SIZE_IN_BYTES)) {
// Check to see if we need to erase before programming the data into NOR. // Check to see if we need to erase before programming the data into NOR.
// If the destination bits are only changing from 1s to 0s we can just write. // If the destination bits are only changing from 1s to 0s we can just write.
// After a block is erased all bits in the block is set to 1. // After a block is erased all bits in the block is set to 1.
// If any byte requires us to erase we just give up and rewrite all of it. // If any byte requires us to erase we just give up and rewrite all of it.
DoErase = FALSE;
BytesToWrite = *NumBytes;
CurOffset = Offset;
// Read the old version of the data into the shadow buffer while (BytesToWrite > 0) {
Status = NorFlashRead ( // Read full word from NOR, splice as required. A word is the smallest
Instance, // unit we can write.
Lba, TempStatus = NorFlashRead (Instance, Lba, CurOffset & ~(0x3), sizeof (Tmp), &Tmp);
Offset & ~BOUNDARY_OF_32_WORDS, if (EFI_ERROR (TempStatus)) {
(*NumBytes | BOUNDARY_OF_32_WORDS) + 1,
Instance->ShadowBuffer
);
if (EFI_ERROR (Status)) {
return EFI_DEVICE_ERROR; return EFI_DEVICE_ERROR;
} }
// Make OrigData point to the start of the old version of the data inside // Physical address of word in NOR to write.
// the word aligned buffer WordAddr = (CurOffset & ~(0x3)) + GET_NOR_BLOCK_ADDRESS (
OrigData = Instance->ShadowBuffer + (Offset & BOUNDARY_OF_32_WORDS); Instance->RegionBaseAddress,
Lba,
BlockSize
);
// The word of data that is to be written.
TmpBuf = *((UINT32 *)(Buffer + (*NumBytes - BytesToWrite)));
// Update the buffer containing the old version of the data with the new // First do word aligned chunks.
// contents, while checking whether the old version had any bits cleared if ((CurOffset & 0x3) == 0) {
// that we want to set. In that case, we will need to erase the block first. if (BytesToWrite >= 4) {
for (CurOffset = 0; CurOffset < *NumBytes; CurOffset++) { // Is the destination still in 'erased' state?
if (~OrigData[CurOffset] & Buffer[CurOffset]) { if (~Tmp != 0) {
goto DoErase; // Check to see if we are only changing bits to zero.
if ((Tmp ^ TmpBuf) & TmpBuf) {
DoErase = TRUE;
break;
}
} }
OrigData[CurOffset] = Buffer[CurOffset]; // Write this word to NOR
WordToWrite = TmpBuf;
CurOffset += sizeof (TmpBuf);
BytesToWrite -= sizeof (TmpBuf);
} else {
// BytesToWrite < 4. Do small writes and left-overs
Mask = ~((~0) << (BytesToWrite * 8));
// Mask out the bytes we want.
TmpBuf &= Mask;
// Is the destination still in 'erased' state?
if ((Tmp & Mask) != Mask) {
// Check to see if we are only changing bits to zero.
if ((Tmp ^ TmpBuf) & TmpBuf) {
DoErase = TRUE;
break;
}
}
// Merge old and new data. Write merged word to NOR
WordToWrite = (Tmp & ~Mask) | TmpBuf;
CurOffset += BytesToWrite;
BytesToWrite = 0;
}
} else {
// Do multiple words, but starting unaligned.
if (BytesToWrite > (4 - (CurOffset & 0x3))) {
Mask = ((~0) << ((CurOffset & 0x3) * 8));
// Mask out the bytes we want.
TmpBuf &= Mask;
// Is the destination still in 'erased' state?
if ((Tmp & Mask) != Mask) {
// Check to see if we are only changing bits to zero.
if ((Tmp ^ TmpBuf) & TmpBuf) {
DoErase = TRUE;
break;
}
}
// Merge old and new data. Write merged word to NOR
WordToWrite = (Tmp & ~Mask) | TmpBuf;
BytesToWrite -= (4 - (CurOffset & 0x3));
CurOffset += (4 - (CurOffset & 0x3));
} else {
// Unaligned and fits in one word.
Mask = (~((~0) << (BytesToWrite * 8))) << ((CurOffset & 0x3) * 8);
// Mask out the bytes we want.
TmpBuf = (TmpBuf << ((CurOffset & 0x3) * 8)) & Mask;
// Is the destination still in 'erased' state?
if ((Tmp & Mask) != Mask) {
// Check to see if we are only changing bits to zero.
if ((Tmp ^ TmpBuf) & TmpBuf) {
DoErase = TRUE;
break;
}
}
// Merge old and new data. Write merged word to NOR
WordToWrite = (Tmp & ~Mask) | TmpBuf;
CurOffset += BytesToWrite;
BytesToWrite = 0;
}
} }
// //
// Write the updated buffer to NOR. // Write the word to NOR.
// //
BlockAddress = GET_NOR_BLOCK_ADDRESS (Instance->RegionBaseAddress, Lba, BlockSize); BlockAddress = GET_NOR_BLOCK_ADDRESS (Instance->RegionBaseAddress, Lba, BlockSize);
if (BlockAddress != PrevBlockAddress) {
// Unlock the block if we have to TempStatus = NorFlashUnlockSingleBlockIfNecessary (Instance, BlockAddress);
Status = NorFlashUnlockSingleBlockIfNecessary (Instance, BlockAddress); if (EFI_ERROR (TempStatus)) {
if (EFI_ERROR (Status)) { return EFI_DEVICE_ERROR;
goto Exit;
} }
Status = NorFlashWriteBuffer ( PrevBlockAddress = BlockAddress;
Instance,
BlockAddress + (Offset & ~BOUNDARY_OF_32_WORDS),
P30_MAX_BUFFER_SIZE_IN_BYTES,
Instance->ShadowBuffer
);
if (EFI_ERROR (Status)) {
goto Exit;
} }
if ((*NumBytes + (Offset & BOUNDARY_OF_32_WORDS)) > P30_MAX_BUFFER_SIZE_IN_BYTES) { TempStatus = NorFlashWriteSingleWord (Instance, WordAddr, WordToWrite);
BlockAddress += P30_MAX_BUFFER_SIZE_IN_BYTES; if (EFI_ERROR (TempStatus)) {
return EFI_DEVICE_ERROR;
Status = NorFlashWriteBuffer ( }
Instance,
BlockAddress + (Offset & ~BOUNDARY_OF_32_WORDS),
P30_MAX_BUFFER_SIZE_IN_BYTES,
Instance->ShadowBuffer + P30_MAX_BUFFER_SIZE_IN_BYTES
);
} }
Exit: // Exit if we got here and could write all the data. Otherwise do the
// Put device back into Read Array mode // Erase-Write cycle.
SEND_NOR_COMMAND (Instance->DeviceBaseAddress, 0, P30_CMD_READ_ARRAY); if (!DoErase) {
return EFI_SUCCESS;
return Status; }
}
// Check we did get some memory. Buffer is BlockSize.
if (Instance->ShadowBuffer == NULL) {
DEBUG ((DEBUG_ERROR, "FvbWrite: ERROR - Buffer not ready\n"));
return EFI_DEVICE_ERROR;
} }
DoErase:
// Read NOR Flash data into shadow buffer // Read NOR Flash data into shadow buffer
Status = NorFlashReadBlocks (Instance, Lba, BlockSize, Instance->ShadowBuffer); TempStatus = NorFlashReadBlocks (Instance, Lba, BlockSize, Instance->ShadowBuffer);
if (EFI_ERROR (Status)) { if (EFI_ERROR (TempStatus)) {
// Return one of the pre-approved error statuses // Return one of the pre-approved error statuses
return EFI_DEVICE_ERROR; return EFI_DEVICE_ERROR;
} }
@@ -639,8 +798,8 @@ DoErase:
CopyMem ((VOID *)((UINTN)Instance->ShadowBuffer + Offset), Buffer, *NumBytes); CopyMem ((VOID *)((UINTN)Instance->ShadowBuffer + Offset), Buffer, *NumBytes);
// Write the modified buffer back to the NorFlash // Write the modified buffer back to the NorFlash
Status = NorFlashWriteBlocks (Instance, Lba, BlockSize, Instance->ShadowBuffer); TempStatus = NorFlashWriteBlocks (Instance, Lba, BlockSize, Instance->ShadowBuffer);
if (EFI_ERROR (Status)) { if (EFI_ERROR (TempStatus)) {
// Return one of the pre-approved error statuses // Return one of the pre-approved error statuses
return EFI_DEVICE_ERROR; return EFI_DEVICE_ERROR;
} }
@@ -648,6 +807,135 @@ DoErase:
return EFI_SUCCESS; return EFI_SUCCESS;
} }
/*
Although DiskIoDxe will automatically install the DiskIO protocol whenever
we install the BlockIO protocol, its implementation is sub-optimal as it reads
and writes entire blocks using the BlockIO protocol. In fact we can access
NOR flash with a finer granularity than that, so we can improve performance
by directly producing the DiskIO protocol.
*/
/**
Read BufferSize bytes from Offset into Buffer.
@param This Protocol instance pointer.
@param MediaId Id of the media, changes every time the media is replaced.
@param Offset The starting byte offset to read from
@param BufferSize Size of Buffer
@param Buffer Buffer containing read data
@retval EFI_SUCCESS The data was read correctly from the device.
@retval EFI_DEVICE_ERROR The device reported an error while performing the read.
@retval EFI_NO_MEDIA There is no media in the device.
@retval EFI_MEDIA_CHANGED The MediaId does not match the current device.
@retval EFI_INVALID_PARAMETER The read request contains device addresses that are not
valid for the device.
**/
EFI_STATUS
EFIAPI
NorFlashDiskIoReadDisk (
IN EFI_DISK_IO_PROTOCOL *This,
IN UINT32 MediaId,
IN UINT64 DiskOffset,
IN UINTN BufferSize,
OUT VOID *Buffer
)
{
NOR_FLASH_INSTANCE *Instance;
UINT32 BlockSize;
UINT32 BlockOffset;
EFI_LBA Lba;
Instance = INSTANCE_FROM_DISKIO_THIS (This);
if (MediaId != Instance->Media.MediaId) {
return EFI_MEDIA_CHANGED;
}
BlockSize = Instance->Media.BlockSize;
Lba = (EFI_LBA)DivU64x32Remainder (DiskOffset, BlockSize, &BlockOffset);
return NorFlashRead (Instance, Lba, BlockOffset, BufferSize, Buffer);
}
/**
Writes a specified number of bytes to a device.
@param This Indicates a pointer to the calling context.
@param MediaId ID of the medium to be written.
@param Offset The starting byte offset on the logical block I/O device to write.
@param BufferSize The size in bytes of Buffer. The number of bytes to write to the device.
@param Buffer A pointer to the buffer containing the data to be written.
@retval EFI_SUCCESS The data was written correctly to the device.
@retval EFI_WRITE_PROTECTED The device can not be written to.
@retval EFI_DEVICE_ERROR The device reported an error while performing the write.
@retval EFI_NO_MEDIA There is no media in the device.
@retval EFI_MEDIA_CHANGED The MediaId does not match the current device.
@retval EFI_INVALID_PARAMETER The write request contains device addresses that are not
valid for the device.
**/
EFI_STATUS
EFIAPI
NorFlashDiskIoWriteDisk (
IN EFI_DISK_IO_PROTOCOL *This,
IN UINT32 MediaId,
IN UINT64 DiskOffset,
IN UINTN BufferSize,
IN VOID *Buffer
)
{
NOR_FLASH_INSTANCE *Instance;
UINT32 BlockSize;
UINT32 BlockOffset;
EFI_LBA Lba;
UINTN RemainingBytes;
UINTN WriteSize;
EFI_STATUS Status;
Instance = INSTANCE_FROM_DISKIO_THIS (This);
if (MediaId != Instance->Media.MediaId) {
return EFI_MEDIA_CHANGED;
}
BlockSize = Instance->Media.BlockSize;
Lba = (EFI_LBA)DivU64x32Remainder (DiskOffset, BlockSize, &BlockOffset);
RemainingBytes = BufferSize;
// Write either all the remaining bytes, or the number of bytes that bring
// us up to a block boundary, whichever is less.
// (DiskOffset | (BlockSize - 1)) + 1) rounds DiskOffset up to the next
// block boundary (even if it is already on one).
WriteSize = MIN (RemainingBytes, ((DiskOffset | (BlockSize - 1)) + 1) - DiskOffset);
do {
if (WriteSize == BlockSize) {
// Write a full block
Status = NorFlashWriteFullBlock (Instance, Lba, Buffer, BlockSize / sizeof (UINT32));
} else {
// Write a partial block
Status = NorFlashWriteSingleBlock (Instance, Lba, BlockOffset, &WriteSize, Buffer);
}
if (EFI_ERROR (Status)) {
return Status;
}
// Now continue writing either all the remaining bytes or single blocks.
RemainingBytes -= WriteSize;
Buffer = (UINT8 *)Buffer + WriteSize;
Lba++;
BlockOffset = 0;
WriteSize = MIN (RemainingBytes, BlockSize);
} while (RemainingBytes);
return Status;
}
EFI_STATUS EFI_STATUS
NorFlashReset ( NorFlashReset (
IN NOR_FLASH_INSTANCE *Instance IN NOR_FLASH_INSTANCE *Instance
@@ -679,6 +967,12 @@ NorFlashVirtualNotifyEvent (
EfiConvertPointer (0x0, (VOID **)&mNorFlashInstances[Index]->DeviceBaseAddress); EfiConvertPointer (0x0, (VOID **)&mNorFlashInstances[Index]->DeviceBaseAddress);
EfiConvertPointer (0x0, (VOID **)&mNorFlashInstances[Index]->RegionBaseAddress); EfiConvertPointer (0x0, (VOID **)&mNorFlashInstances[Index]->RegionBaseAddress);
// Convert BlockIo protocol
EfiConvertPointer (0x0, (VOID **)&mNorFlashInstances[Index]->BlockIoProtocol.FlushBlocks);
EfiConvertPointer (0x0, (VOID **)&mNorFlashInstances[Index]->BlockIoProtocol.ReadBlocks);
EfiConvertPointer (0x0, (VOID **)&mNorFlashInstances[Index]->BlockIoProtocol.Reset);
EfiConvertPointer (0x0, (VOID **)&mNorFlashInstances[Index]->BlockIoProtocol.WriteBlocks);
// Convert Fvb // Convert Fvb
EfiConvertPointer (0x0, (VOID **)&mNorFlashInstances[Index]->FvbProtocol.EraseBlocks); EfiConvertPointer (0x0, (VOID **)&mNorFlashInstances[Index]->FvbProtocol.EraseBlocks);
EfiConvertPointer (0x0, (VOID **)&mNorFlashInstances[Index]->FvbProtocol.GetAttributes); EfiConvertPointer (0x0, (VOID **)&mNorFlashInstances[Index]->FvbProtocol.GetAttributes);

View File

@@ -6,21 +6,23 @@
**/ **/
#ifndef __VIRT_NOR_FLASH__ #ifndef __NOR_FLASH_H__
#define __VIRT_NOR_FLASH__ #define __NOR_FLASH_H__
#include <Base.h> #include <Base.h>
#include <PiDxe.h> #include <PiDxe.h>
#include <Guid/EventGroup.h> #include <Guid/EventGroup.h>
#include <Protocol/BlockIo.h>
#include <Protocol/DiskIo.h>
#include <Protocol/FirmwareVolumeBlock.h> #include <Protocol/FirmwareVolumeBlock.h>
#include <Library/DebugLib.h> #include <Library/DebugLib.h>
#include <Library/IoLib.h> #include <Library/IoLib.h>
#include <Library/NorFlashPlatformLib.h>
#include <Library/UefiLib.h> #include <Library/UefiLib.h>
#include <Library/UefiRuntimeLib.h> #include <Library/UefiRuntimeLib.h>
#include <Library/VirtNorFlashPlatformLib.h>
#define NOR_FLASH_ERASE_RETRY 10 #define NOR_FLASH_ERASE_RETRY 10
@@ -108,6 +110,8 @@
#define NOR_FLASH_SIGNATURE SIGNATURE_32('n', 'o', 'r', '0') #define NOR_FLASH_SIGNATURE SIGNATURE_32('n', 'o', 'r', '0')
#define INSTANCE_FROM_FVB_THIS(a) CR(a, NOR_FLASH_INSTANCE, FvbProtocol, NOR_FLASH_SIGNATURE) #define INSTANCE_FROM_FVB_THIS(a) CR(a, NOR_FLASH_INSTANCE, FvbProtocol, NOR_FLASH_SIGNATURE)
#define INSTANCE_FROM_BLKIO_THIS(a) CR(a, NOR_FLASH_INSTANCE, BlockIoProtocol, NOR_FLASH_SIGNATURE)
#define INSTANCE_FROM_DISKIO_THIS(a) CR(a, NOR_FLASH_INSTANCE, DiskIoProtocol, NOR_FLASH_SIGNATURE)
typedef struct _NOR_FLASH_INSTANCE NOR_FLASH_INSTANCE; typedef struct _NOR_FLASH_INSTANCE NOR_FLASH_INSTANCE;
@@ -127,8 +131,10 @@ struct _NOR_FLASH_INSTANCE {
UINTN RegionBaseAddress; UINTN RegionBaseAddress;
UINTN Size; UINTN Size;
EFI_LBA StartLba; EFI_LBA StartLba;
EFI_LBA LastBlock;
UINT32 BlockSize; EFI_BLOCK_IO_PROTOCOL BlockIoProtocol;
EFI_BLOCK_IO_MEDIA Media;
EFI_DISK_IO_PROTOCOL DiskIoProtocol;
EFI_FIRMWARE_VOLUME_BLOCK2_PROTOCOL FvbProtocol; EFI_FIRMWARE_VOLUME_BLOCK2_PROTOCOL FvbProtocol;
VOID *ShadowBuffer; VOID *ShadowBuffer;
@@ -152,6 +158,77 @@ NorFlashWriteBuffer (
IN UINT32 *Buffer IN UINT32 *Buffer
); );
//
// BlockIO Protocol function EFI_BLOCK_IO_PROTOCOL.Reset
//
EFI_STATUS
EFIAPI
NorFlashBlockIoReset (
IN EFI_BLOCK_IO_PROTOCOL *This,
IN BOOLEAN ExtendedVerification
);
//
// BlockIO Protocol function EFI_BLOCK_IO_PROTOCOL.ReadBlocks
//
EFI_STATUS
EFIAPI
NorFlashBlockIoReadBlocks (
IN EFI_BLOCK_IO_PROTOCOL *This,
IN UINT32 MediaId,
IN EFI_LBA Lba,
IN UINTN BufferSizeInBytes,
OUT VOID *Buffer
);
//
// BlockIO Protocol function EFI_BLOCK_IO_PROTOCOL.WriteBlocks
//
EFI_STATUS
EFIAPI
NorFlashBlockIoWriteBlocks (
IN EFI_BLOCK_IO_PROTOCOL *This,
IN UINT32 MediaId,
IN EFI_LBA Lba,
IN UINTN BufferSizeInBytes,
IN VOID *Buffer
);
//
// BlockIO Protocol function EFI_BLOCK_IO_PROTOCOL.FlushBlocks
//
EFI_STATUS
EFIAPI
NorFlashBlockIoFlushBlocks (
IN EFI_BLOCK_IO_PROTOCOL *This
);
//
// DiskIO Protocol function EFI_DISK_IO_PROTOCOL.ReadDisk
//
EFI_STATUS
EFIAPI
NorFlashDiskIoReadDisk (
IN EFI_DISK_IO_PROTOCOL *This,
IN UINT32 MediaId,
IN UINT64 Offset,
IN UINTN BufferSize,
OUT VOID *Buffer
);
//
// DiskIO Protocol function EFI_DISK_IO_PROTOCOL.WriteDisk
//
EFI_STATUS
EFIAPI
NorFlashDiskIoWriteDisk (
IN EFI_DISK_IO_PROTOCOL *This,
IN UINT32 MediaId,
IN UINT64 Offset,
IN UINTN BufferSize,
IN VOID *Buffer
);
// //
// NorFlashFvbDxe.c // NorFlashFvbDxe.c
// //
@@ -342,4 +419,4 @@ NorFlashVirtualNotifyEvent (
IN VOID *Context IN VOID *Context
); );
#endif /* __VIRT_NOR_FLASH__ */ #endif /* __NOR_FLASH_H__ */

View File

@@ -0,0 +1,123 @@
/** @file NorFlashBlockIoDxe.c
Copyright (c) 2011-2013, ARM Ltd. All rights reserved.<BR>
SPDX-License-Identifier: BSD-2-Clause-Patent
**/
#include <Library/BaseMemoryLib.h>
#include <Library/UefiBootServicesTableLib.h>
#include "NorFlash.h"
//
// BlockIO Protocol function EFI_BLOCK_IO_PROTOCOL.Reset
//
EFI_STATUS
EFIAPI
NorFlashBlockIoReset (
IN EFI_BLOCK_IO_PROTOCOL *This,
IN BOOLEAN ExtendedVerification
)
{
NOR_FLASH_INSTANCE *Instance;
Instance = INSTANCE_FROM_BLKIO_THIS (This);
DEBUG ((DEBUG_BLKIO, "NorFlashBlockIoReset(MediaId=0x%x)\n", This->Media->MediaId));
return NorFlashReset (Instance);
}
//
// BlockIO Protocol function EFI_BLOCK_IO_PROTOCOL.ReadBlocks
//
EFI_STATUS
EFIAPI
NorFlashBlockIoReadBlocks (
IN EFI_BLOCK_IO_PROTOCOL *This,
IN UINT32 MediaId,
IN EFI_LBA Lba,
IN UINTN BufferSizeInBytes,
OUT VOID *Buffer
)
{
NOR_FLASH_INSTANCE *Instance;
EFI_STATUS Status;
EFI_BLOCK_IO_MEDIA *Media;
if (This == NULL) {
return EFI_INVALID_PARAMETER;
}
Instance = INSTANCE_FROM_BLKIO_THIS (This);
Media = This->Media;
DEBUG ((DEBUG_BLKIO, "NorFlashBlockIoReadBlocks(MediaId=0x%x, Lba=%ld, BufferSize=0x%x bytes (%d kB), BufferPtr @ 0x%08x)\n", MediaId, Lba, BufferSizeInBytes, Buffer));
if (!Media) {
Status = EFI_INVALID_PARAMETER;
} else if (!Media->MediaPresent) {
Status = EFI_NO_MEDIA;
} else if (Media->MediaId != MediaId) {
Status = EFI_MEDIA_CHANGED;
} else if ((Media->IoAlign > 2) && (((UINTN)Buffer & (Media->IoAlign - 1)) != 0)) {
Status = EFI_INVALID_PARAMETER;
} else {
Status = NorFlashReadBlocks (Instance, Lba, BufferSizeInBytes, Buffer);
}
return Status;
}
//
// BlockIO Protocol function EFI_BLOCK_IO_PROTOCOL.WriteBlocks
//
EFI_STATUS
EFIAPI
NorFlashBlockIoWriteBlocks (
IN EFI_BLOCK_IO_PROTOCOL *This,
IN UINT32 MediaId,
IN EFI_LBA Lba,
IN UINTN BufferSizeInBytes,
IN VOID *Buffer
)
{
NOR_FLASH_INSTANCE *Instance;
EFI_STATUS Status;
Instance = INSTANCE_FROM_BLKIO_THIS (This);
DEBUG ((DEBUG_BLKIO, "NorFlashBlockIoWriteBlocks(MediaId=0x%x, Lba=%ld, BufferSize=0x%x bytes (%d kB), BufferPtr @ 0x%08x)\n", MediaId, Lba, BufferSizeInBytes, Buffer));
if ( !This->Media->MediaPresent ) {
Status = EFI_NO_MEDIA;
} else if ( This->Media->MediaId != MediaId ) {
Status = EFI_MEDIA_CHANGED;
} else if ( This->Media->ReadOnly ) {
Status = EFI_WRITE_PROTECTED;
} else {
Status = NorFlashWriteBlocks (Instance, Lba, BufferSizeInBytes, Buffer);
}
return Status;
}
//
// BlockIO Protocol function EFI_BLOCK_IO_PROTOCOL.FlushBlocks
//
EFI_STATUS
EFIAPI
NorFlashBlockIoFlushBlocks (
IN EFI_BLOCK_IO_PROTOCOL *This
)
{
// No Flush required for the NOR Flash driver
// because cache operations are not permitted.
DEBUG ((DEBUG_BLKIO, "NorFlashBlockIoFlushBlocks: Function NOT IMPLEMENTED (not required).\n"));
// Nothing to do so just return without error
return EFI_SUCCESS;
}

View File

@@ -6,15 +6,15 @@
**/ **/
#include <Library/BaseMemoryLib.h>
#include <Library/DxeServicesTableLib.h>
#include <Library/HobLib.h>
#include <Library/MemoryAllocationLib.h>
#include <Library/PcdLib.h>
#include <Library/UefiBootServicesTableLib.h>
#include <Library/UefiLib.h> #include <Library/UefiLib.h>
#include <Library/BaseMemoryLib.h>
#include <Library/MemoryAllocationLib.h>
#include <Library/UefiBootServicesTableLib.h>
#include <Library/PcdLib.h>
#include <Library/HobLib.h>
#include <Library/DxeServicesTableLib.h>
#include "VirtNorFlash.h" #include "NorFlash.h"
STATIC EFI_EVENT mNorFlashVirtualAddrChangeEvent; STATIC EFI_EVENT mNorFlashVirtualAddrChangeEvent;
@@ -34,8 +34,35 @@ NOR_FLASH_INSTANCE mNorFlashInstanceTemplate = {
0, // RegionBaseAddress ... NEED TO BE FILLED 0, // RegionBaseAddress ... NEED TO BE FILLED
0, // Size ... NEED TO BE FILLED 0, // Size ... NEED TO BE FILLED
0, // StartLba 0, // StartLba
0, // LastBlock
0, // BlockSize {
EFI_BLOCK_IO_PROTOCOL_REVISION2, // Revision
NULL, // Media ... NEED TO BE FILLED
NorFlashBlockIoReset, // Reset;
NorFlashBlockIoReadBlocks, // ReadBlocks
NorFlashBlockIoWriteBlocks, // WriteBlocks
NorFlashBlockIoFlushBlocks // FlushBlocks
}, // BlockIoProtocol
{
0, // MediaId ... NEED TO BE FILLED
FALSE, // RemovableMedia
TRUE, // MediaPresent
FALSE, // LogicalPartition
FALSE, // ReadOnly
FALSE, // WriteCaching;
0, // BlockSize ... NEED TO BE FILLED
4, // IoAlign
0, // LastBlock ... NEED TO BE FILLED
0, // LowestAlignedLba
1, // LogicalBlocksPerPhysicalBlock
}, // Media;
{
EFI_DISK_IO_PROTOCOL_REVISION, // Revision
NorFlashDiskIoReadDisk, // ReadDisk
NorFlashDiskIoWriteDisk // WriteDisk
},
{ {
FvbGetAttributes, // GetAttributes FvbGetAttributes, // GetAttributes
@@ -94,8 +121,11 @@ NorFlashCreateInstance (
Instance->DeviceBaseAddress = NorFlashDeviceBase; Instance->DeviceBaseAddress = NorFlashDeviceBase;
Instance->RegionBaseAddress = NorFlashRegionBase; Instance->RegionBaseAddress = NorFlashRegionBase;
Instance->Size = NorFlashSize; Instance->Size = NorFlashSize;
Instance->BlockSize = BlockSize;
Instance->LastBlock = (NorFlashSize / BlockSize) - 1; Instance->BlockIoProtocol.Media = &Instance->Media;
Instance->Media.MediaId = Index;
Instance->Media.BlockSize = BlockSize;
Instance->Media.LastBlock = (NorFlashSize / BlockSize)-1;
CopyGuid (&Instance->DevicePath.Vendor.Guid, &gEfiCallerIdGuid); CopyGuid (&Instance->DevicePath.Vendor.Guid, &gEfiCallerIdGuid);
Instance->DevicePath.Index = (UINT8)Index; Instance->DevicePath.Index = (UINT8)Index;
@@ -112,6 +142,8 @@ NorFlashCreateInstance (
&Instance->Handle, &Instance->Handle,
&gEfiDevicePathProtocolGuid, &gEfiDevicePathProtocolGuid,
&Instance->DevicePath, &Instance->DevicePath,
&gEfiBlockIoProtocolGuid,
&Instance->BlockIoProtocol,
&gEfiFirmwareVolumeBlockProtocolGuid, &gEfiFirmwareVolumeBlockProtocolGuid,
&Instance->FvbProtocol, &Instance->FvbProtocol,
NULL NULL
@@ -125,6 +157,10 @@ NorFlashCreateInstance (
&Instance->Handle, &Instance->Handle,
&gEfiDevicePathProtocolGuid, &gEfiDevicePathProtocolGuid,
&Instance->DevicePath, &Instance->DevicePath,
&gEfiBlockIoProtocolGuid,
&Instance->BlockIoProtocol,
&gEfiDiskIoProtocolGuid,
&Instance->DiskIoProtocol,
NULL NULL
); );
if (EFI_ERROR (Status)) { if (EFI_ERROR (Status)) {
@@ -280,9 +316,6 @@ NorFlashWriteFullBlock (
} }
EXIT: EXIT:
// Put device back into Read Array mode
SEND_NOR_COMMAND (Instance->DeviceBaseAddress, 0, P30_CMD_READ_ARRAY);
if (!EfiAtRuntime ()) { if (!EfiAtRuntime ()) {
// Interruptions can resume. // Interruptions can resume.
gBS->RestoreTPL (OriginalTPL); gBS->RestoreTPL (OriginalTPL);
@@ -304,16 +337,16 @@ NorFlashInitialise (
{ {
EFI_STATUS Status; EFI_STATUS Status;
UINT32 Index; UINT32 Index;
VIRT_NOR_FLASH_DESCRIPTION *NorFlashDevices; NOR_FLASH_DESCRIPTION *NorFlashDevices;
BOOLEAN ContainVariableStorage; BOOLEAN ContainVariableStorage;
Status = VirtNorFlashPlatformInitialization (); Status = NorFlashPlatformInitialization ();
if (EFI_ERROR (Status)) { if (EFI_ERROR (Status)) {
DEBUG ((DEBUG_ERROR, "NorFlashInitialise: Fail to initialize Nor Flash devices\n")); DEBUG ((DEBUG_ERROR, "NorFlashInitialise: Fail to initialize Nor Flash devices\n"));
return Status; return Status;
} }
Status = VirtNorFlashPlatformGetDevices (&NorFlashDevices, &mNorFlashDeviceCount); Status = NorFlashPlatformGetDevices (&NorFlashDevices, &mNorFlashDeviceCount);
if (EFI_ERROR (Status)) { if (EFI_ERROR (Status)) {
DEBUG ((DEBUG_ERROR, "NorFlashInitialise: Fail to get Nor Flash devices\n")); DEBUG ((DEBUG_ERROR, "NorFlashInitialise: Fail to get Nor Flash devices\n"));
return Status; return Status;
@@ -409,7 +442,7 @@ NorFlashFvbInitialize (
PcdGet64 (PcdFlashNvStorageVariableBase64) : PcdGet32 (PcdFlashNvStorageVariableBase); PcdGet64 (PcdFlashNvStorageVariableBase64) : PcdGet32 (PcdFlashNvStorageVariableBase);
// Set the index of the first LBA for the FVB // Set the index of the first LBA for the FVB
Instance->StartLba = (mFlashNvStorageVariableBase - Instance->RegionBaseAddress) / Instance->BlockSize; Instance->StartLba = (mFlashNvStorageVariableBase - Instance->RegionBaseAddress) / Instance->Media.BlockSize;
BootMode = GetBootModeHob (); BootMode = GetBootModeHob ();
if (BootMode == BOOT_WITH_DEFAULT_SETTINGS) { if (BootMode == BOOT_WITH_DEFAULT_SETTINGS) {
@@ -422,15 +455,15 @@ NorFlashFvbInitialize (
// Install the Default FVB header if required // Install the Default FVB header if required
if (EFI_ERROR (Status)) { if (EFI_ERROR (Status)) {
// There is no valid header, so time to install one. // There is no valid header, so time to install one.
DEBUG ((DEBUG_INFO, "%a: The FVB Header is not valid.\n", __func__)); DEBUG ((DEBUG_INFO, "%a: The FVB Header is not valid.\n", __FUNCTION__));
DEBUG (( DEBUG ((
DEBUG_INFO, DEBUG_INFO,
"%a: Installing a correct one for this volume.\n", "%a: Installing a correct one for this volume.\n",
__func__ __FUNCTION__
)); ));
// Erase all the NorFlash that is reserved for variable storage // Erase all the NorFlash that is reserved for variable storage
FvbNumLba = (PcdGet32 (PcdFlashNvStorageVariableSize) + PcdGet32 (PcdFlashNvStorageFtwWorkingSize) + PcdGet32 (PcdFlashNvStorageFtwSpareSize)) / Instance->BlockSize; FvbNumLba = (PcdGet32 (PcdFlashNvStorageVariableSize) + PcdGet32 (PcdFlashNvStorageFtwWorkingSize) + PcdGet32 (PcdFlashNvStorageFtwSpareSize)) / Instance->Media.BlockSize;
Status = FvbEraseBlocks (&Instance->FvbProtocol, (EFI_LBA)0, FvbNumLba, EFI_LBA_LIST_TERMINATOR); Status = FvbEraseBlocks (&Instance->FvbProtocol, (EFI_LBA)0, FvbNumLba, EFI_LBA_LIST_TERMINATOR);
if (EFI_ERROR (Status)) { if (EFI_ERROR (Status)) {

Some files were not shown because too many files have changed in this diff Show More