#######################################
Rollback protection in TF-M secure boot
#######################################

:Author: Tamas Ban
:Organization: Arm Limited
:Contact: Tamas Ban <tamas.ban@arm.com>
:Status: Accepted

Anti-rollback protection
========================
The goal of anti-rollback protection is to prevent downgrading of the device to
an older version of its software, which has been deprecated due to security
concerns.

Elements of software upgrade
============================
During a software upgrade the following entities are involved:

 - Boot loader
 - Manifest data: Metadata of the software image: size, version, hash,
   signature, etc.
 - Software image: binary data, elf, etc.

Validation of new image
=======================
Boot loader is responsible to authenticate the new image according to the
required policies and decide whether the new image is fulfilling all the
requirements. Boot loader verifies the image integrity (hash calculation) and
the origination (signature validation), and might verify other requirements as
well. If the new image is successfully authenticated then the boot loader is in
charge to do the necessary steps (load to execute address, etc.) to enable the
new image to be executed. During the validation process the image and the
manifest data is checked.

Manifest format in MCUBoot
==========================
MCUBoot has a custom manifest format, which is composed of two parts:

 - Image header: Prepended to the beginning of the image.
   It is integrity protected:
 - TLV section: Appended to the end of the image. It is not integrity protected:

  - Hash of public key, hash of image, signature of image

.. code-block:: c

    struct image_header {
        uint32_t ih_magic;
        uint32_t ih_load_addr;
        uint16_t ih_hdr_size;
        uint16_t _pad1;
        uint32_t ih_img_size;
        uint32_t ih_flags;
        struct image_version ih_ver;
        uint32_t _pad2;
    };

Security counter
================
The aim of a security counter is to have an independent (from the image version)
counter in the image manifest to ensure anti-rollback protection. During
software release the value of this counter must be increased if a security flaw
was fixed in the current version. Later when this image is installed on the
device then it is not allowed to go back to earlier versions. It is beneficial
to handle this counter independently from image main version number:

 - It does not need to increase with each software release
 - It makes it possible to do software downgrade to some extent: if the security
   counter has the same value in the older image then it is accepted.
 - If the boot loader verifies multiple images then these can be handled
   independently.

However, as an alternative solution the image version number also could serve
as the security counter of the image. Even the version number itself could be
checked during the anti-rollback verification or the value of the security
counter could be derived from the image main version. It is the responsibility
of the software issuer to define which policy to apply.

Implementation of security counter
==================================
The value of the security counter is a security critical data. Any change in
its value has a security implication. Therefore it must be in the integrity
protected part of the image manifest. Because the image header is almost fully
utilized (few unused fields) and the change of image header structure could
lead to compatibility issues between boot loader and runtime software, it is
proposed to extend the integrity protection to some part of the TLV section.
One of the unused fields in the image header can be used to store the size of
the integrity protected area of the TLV section. This is necessary to know how
to calculate properly the image hash and signature. With this extension of the
integrity protected area other attributes that require integrity protection
can easily be added to the image manifest.

Trusted non-volatile (NV) counters
==================================
The Trusted Base System Architecture (TBSA-M) defines non-volatile (NV) counters
or version counters as a counter with the following properties:

 - It must only be possible to increment a version counter through a Trusted
   access.
 - It must only be possible to increment a version counter. It must not be
   possible to decrement it.
 - When a version counter reaches its maximum value, it must not roll over,
   and no further changes must be possible.
 - A version counter must be non-volatile, and the stored value must survive
   a power down period up to the lifetime of the device.

Trusted non-volatile counters can be used to store the value of security
counters per updatable software image. Ideally all independently updatable
software images should have a separate security counter. In current TF-M
implementation the BL2 is not updatable and the secure and non-secure images
are updated together as a single binary. Therefore, one counter is enough to
implement rollback protection. In future the secure and non-secure binaries
will be handled independently; at that time the introduction of a second
counter will be necessary.

Currently the NV counters can be manipulated through the interface described
in ``tfm_plat_nv_counters.h``.

NV counters and anti-rollback protection
========================================
Trusted non-volatile counters might not be supported by a hardware platform.
In this case anti-rollback protection might still be feasible.

The device threat model needs to consider the following aspects:

 - What is the trust level of the boot loader towards the active software

  - If the boot loader cannot protect the anti-rollback mechanism from the
    secure image then the following threat is unmitigated: The content of the
    memory area which holds the active image could be replaced with a valid but
    an older version of the software with software only attack, i.e.: remote
    code execution.
  - If the boot loader does not trust the loaded image at all then security
    counter must have a copy in NV counter area.

 - Another aspect to consider is where the active image is stored

  - Trusted memory: i.e. on-chip flash (eFlash). The threat that a malicious
    actor can modify the content of trusted memory with HW attack is out of
    scope for the current implementation. It is assumed that if an active image
    and related manifest data is stored in trusted memory then the included
    security counter cannot be compromised.
  - Untrusted memory: i.e. external (off-chip) storage, where malicious actor
    can physically access it so it is possible to modify its content, therefore
    the value of included security counter is unreliable.

If the active image is stored in untrusted storage and it is feasible to modify
its content (i.e. replace the whole image to an older version including
corresponding manifest) then the value of security counter must be copied to
the NV counter area. During software validation the boot loader must compare
the new image's security counters against the security counter stored in
non-volatile counters.

If the active image is stored in trusted memory and boot loader trusts in the
active software then it is not mandatory to store the security counter to
non-volatile counter area. During software validation the boot loader is
allowed to compare the new image's security counters against active image's
security counter.

The evaluation of trusted and untrusted memory must be done per target platform
during threat modelling.

For the most robust implementation the following principles should be applied:

 - Always use NV counters for storing security counter value if supported by
   the hardware.
 - Each software stage must not be able to decrease their corresponding NV
   counter.

Boot flow with anti-rollback protection
=======================================
During software upgrade as part of the image validation process the new and
active image security counters must be compared. The new image can be accepted
if its security counter has a greater or equal value than the active image
security counter. From where to extract the active image security counter it
can be platform dependent. It might read out directly from active image
manifest data (only if it is in trusted memory) or the corresponding
non-volatile counter is read.

If non-volatile counters are used to save security counters then their value
must be updated:

 - If the boot loader does not support to revert previous images (just
   overwrites the previously active image with the new one) in case of faulty
   update then the non-volatile counter can be updated to be equal with the
   new image security counter after successful authentication of the new image.
 - If revert is supported then non-volatile counter can be updated just after
   a test run of the new software when its health check is done. Just in case
   of successful health check can the counter updated to avoid the prevention
   of the revert. This might require a secondary restart of the device.

Tool support
============
There is a Python script, ``imgtool.py`` which is used to prepare the new image
for upgrade (add header, sign the image, append TLV section). This script must
be modified to get an additional command line argument which serves as security
counter. The security counter must be included in the integrity protected part
of the TLV section.

--------------

*Copyright (c) 2019-2020, Arm Limited. All rights reserved.*
