diff --git a/building/devices/versal.rst b/building/devices/versal.rst index bcee3b0..d9b3c57 100644 --- a/building/devices/versal.rst +++ b/building/devices/versal.rst @@ -1,167 +1,868 @@ .. _versal: -############################# -AMD-Xilinx Versal ACAP VCK190 -############################# -Instructions below show how to run OP-TEE on the `VCK190`_ development board. -Details of the Versal ACAP can be found in the Versal Technical Reference Manual -(`Versal_TRM`_). - -Supported boards +############################################ +AMD-Xilinx Versal ACAP and Versal NET boards +############################################ + +Instructions below show how to run OP-TEE on Versal ACAP and Versal NET +boards. Explicitly tested and mentioned are the `VCK190`_ **Versal ACAP +development board**, and the **VNX B2197 Versal NET board**. + +Details on Versal ACAP devices can be found in the *Versal Adaptive SoC +Technical Reference Manual* (`AM011`_). For Versal NET devices it is the *Versal +NET Technical Reference Manual* (AM021, NDA required). + + +Supported PLM Firmware +********************** + +On any Versal device almost all security hardware is to be accessed indirectly +via the Platform Management Controller (PMC) and its PLM Firmware and **not** in +a direct, memory-mapped fashion. Thus **this OP-TEE port heavily depends on the +interface to PLM Firmware, which can be changed by AMD-Xilinx from release to +release in incompatible ways**. + +**The Versal OP-TEE port is currently based on AMD-Xilinx PLM Firmware release +2024.2, only.** + +Another important dependency in terms of interfaces is the ARM Trusted Firmware, +which is changing its interface far less often than the PLM Firmware interface +is changed. **This port is based AMD-Xilinx release 2024.2, which is based on +ARM Trusted Firmware 2.10.0.** + + +Supported Boards **************** -This makefile supports the VCK190 but also supports the `VMK180`_ development -board as well. -Setting up the toolchain +This port of OP-TEE should be applicable to all other boards based on Versal +ACAP (like `VMK180`_) or Versal NET. In most cases, regarding OP-TEE OS, the +main difference lies in selecting the right PS UART peripheral(s) out of two +available ones for console output. All other hardware peripherals used by this +port are integral components of the respective devices. + + +Prerequisites +************* + +The user is required to provide a *Board Support Package* (BSP) as an input to +the OP-TEE build system. Such a BSP in context of this OP-TEE port comprises at +least: + +1. a Programmable Device Image (PDI, ``.pdi`` file): settings, low level + firmware(s) and other startup files for various components, next to a + *bitstream* for the Programmable Logic (PL) of Versal devices; **and** + +2. a matching Device Tree Blob (DTB, ``.dtb`` file) for U-Boot and Linux. + +Depending on Versal ACAP or NET, such a BSP may come in two major forms: + +a. For Versal ACAP boards + + Usually a Versal ACAP board comes with a AMD-Xilinx PetaLinux BSP (or, + alternatively, a fully built PetaLinux project). See `Downloads`_, section + *Versal Adaptive SoC Board Support Packages*. For example file + ``xilinx-vck190-v2024.2-11110212.bsp`` for the `VCK190`_ board. + + To use (extract) such a PetaLinux BSP, download PetaLinux (also + `Downloads`_, section *PetaLinux Tools - Installer*) and `install`_ it. + + .. note:: + + You will need a free AMD-Xilinx account to proceed with the two previous + steps. + +b. For Versal NET boards + + A Versal NET board typically comes with a subset of such a PetaLinux BSP: a + set of two files, as mentioned above. These are available upon request from + your AMD-Xilinx FAE: + + - ``versal-net-bsp`` folder with: + + - ``design.pdi`` + + Bootable PDI as produced by AMD-Xilinx toolchain; suitable for + operating all security hardware, especially the PKI Accelerator. + + - ``design.dtb`` + + DTB for U-Boot and Linux; especially for selecting the correct UART + and reserving space for OP-TEE memory through ``reserved-memory`` + nodes. + + +Configuring and building ************************ -This build chain relies on Petalinux 2022.1, therefore the first step will be to -download and `install`_ it from the AMD-Xilinx website (`Downloads`_). -Then, you will also need to download the board support package (BSP) from the -AMD-Xilinx website (`Downloads`_). It contains prebuilt firmwares and hardware -definition files required to assemble a bootable image. +Fetching source code +==================== -.. note:: - You will need a free AMD-Xilinx account to proceed with the two previous - steps. +a. For Versal boards: -Configuring and building for VCK190 -*********************************** -Lets summarize the steps taken so far; these are common to all boards. +.. code-block:: console -.. code-block:: bash + $ mkdir optee-project + $ cd optee-project/ + $ repo init -u https://github.com/OP-TEE/manifest.git -m versal.xml + $ repo sync -j4 --no-clone-bundle + +b. For Versal NET boards: + +.. code-block:: console + + $ mkdir optee-project + $ cd optee-project/ + $ repo init -u https://github.com/OP-TEE/manifest.git -m versal_net.xml + $ repo sync -j4 --no-clone-bundle + +This shall have created a new working directory ``optee-project/`` with all the +repositories required with the exception of a directory for a BSP. + +Adding BSP +========== + +The BSP can be provided in one of two major forms: + +a. A PetaLinux BSP (``.bsp``) file (or an existing, fully built PetaLinux + project directory). + + .. note:: + + This form of providing the BSP is common for Versal ACAP boards and + rather uncommon for Versal NET boards. + + A prerequisite for unpacking a BSP file (or building a PetaLinux project) is + `install`_ ing PetaLinux as previously mentioned. + + To unpack a PetaLinux BSP file: + + .. code-block:: bash + + $ cd optee-project/ + $ bash + $ source /settings.sh + $ petalinux-create project -s + $ exit + + The ``petalinux-create`` command shall have created a new directory in + ``optee-project/``, for example called ``xilinx-vck190-2024.2`` when using + the BSP file ``xilinx-vck190-v2024.2-11110212.bsp``. + + To make the build system pick up this BSP directory automatically, it shall + be renamed to simply ``versal-bsp``: + + .. code-block:: bash + + $ cd optee-project/ + $ mv -iv xilinx-vck190-2024.2 versal-bsp + +b. A set of two files - a Bootable PDI file, as produced by AMD-Xilinx + toolchain and an appropriate DTB file to be used with U-Boot and Linux. + + To make the build system pick up these two files automatically place them in + a new directory called ``versal-net-bsp`` with names ``design.pdi`` and + ``design.dtb``: + + .. code-block:: bash - $ mkdir ~/optee-project - $ cd ~/optee-project - $ repo init -u https://github.com/OP-TEE/manifest.git -m versal.xml - $ repo sync -j4 --no-clone-bundle - $ cd build - $ make -j8 toolchains - $ make -j8 + $ cd optee-project/ + $ mkdir versal-net-bsp + $ mv -iv versal-net-bsp/design.pdi + $ mv -iv versal-net-bsp/design.dtb -At this point we have a working directory ``~/optee-project`` with all the -repositories required with the exception of the Versal ACAP board support -package. A pre-requisite to unpacking the BSP file is installing Petalinux -(`install`_) as previously mentioned. + .. note:: -Having done that, now is the time to unpack the BSP: + This form of providing the BSP is especially common for Versal NET + boards. Of course it may also be used for Versal ACAP boards. + +Preparing toolchains +==================== .. code-block:: bash - $ cd ~/optee-project - $ cp ~/Downloads/xilinx-vck190-v2022.1-04191534.bsp . - $ source /path/to/petalinux.2022.1/settings.sh - $ petalinux-create --type project -s xilinx-vck190-v2022.1-04191534.bsp - $ ls - xilinx-vck190-2022.1 + $ cd optee-project/build/ + $ make -j8 toolchains + +This shall have created a ``toolchains`` directory within the ``optee-project/`` +working directory with all the required ARM cross-compile toolchain executables. -In order for the Versal OP-TEE port to work correctly, the PLM needs to be -updated to add the XilNvm and XilPuf libraries. This can be accomplished by the -following steps within the PetaLinux workspace created above: +Building the bootimage +====================== + +To build a bootable image, execute the following commands: .. code-block:: bash - $ mkdir project-spec/meta-user/recipes-bsp/embeddedsw - $ cp ~/optee-project/build/versal/plm-firmware_%.bbappend project-spec/meta-user/recipes-bsp/embeddedsw - $ petalinux-build -c plm + $ cd optee-project/build/ + $ make -j8 bootimage -The newly created PLM will be located in the folder ``images/linux/plm.elf``. +This will build ARM Trusted Firmware and OP-TEE with output on PS UART0 by +default. See the next section *Build options* for further settings. .. note:: - Replace the VCK190 BSP with the VMK180 BSP if you want to build this project - for the VMK180 development board. -Before building the release, you will need to edit the Boot Image File (BIF) -``build/versal/bootImage-versal-vck190.bif`` to point to the required BSP files. -The paths for the following files in the BIF will need to be updated *before* -proceeding: + Both, the `VCK190`_ and the VNX B2197 boards have at least PS UART0 + accessible. + +After ``make`` has finished a bootable image shall be available at +``optee-project/build/versal/BOOT.BIN``. This bootable image comprises all +components, including the Linux kernel and a minimal root filesystem (as +initramfs) with OP-TEE Linux userspace tools like ``xtest``. + + +Build options +============= + +The ``versal.mk`` Makefile in ``optee-project/build/`` accepts the following +build options in the form of environment variables or command line ``make`` +variable assignments: -- vpl_gen_fixed.pdi -- plm.elf -- psmfw.elf +#. ``VERSAL_UART1=y`` + + To build ARM Trusted Firmware and OP-TEE for output on PS UART1 instead of + UART0 set ``VERSAL_UART1=y`` as shown below. + + .. code-block:: bash + + $ cd optee-project/build/ + $ make -j8 VERSAL_UART1=y bootimage .. note:: - The default PLM **only** contains the xilsecure library. If you would like to - take advantage of all of hardware cryptographic features implemented for - Versal, you **must** enable the xilpuf and xilnvm libraries by following the - steps above for customizing the PLM (`PLM_Customization`_). -The xilpuf library enables support of the physically unclonable function (PUF) -and the xilnvm library enables support of reading and writing to eFUSEs. Once -these libraries are enabled, be sure to point to the updated PLM firmware in the -previously mentioned BIF file. + The UART chosen by setting or not setting ``VERSAL_UART1`` to ``y`` is + called the *primary* UART in this document. -After you have done that you can build the images as follows: +#. ``VERSAL_UART2ND_OPTEE=y`` -.. code-block:: bash + Since the Processing System (PS) of Versal devices comes with 2 UART + instances, there may be the possibility for a *secondary* accessible + UART. Obviously this depends on the board the Versal device resides on - + whether both UARTs are physically accessible or not. - $ cd ~/optee-project - $ cd build - $ make -f versal.mk image - $ ls versal | grep -E 'BIN|ub' - BOOT.BIN - versal-vck190.ub + *secondary* UART means PS UART1 if ``VERSAL_UART1`` is unset (or ``n``) and + PS UART0 if ``VERSAL_UART1=y``. + To exclusively use the *secondary* UART for OP-TEE OS output use + ``VERSAL_UART2ND_OPTEE=y``. -JTAG boot to U-Boot shell -************************* -To run the bootable image ``BOOT.BIN`` via JTAG, configure the boot switches as -seen below and then power up the board. -.. figure:: /images/boards/vck190-jtag-boot.png - :width: 400 - :align: center +#. ``BSP_PATH=`` -Then run the boot_jtag.sh script. + The path to an extracted PetaLinux BSP file (or a fully built PetaLinux + project) to take the various boot files from can be specified with + ``BSP_PATH``. The Makefile looks for the following components as they are + the usual build results of PetaLinux: -This script will first ask for the path of the Petalinux installation; once -entered, it will download and execute the image on the Versal ACAP platform. + - Bootable PDI (``project-spec/hw-description/*.pdi``) -.. code-block:: bash + - PLM Firmware executable + (``{images/linux,pre-built/linux/images}/plm.elf``) - $ cd ~/optee-project/build/versal/ - $ ./boot_jtag.sh + - PSM Firmware executable + (``{images/linux,pre-built/linux/images}/psmfw.elf``) + - DTB (``{images/linux,pre-built/linux/images}/system.dtb``) + Setting ``BSP_PATH`` is the typical use case when the BSP is ***not** + placed in in directory ``optee-project/versal-bsp/`` for Versal ACAP and + ``optee-project/versal-net-bsp/`` for Versal NET respectively. -SD card creation and boot -************************* -Prepare a SD card with a single **bootable** partition large enough to hold both -of the built files. +#. ``PDI_PATH=``, ``DTB_PATH=`` -Using ``gparted`` or any other partition manager tool create a single partition -on the card (remember to flag it as bootable) + Instead of being searched for via ``BSP_PATH`` the required Bootable PDI + file and DTB can be specified directly using ``PDI_PATH`` and ``DTB_PATH``. - * 1GB FAT32 bootable partition (i.e: ``/dev/sdc1``). + Setting ``PDI_PATH`` and ``DTB_PATH`` is the typical use case when there no + PetaLinux BSP (or fully built PetaLinux project) available. -Once SD card is partitioned, mount it on your file system and copy the images: + If neither ``BSP_PATH``, nor ``PDI_PATH`` and/or ``DTB_PATH`` are specified, + the build system looks for files called ``design.pdi`` and/or ``design.dtb`` + in directory ``optee-project/versal-bsp/`` for Versal ACAP and + ``optee-project/versal-net-bsp/`` for Versal NET. -.. code-block:: bash +#. ``PLM_PATH=``, ``PSM_PATH=`` + + .. warning:: + + Do **not** execute the ``make`` command from within an active Vitis or + PetaLinux environment! If needed (see below) determine the absolute path + to the Microblaze GCC executable and use that path as-is for setting + ``CROSS_COMPILE_FIRMWARE``. + + Usually the new bootable image is built either ... + + 1. reusing the PLM and PSM Firmware executables included in the given PDI + file (as produced by Vitis toolchain), or + + 2. using the ones produced by PetaLinux, if a PetaLinux BSP is available. + + Instead the Makefile allows the user to either ... + + a. point to preexisting PLM and/or PSM Firmware ELF files using + ``PLM_PATH`` and/or ``PSM_PATH``. There is no need to set + ``CROSS_COMPILE_FIRMWARE`` in this case, or + + b. let the build system generate new, custom PLM and/or PSM Firmware ELF + files from scratch using the clone of AMD-Xilinx `embeddedsw`_ + repository and its `Building from Git`_ flow. + + This can be necessary to have all desirable security features enabled, + since the default PLM Firmware as generated by Vitis or PetaLinux + toolchain usually lack the following features (see `xparameters.h`_): + + #. Inclusion of modules `XilNVM`_ and `XilPUF`_ (remove + ``PLM_{NVM,PUF}_EXCLUDE``) + + #. NIST Curves P256 and P521 (add + ``XSECURE_ECC_SUPPORT_NIST_{P256,P521}``) + + #. Versal ACAP: Save code size due to limited PMC RAM by disabling boot + from QSPI and OSPI (add ``PLM_{QSPI,OSPI}_EXCLUDE``), and debug + prints (replace ``PLM_DEBUG`` by ``PLM_PRINT``). + + Set variables ``PLM_PATH=generate`` and/or ``PSM_PATH=generate``, and + set variable ``CROSS_COMPILE_FIRMWARE`` to the path of the Microblaze + GCC compiler executable. In the installation of Vitis, + compiler can usually be found in: + + ``$XILINX_VIVADO/gnu/microblaze/lin/bin/mb-gcc`` + + In the installation of PetaLinux, it can usually be found in: + + ``$PETALINX/components/xsct/gnu/microblaze/lin/bin/mb-gcc`` + + .. note:: + + Just like ARM Trusted Firmware, when built from scratch, PLM and PSM + Firmware are configured to output on the *primary* UART (PS UART0 if + ``VERSAL_UART1`` is unset or ``n`` and to output on PS UART1 if + ``VERSAL_UART1=y``). + + +#. ``IUB_BIF_PATH=n`` + + By default the bootable image (``optee-project/build/versal/BOOT.BIN``) + comprises all components, including a U-Boot FIT image + (i.e. ``optee-project/build/versal/versal-vck190.ub``), which + comprises the Linux kernel binary, the root filesystem (initramfs) image and + various DTBs for Linux. At the same time the default "boot + command" built into U-Boot is modified to explicitly load this U-Boot FIT + Image. + + By setting ``IUB_BIF_PATH=n`` the generated U-Boot FIT Image is **not** + included in the bootable image. Furthermore if ``IUB_BIF_PATH=n`` the + default "boot command" built into U-Boot is **not** modified anymore. + + Not including the U-Boot FIT Image makes the bootable image significantly + smaller, of course, which can be beneficial when there are other means than + (slow) JTAG to load it. + + .. note:: + + As a consequence, after having loaded such a reduced bootable image, for + example via JTAG, it is up to the user to also load the U-Boot FIT image + into memory and operate the U-Boot console to run it. + + Loading the U-Boot FIT Image into memory separately may be done from an + SD card or via network (TFTP) for example. + + +Booting the image +***************** + +.. note:: + + The instructions in this part assume that build option ``IUB_BIF_PATH=n`` + has **not** been set. + +JTAG Boot to Linux +================== + +.. note:: + + The commands in this section are supposed to be executed within an active + Vitis or PetaLinux environment with appropriate environment variables set to + locate ``xsdb`` (e.g ``$PATH`` in case of Vitis and ``$PETALINUX`` in case + of PetaLinux). PetaLinux can be downloaded and `install`_ ed from the + AMD-Xilinx website (`Downloads`_). + + The user that runs these executables must have the correct UNIX access + rights to open the underlying USB device node(s) related to UART and JTAG + towards the board. Regarding UART devices most of the time adding said user + to the ``dialout`` UNIX group is enough on Ubuntu/Debian-based + systems. Regarding the JTAG server ``hw_server`` the Vitis installer usually + guides the user to install appropriate udev rules. - $ cp ~/optee-project/build/versal/BOOT.BIN / - $ cp ~/optee-project/build/versal/versal-vck190.ub / - $ sync - $ umount +1. To load and execute the bootable image ``BOOT.BIN`` via JTAG, configure + Versal boot mode switches for JTAG and then power up the board. -Now you can use the newly created SD card to boot your board. Make sure the boot -switches are configured for SD boot. + In case of the `VCK190`_ board see the figure below. The boot mode switches + are marked in red on the right hand side (zoom in!): -.. figure:: /images/boards/vck190-sd-boot.png + .. figure:: /images/boards/vck190-jtag-boot.png + :width: 400 + :align: center + +2. Then run the ``optee-project/versal/boot_jtag.sh`` script: + + .. code-block:: console + + $ cd optee-project/ + $ ./build/versal/boot_jtag.sh + + This script will locate and start the tool ``xsdb``, automatically start a + local ``hw_server`` instance, force boot mode to JTAG, trigger a reset and + finally download and execute the bootable image on the Versal board + (``xsdb`` command ``device program``). + + .. hint:: + + Alternatively, to specify a remote and already started ``hw_server`` + instance on ``$HOST``, listening on port ``$PORT`` (default: 3121) use + option ``-u``. Example: + + .. code-block:: console + + $ cd optee-project/ + $ ./build/versal/boot_jtag.sh -u tcp:$HOST:$PORT + + .. hint:: + + To get a progress indication while the bootable image is being loaded by + ``xsdb`` **and** drop to the interactive TCL shell after loading has + finished, use option ``-i``. + +3. Shortly after ``boot_jtag.sh`` shows the following output, PLM (and PSM) + Firmware messages shall appear on the *primary* UART. + + .. code-block:: console + + $ cd optee-project/ + $ ./build/versal/boot_jtag.sh + + Selecting target Versal + Clear PMC_MULTI_BOOT register (0x00f1110004 = 0x0) + Switch to JTAG boot mode, BOOT_MODE_USER register (0x00f1260200 = 0x0100) + Selecting target PMC + Reset system + Selecting target Versal + Loading BOOT.BIN + +4. PLM Firmware messages shall be followed by startup messages from ARM Trusted + Firmware, OP-TEE OS, then U-Boot and finally Linux. + + When Linux has completed its boot sequence, the user may login as ``root`` + without any password. All OP-TEE services should have been started at this + point and the user may run the ``xtest`` tool to run OP-TEE test suite(s): + + .. code-block:: console + + OP-TEE embedded distrib for versal-net-vnx-b2197-revA + buildroot login: root + # xtest + +SD card boot to Linux +===================== + +If the board offers an SD card slot (i.e. `VCK190`_): + +1. Prepare an SD card with a single **bootable** partition large enough to hold + the bootable image ``BOOT.BIN``. + + Using ``gparted`` or any other partition manager tool create a single + partition on the card (remember to flag it as bootable) + + * 1GB FAT32 bootable partition (i.e: ``/dev/sdc1``). + + Once the SD card is partitioned and the first partition is formatted, mount + it on your file system and copy the image: + + .. code-block:: bash + + $ cp optee-project/build/versal/BOOT.BIN / + $ sync + $ umount + +2. Now the newly created SD card can be used to boot the board. Make sure the + boot switches are configured for SD boot. + + For `VCK190`_, right hand side (zoom in!): + + .. figure:: /images/boards/vck190-sd-boot.png :width: 400 :align: center -Unless you have modified the default U-boot boot command, you will need to stop -the sequence at the U-boot shell and issue these three additional commands to -boot to Linux: +3. Shortly after powering the board on PLM (and PSM) Firmware messages shall + appear on the *primary* UART. + +4. Continue with step 4 in the previous section. + + + +Features +******** + +Crypto +====== + +The Versal OP-TEE port supports the following hardware-backed algorithms: + + - ECDSA Key Generation, Signature and Verification for NIST P-256, P-384 and + P-521 curves + + - In contrast to Versal ACAP, Versal NET uses a dedicated PKI + Accelerator hardware engine. Key generation for these algorithms makes + use of a dedicated hardware TRNG. + + - AES-GCM for 128 and 256-bit keys + - RSA 2048, 3072 and 4096 + - SHA3-384 + - GMAC + - HMAC + - TRNG + - Other algorithms make use of ARMv8 Crypto Extensions where applicable + +Subsystem PDI Loader +==================== + +The Versal OP-TEE port includes a ``loader`` pseudo-TA that can be used to load +Subsystem PDI files, such as bitstreams for the Programmable Logic (PL): + +.. code-block:: c + :caption: Sample code to load a Subsystem PDI from Linux userspace + + #define PTA_VERSAL_LOADER_UUID { 0xa6b493c0, 0xe100, 0x4a13, \ + { 0x9b, 0x00, 0xbc, 0xe4, 0x2d, 0x53, 0xce, 0xd8 } } + + /** + * Load subsystem PDI + * + * [in] memref[0] Subsystem PDI buffer (for VA operation) + * [in] value[0].a HIGH part of 64-bit address (for PA operation) + * [in] value[0].b LOW part of 64-bit address (for PA operation) + * [in] value[1].a Mode of Operation + * + * Return codes: + * TEE_SUCCESS - Invoke command success + * TEE_ERROR_BAD_PARAMETERS - Incorrect input param + * TEE_ERROR_OUT_OF_MEMORY - Could not alloc internal buffer + */ + #define PTA_VERSAL_LOADER_SUBSYS 0x0 + + /** + * PDI Loading Mode + * + * PTA_VERSAL_LOADER_MODE_VA - Load Subsystem PDI from virtual address + * PTA_VERSAL_LOADER_MODE_PA - Load Subsystem PDI from physical address + */ + #define PTA_VERSAL_LOADER_MODE_VA 0x0 + #define PTA_VERSAL_LOADER_MODE_PA 0x1 + + TEEC_Result load_subsyspdi(uint8_t *subsyspdi, size_t size) + { + TEEC_Context ctx; + TEEC_Session sess; + TEEC_Operation op; + TEEC_UUID uuid = PTA_VERSAL_LOADER_UUID; + TEEC_Result ret = TEEC_SUCCESS; + uint32_t origin; + + ret = TEEC_InitializeContext(NULL, &ctx); + if (ret != TEEC_SUCCESS) + return ret; + + /* Open a session with the TA */ + ret = TEEC_OpenSession(&ctx, &sess, &uuid, + TEEC_LOGIN_PUBLIC, NULL, NULL, &origin); + if (ret != TEEC_SUCCESS) + goto out; + + memset(&op, 0, sizeof(op)); + op.paramTypes = TEEC_PARAM_TYPES(TEEC_MEMREF_TEMP_INPUT, + TEEC_VALUE_INPUT, + TEEC_NONE, + TEEC_NONE); + + op.params[0].tmpref.buffer = subsyspdi; + op.params[0].tmpref.size = size; + op.params[1].value.a = PTA_VERSAL_LOADER_MODE_VA; + + ret = TEEC_InvokeCommand(&sess, PTA_VERSAL_LOADER_SUBSYS, + &op, &origin); + + TEEC_CloseSession(&sess); + out: + TEEC_FinalizeContext(&ctx); + return ret; + } + +The example above shows a ``load_subsyspdi()`` function that expects a buffer +(and its size) as its parameters. This buffer holds the actual Subsystem PDI +binary loaded from Linux filesystem for instance. + +As indicated in the example code above, the pseudo-TA can also be instructed to +load from a physical address. In this case the first parameter to command +``PTA_VERSAL_LOADER_SUBSYS`` comprises the high and low part of this physical +address as pure 32 bit values, instead of a memory reference. The second +parameter, called *mode* then has to indicate that by the value +``PTA_VERSAL_LOADER_MODE_PA`` (instead of ``PTA_VERSAL_LOADER_MODE_VA``). -.. code-block:: bash +.. note:: + + Subsystem PDI files loaded with the function ``load_subsyspdi()`` using mode + ``PTA_VERSAL_LOADER_MODE_VA`` have their size limited by the amount of + trusted shared memory available and OP-TEE kernel heap size + (``CFG_CORE_HEAP_SIZE`` and thus ``CFG_TEE_RAM_VA_SIZE``), since Subsystem + PDI files are **copied as a whole** from shared memory **onto the kernel + heap** to circumvent fragmentation and handover a single contiguous memory + block to PLM Firmware. + + Mode ``PTA_VERSAL_LOADER_MODE_PA`` does not have this limitation, but + requires to have a potentially rather statically reserved area of main + memory! + +NVM +=== + +The Versal OP-TEE port provides APIs to read and write eFuses to other OP-TEE OS +components. The API is available in ``core/include/drivers/versal_nvm.h`` and is +reflects the `XilNVM`_ server side IPI interface in terms of functions and their +parameters. + +.. code-block:: c + :caption: Example - Read the DNA value within OP-TEE OS + + #include + + static TEE_Result read_dna(uint32_t *dna) + { + return versal_efuse_read_dna(dna, EFUSE_DNA_LEN); + } + +.. code-block:: c + :caption: Example - Write Black Obfuscation IV within OP-TEE OS + + #include - uboot shell$ mmc dev 0 - uboot shell$ fatload mmc 0:1 0x20000000 versal-vck190.ub - uboot shell$ bootm 0x20000000 + static TEE_Result write_black_iv(uint32_t *iv) + { + struct versal_efuse_ivs ivs = { }; + ivs.prgm_blk_obfus_iv = 1; + memcpy(ivs.blk_obfus_iv, iv, EFUSE_IV_LEN); -.. _Downloads: https://www.xilinx.com/support/download/index.html/content/xilinx/en/downloadNav/embedded-design-tools/2022-1.html + return versal_efuse_write_iv(&ivs); + } + +PUF +=== + +The Versal OP-TEE port provides access to the Physically Unclonable Function +(PUF) to other OP-TEE OS components. The corresponding API is available in +``core/include/drivers/versal_puf.h`` and reflects the `XilPUF`_ server side IPI +interface in terms of functions and their parameters. + +.. code-block:: c + :caption: Example - PUF Registration from within OP-TEE OS + + #include + + static TEE_Result register_puf(struct versal_puf_data *data) + { + struct versal_puf_cfg cfg = { }; + + cfg.puf_operation = VERSAL_PUF_REGISTRATION; + cfg.shutter_value = VERSAL_PUF_SHUTTER_VALUE; + cfg.global_var_filter = VERSAL_PUF_GLBL_VAR_FLTR_OPTION; + #if defined(PLATFORM_FLAVOR_net) + cfg.ro_swap_value = VERSAL_PUF_RO_SWAP_VALUE; + #endif + + return versal_puf_register(data, &cfg); + } + +OCP +=== + +On Versal NET devices only, the Versal OP-TEE port provides access to a subset +of Open Compute Platform (OCP) features: + +- Device Management Endorsement (DME) +- Platform Configuration Register (PCR) extension support +- Device Key Management and Attestation +- Generation of self-signed DevIK X.509 certificate and DevAK X.509 certificate + signed with DevIK. + +The corresponding API is available in ``core/include/drivers/versal_ocp.h`` and +reflects the `XilOCP`_ client side API in terms of functions and their +parameters. + +.. note:: + + Unlike functions in the `XilOCP`_ client API, some - not all - functions in + this OP-TEE OCP API use multiple individual arguments instead of a single + argument pointing to a specific C ``struct`` with multiple members. Also in + contrast to `XilOCP`_ client side API: if a buffer for input or output data + needs to be specified, there is always the need for specifying its size in + bytes, unless the buffer is supposed to be a single item of a certain type. + +.. code-block:: c + : caption: Example - Extending and reading Hardware PCR from within OP-TEE + OS + + #include + + static TEE_Result extend_and_read_hwpcr(uint8_t *hash, size_t size) + { + TEE_Result ret = TEE_ERROR_GENERIC; + + ret = versal_ocp_extend_hwpcr(VERSAL_OCP_PCR_2, hash, size); + if (ret != TEE_SUCCESS) + return ret; + + return versal_ocp_get_hwpcr(0x4, hash, size); + } + + +Memory Map +********** + +By default the build system and the various configuration files are setup, +partially rather hard-coded, to follow the memory maps shown in this part for +loading the individual software components to main memory (DDR RAM). + +Versal ACAP +=========== + +.. csv-table:: Versal ACAP memory map + :header: "Base Address", "Size", "Loaded by", "Loaded from", "Description" + + + + "0x00001000", "127k", "PLM", "``BOOT.BIN``", "DTB for U-Boot (and, if necessary Linux)" + "0x08000000", "", "PLM", "``BOOT.BIN``", "U-Boot" + "0x20000000", "512M", "PLM", "``BOOT.BIN``", "pure Linux kernel or U-Boot FIT image (comprising kernel, DTBs, ramdisk)" + "0x60000000", "256M", "PLM", "``BOOT.BIN``", "OP-TEE system" + "0x70000000", "128M", "PLM", "", "OP-TEE static shared memory" + "0x78000000", "128M", "", "", "*assumed to be reserved by Linux*" + "0xFFFE0000", "128k", "PLM", "``BOOT.BIN``", "ATF (in OCM, **not DDR**)" + "", "", "", "" + "0x00800000", "248M", "U-Boot", "FIT image", "Linux kernel" + "0x10000000", "2M", "U-Boot", "FIT image", "DTBs" + +.. hint:: + + Since a typical PetaLinux BSP for Versal ACAP does not come with a DTB + including ``reserved-memory`` nodes for *OP-TEE system* and *static shared + memory* (0x60000000 - 0x77FFFFFF), the build system is setup (hard-coded) to + include such nodes using the Device Tree Overlay in + ``optee-project/build/versal/versal-optee-mem.dtso`` in the U-Boot FIT + image. + + +Versal NET +========== + +.. csv-table:: Versal NET memory map + :header: "Base Address", "Size", "Loaded by", "Loaded from", "Description" + + "0x00000000", "256M", "", "", "*assumed to be reserved*" + "0x22200000", "39M", "PLM", "``BOOT.BIN``", "OP-TEE system" + "0x24900000", "25M", "PLM", "", "OP-TEE static shared memory" + "0x26200000", "1M", "PLM", "``BOOT.BIN``", "ATF" + "0x26300000", "14M", "PLM", "``BOOT.BIN``", "U-Boot" + "0x27100000", "512k", "PLM", "``BOOT.BIN``", "DTB for U-Boot (and, if necessary Linux)" + "0x27200000", "398M", "PLM", "``BOOT.BIN``", "pure Linux kernel or U-Boot FIT image (comprising kernel, DTBs, ramdisk)" + "0x78000000", "128M", "", "", "*assumed to be reserved by Linux*" + "", "", "", "" + "0x40000000", "2M", "U-Boot", "FIT image", "DTBs" + "0x40200000", "", "U-Boot", "FIT image", "Linux kernel" + +.. danger:: + + Since it is (hereby declared) customary to already have a DTB with all + required ``reserved-memory`` nodes in place, as part of the BSP, on Versal + NET boards, the build system is **not** setup to add any such nodes! + + +Known Issues +************ + +Authenticated Encryption - RAM requirements +=========================================== + +The existing implementation of Authenticated Encryption can require an unusually +high amount of OP-TEE kernel heap memory depending the number of "update" calls. +Per call to the following "update" functions, without "freeing" the operation +handle in between, the specified quantity of memory is allocated until the end +of the operation handle's lifetime: + +- ``TEE_AEUpdate()`` - (120 + 64 + ( * 2)) Bytes +- ``TEE_AEUpdateAAD()`` - (120 + 64 + ) Bytes + +The reason for this lies in the support for ``TEE_CopyOperation()`` and the +creation of a "replay" list: Only a single, truly independent, operation handle +can be "active" (``TEE_AEInit()`` called on it) at the same time. However, +``TEE_CopyOperation()`` on that "active" operation handle is supported. Until +all but a single one of these copies have been finished +(``TEE_FreeOperation()``), only ``TEE_AEEncryptFinal()`` is allowed on them. To +support that, each update (``TEE_AEUpdate*()*``) is recorded on the heap, to +then be able to "replay" them after one copy of the operation handle has been +finished and before the next one can be finished, if any. + +xtest regression 4005.7 and following +===================================== + +Concerns Authenticated Encryption. + +Subcases 4005.7 and following subcases are known to fail since they involve zero +length payloads handed over to ``TEE_AEEncryptFinal()``, which is not supported +by module XilSecure in PLM Firmware. The problem specifically lies in the PMC +DMA engine driver code (function ``XSecure_AesPlatPmcDmaCfgAndXfer()``), which +does not allow zero length payloads, but is called for *any* payload length. + +Note that the Versal OP-TEE currently catches cases of zero length payload and +does not even bother to call out to PLM Firmware (function ``update_payload()`` +in ``core/drivers/crypto/versal/authenc.c``). + +xtest regression 4017.9 and 4017.10 +=================================== + +Concerns Authenticated Encryption. + +Subcases 4017.9 and 4017.10 are known to fail since they involve calling +``TEE_AEInit()`` after ``TEE_AEEncryptFinal()``. As per the `TEE Internal Core +API Specification v1.3.1`_, page 216 this should be possible. However the Versal +OP-TEE port does currently not allow this +(``core/drivers/crypto/versal/authenc.c``). Rather small research and +experiments with module XilSecure of PLM Firmware leave doubts whether this can +be supported at all, unless PLM Firmware is updated. + +Furthermore, it looks like subcases 4017.9 and 4017.10 are going to trigger +alignment issues on Versal ACAP **only** should the above issue be solved one +day. Module XilSecure in PLM Firmware expects payloads to be aligned to 4 Bytes +for regular updates (``TEE_AEUpdate()``) and 16 Bytes for final updates +(```TEE_AEEncryptFinal()``). This can be observed in XilSecure code, function +``XSecure_AesValidateSize()``. + +PLM Firmware for Versal NET device does **not** have this limitation regarding +payload sizes! + +Note that the Versal OP-TEE currently catches cases of unaligned payload sizes +on Versal ACAP and does not even bother to call out to PLM Firmware (function +``update_payload()`` in ``core/drivers/crypto/versal/authenc.c``). + +xtest pkcs11 1030 +================= + +Concerns Authenticated Encryption. + +Case 1030 is known to fail since it runs into the same issue as xtest regression +4005.7. + + +.. _Downloads: https://www.xilinx.com/support/download/index.html/content/xilinx/en/downloadNav/embedded-design-tools/2024-2.html .. _VCK190: https://www.xilinx.com/products/boards-and-kits/vck190.html @@ -169,6 +870,18 @@ boot to Linux: .. _install: https://docs.xilinx.com/r/en-US/ug1144-petalinux-tools-reference-guide/Installing-the-PetaLinux-Tool -.. _Versal_TRM: https://docs.xilinx.com/r/en-US/am011-versal-acap-trm +.. _AM011: https://docs.xilinx.com/r/en-US/am011-versal-acap-trm + +.. _embeddedsw: https://github.com/Xilinx/embeddedsw + +.. _Building from Git: https://github.com/Xilinx/embeddedsw/blob/master/lib/sw_apps/versal_plm/misc/Readme.txt + +.. _xparameters.h: https://github.com/Xilinx/embeddedsw/blob/master/lib/sw_apps/versal_plm/misc/versal/xparameters.h + +.. _XilNVM: https://github.com/Xilinx/embeddedsw/blob/master/lib/sw_services/xilnvm + +.. _XilPUF: https://github.com/Xilinx/embeddedsw/blob/master/lib/sw_services/xilpuf + +.. _XilOCP: https://github.com/Xilinx/embeddedsw/blob/master/lib/sw_services/xilocp -.. _PLM_Customization: https://xilinx-wiki.atlassian.net/wiki/spaces/A/pages/2037088327/Versal+Platform+Loader+and+Manager#PLM-Feature-Configuration-for-PetaLinux +.. _TEE Internal Core API Specification v1.3.1: https://globalplatform.org/wp-content/uploads/2021/03/GPD_TEE_Internal_Core_API_Specification_v1.3.1_PublicRelease_CC.pdf diff --git a/general/platforms.rst b/general/platforms.rst index 7cfd0b4..b4d4dfd 100644 --- a/general/platforms.rst +++ b/general/platforms.rst @@ -298,6 +298,11 @@ please refer to the file MAINTAINERS_ for contact details for various platforms. - Yes - Yes + * - `AMD/Xilinx Versal NET`_ + - ``PLATFORM=versal-net`` + - No + - Yes + * - `Telechips TCC805x `_ - ``PLATFORM=telechips-tcc805x`` - Yes