1 2Realm Management Extension (RME) 3==================================== 4 5FEAT_RME (or RME for short) is an Armv9-A extension and is one component of the 6`Arm Confidential Compute Architecture (Arm CCA)`_. TF-A supports RME starting 7from version 2.6. This chapter discusses the changes to TF-A to support RME and 8provides instructions on how to build and run TF-A with RME. 9 10RME support in TF-A 11--------------------- 12 13The following diagram shows an Arm CCA software architecture with TF-A as the 14EL3 firmware. In the Arm CCA architecture there are two additional security 15states and address spaces: ``Root`` and ``Realm``. TF-A firmware runs in the 16Root world. In the realm world, a Realm Management Monitor firmware (`RMM`_) 17manages the execution of Realm VMs and their interaction with the hypervisor. 18 19.. image:: ../resources/diagrams/arm-cca-software-arch.png 20 21RME is the hardware extension to support Arm CCA. To support RME, various 22changes have been introduced to TF-A. We discuss those changes below. 23 24Changes to translation tables library 25*************************************** 26RME adds Root and Realm Physical address spaces. To support this, two new 27memory type macros, ``MT_ROOT`` and ``MT_REALM``, have been added to the 28:ref:`Translation (XLAT) Tables Library`. These macros are used to configure 29memory regions as Root or Realm respectively. 30 31.. note:: 32 33 Only version 2 of the translation tables library supports the new memory 34 types. 35 36Changes to context management 37******************************* 38A new CPU context for the Realm world has been added. The existing can be used 39to manage Realm context. 40 41Boot flow changes 42******************* 43In a typical TF-A boot flow, BL2 runs at Secure-EL1. However when RME is 44enabled, TF-A runs in the Root world at EL3. Therefore, the boot flow is 45modified to run BL2 at EL3 when RME is enabled. In addition to this, a 46Realm-world firmware (`RMM`_) is loaded by BL2 in the Realm physical address 47space. 48 49The boot flow when RME is enabled looks like the following: 50 511. BL1 loads and executes BL2 at EL3 522. BL2 loads images including RMM 533. BL2 transfers control to BL31 544. BL31 initializes SPM (if SPM is enabled) 555. BL31 initializes RMM 566. BL31 transfers control to Normal-world software 57 58Granule Protection Tables (GPT) library 59***************************************** 60Isolation between the four physical address spaces is enforced by a process 61called Granule Protection Check (GPC) performed by the MMU downstream any 62address translation. GPC makes use of Granule Protection Table (GPT) in the 63Root world that describes the physical address space assignment of every 64page (granule). A GPT library that provides APIs to initialize GPTs and to 65transition granules between different physical address spaces has been added. 66More information about the GPT library can be found in the 67:ref:`Granule Protection Tables Library` chapter. 68 69RMM Dispatcher (RMMD) 70************************ 71RMMD is a new standard runtime service that handles the switch to the Realm 72world. It initializes the `RMM`_ and handles Realm Management Interface (RMI) 73SMC calls from Non-secure. 74 75There is a contract between `RMM`_ and RMMD that defines the arguments that the 76former needs to take in order to initialize and also the possible return values. 77This contract is defined in the `RMM`_ Boot Interface, which can be found at 78:ref:`rmm_el3_boot_interface`. 79 80There is also a specification of the runtime services provided by TF-A 81to `RMM`_. This can be found at :ref:`runtime_services_and_interface`. 82 83Test Realm Payload (TRP) 84************************* 85TRP is a small test payload that runs at R-EL2 and implements a subset of 86the Realm Management Interface (RMI) commands to primarily test EL3 firmware 87and the interface between R-EL2 and EL3. When building TF-A with RME enabled, 88if the path to an RMM image is not provided, TF-A builds the TRP by default 89and uses it as the R-EL2 payload. 90 91Building and running TF-A with RME 92---------------------------------- 93 94This section describes how you can build and run TF-A with RME enabled. 95We assume you have read the :ref:`Prerequisites` to build TF-A. 96 97The following instructions show you how to build and run TF-A with RME 98on FVP for two scenarios: 99 100- Three-world execution: This is the configuration to use if Secure 101 world functionality is not needed. TF-A is tested with the following 102 software entities in each world as listed below: 103 104 - NS Host (RME capable Linux or TF-A Tests), 105 - Root (TF-A) 106 - R-EL2 (`RMM`_ or TRP) 107 108- Four-world execution: This is the configuration to use if both Secure 109 and Realm world functionality is needed. TF-A is tested with the following 110 software entities in each world as listed below: 111 112 - NS Host (RME capable Linux or TF-A Tests), 113 - Root (TF-A) 114 - R-EL2 (`RMM`_ or TRP) 115 - S-EL2 (Hafnium SPM) 116 117To run the tests, you need an FVP model. Please use the :ref:`latest version 118<Arm Fixed Virtual Platforms (FVP)>` of *FVP_Base_RevC-2xAEMvA* model. If NS 119Host is Linux, then the below instructions assume that a suitable RME enabled 120kernel image and associated root filesystem are available. 121 122Three-world execution 123********************* 124 125**1. Clone and build RMM Image** 126 127Please refer to the `RMM Getting Started`_ on how to setup 128Host Environment and build `RMM`_. The build commands assume that 129an AArch64 toolchain and CMake executable are available in the 130shell PATH variable and CROSS_COMPILE variable has been setup 131appropriately. 132 133To clone `RMM`_ and build using the default build options for FVP: 134 135.. code:: shell 136 137 git clone --recursive https://git.trustedfirmware.org/TF-RMM/tf-rmm.git 138 cd tf-rmm 139 cmake -DRMM_CONFIG=fvp_defcfg -S . -B build 140 cmake --build build 141 142This will generate **rmm.img** in **build/Release** folder. 143 144**2. Clone and build TF-A Tests with Realm Payload** 145 146This step is only needed if NS Host is TF-A Tests. The full set 147of instructions to setup build host and build options for 148TF-A-Tests can be found in the `TFTF Getting Started`_. TF-A Tests 149can test Realm world with either `RMM`_ or TRP in R-EL2. In the TRP case, 150some tests which are not applicable will be skipped. 151 152Use the following instructions to build TF-A with `TF-A Tests`_ as the 153non-secure payload (BL33). 154 155.. code:: shell 156 157 git clone https://git.trustedfirmware.org/TF-A/tf-a-tests.git 158 cd tf-a-tests 159 make CROSS_COMPILE=aarch64-none-elf- PLAT=fvp DEBUG=1 ENABLE_REALM_PAYLOAD_TESTS=1 all 160 161This produces a TF-A Tests binary (**tftf.bin**) with Realm payload packaged 162and **sp_layout.json** in the **build/fvp/debug** directory. 163 164 165**3. Build RME Enabled TF-A** 166 167The `TF-A Getting Started`_ has the necessary instructions to setup Host 168machine and build TF-A. 169 170To build for RME, set ``ENABLE_RME`` build option to 1 and provide the path to 171the `RMM`_ binary ``rmm.img`` using ``RMM`` build option. 172 173.. note:: 174 175 ENABLE_RME build option is currently experimental. 176 177.. note:: 178 179 If the ``RMM`` option is not specified, TF-A builds the TRP to load and 180 run at R-EL2. 181 182.. code:: shell 183 184 git clone https://git.trustedfirmware.org/TF-A/trusted-firmware-a.git 185 cd trusted-firmware-a 186 make CROSS_COMPILE=aarch64-none-elf- \ 187 PLAT=fvp \ 188 ENABLE_RME=1 \ 189 RMM=<path/to/rmm.img> \ 190 FVP_HW_CONFIG_DTS=fdts/fvp-base-gicv3-psci-1t.dts \ 191 DEBUG=1 \ 192 BL33=<path/to/bl33> \ 193 all fip 194 195``BL33`` can point to a Non Secure Bootloader like UEFI/U-Boot or 196the TF-A Tests binary(**tftf.bin**) from the previous step. 197 198This produces **bl1.bin** and **fip.bin** binaries in the **build/fvp/debug** 199directory. 200 201TF-A can also directly boot Linux kernel on the FVP. The kernel needs to be 202`preloaded` to a suitable memory location and this needs to be specified via 203``PRELOADED_BL33_BASE`` build option. Also TF-A should implement the Linux 204kernel register conventions for boot and this can be set using the 205``ARM_LINUX_KERNEL_AS_BL33`` option. 206 207.. code-block:: shell 208 209 cd trusted-firmware-a 210 make CROSS_COMPILE=aarch64-none-elf- \ 211 PLAT=fvp \ 212 ENABLE_RME=1 \ 213 RMM=<path/to/rmm.img> \ 214 FVP_HW_CONFIG_DTS=fdts/fvp-base-gicv3-psci-1t.dts \ 215 DEBUG=1 \ 216 ARM_LINUX_KERNEL_AS_BL33=1 \ 217 PRELOADED_BL33_BASE=0x84000000 \ 218 all fip 219 220The above command assumes that the Linux kernel will be placed in FVP 221memory at 0x84000000 via suitable FVP option (see the next step). 222 223.. _fvp_3_world_cmd: 224 225**4. Running FVP for 3 world setup** 226 227Use the following command to run the tests on FVP. 228 229.. code:: shell 230 231 FVP_Base_RevC-2xAEMvA \ 232 -C bp.refcounter.non_arch_start_at_default=1 \ 233 -C bp.secureflashloader.fname=<path/to/bl1.bin> \ 234 -C bp.flashloader0.fname=<path/to/fip.bin> \ 235 -C bp.refcounter.use_real_time=0 \ 236 -C bp.ve_sysregs.exit_on_shutdown=1 \ 237 -C cache_state_modelled=1 \ 238 -C bp.dram_size=4 \ 239 -C bp.secure_memory=0 \ 240 -C pci.pci_smmuv3.mmu.SMMU_ROOT_IDR0=3 \ 241 -C pci.pci_smmuv3.mmu.SMMU_ROOT_IIDR=0x43B \ 242 -C pci.pci_smmuv3.mmu.root_register_page_offset=0x20000 \ 243 -C cluster0.NUM_CORES=4 \ 244 -C cluster0.PA_SIZE=48 \ 245 -C cluster0.ecv_support_level=2 \ 246 -C cluster0.gicv3.cpuintf-mmap-access-level=2 \ 247 -C cluster0.gicv3.without-DS-support=1 \ 248 -C cluster0.gicv4.mask-virtual-interrupt=1 \ 249 -C cluster0.has_arm_v8-6=1 \ 250 -C cluster0.has_amu=1 \ 251 -C cluster0.has_branch_target_exception=1 \ 252 -C cluster0.rme_support_level=2 \ 253 -C cluster0.has_rndr=1 \ 254 -C cluster0.has_v8_7_pmu_extension=2 \ 255 -C cluster0.max_32bit_el=-1 \ 256 -C cluster0.stage12_tlb_size=1024 \ 257 -C cluster0.check_memory_attributes=0 \ 258 -C cluster0.ish_is_osh=1 \ 259 -C cluster0.restriction_on_speculative_execution=2 \ 260 -C cluster0.restriction_on_speculative_execution_aarch32=2 \ 261 -C cluster1.NUM_CORES=4 \ 262 -C cluster1.PA_SIZE=48 \ 263 -C cluster1.ecv_support_level=2 \ 264 -C cluster1.gicv3.cpuintf-mmap-access-level=2 \ 265 -C cluster1.gicv3.without-DS-support=1 \ 266 -C cluster1.gicv4.mask-virtual-interrupt=1 \ 267 -C cluster1.has_arm_v8-6=1 \ 268 -C cluster1.has_amu=1 \ 269 -C cluster1.has_branch_target_exception=1 \ 270 -C cluster1.rme_support_level=2 \ 271 -C cluster1.has_rndr=1 \ 272 -C cluster1.has_v8_7_pmu_extension=2 \ 273 -C cluster1.max_32bit_el=-1 \ 274 -C cluster1.stage12_tlb_size=1024 \ 275 -C cluster1.check_memory_attributes=0 \ 276 -C cluster1.ish_is_osh=1 \ 277 -C cluster1.restriction_on_speculative_execution=2 \ 278 -C cluster1.restriction_on_speculative_execution_aarch32=2 \ 279 -C pctl.startup=0.0.0.0 \ 280 -C bp.smsc_91c111.enabled=1 \ 281 -C bp.hostbridge.userNetworking=1 \ 282 -C bp.virtioblockdevice.image_path=<path/to/rootfs.ext4> 283 284The ``bp.virtioblockdevice.image_path`` option presents the rootfs as a 285virtio block device to Linux kernel. It can be ignored if NS Host is 286TF-A-Tests or rootfs is accessed by some other mechanism. 287 288If TF-A was built to expect a preloaded Linux kernel, then use the following 289FVP argument to load the kernel image at the expected address. 290 291.. code-block:: shell 292 293 --data cluster0.cpu0=<path_to_kernel_Image>@0x84000000 \ 294 295 296.. tip:: 297 Tips to boot and run Linux faster on the FVP : 298 1. Set the FVP option ``cache_state_modelled`` to 0. 299 2. Disable the CPU Idle driver in Linux either by setting the kernel command line 300 parameter "cpuidle.off=1" or by disabling the ``CONFIG_CPU_IDLE`` kernel config. 301 302If the NS Host is TF-A-Tests, then the default test suite in TFTF 303will execute on the FVP and this includes Realm world tests. The 304tail of the output from *uart0* should look something like the following. 305 306.. code-block:: shell 307 308 ... 309 310 > Test suite 'FF-A Interrupt' 311 Passed 312 > Test suite 'SMMUv3 tests' 313 Passed 314 > Test suite 'PMU Leakage' 315 Passed 316 > Test suite 'DebugFS' 317 Passed 318 > Test suite 'RMI and SPM tests' 319 Passed 320 > Test suite 'Realm payload at EL1' 321 Passed 322 > Test suite 'Invalid memory access' 323 Passed 324 ... 325 326Four-world execution 327******************** 328 329Four-world execution involves software components in each security state: root, 330secure, realm and non-secure. This section describes how to build TF-A 331with four-world support. 332 333We use TF-A as the root firmware, `Hafnium SPM`_ is the reference Secure world 334component running at S-EL2. `RMM`_ can be built as described in previous 335section. The examples below assume TF-A-Tests as the NS Host and utilize SPs 336from TF-A-Tests. 337 338**1. Obtain and build Hafnium SPM** 339 340.. code:: shell 341 342 git clone --recurse-submodules https://git.trustedfirmware.org/hafnium/hafnium.git 343 cd hafnium 344 # Use the default prebuilt LLVM/clang toolchain 345 PATH=$PWD/prebuilts/linux-x64/clang/bin:$PWD/prebuilts/linux-x64/dtc:$PATH 346 347Feature MTE needs to be disabled in Hafnium build, apply following patch to 348project/reference submodule 349 350.. code:: diff 351 352 diff --git a/BUILD.gn b/BUILD.gn 353 index cc6a78f..234b20a 100644 354 --- a/BUILD.gn 355 +++ b/BUILD.gn 356 @@ -83,7 +83,6 @@ aarch64_toolchains("secure_aem_v8a_fvp") { 357 pl011_base_address = "0x1c090000" 358 smmu_base_address = "0x2b400000" 359 smmu_memory_size = "0x100000" 360 - enable_mte = "1" 361 plat_log_level = "LOG_LEVEL_INFO" 362 } 363 } 364 365.. code:: shell 366 367 make PROJECT=reference 368 369The Hafnium binary should be located at 370*out/reference/secure_aem_v8a_fvp_clang/hafnium.bin* 371 372**2. Build RME enabled TF-A with SPM** 373 374Build TF-A with RME as well as SPM enabled. 375 376Use the ``sp_layout.json`` previously generated in TF-A Tests 377build to run SP tests. 378 379.. code:: shell 380 381 make CROSS_COMPILE=aarch64-none-elf- \ 382 PLAT=fvp \ 383 ENABLE_RME=1 \ 384 FVP_HW_CONFIG_DTS=fdts/fvp-base-gicv3-psci-1t.dts \ 385 SPD=spmd \ 386 BRANCH_PROTECTION=1 \ 387 CTX_INCLUDE_PAUTH_REGS=1 \ 388 DEBUG=1 \ 389 SP_LAYOUT_FILE=<path/to/sp_layout.json> \ 390 BL32=<path/to/hafnium.bin> \ 391 BL33=<path/to/tftf.bin> \ 392 RMM=<path/to/rmm.img> \ 393 all fip 394 395**3. Running the FVP for a 4 world setup** 396 397Use the following arguments in addition to the FVP options mentioned in 398:ref:`4. Running FVP for 3 world setup <fvp_3_world_cmd>` to run tests for 3994 world setup. 400 401.. code:: shell 402 403 -C pci.pci_smmuv3.mmu.SMMU_AIDR=2 \ 404 -C pci.pci_smmuv3.mmu.SMMU_IDR0=0x0046123B \ 405 -C pci.pci_smmuv3.mmu.SMMU_IDR1=0x00600002 \ 406 -C pci.pci_smmuv3.mmu.SMMU_IDR3=0x1714 \ 407 -C pci.pci_smmuv3.mmu.SMMU_IDR5=0xFFFF0475 \ 408 -C pci.pci_smmuv3.mmu.SMMU_S_IDR1=0xA0000002 \ 409 -C pci.pci_smmuv3.mmu.SMMU_S_IDR2=0 \ 410 -C pci.pci_smmuv3.mmu.SMMU_S_IDR3=0 411 412.. _Arm Confidential Compute Architecture (Arm CCA): https://www.arm.com/why-arm/architecture/security-features/arm-confidential-compute-architecture 413.. _Arm Architecture Models website: https://developer.arm.com/tools-and-software/simulation-models/fixed-virtual-platforms/arm-ecosystem-models 414.. _TF-A Getting Started: https://trustedfirmware-a.readthedocs.io/en/latest/getting_started/index.html 415.. _TF-A Tests: https://trustedfirmware-a-tests.readthedocs.io/en/latest 416.. _TFTF Getting Started: https://trustedfirmware-a-tests.readthedocs.io/en/latest/getting_started/index.html 417.. _Hafnium SPM: https://www.trustedfirmware.org/projects/hafnium 418.. _RMM Getting Started: https://tf-rmm.readthedocs.io/en/latest/getting_started/index.html 419.. _RMM: https://www.trustedfirmware.org/projects/tf-rmm/ 420