Imre Kis | 0706b65 | 2024-08-08 16:42:02 +0200 | [diff] [blame] | 1 | Firmware update on A+M systems |
| 2 | ------------------------------ |
| 3 | |
| 4 | Concept |
| 5 | ''''''' |
| 6 | |
| 7 | Some platforms have both Cortex-A and Cortex-M subsystems and implement the PSA RoT on the M class core. On such systems |
| 8 | the firmware store is usually read-only or not accessible to the Cortex-A cores due to security reasons. In such cases |
| 9 | it may still be beneficial to implement the cloud update client on the Cortex-A subsystem, and a solution is needed to |
| 10 | bridge the Cortex-A and the Cortex-M firmware update implementations. For this purpose TS implements a special firmware |
| 11 | update agent which is documented below. |
| 12 | |
| 13 | .. figure:: ../image/psa-fwu-m-block.svg |
| 14 | |
| 15 | Components on an A+M system. |
| 16 | |
| 17 | Standards and specifications |
| 18 | '''''''''''''''''''''''''''' |
| 19 | |
| 20 | * `Platform Security Firmware Update for the A-profile Arm Architecture`_ (A class FWU specification) |
| 21 | * `PSA Certified Firmware Update API 1.0`_ (M class FWU specification) |
| 22 | * `Trusted Firmware-M FWU service`_ |
| 23 | |
| 24 | Update agent implementation |
| 25 | ''''''''''''''''''''''''''' |
| 26 | |
| 27 | The update agent implements the `Platform Security Firmware Update for the A-profile Arm Architecture`_ API (prefixed |
| 28 | with ``fwu_``) and acts as a `PSA Certified Firmware Update API 1.0`_ client (prefixed with ``psa_fwu_``). The update |
| 29 | agent has to align the slightly different APIs by maintaining an internal registry of image states and image handles. |
| 30 | The differences between the two firmware update protocols are: |
| 31 | |
| 32 | * `Platform Security Firmware Update for the A-profile Arm Architecture`_ identifies images by UUID while |
| 33 | `PSA Certified Firmware Update API 1.0`_ identifies component by an 8 bit component ID. |
| 34 | * Although similar calls are implemented, FWU-A operates on images, while FWU-M on the whole image set. |
| 35 | * There is no *image handle* concept in `PSA Certified Firmware Update API 1.0`_ |
| 36 | * Differences in the returned details of the image query functions |
| 37 | |
| 38 | The solutions to these differences: |
| 39 | |
| 40 | * A static UUID to component ID mapping is used. This has to be passed to the agent init function. |
| 41 | * Gathering per image based calls and then make the actual call to the M class side when the operation was called on |
| 42 | each image. |
| 43 | * Implement internal image handle registry. |
| 44 | * Convert the image query result returned by FWU-M to FWU-A format. There are similar field, but this imposes some |
| 45 | limitations. |
| 46 | |
Imre Kis | 9aba094 | 2025-02-05 14:27:45 +0100 | [diff] [blame] | 47 | Initialization |
| 48 | ``````````````` |
| 49 | |
| 50 | The initial image and agent state is determined based on the image state returned by ``psa_fwu_query()``. |
| 51 | |
Imre Kis | 0706b65 | 2024-08-08 16:42:02 +0200 | [diff] [blame] | 52 | |
| 53 | ``fwu_discover()`` |
| 54 | `````````````````` |
| 55 | |
| 56 | This function returns the list of implemented features. |
| 57 | |
| 58 | ``fwu_begin_staging()`` |
| 59 | ``````````````````````` |
| 60 | |
| 61 | Clients can only write images in staging state. In order to switch to staging state, the client must call |
| 62 | ``fwu_begin_staging()``. This results in ``psa_fwu_start()`` calls on all selected images. The client can pass a list of |
| 63 | the selected image UUIDs or select all images for staging. |
| 64 | |
| 65 | If the agent is already in staging state when ``fwu_begin_staging()`` is called, then the agent first discards all |
| 66 | transient state by calling ``fwu_cancel_staging()`` and ``psa_fwu_clean()`` on all image. |
| 67 | |
| 68 | .. uml:: ../uml/psa_fwu_m_update_agent/fwu_begin_staging.puml |
| 69 | |
| 70 | ``fwu_end_staging()`` |
| 71 | ````````````````````` |
| 72 | |
| 73 | Finishes the staging state when all images that were selected for the update have been updated. If all selected images |
| 74 | are also accepted the agent switches to regular state and the update is completed. If there are not accepted images, the |
| 75 | agent switches to trial state, so the client can validate the new set of images and accept or reject them. |
| 76 | |
| 77 | On calling ``fwu_end_staging()`` the agent calls ``psa_fwu_finish()`` on each selected image, then calls |
| 78 | ``psa_fwu_install()``. If all images have been accepted (see ``fwu_commit()``) it also calls ``psa_fwu_accept()``. |
Imre Kis | 9aba094 | 2025-02-05 14:27:45 +0100 | [diff] [blame] | 79 | The implementation treats ``PSA_SUCCESS_REBOOT`` and ``PSA_SUCCESS_RESTART`` status values as error. In an A+M system the M |
| 80 | class side shouldn't restart the system, so calling ``psa_fwu_request_reboot()`` does not fit the system. There's also no |
| 81 | PSA FWU A return code for inidicating the restart request to the normal world. If the normal world has to restart the |
| 82 | system after ending the staging phase, it has to do it in an implementation defined way. |
Imre Kis | 0706b65 | 2024-08-08 16:42:02 +0200 | [diff] [blame] | 83 | |
| 84 | .. uml:: ../uml/psa_fwu_m_update_agent/fwu_end_staging.puml |
| 85 | |
| 86 | ``fwu_cancel_staging()`` |
| 87 | ```````````````````````` |
| 88 | |
| 89 | Cancels staging state and reverts to original regular state. The function calls ``psa_fwu_cancel()`` on each selected |
| 90 | image. |
| 91 | |
| 92 | .. uml:: ../uml/psa_fwu_m_update_agent/fwu_cancel_staging.puml |
| 93 | |
| 94 | ``fwu_open()`` |
| 95 | `````````````` |
| 96 | |
| 97 | `Platform Security Firmware Update for the A-profile Arm Architecture`_ has a concept of image handles. An image can be |
| 98 | opened via ``fwu_open()``, then accessed by calling ``fwu_write_stream()`` or ``fwu_read_stream()``, and finally it can |
| 99 | be closed by invoking ``fwu_commit()``. However `PSA Certified Firmware Update API 1.0`_ does not have a similar concept |
| 100 | and once the staging process was started for an image by calling ``psa_fwu_start()``, the image can be written through |
| 101 | ``psa_fwu_write()``. |
| 102 | |
| 103 | The update agent provides an internal registry of opened images and their access rights so it can handle subsequent |
| 104 | calls on the image handle. The open call can open an image for either write or read operations but not for both. The |
| 105 | image is identified by its UUID. Only images which were selected for staging can be opened for write. |
| 106 | |
| 107 | There is no actual call made to the M class side on opening a image. |
| 108 | |
| 109 | `PSA Certified Firmware Update API 1.0`_ does not provide a function for reading images, so opening images will fail |
| 110 | except for opening the image directory. Only the image directory supports read operations. |
| 111 | |
| 112 | ``fwu_write_stream()`` |
| 113 | `````````````````````` |
| 114 | |
| 115 | This function writes data into the opened image. The image handle has to be opened for write operations. The agent calls |
| 116 | ``psa_fwu_write()`` for doing the actual write and the write offset is tracked internally. |
| 117 | |
| 118 | ``fwu_read_stream()`` |
| 119 | ````````````````````` |
| 120 | |
| 121 | This function read data from the opened image. The image handle has to be opened for read operations. |
| 122 | |
| 123 | This call is only implemented for the image directory which returns the available image list as specified in |
| 124 | `Platform Security Firmware Update for the A-profile Arm Architecture`_. It does not support the partial reading of the |
| 125 | image directory. |
| 126 | |
| 127 | ``fwu_commit()`` |
| 128 | ```````````````` |
| 129 | |
| 130 | The commit call closes the image handle. The client can also mark the image as accepted on commit and this the method |
| 131 | for accepting all images before calling ``fwu_end_staging()``. |
| 132 | |
| 133 | There is no actual call made to the M class side on comiting an image. |
| 134 | |
| 135 | ``fwu_accept_image()`` |
| 136 | `````````````````````` |
| 137 | |
| 138 | `PSA Certified Firmware Update API 1.0`_ only provides a ``psa_fwu_accept()`` function which accepts the whole set of |
| 139 | selected images. In order to align with the ``fwu_accept_image()`` API, it only marks the given image as accepted and |
| 140 | calls ``psa_fwu_accept()`` when all images have been accepted. This results in a state transition to regular state. |
| 141 | |
| 142 | .. uml:: ../uml/psa_fwu_m_update_agent/fwu_accept.puml |
| 143 | |
| 144 | ``fwu_select_previous()`` |
| 145 | ````````````````````````` |
| 146 | |
| 147 | Selects previous working state (i.e. rejects the firmware update) and transitions back to regular state after calling |
Imre Kis | 9aba094 | 2025-02-05 14:27:45 +0100 | [diff] [blame] | 148 | ``psa_fwu_reject()``. The implementation treats ``PSA_SUCCESS_REBOOT`` and ``PSA_SUCCESS_RESTART`` status values as error. |
| 149 | In an A+M system the M class side shouldn't restart the system, so calling ``psa_fwu_request_reboot()`` does not fit the |
| 150 | system. There's also no PSA FWU A return code for inidicating the restart request to the normal world. If the normal |
| 151 | world has to restart the system when rejecting the installed firmware, it has to do it in an implementation defined way. |
Imre Kis | 0706b65 | 2024-08-08 16:42:02 +0200 | [diff] [blame] | 152 | |
| 153 | .. uml:: ../uml/psa_fwu_m_update_agent/fwu_select_previous.puml |
| 154 | |
| 155 | Image directory |
| 156 | ''''''''''''''' |
| 157 | |
| 158 | The client can read the image directory by opening and reading an image with dedicated UUID |
| 159 | (``deee58d9-5147-4ad3-a290-77666e2341a5``). On image directory read, the agent will call ``psa_fwu_query()`` on each |
| 160 | image and convert the value of similar fields. |
| 161 | |
| 162 | * The UUID is based on the UUID - component ID mapping passed upon agent initialization. |
| 163 | * The images only support write operation due to FWU-M limitation. |
| 164 | * The image maximal size is copied from the component info structure. |
| 165 | * The lowest accepted version is set to 0. |
| 166 | * The image version is converted from the fields of the component info structure into a single 32 bit value. The build |
| 167 | field is dropped due to lack of space in the 32 bit field. |
| 168 | * The images is marked accepted if its state in the component info structure is ``PSA_FWU_UPDATED``. |
| 169 | |
| 170 | .. uml:: ../uml/psa_fwu_m_update_agent/image_directory.puml |
| 171 | |
| 172 | -------------- |
| 173 | |
| 174 | .. _`Platform Security Firmware Update for the A-profile Arm Architecture`: https://developer.arm.com/documentation/den0118/latest/ |
| 175 | .. _`PSA Certified Firmware Update API 1.0`: https://arm-software.github.io/psa-api/fwu/1.0/ |
| 176 | .. _`Trusted Firmware-M FWU service`: https://tf-m-user-guide.trustedfirmware.org/design_docs/services/tfm_fwu_service.html |
| 177 | |
| 178 | *Copyright (c) 2024, Arm Limited and Contributors. All rights reserved.* |
| 179 | |
| 180 | SPDX-License-Identifier: BSD-3-Clause |