Encrypted Payloads in SUIT Manifests
Hannes Tschofenig
University of Applied Sciences Bonn-Rhein-Sieg
Hannes.Tschofenig@gmx.net
Russ Housley
Vigil Security, LLC
housley@vigilsec.com
Brendan Moran
Arm Limited
Brendan.Moran@arm.com
David Brown
Linaro
david.brown@linaro.org
Ken Takayama
SECOM CO., LTD.
ken.takayama.ietf@gmail.com
21 October 2024
Security
SUIT
Internet-Draft
This document specifies techniques for encrypting software, firmware, machine learning models, and personalization data by utilizing the IETF SUIT manifest. Key agreement is provided by ephemeral-static (ES) Diffie-Hellman (DH) and AES Key Wrap (AES-KW). ES-DH uses public key cryptography while AES-KW uses a pre-shared key. Encryption of the plaintext is accomplished with conventional symmetric key cryptography.
Introduction
Vulnerabilities in Internet of Things (IoT) devices have highlighted the need for a reliable and secure firmware update mechanism, especially for constrained devices. To protect firmware images, the SUIT manifest format was developed [I-D.ietf-suit-manifest]. This format provides a bundle of metadata, including the payload location, applicable devices, and a security wrapper.
[RFC9124] outlines the necessary information provided by the SUIT manifest format. In addition to protecting against modification via digital signatures or message authentication codes, the format can also offer confidentiality.
Encryption prevents third parties, including attackers, from accessing the payload. Attackers often require detailed knowledge of a binary, such as a firmware image, to launch successful attacks. For instance, return-oriented programming (ROP) [ROP] requires access to the binary, and encryption makes writing exploits significantly more difficult. Beyond ensuring the confidentiality of the binary itself, protecting the confidentiality of the source code (e.g., in the case of open source software) may also be necessary to prevent reverse engineering and reproduction of the firmware.
While the initial motivation for this document was firmware encryption, the use of SUIT manifests has expanded to cover other scenarios requiring integrity and confidentiality protection, such as:
- software packages,
- personalization data,
- configuration data, and
- machine learning models.
Thus, the term "payload" is used generically to refer to all these objects.
The payload is encrypted using a symmetric content encryption key, which can be established through various mechanisms. This document defines two content key distribution methods for use with the IETF SUIT manifest:
- Ephemeral-Static (ES) Diffie-Hellman (DH), and
- AES Key Wrap (AES-KW).
The first method relies on asymmetric cryptography, while the second uses symmetric cryptography.
Our design aims to reduce the number of content key distribution methods for payload encryption, thereby increasing interoperability between different SUIT manifest parser implementations.
The goal of this specification is to protect payloads both during end-to-end transport (from the distribution system to the device) and at rest when stored on the device. Constrained devices often employ eXecute In Place (XIP), a method of executing code directly from flash memory rather than loading it into RAM. Many of these devices lack hardware-based, on-the-fly decryption for code stored in flash memory, which may require decrypting and storing firmware images in on-chip flash before execution. However, we expect hardware-based, on-the-fly decryption to become more common in the future, enhancing confidentiality at rest.
Conventions and Terminology
The key words "MUST", "MUST NOT", "REQUIRED", "SHALL", "SHALL NOT", "SHOULD", "SHOULD NOT", "RECOMMENDED", "NOT RECOMMENDED", "MAY", and "OPTIONAL" in this document are to be interpreted as described in BCP 14 [RFC2119] [RFC8174] when, and only when, they appear in all capitals, as shown here.
This document assumes familiarity with the IETF SUIT manifest [I-D.ietf-suit-manifest], the SUIT information model [RFC9124], and the SUIT architecture [RFC9019].
The following abbreviations are used in this document:
- Key Wrap (KW), defined in [RFC3394] (for use with AES)
- Key-Encryption Key (KEK) [RFC3394]
- Content-Encryption Key (CEK) [RFC5652]
- Ephemeral-Static (ES) Diffie-Hellman (DH) [RFC9052]
- Authenticated Encryption with Associated Data (AEAD)
- Execute in Place (XIP)
The terms sender and recipient have the following meaning:
- Sender: Entity that sends an encrypted payload.
- Recipient: Entity that receives an encrypted payload.
Additionally, we introduce the term "distribution system" (or distributor) to refer to an entity that knows the recipients of payloads. It is important to note that the distribution system is far more than a file server. For use of encryption, the distribution system either knows the public key of the recipient (for ES-DH), or the KEK (for AES-KW).
The author, which is responsible for creating the payload, does not know the recipients. The authors may, for example, be a developer building a firmware image.
The author and the distribution system are logical roles. In some deployments these roles are separated in different physical entities and in others they are co-located.
Architecture
[RFC9019] outlines the architecture for distributing payloads and manifests from an author to devices. However, it does not cover payload encryption in detail. This document extends that architecture to support encryption, as illustrated in Figure 1.
To encrypt a payload, it is essential to know the recipient. For AES-KW, the Key Encryption Key (KEK) must be known, and for ES-DH, the sender needs access to the recipient's public key. This public key and its associated parameters may be found in the recipient's X.509 certificate [RFC5280]. For authentication and integrity protection, recipients must be provisioned with a trust anchor when the manifest is protected by a digital signature. If a MAC is used for manifest protection, a symmetric key must be shared between the recipient and the sender.
With encryption, the author cannot simply create and sign a manifest for the payload, as the recipients are often unknown. Therefore, the author must collaborate with the distribution system. The degree of this collaboration is discussed below.
The primary purpose of encryption is to protect against adversaries along the path between the distribution system and the device. There is also a risk that adversaries may extract the decrypted firmware image from the device itself. Consequently, the device must be safeguarded against physical attacks, though such countermeasures are typically beyond the scope of IETF specifications.
Note: It is assumed that the communication between the author and the distribution system is secure. For example, the author might upload the manifest and firmware image to the distribution system using a secure HTTPS REST API.

Architecture for the distribution of Encrypted Payloads.

Device

1

Author

Payload
+

Manifest

Device

Payload
+

Manifest

Distribution

2

System
...

Device

n

 +----------+
 |  Device  |                              +----------+
 |    1     |<--+                          |  Author  |
 |          |   |                          +----------+
 +----------+   |                               |
                |                               | Payload +
                |                               | Manifest
                |                               v
 +----------+   |                        +--------------+
 |  Device  |   |  Payload + Manifest    | Distribution |
 |    2     |<--+------------------------|    System    |
 |          |   |                        +--------------+
 +----------+   |
                |
      ...       |
                |
 +----------+   |
 |  Device  |   |
 |    n     |<--+
 |          |
 +----------+

When the author delegates encryption rights to the distributor, two models are possible:
1. Replacing the COSE_Encrypt and Re-signing the Manifest: The distributor replaces the COSE_Encrypt structure in the manifest and then signs the manifest again. However, since the COSE_Encrypt structure is within a signed container, this presents a challenge: replacing COSE_Encrypt alters the digest of the manifest, thereby invalidating the signature. As a result, the distributor must be able to sign the new manifest. If this is the case, the distributor gains the authority to construct and sign manifests, effectively allowing them to sign code and giving them full control over the recipient. Distributors typically perform re-encryption online to manage large numbers of devices efficiently, which prevents air-gapping the signing operations. This has implications for the recommendations in Section 4.3.17 of [RFC9124]. Despite these issues, this model represents the current standard practice for IoT firmware updates.
2. Two-Layer Manifest System: The distributor creates a new manifest that overrides the COSE_Encrypt using the dependency system defined in [I-D.ietf-suit-trust-domains]. This method introduces additional overhead, including one more signature verification, one extra manifest, and the need for extra mechanisms on the recipient side to handle dependency processing. While this adds complexity, it also enhances security.
These two models offer different threat profiles for the distributor. If the distributor is limited to encryption rights, an attacker who breaches the distributor can only launch a limited attack by encrypting a modified binary. However, recipients will detect the attack during the image digest check and immediately revert to the correct image.
It is RECOMMENDED that distributors adopt the two-layer manifest approach to distribute content encryption keys without re-signing the manifest, despite the added complexity and the increased number of signature verifications required on the recipient side.
Encryption Extensions
This specification introduces a new extension to the SUIT_Parameters structure.
The SUIT_Encryption_Info structure (referred to as suit-parameter-encryption-info in Figure 2) contains the content key distribution information. The details of the SUIT_Encryption_Info structure are provided in Section 6.1 (for AES-KW) and Section 6.2 (for ES-DH).
Once a CEK is available, the steps outlined in Section 7 apply to both content key distribution methods described in this section.
The SUIT_Encryption_Info structure is carried within either the suit-directive-override-parameters or suit-directive-set-parameters used in the "Directive Write" and "Directive Copy" operations. An implementation conforming to this specification must support these two parameters.
Interoperability requirements for content key distribution methods vary: since a device will typically support only one of the two specified methods, the distribution system needs to know which method is supported. Limiting a constrained device to a single content key distribution method also helps reduce code size.

CDDL of the SUIT_Parameters Extension.

SUIT_Parameters //= (suit-parameter-encryption-info
    => bstr .cbor SUIT_Encryption_Info)

suit-parameter-encryption-info = TBD19

RFC Editor's Note (TBD19): The value for the suit-parameter-encryption-info parameter is set to 19, as the proposed value.
Extended Directives
Here’s an improved version of your text:
This specification extends the following directives:
- Directive Write (suit-directive-write): Used to decrypt the content specified by suit-parameter-content using suit-parameter-encryption-info.
- Directive Copy (suit-directive-copy): Used to decrypt the content of the component specified by suit-parameter-source-component using suit-parameter-encryption-info.
Examples of these two directives are provided below, focusing on the essential aspects. A complete example for AES Key Wrap with the Fetch and Copy directives can be found in Section 10.2, while an example illustrating the Write directive is shown in Section 10.1.
Figure 3 illustrates the Directive Write. The encrypted payload specified by parameter-content, represented as h'EA1...CED' in the example, is decrypted using the SUIT_Encryption_Info structure referenced by parameter-encryption-info, i.e., h'D86...1F0'. The resulting plaintext payload is then stored in component #0.

Example showing the extended suit-directive-write.

/ directive-override-parameters / 20, {
  / parameter-content / 18: h'EA1...CED',
  / parameter-encryption-info / TBD19: h'D86...1F0'
},
/ directive-write / 18, 15

RFC Editor's Note (TBD19): The value for the parameter-encryption-info parameter is set to 19, as the proposed value.
Figure 4 illustrates the Directive Copy. In this example the encrypted payload is found at the URI indicated by the parameter-uri, i.e. "http://example.com/encrypted.bin". The encrypted payload will be downloaded and stored in component #1. Then, the information in the SUIT_Encryption_Info structure referred to by parameter-encryption-info, i.e. h'D86...1F0', will be used to decrypt the content in component #1 and the resulting plaintext payload will be stored into component #0.

Example showing the extended suit-directive-copy.

/ directive-set-component-index / 12, 1,
/ directive-override-parameters / 20, {
  / parameter-uri / 21: "http://example.com/encrypted.bin",
},
/ directive-fetch / 21, 15,
/ directive-set-component-index / 12, 0,
/ directive-override-parameters / 20, {
  / parameter-encryption-info / TBD19: h'D86...1F0',
  / parameter-source-component / 22: 1
},
/ directive-copy / 22, 15

RFC Editor's Note (TBD19): The value for the suit-parameter-encryption-info parameter is set to 19, as the proposed value.
The payload to be encrypted may be detached and, in that case, it is not covered by the digital signature or the MAC protecting the manifest. (To be more precise, the suit-authentication-wrapper found in the envelope contains a digest of the manifest in the SUIT Digest Container.)
The lack of authentication and integrity protection of the payload is particularly a concern when a cipher without integrity protection is used.
To provide authentication and integrity protection of the payload in the detached payload case a SUIT Digest Container with the hash of the encrypted and/or plaintext payload MUST be included in the manifest. See suit-parameter-image-digest parameter in Section 8.4.8.6 of [I-D.ietf-suit-manifest].
Once a CEK is available, the steps described in Section 7 are applicable. These steps apply to both content key distribution methods.
Content Key Distribution
The following sub-sections describe two content key distribution methods: AES Key Wrap (AES-KW) and Ephemeral-Static Diffie-Hellman (ES-DH). While many other methods are specified in the literature and supported by COSE, AES-KW and ES-DH were chosen for their widespread use in the market today. They were selected for their maturity, differing security properties, and strong interoperability.
Both content key distribution methods require the CEKs to be randomly generated. The guidelines for random number generation in [RFC8937] MUST be followed.
When sending an encrypted payload to multiple recipients, various deployment options are available. The following notation is used to explain these options:

  - KEK[R1, S] refers to a KEK shared between recipient R1 and
    the sender S.
  - CEK[R1, S] refers to a CEK shared between R1 and S.
  - CEK[*, S] or KEK[*, S] are used when a single CEK or a single
    KEK is shared with all authorized recipients by a given sender
    S in a certain context.
  - ENC(plaintext, k) refers to the encryption of plaintext with
    a key k.

Content Key Distribution with AES Key Wrap
Introduction
The AES Key Wrap (AES-KW) algorithm, as described in [RFC3394], is used to encrypt a randomly generated content-encryption key (CEK) with a pre-shared key-encryption key (KEK). The COSE conventions for using AES-KW are specified in Section 8.5.2 of [RFC9052] and in Section 6.2.1 of [RFC9053]. The encrypted CEK is carried within the COSE_recipient structure , which includes the necessary information for AES-KW. The COSE_recipient structure, a substructure of COSE_Encrypt, contains the CEK encrypted by the KEK.
To ensure high security when using AES Key Wrap, it is important that the KEK is of high entropy and that implementations protect the KEK from disclosure. A compromised KEK could expose all data encrypted with it, including binaries and configuration data.
The COSE_Encrypt structure conveys the information needed to encrypt the payload, including details such as the algorithm and IV. Even though the payload may be conveyed as detached content, the encryption information is still embedded in the COSE_Encrypt.ciphertext structure.
Deployment Options
There are three deployment options for use with AES Key Wrap for payload encryption:
- If all recipients (typically of the same product family) share the same KEK, a single COSE_recipient structure contains the encrypted CEK. The sender executes the following steps:

     1. Fetch KEK[*, S]
     2. Generate CEK
     3. ENC(CEK, KEK)
     4. ENC(payload, CEK)

This deployment option is strongly discouraged. An attacker gaining access to the KEK will be able to encrypt and send payloads to all recipients configured to use this KEK.
- If recipients have different KEKs, then multiple COSE_recipient structures are included but only a single CEK is used. Each COSE_recipient structure contains the CEK encrypted with the KEKs appropriate for a given recipient. The benefit of this approach is that the payload is encrypted only once with a CEK while there is no sharing of the KEK across recipients. Hence, authorized recipients still use their individual KEK to decrypt the CEK and to subsequently obtain the plaintext. The steps taken by the sender are:

    1.  Generate CEK
    2.  for i=1 to n
        {
    2a.    Fetch KEK[Ri, S]
    2b.    ENC(CEK, KEK[Ri, S])
        }
    3.  ENC(payload, CEK)

- The third option is to use different CEKs encrypted with KEKs of authorized recipients. This approach is appropriate when no benefits can be gained from encrypting and transmitting payloads only once. Assume there are n recipients with their unique KEKs - KEK[R1, S], ..., KEK[Rn, S] and unique CEKs. The sender needs to execute the following steps:

    1.  for i=1 to n
        {
    1a.    Fetch KEK[Ri, S]
    1b.    Generate CEK[Ri, S]
    1c.    ENC(CEK[Ri, S], KEK[Ri, S])
    1d.    ENC(payload, CEK[Ri, S])
    2.  }

CDDL
The CDDL for the AES-KW binary is shown in Figure 5. empty_or_serialized_map and header_map are structures defined in [RFC9052].

CDDL for AES-KW-based Content Key Distribution

=============== NOTE: '\' line wrapping per RFC 8792 ================

SUIT_Encryption_Info_AESKW = #6.96([
  protected   : outer_header_map_protected,
  unprotected : outer_header_map_unprotected,
  ciphertext  : bstr / nil,
  recipients  : [ + COSE_recipient_AESKW ]
])

outer_header_map_protected = empty_or_serialized_map
outer_header_map_unprotected = header_map

COSE_recipient_AESKW = [
  protected   : bstr .size 0 / bstr .cbor empty_map,
  unprotected : recipient_header_unpr_map_aeskw,
  ciphertext  : bstr        ; CEK encrypted with KEK
]

empty_map = {}

recipient_header_unpr_map_aeskw =
{
    1 => int,     ; algorithm identifier
  ? 4 => bstr,    ; identifier of the KEK pre-shared with the \
                                                            recipient
  * label => values   ; extension point
}

Note that the AES-KW algorithm, as defined in Section 2.2.3.1 of [RFC3394], does not have public parameters that vary on a per-invocation basis. Hence, the protected header in the COSE_recipient structure is a byte string of zero length.
Content Key Distribution with Ephemeral-Static Diffie-Hellman
Introduction
Ephemeral-Static Diffie-Hellman (ES-DH) is a public key encryption scheme that enables encryption using the recipient's public key. There are several variations of this scheme; this document adopts the version specified in Section 8.5.5 of [RFC9052].
The structure is composed of two layers:
- Layer 0: Contains content encrypted with a Content Encryption Key (CEK). The content may be provided separately.
- Layer 1: Uses the AES Key Wrap (AES-KW) algorithm to encrypt the randomly generated CEK with a Key Encryption Key (KEK) derived via ES-DH. The resulting symmetric key is processed through an HKDF-based key derivation function.
This two-layer structure combines ES-DH with AES-KW and HKDF, referred to as ECDH-ES + AES-KW. An example can be found in Figure 10.
Another variant of the ES-DH algorithm, called ECDH-ES + HKDF, does not utilize AES Key Wrap. However, this version is not covered in this document.
Deployment Options
This approach supports only two deployment options, as it assumes that each recipient is always equipped with a device-specific public/private key pair.
- When a sender transmits a payload to multiple recipients, all recipients receive the same encrypted payload, meaning the same CEK is used to encrypt the content. For each recipient, a separate COSE_recipient structure is used, which contains the CEK encrypted with the recipient-specific KEK. To derive the KEK, each COSE_recipient structure includes a COSE_recipient_inner structure that carries the sender's ephemeral key and an identifier for the recipient's public key.
The steps taken by the sender are:

    1.  Generate CEK
    2.  for i=1 to n
        {
    2a.     Generate KEK[Ri, S] using ES-DH
    2b.     ENC(CEK, KEK[Ri, S])
        }
    3.  ENC(payload,CEK)

- The alternative is to encrypt the payload with a unique CEK for each recipient, resulting in multiple manifests. This approach is useful when payloads contain device-specific information. In this case, the encryption operation becomes ENC(payload_i, CEK[Ri, S]) where each recipient Ri receives a unique CEK. Assume that KEK[R1, S],..., KEK[Rn, S] have been generated for the recipients using ES-DH. The sender must then follow these steps:

    1.  for i=1 to n
        {
    1a.     Generate KEK[Ri, S] using ES-DH
    1b.     Generate CEK[Ri, S]
    1c.     ENC(CEK[Ri, S], KEK[Ri, S])
    1d.     ENC(payload, CEK[Ri, S])
        }

CDDL
The CDDL for the ECDH-ES+AES-KW binary is provided in Figure 6. Only the essential parameters are included. The structures empty_or_serialized_map and header_map are defined in [RFC9052].

CDDL for ES-DH-based Content Key Distribution

SUIT_Encryption_Info_ESDH = #6.96([
  protected   : outer_header_map_protected,
  unprotected : outer_header_map_unprotected,
  ciphertext  : bstr / nil,
  recipients  : [ + COSE_recipient_ESDH ]
])

outer_header_map_protected = empty_or_serialized_map
outer_header_map_unprotected = header_map

COSE_recipient_ESDH = [
  protected   : bstr .cbor recipient_header_map_esdh,
  unprotected : recipient_header_unpr_map_esdh,
  ciphertext  : bstr        ; CEK encrypted with KEK
]

recipient_header_map_esdh =
{
    1 => int,         ; algorithm identifier
  * label => values   ; extension point
}

recipient_header_unpr_map_esdh =
{
  ? 4 => bstr,        ; identifier of the recipient public key
   -1 => COSE_Key,    ; ephemeral public key for the sender
  * label => values   ; extension point
}

See Section 7 for a description on how to encrypt the payload.
Context Information Structure
The context information structure ensures that the derived keying material is "bound" to the specific context of the transaction. This specification reuses the structure defined in Section 5.2 of [RFC9053], with modifications to fit the current use case.
The following elements are bound to the context:
- the protocol employing the key-derivation method,
- information about the utilized AES Key Wrap algorithm, and the key length.
- the protected header field, which contains the content key encryption algorithm.
The sender and recipient identities are left empty.
The following fields in Figure 7 require an explanation:
- The COSE_KDF_Context.AlgorithmID field MUST contain the identifier for the AES Key Wrap algorithm being used. This specification uses the following values: A128KW (value -3), A192KW (value -4), or A256KW (value -5)
- The COSE_KDF_Context.SuppPubInfo.keyDataLength field MUST specify the key length, in bits, corresponding to the algorithm in the AlgorithmID field. For A128KW the value is 128, for A192KW the value is 192, and for A256KW the value 256.
- The COSE_KDF_Context.SuppPubInfo.other field captures the protocol that uses the ES-DH content key distribution algorithm. It MUST be set to the constant string "SUIT Payload Encryption".
- The COSE_KDF_Context.SuppPubInfo.protected field MUST contain the serialized content of the recipient_header_map_esdh field, which contains (among other elements) the identifier of the content key distribution method.

CDDL for COSE_KDF_Context Structure

COSE_KDF_Context = [
    AlgorithmID : int,
    PartyUInfo : [ PartyInfoSender ],
    PartyVInfo : [ PartyInfoRecipient ],
    SuppPubInfo : [
        keyDataLength : uint,
        protected : bstr,
        other: 'SUIT Payload Encryption'
    ],
    ? SuppPrivInfo : bstr
]

PartyInfoSender = (
    identity : nil,
    nonce : nil,
    other : nil
)

PartyInfoRecipient = (
    identity : nil,
    nonce : nil,
    other : nil
)

The HKDF-based key derivation function MAY contain a salt value, as described in Section 5.1 of [RFC9053]. This optional value influences the key generation process, though this specification does not require the use of a salt. If the salt is public and included in the message, the "salt" algorithm header parameter MUST be used. The salt adds extra randomness to the KDF context. When the salt is transmitted via the "salt" algorithm header parameter, the receiver MUST be capable of processing it and MUST pass it into the key derivation function. For more details on salt usage, refer to [RFC5869] and NIST SP800-56 [SP800-56].
Profiles of this specification MAY define an extended version of the context information structure or MAY employ a different context information structure.
Content Encryption
This section summarizes the steps involved in content encryption, applicable to both content key distribution methods.
When using AEAD ciphers, such as AES-GCM or ChaCha20/Poly1305, the COSE specification requires a consistent byte stream to create the authenticated data structure. This structure is illustrated in Figure 8 and defined in Section 5.3 of [RFC9052].

CDDL for Enc_structure Data Structure

 Enc_structure = [
   context : "Encrypt",
   protected : empty_or_serialized_map,
   external_aad : bstr
 ]

This Enc_structure must be populated as follows:
- The protected field in the Enc_structure from Figure 8 refers to the content of the protected field in the COSE_Encrypt structure.
- The value of external_aad MUST be set to a zero-length byte string, represented as h'' in diagnostic notation and encoded as 0x40.
Some ciphers, such as AES-CTR and AES-CBC, provide confidentiality without integrity protection (see [RFC9459]). For these ciphers, the Enc_structure shown in Figure 8 cannot be used, as the Additional Authenticated Data (AAD) byte string is only applicable to AEAD ciphers. Therefore, the AAD structure is not passed to the API for these ciphers, and the protected header in the SUIT_Encryption_Info structure MUST be a zero-length byte string.
AES-CTR and AES-CBC are discussed in separate sub-sections below and Figure 11 and Figure 14 use the following abbreviations:
- Pi = Plaintext blocks
- Ci = Ciphertext blocks
- E = Encryption function
- k = Symmetric key
- ⊕ = XOR operation
AES-GCM
Introduction
AES-GCM is an AEAD cipher and provides confidentiality and integrity protection.
Examples in this section use the following parameters:
- Algorithm for payload encryption: AES-GCM-128
  - k: h'15F785B5C931414411B4B71373A9C0F7'
  - IV: h'F14AAB9D81D51F7AD943FE87AF4F70CD'
- Plaintext: "This is a real firmware image."
  - in hex: 546869732069732061207265616C206669726D7761726520696D6167652E
AES-KW + AES-GCM Example
This example uses the following parameters:
- Algorithm id for key wrap: A128KW
- KEK COSE_Key (Secret Key):
  - kty: Symmetric
  - k: 'aaaaaaaaaaaaaaaa'
  - kid: 'kid-1'
The COSE_Encrypt structure, in hex format, is (with a line break inserted):

D8608443A10101A1054CF14AAB9D81D51F7AD943FE87F6818340A2012204
456B69642D31581875603FFC9518D794713C8CA8A115A7FB32565A6D5953
4D62

The resulting COSE_Encrypt structure in a diagnostic format is shown in Figure 9.

COSE_Encrypt Example for AES Key Wrap

96([
  / protected: / << {
    / alg / 1: 1 / A128GCM /
  } >>,
  / unprotected: / {
    / IV / 5: h'F14AAB9D81D51F7AD943FE87'
  },
  / payload: / null / detached ciphertext /,
  / recipients: / [
    [
      / protected: / h'',
      / unprotected: / {
        / alg / 1: -3 / A128KW /,
        / kid / 4: 'kid-1'
      },
      / payload: /
        h'75603FFC9518D794713C8CA8A115A7FB32565A6D59534D62'
        / CEK encrypted with KEK /
    ]
  ]
])

The encrypted payload (with a line feed added) was:

758C4B7BBAE2C4C1D462423E0F0DC3164FFA7B85BB94D4BD6D7ED26AB32F
EB063385D4D3465927EC82CB5E198A59

ECDH-ES+AES-KW + AES-GCM Example
This example uses the following parameters:
- Algorithm for content key distribution: ECDH-ES + A128KW
- KEK COSE_Key (Receiver's Private Key):
  - kty: EC2
  - crv: P-256
  - x: h'5886CD61DD875862E5AAA820E7A15274C968A9BC96048DDCACE32F50C3651BA3'
  - y: h'9EED8125E932CD60C0EAD3650D0A485CF726D378D1B016ED4298B2961E258F1B'
  - d: h'60FE6DD6D85D5740A5349B6F91267EEAC5BA81B8CB53EE249E4B4EB102C476B3'
  - kid: 'kid-2'
- KDF Context
  - Algorithm ID: -3 (A128KW)
  - SuppPubInfo
    - keyDataLength: 128
    - protected: { / alg / 1: -29 / ECDH-ES+A128KW / }
    - other: 'SUIT Payload Encryption'
The COSE_Encrypt structure, in hex format, is (with a line break inserted):

D8608443A10101A1054CF14AAB9D81D51F7AD943FE87F6818344A101381C
A120A40102200121582073024F415AA51529A66CCEFD88F3F62A734492FF
45F6AD37FD2888E73EAF19DA2258204005B48A6FD091AA6ABFE3CFBEEDE8
8B347E521D43405FDBD7D2CFF0EBC21B265818A06B8E6550F308712B1DF0
44B21B7D11D9B22792F1DE0997

The resulting COSE_Encrypt structure in a diagnostic format is shown in Figure 10.

COSE_Encrypt Example for ES-DH

96([
  / protected: / << {
    / alg / 1: 1 / A128GCM /
  } >>,
  / unprotected: / {
    / IV / 5: h'F14AAB9D81D51F7AD943FE87'
  },
  / payload: / null / detached ciphertext /,
  / recipients: / [
    [
      / protected: / << {
        / alg / 1: -29 / ECDH-ES + A128KW /
      } >>,
      / unprotected: / {
        / ephemeral key / -1: {
          / kty / 1: 2 / EC2 /,
          / crv / -1: 1 / P-256 /,
          / x / -2: h'73024F415AA51529A66CCEFD88F3F62A
                      734492FF45F6AD37FD2888E73EAF19DA',
          / y / -3: h'4005B48A6FD091AA6ABFE3CFBEEDE88B
                      347E521D43405FDBD7D2CFF0EBC21B26'
        }
      },
      / payload:
        / h'A06B8E6550F308712B1DF044B21B7D11D9B22792F1DE0997'
        / CEK encrypted with KEK /
    ]
  ]
])

The encrypted payload (with a line feed added) was:

758C4B7BBAE2C4C1D462423E0F0DC3164FFA7B85BB94D4BD6D7ED26AB32F
EB063385D4D3465927EC82CB5E198A59

AES-CTR
Introduction
AES-CTR is a non-AEAD cipher that provides confidentiality but lacks integrity protection. Unlike AES-CBC, AES-CTR uses an IV per AES operation, as shown in Figure 11. Hence, when an image is encrypted using AES-CTR-128 or AES-CTR-256, the IV MUST start with zero (0) and MUST be incremented by one for each 16-byte plaintext block within the entire slot.
Using the previous example with a slot size of 64 KiB, the sector size 4096 bytes and the AES plaintext block size of 16 byte requires IVs from 0 to 255 in the first sector and 16 * 256 IVs for the remaining sectors in the slot.
In our example, we assume the slot size of a specific flash controller on an IoT device is 64 KiB, the sector size 4096 bytes (4 KiB) and an AES plaintext block size of 16 bytes, the IVs range from 0 to 255 in the first sector, and 16 * 256 IVs are required for the remaining sectors in the slot.

AES-CTR Operation

IV1

IV2

k--

E

k--

E
|
|

P1
⊕

P2
⊕

C1

C2

         IV1            IV2
          |              |
          |              |
          |              |
      +-------+      +-------+
      |       |      |       |
      |       |      |       |
   k--|  E    |   k--|  E    |
      |       |      |       |
      +-------+      +-------+
          |              |
     P1---⊕        P2---⊕
          |              |
          |              |
          C1             C2

Note: The abbreviations shown in Figure 11 are described in Section 7.
Examples in this section use the following parameters:
- Algorithm for payload encryption: AES-CTR-128
  - k: h'261DE6165070FB8951EC5D7B92A065FE'
  - IV: h'DAE613B2E0DC55F4322BE38BDBA9DC68'
- Plaintext: "This is a real firmware image."
  - in hex: 546869732069732061207265616C206669726D7761726520696D6167652E
AES-KW + AES-CTR Example
This example uses the following parameters:
- Algorithm id for key wrap: A128KW
- KEK COSE_Key (Secret Key):
  - kty: Symmetric
  - k: 'aaaaaaaaaaaaaaaa'
  - kid: 'kid-1'
The COSE_Encrypt structure, in hex format, is (with a line break inserted):

D8608440A20139FFFD0550DAE613B2E0DC55F4322BE38BDBA9DC68F68183
40A2012204456B69642D315818CE34035CE5C2E2666E46D4C131FC561DD1
90A6D26CFA1990

The resulting COSE_Encrypt structure in a diagnostic format is shown in Figure 12.

COSE_Encrypt Example for AES Key Wrap

96([
  / protected: / h'',
  / unprotected: / {
    / alg / 1: -65534 / A128CTR /,
    / IV / 5: h'DAE613B2E0DC55F4322BE38BDBA9DC68'
  },
  / payload: / null / detached ciphertext /,
  / recipients: / [
    [
      / protected: / h'',
      / unprotected: / {
        / alg / 1: -3 / A128KW /,
        / kid / 4: 'kid-1'
      },
      / payload: /
        h'CE34035CE5C2E2666E46D4C131FC561DD190A6D26CFA1990'
        / CEK encrypted with KEK /
    ]
  ]
])

The encrypted payload (with a line feed added) was:

2BB8DB522AE978246CC775C3B0241BD4B0333FFDD2DB70C7EE7A4966E3B7

ECDH-ES+AES-KW + AES-CTR Example
This example uses the following parameters:
- Algorithm for content key distribution: ECDH-ES + A128KW
- KEK COSE_Key (Receiver's Private Key):
  - kty: EC2
  - crv: P-256
  - x: h'5886CD61DD875862E5AAA820E7A15274C968A9BC96048DDCACE32F50C3651BA3'
  - y: h'9EED8125E932CD60C0EAD3650D0A485CF726D378D1B016ED4298B2961E258F1B'
  - d: h'60FE6DD6D85D5740A5349B6F91267EEAC5BA81B8CB53EE249E4B4EB102C476B3'
  - kid: 'kid-2'
- KDF Context
  - Algorithm ID: -3 (A128KW)
  - SuppPubInfo
    - keyDataLength: 128
    - protected: { / alg / 1: -29 / ECDH-ES+A128KW / }
    - other: 'SUIT Payload Encryption'
The COSE_Encrypt structure, in hex format, is (with a line break inserted):

D8608440A20139FFFD0550DAE613B2E0DC55F4322BE38BDBA9DC68F68183
44A101381CA120A401022001215820EE0718F6B019C29CC611C18CEDE221
4066DDCEDC2F0DBEF873CB224C715C1174225820279F2A88E4AB9E2ED30C
0FCB69515B31B5D36725BFDB9AE02032ED4D5AB52CB85818E28B4502E4F5
151884A995405579006E9465C3E94E3E0808

The resulting COSE_Encrypt structure in a diagnostic format is shown in Figure 13.

COSE_Encrypt Example for ES-DH

=============== NOTE: '\' line wrapping per RFC 8792 ================

96([
  / protected: / h'',
  / unprotected: / {
    / alg / 1: -65534 / A128CTR /,
    / IV / 5: h'DAE613B2E0DC55F4322BE38BDBA9DC68'
  },
  / payload: / null / detached ciphertext /,
  / recipients: / [
    [
      / protected: / << {
        / alg / 1: -29 / ECDH-ES + A128KW /
      } >>,
      / unprotected: / {
        / ephemeral key / -1: {
          / kty / 1: 2 / EC2 /,
          / crv / -1: 1 / P-256 /,
          / x / -2: h'EE0718F6B019C29CC611C18CEDE22140
                      66DDCEDC2F0DBEF873CB224C715C1174',
          / y / -3: h'279F2A88E4AB9E2ED30C0FCB69515B31
                      B5D36725BFDB9AE02032ED4D5AB52CB8'
        }
      },
      / payload: / h'\
                    E28B4502E4F5151884A995405579006E9465C3E94E3E0808'
        / CEK encrypted with KEK /
    ]
  ]
])

The encrypted payload (with a line feed added) was:

2BB8DB522AE978246CC775C3B0241BD4B0333FFDD2DB70C7EE7A4966E3B7

AES-CBC
Introduction
AES-CBC is a non-AEAD cipher that provides confidentiality but but does not offer integrity protection. In AES-CBC, a single IV is used to encrypt the firmware belonging to a single sector, as individual AES blocks are chained together, as illustrated in Figure 14. The numbering of sectors in a slot start with zero (0) and increase by one with every sector till the end of the slot is reached. The IV follows this numbering.
For example, let us assume the slot size of a specific flash controller on an IoT device is 64 KiB, the sector size 4096 bytes (4 KiB) and AES-128-CBC uses an AES-block size of 128 bit (16 bytes). Hence, sector 0 needs 4096/16=256 AES-128-CBC operations using IV 0. If the firmware image occupies the entire slot, it will contain 16 sectors, corresponding to IVs ranging from 0 to 15.

AES-CBC Operation

P1

P2
|
|

IV
⊕
⊕

k--

E

k--

E

C1

C2

       P1              P2
        |              |
   IV---⊕    +--------⊕
        |     |        |
        |     |        |
    +-------+ |    +-------+
    |       | |    |       |
    |       | |    |       |
 k--|  E    | | k--|  E    |
    |       | |    |       |
    +-------+ |    +-------+
        |     |        |
        +-----+        |
        |              |
        |              |
        C1             C2

Note: The abbreviations shown in Figure 14 are described in Section 7.
Examples in this section use the following parameters:
- Algorithm for payload encryption: AES-CBC-128
  - k: h'627FCF0EA82C967D5ED8981EB325F303'
  - IV: h'93702C81590F845D9EC866CCAC767BD1'
- Plaintext: "This is a real firmware image."
  - in hex: 546869732069732061207265616C206669726D7761726520696D6167652E
AES-KW + AES-CBC Example
This example uses the following parameters:
- Algorithm id for key wrap: A128KW
- KEK COSE_Key (Secret Key):
  - kty: Symmetric
  - k: 'aaaaaaaaaaaaaaaa'
  - kid: 'kid-1'
The COSE_Encrypt structure, in hex format, is (with a line break inserted):

D8608440A20139FFFA055093702C81590F845D9EC866CCAC767BD1F68183
40A2012204456B69642D315818E198FF269626EC43299D33586FC7B2646B
13292261160422

The resulting COSE_Encrypt structure in a diagnostic format is shown in Figure 15.

COSE_Encrypt Example for AES Key Wrap

96([
  / protected: / h'',
  / unprotected: / {
    / alg / 1: -65531 / A128CBC /,
    / IV / 5: h'93702C81590F845D9EC866CCAC767BD1'
  },
  / payload: / null / detached ciphertext /,
  / recipients: / [
    [
      / protected: / h'',
      / unprotected: / {
        / alg / 1: -3 / A128KW /,
        / kid / 4: 'kid-1'
      },
      / payload: /
        h'E198FF269626EC43299D33586FC7B2646B13292261160422'
        / CEK encrypted with KEK /
    ]
  ]
])

The encrypted payload (with a line feed added) was:

9C09156CF4ACE0401086D98586E0B09FA5B5CF78F2BCCBF6C914DDB42BF0
E21E

ECDH-ES+AES-KW + AES-CBC Example
This example uses the following parameters:
- Algorithm for content key distribution: ECDH-ES + A128KW
- KEK COSE_Key (Receiver's Private Key):
  - kty: EC2
  - crv: P-256
  - x: h'5886CD61DD875862E5AAA820E7A15274C968A9BC96048DDCACE32F50C3651BA3'
  - y: h'9EED8125E932CD60C0EAD3650D0A485CF726D378D1B016ED4298B2961E258F1B'
  - d: h'60FE6DD6D85D5740A5349B6F91267EEAC5BA81B8CB53EE249E4B4EB102C476B3'
  - kid: 'kid-2'
- KDF Context
  - Algorithm ID: -3 (A128KW)
  - SuppPubInfo
    - keyDataLength: 128
    - protected: { / alg / 1: -29 / ECDH-ES+A128KW / }
    - other: 'SUIT Payload Encryption'
The COSE_Encrypt structure, in hex format, is (with a line break inserted):

D8608440A20139FFFA055093702C81590F845D9EC866CCAC767BD1F68183
44A101381CA120A40102200121582084C1768A1AFA92BAF27C3289A3FAF7
5E7511B27C654947BBD391E8A12EB8295B225820F32B0AECA4F8B6C51C15
5037B1FB726CAE3D0C77976864EF725DB2B30ABCE6F6581804928D52CD34
AC8CA0427CEED6D7C5D06A21B5F4F79CAA18

The resulting COSE_Encrypt structure in a diagnostic format is shown in Figure 16.

COSE_Encrypt Example for ES-DH

=============== NOTE: '\' line wrapping per RFC 8792 ================

96([
  / protected: / h'',
  / unprotected: / {
    / alg / 1: -65531 / A128CBC /,
    / IV / 5: h'93702C81590F845D9EC866CCAC767BD1'
  },
  / payload: / null / detached ciphertext /,
  / recipients: / [
    [
      / protected: / << {
        / alg / 1: -29 / ECDH-ES + A128KW /
      } >>,
      / unprotected: / {
        / ephemeral key / -1: {
          / kty / 1: 2 / EC2 /,
          / crv / -1: 1 / P-256 /,
          / x / -2: h'84C1768A1AFA92BAF27C3289A3FAF75E
                      7511B27C654947BBD391E8A12EB8295B',
          / y / -3: h'F32B0AECA4F8B6C51C155037B1FB726C
                      AE3D0C77976864EF725DB2B30ABCE6F6'
        }
      },
      / payload: / h'\
                    04928D52CD34AC8CA0427CEED6D7C5D06A21B5F4F79CAA18'
        / CEK encrypted with KEK /
    ]
  ]
])

The encrypted payload (with a line feed added) was:

9C09156CF4ACE0401086D98586E0B09FA5B5CF78F2BCCBF6C914DDB42BF0
E21E

Integrity Check on Encrypted and Decrypted Payloads
In addition to suit-condition-image-match (see Section 8.4.9.2 of [I-D.ietf-suit-manifest]), AEAD algorithms used for content encryption provides another way to validate the integrity of components. This section provides a guideline to construct secure but not redundant SUIT Manifest for encrypted payloads.
Validating Payload Integrity
This sub-section explains three ways to validate the integrity of payloads.
Image Match after Decryption
The suit-condition-image-match on the plaintext payload is used after decryption. An example command sequence is shown in Figure 17.

Check Image Match After Decryption

/ directive-set-component-index / 12, 1,
/ directive-override-parameters / 20, {
  / parameter-uri / 21: "http://example.com/encrypted.bin"
},
/ directive-fetch / 21, 15,

/ directive-set-component-index / 12, 0,
/ directive-override-parameters / 20, {
  / parameter-image-digest / 3: << {
    / algorithm-id: / -16 / SHA256 /,
    / digest-bytes: / h'3B1...92A' / digest of plaintext payload /
  } >>,
  / parameter-image-size / 14: 30 / size of plaintext payload /,
  / parameter-encryption-info / TBD19: h'369...50F',
  / parameter-source-component / 22: 1
},
/ directive-copy / 22, 15,
/ condition-image-match / 3, 15 / check decrypted payload integrity /,

RFC Editor's Note (TBD19): The value for the suit-parameter-encryption-info parameter is set to 19, as the proposed value.
Image Match before Decryption
The suit-condition-image-match can also be applied on encrypted payloads before decryption takes place. An example command sequence is shown in Figure 18.
This option mitigates battery exhaustion attacks discussed in Section 12.

Check Image Match Before Decryption

/ directive-set-component-index / 12, 1,
/ directive-override-parameters / 20, {
  / parameter-image-digest / 3: << {
    / algorithm-id: / -16 / SHA256 /,
    / digest-bytes: / h'8B4...D34' / digest of encrypted payload /
  } >>,
  / parameter-image-size / 14: 30 / size of encrypted payload /,
  / parameter-uri / 21: "http://example.com/encrypted.bin"
},
/ directive-fetch / 21, 15,
/ condition-image-match / 3, 15 / check decrypted payload integrity /,

/ directive-set-component-index / 12, 0,
/ directive-override-parameters / 20, {
  / parameter-encryption-info / TBD19: h'D86...1F0',
  / parameter-source-component / 22: 1
},
/ directive-copy / 22, 15,

RFC Editor's Note (TBD19): The value for the suit-parameter-encryption-info parameter is set to 19, as the proposed value.
Checking Authentication Tag while Decrypting
AEAD algorithms, such as AES-GCM and ChaCha20/Poly1305, verify the integrity of the encrypted concent.
Payload Integrity Validation
This subsection offers guidelines for validating the integrity of payloads within the SUIT manifest. The decision tree in Figure 19 illustrates the process for establishing payload integrity.

Decision Tree: Validating the Payload

Q1.

Payload

Delivery

in

Content

others

Q2.

Mitigate

Battery

Exhaustion

Attacks

No

Yes

Q3.

AEAD

cipher

Yes

No

NOT

AFTER

BEFORE

Required

Decryption

Decryption

+------------------------------------------------+
|              Q1. Payload Delivery              |
+-+--------------------------------------------+-+
  |                                            |
  | in Content                          others |
  |                                            v
  |             +--------------------------------+
  |             |      Q2. Mitigate Battery      |
  |             |       Exhaustion Attacks       |
  |             +-+----------------------------+-+
  |               |                            |
  |               | No                     Yes |
  |               v                            |
  |    +-----------------+                     |
  |    | Q3. AEAD cipher |                     |
  |    +-+-------------+-+                     |
  |      |             |                       |
  |      | Yes      No |                       |
  v      v             v                       v
 .+------+.      .-----+-----.      .----------+.
|   NOT    |    |    AFTER    |    |   BEFORE    |
| Required |    | Decryption  |    | Decryption  |
 '--------'      '-----------'      '-----------'

There are three conditions to consider:
- Q1. How does the recipient receive the encrypted payload? If the encrypted payload is part of an integrated payload, its integrity is already validated by the suit-authentication-wrapper, so no additional integrity check is necessary.
- Q2. Does the sender wish to mitigate battery exhaustion attacks? If so, the encrypted payload must be validated before decryption.
- Q3. Is the payload encrypted with an AEAD cipher? If yes, no additional integrity check is required, as the recipient verifies the payload's integrity during decryption. If no, integrity validation can occur either before or after decryption; however, validating integrity before decryption is RECOMMENDED.
Firmware Updates on IoT Devices with Flash Memory
Embedded devices come in many forms, and the market is both large and fragmented. As a result, some implementations and deployments may adopt firmware update procedures that differ from the descriptions provided here. On a positive note, the SUIT manifest accommodates various deployment scenarios, thanks to the "scripting" functionality offered by its commands.
This section specifically addresses firmware images on microcontrollers and does not pertain to generic software, configuration data, or machine learning models. The differences arise from two main aspects:
- Use of Flash Memory: Flash memory in microcontrollers is a type of non-volatile memory that erases data in larger units called blocks, pages, or sectors, and rewrites data at the byte level (often 4 bytes) or larger units. Furthermore, flash memory is segmented into different regions, storing the bootloader, various versions of firmware images (in designated slots), and configuration data. An example layout of a microcontroller flash area is illustrated in Figure 20.
- Microcontroller Design: Code on microcontrollers typically cannot be executed from arbitrary locations in flash memory without additional software development and design efforts. Consequently, developers often compile firmware so that the bootloader can execute code from a specific location in flash memory, commonly referred to as the "primary slot."
Once the encrypted firmware image is transferred to the device, it is usually stored in a dedicated area known as the "secondary slot."
During the next boot, the bootloader detects the new firmware image and begins decrypting it sector by sector, swapping it with the image located in the primary slot. This method of swapping the newly downloaded image with the previously valid one requires two slots, allowing for a rollback if the new firmware fails to boot, thereby enhancing the robustness of the firmware update process.
The swap occurs only after verifying the signature on the plaintext. It is important to note that the plaintext firmware image is available in the primary slot only after the swap is completed, unless "dummy decrypt" is used to compute the hash over the plaintext prior to executing the decryption during the swap. In this context, dummy decryption refers to decrypting the firmware image in the secondary slot sector by sector while computing a rolling hash over the resulting plaintext (also sector by sector) without performing the swap operation. Although performance optimizations, such as conveying hashes for each sector in the manifest rather than a hash of the entire firmware image, are possible, these optimizations are not detailed in this specification.
Without hardware-based, on-the-fly decryption, the image in the primary slot is available in cleartext and may need to be re-encrypted before copying it to the secondary slot. This step might be necessary if the secondary slot has different access permissions or is located in off-chip flash memory, which tends to be more vulnerable to physical attacks.

Example Flash Area Layout

Bootloader

Primary

Slot

(sector

1)
..................................................

(sector

2)
..................................................

(sector

3)
..................................................

(sector

4)

Secondary

Slot

(sector

1)
..................................................

(sector

2)
..................................................

(sector

3)
..................................................

(sector

4)

Swap

Area

Configuration

Data

+--------------------------------------------------+
| Bootloader                                       |
+--------------------------------------------------+
| Primary Slot                                     |
|                                        (sector 1)|
|..................................................|
|                                                  |
|                                        (sector 2)|
|..................................................|
|                                                  |
|                                        (sector 3)|
|..................................................|
|                                                  |
|                                        (sector 4)|
+--------------------------------------------------+
| Secondary Slot                                   |
|                                        (sector 1)|
|..................................................|
|                                                  |
|                                        (sector 2)|
|..................................................|
|                                                  |
|                                        (sector 3)|
|..................................................|
|                                                  |
|                                        (sector 4)|
+--------------------------------------------------+
| Swap Area                                        |
|                                                  |
+--------------------------------------------------+
| Configuration Data                               |
+--------------------------------------------------+

The ability to resume an interrupted firmware update is often essential for unattended devices, including low-end, constrained IoT devices. To meet this requirement, a firmware image must be divided into sectors, with each sector encrypted individually using a cipher that does not increase the size of the resulting ciphertext (i.e., by avoiding the addition of an authentication tag after each encrypted block).
If an update is aborted while the bootloader is decrypting the newly received image and swapping the sectors, the bootloader can restart from where it left off. This technique enhances robustness and performance.
For this purpose, ciphers without integrity protection are employed to encrypt the firmware image. It is crucial that integrity protection for the firmware image is provided, and the suit-parameter-image-digest, defined in Section 8.4.8.6 of [I-D.ietf-suit-manifest], MUST be utilized.
[RFC9459] specifies the AES Counter (AES-CTR) mode and AES Cipher Block Chaining (AES-CBC) ciphers, both of which do not provide integrity protection. These ciphers are suitable for firmware encryption in IoT devices. However, for many other scenarios involving software packages, configuration information, or personalization data, the use of AEAD ciphers is RECOMMENDED.
The following subsections offer additional information on the selection of initialization vectors (IVs) for use with AES-CBC and AES-CTR in the context of firmware encryption. An IV MUST NOT be reused when the same key is employed. In this application, the IVs are not random but are instead based on the slot/sector combination in flash memory. The discussion assumes that the block size of AES is significantly smaller than the sector size. Typically, flash memory sectors are measured in KiB, necessitating the decryption of multiple AES blocks to complete the decryption of an entire sector.
Complete Examples
The following manifests illustrate how to deliver an encrypted payload along with its encryption information to devices.
In the AES-KW examples, HMAC-256 MACs are included, utilizing the following secret key:

  'aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa'
  (616161... in hex, and its length is 32)

ES-DH examples are signed using the following ECDSA secp256r1 key:

-----BEGIN PRIVATE KEY-----
MIGHAgEAMBMGByqGSM49AgEGCCqGSM49AwEHBG0wawIBAQQgApZYjZCUGLM50VBC
CjYStX+09jGmnyJPrpDLTz/hiXOhRANCAASEloEarguqq9JhVxie7NomvqqL8Rtv
P+bitWWchdvArTsfKktsCYExwKNtrNHXi9OB3N+wnAUtszmR23M4tKiW
-----END PRIVATE KEY-----

The corresponding public key can be used to verify these examples:

-----BEGIN PUBLIC KEY-----
MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEhJaBGq4LqqvSYVcYnuzaJr6qi/Eb
bz/m4rVlnIXbwK07HypLbAmBMcCjbazR14vTgdzfsJwFLbM5kdtzOLSolg==
-----END PUBLIC KEY-----

Each example uses SHA-256 as the digest function.
AES Key Wrap Example with Write Directive
The following SUIT manifest instructs a parser to authenticate the manifest using COSE_Mac0 with HMAC256. It also directs the parser to write and decrypt the encrypted payload into a component using the suit-directive-write directive.
The SUIT manifest in diagnostic notation (with line breaks added for clarity) is displayed below:

=============== NOTE: '\' line wrapping per RFC 8792 ================

/  1/ / SUIT_Envelope_Tagged / 107({
/  2/   / authentication-wrapper / 2: << [
/  3/     << [
/  4/       / digest-algorithm-id: / -16 / SHA256 /,
/  5/       / digest-bytes: / h'037A5C325CE14078A0AADF007428EAC6
/  6/                           59361AD9402A732410BDA542FAE94E2C'
/  7/     ] >>,
/  8/     << / COSE_Mac0_Tagged / 17([
/  9/       / protected: / << {
/ 10/         / algorithm-id / 1: 5 / HMAC256 /
/ 11/       } >>,
/ 12/       / unprotected: / {},
/ 13/       / payload: / null,
/ 14/       / tag: / h'8D92599011C451A4C5FB69709FA6CA6C
/ 15/                  0F846D692BDBB3F624EC91F82F9F620A'
/ 16/     ]) >>
/ 17/   ] >>,
/ 18/   / manifest / 3: << {
/ 19/     / manifest-version / 1: 1,
/ 20/     / manifest-sequence-number / 2: 1,
/ 21/     / common / 3: << {
/ 22/       / components / 2: [
/ 23/         ['plaintext-firmware']
/ 24/       ]
/ 25/     } >>,
/ 26/     / install / 20: << [
/ 27/       / fetch encrypted firmware /
/ 28/       / directive-override-parameters / 20, {
/ 29/         / parameter-content / 18:
/ 30/           h'758C4B7BBAE2C4C1D462423E0F0DC3164FFA7B85BB94D4
/ 31/             BD6D7ED26AB32FEB063385D4D3465927EC82CB5E198A59',
/ 32/         / parameter-encryption-info / 19: << 96([
/ 33/           / protected: / << {
/ 34/             / alg / 1: 1 / A128GCM /
/ 35/           } >>,
/ 36/           / unprotected: / {
/ 37/             / IV / 5: h'F14AAB9D81D51F7AD943FE87'
/ 38/           },
/ 39/           / payload: / null / detached ciphertext /,
/ 40/           / recipients: / [
/ 41/             [
/ 42/               / protected: / h'',
/ 43/               / unprotected: / {
/ 44/                 / alg / 1: -3 / A128KW /,
/ 45/                 / kid / 4: 'kid-1'
/ 46/               },
/ 47/               / payload: /
/ 48/               h'\
                    75603FFC9518D794713C8CA8A115A7FB32565A6D59534D62'
/ 49/                 / CEK encrypted with KEK /
/ 50/             ]
/ 51/           ]
/ 52/         ]) >>
/ 53/       },
/ 54/
/ 55/       / decrypt encrypted firmware /
/ 56/       / directive-write / 18, 15
/ 57/         / consumes the SUIT_Encryption_Info above /
/ 58/     ] >>
/ 59/   } >>
/ 60/ })

In hex format, the SUIT manifest is:

D86BA2025853825824822F5820037A5C325CE14078A0AADF007428EAC659
361AD9402A732410BDA542FAE94E2C582AD18443A10105A0F658208D9259
9011C451A4C5FB69709FA6CA6C0F846D692BDBB3F624EC91F82F9F620A03
5898A4010102010357A102818152706C61696E746578742D6669726D7761
72651458778414A212582E758C4B7BBAE2C4C1D462423E0F0DC3164FFA7B
85BB94D4BD6D7ED26AB32FEB063385D4D3465927EC82CB5E198A5913583E
D8608443A10101A1054CF14AAB9D81D51F7AD943FE87F6818340A2012204
456B69642D31581875603FFC9518D794713C8CA8A115A7FB32565A6D5953
4D62120F

AES Key Wrap Example with Fetch + Copy Directives
The following SUIT manifest instructs a parser to fetch and store the encrypted payload. Subsequently, the payload is decrypted and copied into another component using the suit-directive-copy directive. This approach is particularly effective for constrained devices with execute-in-place (XIP) flash memory.
The SUIT manifest in diagnostic notation (with line breaks added for clarity) is displayed below:

=============== NOTE: '\' line wrapping per RFC 8792 ================

/  1/ / SUIT_Envelope_Tagged / 107({
/  2/   / authentication-wrapper / 2: << [
/  3/     << [
/  4/       / digest-algorithm-id: / -16 / SHA256 /,
/  5/       / digest-bytes: / h'8814BC46089ACA6A863A7BA8393F9747
/  6/                           589940EFA40641335EF86155598F06C3'
/  7/     ] >>,
/  8/     << / COSE_Mac0_Tagged / 17([
/  9/       / protected: / << {
/ 10/         / algorithm-id / 1: 5 / HMAC256 /
/ 11/       } >>,
/ 12/       / unprotected: / {},
/ 13/       / payload: / null,
/ 14/       / tag: / h'B68572F6F0494FEAF390CE44B462F2A7
/ 15/                  BDF73EF5DFE9FB8E12585A12F8F641AD'
/ 16/     ]) >>
/ 17/   ] >>,
/ 18/   / manifest / 3: << {
/ 19/     / manifest-version / 1: 1,
/ 20/     / manifest-sequence-number / 2: 1,
/ 21/     / common / 3: << {
/ 22/       / components / 2: [
/ 23/         ['plaintext-firmware'],
/ 24/         ['encrypted-firmware']
/ 25/       ]
/ 26/     } >>,
/ 27/     / install / 20: << [
/ 28/       / fetch encrypted firmware /
/ 29/       / directive-set-component-index / 12, 1
/ 30/         / ['encrypted-firmware'] /,
/ 31/       / directive-override-parameters / 20, {
/ 32/         / parameter-image-size / 14: 46,
/ 33/         / parameter-uri / 21:
/ 34/           "https://example.com/encrypted-firmware"
/ 35/       },
/ 36/       / directive-fetch / 21, 15,
/ 37/
/ 38/       / decrypt encrypted firmware /
/ 39/       / directive-set-component-index / 12, 0
/ 40/         / ['plaintext-firmware'] /,
/ 41/       / directive-override-parameters / 20, {
/ 42/         / parameter-encryption-info / 19: << 96([
/ 43/           / protected: / << {
/ 44/             / alg / 1: 1 / A128GCM /
/ 45/           } >>,
/ 46/           / unprotected: / {
/ 47/             / IV / 5: h'F14AAB9D81D51F7AD943FE87'
/ 48/           },
/ 49/           / payload: / null / detached ciphertext /,
/ 50/           / recipients: / [
/ 51/             [
/ 52/               / protected: / h'',
/ 53/               / unprotected: / {
/ 54/                 / alg / 1: -3 / A128KW /,
/ 55/                 / kid / 4: 'kid-1'
/ 56/               },
/ 57/               / payload: /
/ 58/               h'\
                    75603FFC9518D794713C8CA8A115A7FB32565A6D59534D62'
/ 59/                 / CEK encrypted with KEK /
/ 60/             ]
/ 61/           ]
/ 62/         ]) >>,
/ 63/         / parameter-source-component / 22: 1
/ 64/           / ['encrypted-firmware'] /
/ 65/       },
/ 66/       / directive-copy / 22, 15
/ 67/         / consumes the SUIT_Encryption_Info above /
/ 68/     ] >>
/ 69/   } >>
/ 70/ })

The default storage area is defined by the component identifier (see Section 8.4.5.1 of [I-D.ietf-suit-manifest]). In this example, the component identifier for component #0 is ['plaintext-firmware'] and the file path "/plaintext-firmware" is the expected location.
While parsing the manifest, the behavior of SUIT manifest processor would be
- [L2-L17] authenticates the manifest part on [L18-L68]
- [L22-L25] gets two component identifiers; ['plaintext-firmware'] for component #0, and ['encrypted-firmware'] for component # 1 respectively
- [L29] sets current component index # 1 (the lasting directives target ['encrypted-firmware'])
- [L33-L34] sets source uri parameter "https://example.com/encrypted-firmware"
- [L36] fetches content from source uri into ['encrypted-firmware']
- [L39] sets current component index # 0 (the lasting directives target ['plaintext-firmware'])
- [L42-L62] sets SUIT encryption info parameter
- [L63-L64] sets source component index parameter # 1
- [L66] decrypts component # 1 (source component index) and stores the result into component # 0 (current component index)
The following attributes and features from the SUIT manifest specification are used:
Attribute Name | Abb. | Manifest Ref.
component identifier | CI | Sec. 8.4.5.1
(destination) component index | dst-CI | Sec. 8.4.10.1
(destination) component slot OPTIONAL param | dst-CS | Sec. 8.4.8.8
(source) uri OPTIONAL parameter | src-URI | Sec. 8.4.8.10
source component index OPTIONAL parameter | src-CI | Sec. 8.4.8.11
The resulting state of SUIT manifest processor is shown in the following table:
Abbreviation | Plaintext | Ciphertext
CI | ['plaintext-firmware'] | ['encrypted-firmware']
dst-CI | 0 | 1
dst-CS | N/A | N/A
src-URI | N/A | "https://example.com/encrypted-firmware"
src-CI | 1 | N/A
In hex format, the SUIT manifest shown above is:

D86BA2025853825824822F58208814BC46089ACA6A863A7BA8393F974758
9940EFA40641335EF86155598F06C3582AD18443A10105A0F65820B68572
F6F0494FEAF390CE44B462F2A7BDF73EF5DFE9FB8E12585A12F8F641AD03
58B2A40101020103582BA102828152706C61696E746578742D6669726D77
6172658152656E637279707465642D6669726D7761726514587C8C0C0114
A20E182E15782668747470733A2F2F6578616D706C652E636F6D2F656E63
7279707465642D6669726D77617265150F0C0014A213583ED8608443A101
01A1054CF14AAB9D81D51F7AD943FE87F6818340A2012204456B69642D31
581875603FFC9518D794713C8CA8A115A7FB32565A6D59534D621601160F

The previous example does not utilize storage slots. However, it is possible to implement this functionality for devices that support slots in flash memory. In the enhanced example below, we reference the slots using [h'00'] and [h'01']. In this context, the component identifier [h'00'] designates component slot #0.

=============== NOTE: '\' line wrapping per RFC 8792 ================

/  1/ / SUIT_Envelope_Tagged / 107({
/  2/   / authentication-wrapper / 2: << [
/  3/     << [
/  4/       / digest-algorithm-id: / -16 / SHA256 /,
/  5/       / digest-bytes: / h'A6D2C13A0DEFD57A09FA65C24206A9A8
/  6/                           747261E6EA017532B3DAB0419C42A2FC'
/  7/     ] >>,
/  8/     << / COSE_Mac0_Tagged / 17([
/  9/       / protected: / << {
/ 10/         / algorithm-id / 1: 5 / HMAC256 /
/ 11/       } >>,
/ 12/       / unprotected: / {},
/ 13/       / payload: / null,
/ 14/       / tag: / h'DB350AC9603B0BBA3895B85019699363
/ 15/                  3F314A9066634B31BF62E596FD870434'
/ 16/     ]) >>
/ 17/   ] >>,
/ 18/   / manifest / 3: << {
/ 19/     / manifest-version / 1: 1,
/ 20/     / manifest-sequence-number / 2: 1,
/ 21/     / common / 3: << {
/ 22/       / components / 2: [
/ 23/         [h'00'],
/ 24/         [h'01']
/ 25/       ]
/ 26/     } >>,
/ 27/     / install / 20: << [
/ 28/       / fetch encrypted firmware /
/ 29/       / directive-set-component-index / 12, 1 / [h'01'] /,
/ 30/       / directive-override-parameters / 20, {
/ 31/         / parameter-image-size / 14: 46,
/ 32/         / parameter-uri / 21:
/ 33/           "https://example.com/encrypted-firmware"
/ 34/       },
/ 35/       / directive-fetch / 21, 15,
/ 36/
/ 37/       / decrypt encrypted firmware /
/ 38/       / directive-set-component-index / 12, 0 / ['00'] /,
/ 39/       / directive-override-parameters / 20, {
/ 40/         / parameter-encryption-info / 19: << 96([
/ 41/           / protected: / << {
/ 42/             / alg / 1: 1 / A128GCM /
/ 43/           } >>,
/ 44/           / unprotected: / {
/ 45/             / IV / 5: h'F14AAB9D81D51F7AD943FE87'
/ 46/           },
/ 47/           / payload: / null / detached ciphertext /,
/ 48/           / recipients: / [
/ 49/             [
/ 50/               / protected: / h'',
/ 51/               / unprotected: / {
/ 52/                 / alg / 1: -3 / A128KW /,
/ 53/                 / kid / 4: 'kid-1'
/ 54/               },
/ 55/               / payload: /
/ 56/               h'\
                    75603FFC9518D794713C8CA8A115A7FB32565A6D59534D62'
/ 57/                 / CEK encrypted with KEK /
/ 58/             ]
/ 59/           ]
/ 60/         ]) >>,
/ 61/         / parameter-source-component / 22: 1 / [h'01'] /
/ 62/       },
/ 63/       / directive-copy / 22, 15
/ 64/         / consumes the SUIT_Encryption_Info above /
/ 65/     ] >>
/ 66/   } >>
/ 67/ })

ES-DH Example with Write + Copy Directives
The following SUIT manifest instructs a parser to authenticate the manifest using COSE_Sign1 with ES256. It also directs the parser to write and decrypt the encrypted payload into a component via the suit-directive-write directive.
The SUIT manifest in diagnostic notation (formatted with line breaks for clarity) is presented below:

=============== NOTE: '\' line wrapping per RFC 8792 ================

/  1/ / SUIT_Envelope_Tagged / 107({
/  2/   / authentication-wrapper / 2: << [
/  3/     << [
/  4/       / digest-algorithm-id: / -16 / SHA256 /,
/  5/       / digest-bytes: / h'1DB69EF1477E9942815F29F78E09957B
/  6/                           26B4ADD03902BDB3D1EDF3DA2075F593'
/  7/     ] >>,
/  8/     << / COSE_Sign1_Tagged / 18([
/  9/       / protected: / << {
/ 10/         / algorithm-id / 1: -7 / ES256 /
/ 11/       } >>,
/ 12/       / unprotected: / {},
/ 13/       / payload: / null,
/ 14/       / signature: / h'CB4EADA6BEC17EEB22EB836FB2BF9136
/ 15/                        A6EF733C11DAC955F543BBDCAA373B85
/ 16/                        9321BC77969917E4C70F049527607F4C
/ 17/                        32752D53E01346E96BFF4880B437DF64'
/ 18/     ]) >>
/ 19/   ] >>,
/ 20/   / manifest / 3: << {
/ 21/     / manifest-version / 1: 1,
/ 22/     / manifest-sequence-number / 2: 1,
/ 23/     / common / 3: << {
/ 24/       / components / 2: [
/ 25/         ['decrypted-firmware']
/ 26/       ]
/ 27/     } >>,
/ 28/     / install / 20: << [
/ 29/       / directive-set-component-index / 12, 0
/ 30/         / ['plaintext-firmware'] /,
/ 31/       / directive-override-parameters / 20, {
/ 32/         / parameter-content / 18:
/ 33/           h'758C4B7BBAE2C4C1D462423E0F0DC3164FFA7B85BB94D4
/ 34/             BD6D7ED26AB32FEB063385D4D3465927EC82CB5E198A59',
/ 35/         / parameter-encryption-info / 19: << 96([
/ 36/           / protected: / << {
/ 37/             / alg / 1: 1 / A128GCM /
/ 38/           } >>,
/ 39/           / unprotected: / {
/ 40/             / IV / 5: h'F14AAB9D81D51F7AD943FE87'
/ 41/           },
/ 42/           / payload: / null / detached ciphertext /,
/ 43/           / recipients: / [
/ 44/             [
/ 45/               / protected: / << {
/ 46/                 / alg / 1: -29 / ECDH-ES + A128KW /
/ 47/               } >>,
/ 48/               / unprotected: / {
/ 49/                 / ephemeral key / -1: {
/ 50/                   / kty / 1: 2 / EC2 /,
/ 51/                   / crv / -1: 1 / P-256 /,
/ 52/                   / x / -2: h'73024F415AA51529A66CCEFD88F3F62A
/ 53/                               734492FF45F6AD37FD2888E73EAF19DA\
                                                                   ',
/ 54/                   / y / -3: h'4005B48A6FD091AA6ABFE3CFBEEDE88B
/ 55/                               347E521D43405FDBD7D2CFF0EBC21B26'
/ 56/                 },
/ 57/                 / kid / 4: 'kid-2'
/ 58/               },
/ 59/               / payload: /
/ 60/               h'\
                    A06B8E6550F308712B1DF044B21B7D11D9B22792F1DE0997'
/ 61/                 / CEK encrypted with KEK /
/ 62/             ]
/ 63/           ]
/ 64/         ]) >>
/ 65/       },
/ 66/       / directive-write / 18, 15
/ 67/         / consumes the SUIT_Encryption_Info above /
/ 68/     ] >>
/ 69/   } >>
/ 70/ })

In hex format, the SUIT manifest is this:

D86BA2025873825824822F58201DB69EF1477E9942815F29F78E09957B26
B4ADD03902BDB3D1EDF3DA2075F593584AD28443A10126A0F65840CB4EAD
A6BEC17EEB22EB836FB2BF9136A6EF733C11DAC955F543BBDCAA373B8593
21BC77969917E4C70F049527607F4C32752D53E01346E96BFF4880B437DF
640358E8A4010102010357A1028181526465637279707465642D6669726D
776172651458C7860C0014A212582E758C4B7BBAE2C4C1D462423E0F0DC3
164FFA7B85BB94D4BD6D7ED26AB32FEB063385D4D3465927EC82CB5E198A
5913588CD8608443A10101A1054CF14AAB9D81D51F7AD943FE87F6818344
A101381CA220A40102200121582073024F415AA51529A66CCEFD88F3F62A
734492FF45F6AD37FD2888E73EAF19DA2258204005B48A6FD091AA6ABFE3
CFBEEDE88B347E521D43405FDBD7D2CFF0EBC21B2604456B69642D325818
A06B8E6550F308712B1DF044B21B7D11D9B22792F1DE0997120F

ES-DH Example with Dependency
The following SUIT manifest requests a parser to resolve the dependency.
The dependent manifest is signed with another key:

-----BEGIN EC PRIVATE KEY-----
MHcCAQEEIIQa67e56m8CYL5zVaJFiLl30j0qxb8ray2DeUMqH+qYoAoGCCqGSM49
AwEHoUQDQgAEDpCKqPBm2x8ITgw2UsY5Ur2Z8qW9si+eATZ6rQOrpot32hvYrE8M
tJC6IQZIv3mrFk1JrTVR1x0xSydJ7kLSmg==
-----END EC PRIVATE KEY-----

The dependency manifest is embedded as an integrated-dependency and referred to by the "#dependency-manifest" URI.
The SUIT manifest in diagnostic notation (with line breaks added for readability) is shown here:

=============== NOTE: '\' line wrapping per RFC 8792 ================

/  1/ / SUIT_Envelope_Tagged / 107({
/  2/   / authentication-wrapper / 2: << [
/  3/     << [
/  4/       / digest-algorithm-id: / -16 / SHA256 /,
/  5/       / digest-bytes: / h'A00CB6C85515C1EF471B50B542FACDD8
/  6/                           8B71B3C7EA2A43DE13D32C4A99056FE9'
/  7/     ] >>,
/  8/     << / COSE_Sign1_Tagged / 18([
/  9/       / protected: / << {
/ 10/         / algorithm-id / 1: -7 / ES256 /
/ 11/       } >>,
/ 12/       / unprotected: / {},
/ 13/       / payload: / null,
/ 14/       / signature: / h'421B30FE76DA848616D72FC1115EA610
/ 15/                        5578CB95DF9C6BEAD931105C9D555CF8
/ 16/                        CD38C8FD68ACE43445D8D2CAE6391A99
/ 17/                        5A212487D92F8DAD789F65511AC61778'
/ 18/     ]) >>
/ 19/   ] >>,
/ 20/   / manifest / 3: << {
/ 21/     / manifest-version / 1: 1,
/ 22/     / manifest-sequence-number / 2: 1,
/ 23/     / common / 3: << {
/ 24/       / dependencies / 1: {
/ 25/         / component-index / 1: {
/ 26/           / dependency-prefix / 1: [
/ 27/              'dependency-manifest.suit'
/ 28/           ]
/ 29/         }
/ 30/       },
/ 31/       / components / 2: [
/ 32/         ['decrypted-firmware']
/ 33/       ]
/ 34/     } >>,
/ 35/     / manifest-component-id / 5: [
/ 36/       'dependent-manifest.suit'
/ 37/     ],
/ 38/     / install / 20: << [
/ 39/       / NOTE: set SUIT_Encryption_Info /
/ 40/       / directive-set-component-index / 12, 0
/ 41/         / ['decrypted-firmware'] /,
/ 42/       / directive-override-parameters / 20, {
/ 43/         / parameter-content / 18:
/ 44/           h'758C4B7BBAE2C4C1D462423E0F0DC3164FFA7B85BB94D4
/ 45/             BD6D7ED26AB32FEB063385D4D3465927EC82CB5E198A59',
/ 46/         / parameter-encryption-info / 19: << 96([
/ 47/           / protected: / << {
/ 48/             / alg / 1: 1 / A128GCM /
/ 49/           } >>,
/ 50/           / unprotected: / {
/ 51/             / IV / 5: h'F14AAB9D81D51F7AD943FE87'
/ 52/           },
/ 53/           / payload: / null / detached ciphertext /,
/ 54/           / recipients: / [
/ 55/             [
/ 56/               / protected: / << {
/ 57/                 / alg / 1: -29 / ECDH-ES + A128KW /
/ 58/               } >>,
/ 59/               / unprotected: / {
/ 60/                 / ephemeral key / -1: {
/ 61/                   / kty / 1: 2 / EC2 /,
/ 62/                   / crv / -1: 1 / P-256 /,
/ 63/                   / x / -2: h'73024F415AA51529A66CCEFD88F3F62A
/ 64/                               734492FF45F6AD37FD2888E73EAF19DA\
                                                                   ',
/ 65/                   / y / -3: h'4005B48A6FD091AA6ABFE3CFBEEDE88B
/ 66/                               347E521D43405FDBD7D2CFF0EBC21B26'
/ 67/                 },
/ 68/                 / kid / 4: 'kid-2'
/ 69/               },
/ 70/               / payload: /
/ 71/               h'\
                    A06B8E6550F308712B1DF044B21B7D11D9B22792F1DE0997'
/ 72/                 / CEK encrypted with KEK /
/ 73/             ]
/ 74/           ]
/ 75/         ]) >>
/ 76/       },
/ 77/
/ 78/       / NOTE: call dependency-manifest /
/ 79/       / directive-set-component-index / 12, 1
/ 80/         / ['dependenty-manifest.suit'] /,
/ 81/       / directive-override-parameters / 20, {
/ 82/         / parameter-image-digest / 3: << [
/ 83/           / algorithm-id / -16 / SHA256 /,
/ 84/           / digest-bytes / h'4B15C90FBD776A820E7E733DF040D90B
/ 85/                              356B5C75982ECAECE8673818179BDF16'
/ 86/         ] >>,
/ 87/         / parameter-image-size / 14: 247,
/ 88/         / parameter-uri / 21: "#dependency-manifest"
/ 89/       },
/ 90/       / directive-fetch / 21, 15,
/ 91/       / condition-dependency-integrity / 7, 15,
/ 92/       / directive-process-dependency / 11, 15
/ 93/     ] >>
/ 94/   } >>,
/ 95/   "#dependency-manifest": <<
/ 96/     / SUIT_Envelope_Tagged / 107({
/ 97/       / authentication-wrapper / 2: << [
/ 98/         << [
/ 99/           / digest-algorithm-id: / -16 / SHA256 /,
/100/           / digest-bytes: / h'4B15C90FBD776A820E7E733DF040D90B
/101/                               356B5C75982ECAECE8673818179BDF16'
/102/         ] >>,
/103/         << / COSE_Sign1_Tagged / 18([
/104/           / protected: / << {
/105/             / algorithm-id / 1: -7 / ES256 /
/106/           } >>,
/107/           / unprotected: / {},
/108/           / payload: / null,
/109/           / signature: / h'2B1B9C4E44E52863A78F73DA2A935823
/110/                            B28AEAE6A85CADAC4C4E3AABAAD56CBC
/111/                            E5A47D288F86B54D0186657E972E748B
/112/                            48CDB1D420FBAC1285DCC978382F62CC'
/113/         ]) >>
/114/       ] >>,
/115/       / manifest / 3: << {
/116/         / manifest-version / 1: 1,
/117/         / manifest-sequence-number / 2: 1,
/118/         / common / 3: << {
/119/           / components / 2: [
/120/             ['decrypted-firmware']
/121/           ],
/122/           / shared-sequence / 4: << [
/123/             / directive-set-componnt-index / 12, 0
/124/               / ['decrypted-firmware'] /,
/125/             / directive-override-parameters / 20, {
/126/               / parameter-image-digest / 3: << [
/127/                 / algorithm-id / -16 / SHA256 /,
/128/                 / digest-bytes /
/129/                   h'36921488FE6680712F734E11F58D87EE
/130/                     B66D4B21A8A1AD3441060814DA16D50F'
/131/               ] >>,
/132/               / parameter-image-size / 14: 30
/133/             }
/134/           ] >>
/135/         } >>,
/136/         / manifest-component-id / 5: [
/137/           'dependency-manifest.suit'
/138/         ],
/139/         / validate / 7: << [
/140/           / condition-image-match / 3, 15
/141/         ] >>,
/142/         / install / 20: << [
/143/           / directive-set-component-index / 12, 0
/144/             / ['decrypted-firmware'] /,
/145/           / directive-write / 18, 15
/146/             / consumes the SUIT_Encryption_Info in dependent /,
/147/           / condition-image-match / 3, 15
/148/             / check the integrity of the decrypted payload /
/149/         ] >>
/150/       } >>
/151/     })
/152/   >>
/153/ })

In hex format, the SUIT manifest is this:

D86BA3025873825824822F5820A00CB6C85515C1EF471B50B542FACDD88B
71B3C7EA2A43DE13D32C4A99056FE9584AD28443A10126A0F65840421B30
FE76DA848616D72FC1115EA6105578CB95DF9C6BEAD931105C9D555CF8CD
38C8FD68ACE43445D8D2CAE6391A995A212487D92F8DAD789F65511AC617
780359016CA501010201035837A201A101A101815818646570656E64656E
63792D6D616E69666573742E73756974028181526465637279707465642D
6669726D77617265058157646570656E64656E742D6D616E69666573742E
737569741459010F8E0C0014A212582E758C4B7BBAE2C4C1D462423E0F0D
C3164FFA7B85BB94D4BD6D7ED26AB32FEB063385D4D3465927EC82CB5E19
8A5913588CD8608443A10101A1054CF14AAB9D81D51F7AD943FE87F68183
44A101381CA220A40102200121582073024F415AA51529A66CCEFD88F3F6
2A734492FF45F6AD37FD2888E73EAF19DA2258204005B48A6FD091AA6ABF
E3CFBEEDE88B347E521D43405FDBD7D2CFF0EBC21B2604456B69642D3258
18A06B8E6550F308712B1DF044B21B7D11D9B22792F1DE09970C0114A303
5824822F58204B15C90FBD776A820E7E733DF040D90B356B5C75982ECAEC
E8673818179BDF160E18F7157423646570656E64656E63792D6D616E6966
657374150F070F0B0F7423646570656E64656E63792D6D616E6966657374
58F7D86BA2025873825824822F58204B15C90FBD776A820E7E733DF040D9
0B356B5C75982ECAECE8673818179BDF16584AD28443A10126A0F658402B
1B9C4E44E52863A78F73DA2A935823B28AEAE6A85CADAC4C4E3AABAAD56C
BCE5A47D288F86B54D0186657E972E748B48CDB1D420FBAC1285DCC97838
2F62CC03587BA601010201035849A2028181526465637279707465642D66
69726D7761726504582F840C0014A2035824822F582036921488FE668071
2F734E11F58D87EEB66D4B21A8A1AD3441060814DA16D50F0E181E058158
18646570656E64656E63792D6D616E69666573742E73756974074382030F
1447860C00120F030F

Operational Considerations
The algorithms outlined in this document assume that the party responsible for payload encryption:
- shares a key-encryption key (KEK) with the recipient (for use with the AES Key Wrap scheme), or
- possesses the recipient's public key (for use with ES-DH).
Both scenarios necessitate initial communication to distribute these keys among the involved parties. This interaction can be facilitated by a device management protocol, as described in [RFC9019], or may occur earlier in the device lifecycle, such as during manufacturing or commissioning. In addition to the keying material, key identifiers and algorithm information must also be provisioned. This specification does not impose any requirements on the structure of the key identifier.
In certain situations, third-party companies analyze binaries for known security vulnerabilities. However, encrypted payloads hinder this type of analysis. Consequently, these third-party companies must either be granted access to the plaintext binary before encryption or be authorized recipients of the encrypted payloads. In either case, it is essential to explicitly consider these third parties in the software supply chain when binary analysis is required.
Security Considerations
This entire document focuses on security.
It is considered best security practice to use different keys for different purposes. For instance, the key-encryption key (KEK) utilized in an AES-KW-based content key distribution method for encryption should be distinct from the long-term symmetric key employed for authentication in a communication security protocol.
To further minimize the attack surface, it may be advantageous to use different long-term keys for encrypting various types of payloads. For example, KEK_1 could be used with an AES-KW content key distribution method to encrypt a firmware image, while KEK_2 would encrypt configuration data.
A significant portion of this document addresses content key distribution, employing two methods: AES Key Wrap (AES-KW) and Ephemeral-Static Diffie-Hellman (ES-DH). The table below summarizes the main properties related to their deployment:
Number ofLong-TermKeys
Number ofContentEncryptionKeys (CEKs)
Use Case
Recommended?
Same key
for all
devices
Single
CEK per
payload
shared
with all
devies
Legacy
Usage
No, bad
practice
One key
per device
Single
CEK per
payload
shared
with all
devies
Efficient
Payload
Distribution
Yes
One Key
per device
One CEK
per payload
encryption
transaction
per device
Point-to-
Point Payload
Distribution
Yes
The use of firmware encryption in IoT devices introduces the risk of a battery exhaustion attack. This attack exploits the high energy cost of flash memory operations. To execute this attack, the adversary must be able to swap detached payloads and trick the device into processing an incorrect payload. Payload swapping is feasible only if there is no communication security protocol between the device and the distribution system or if the distribution system itself has been compromised.
While the security features provided by the manifest can detect this attack and prevent the device from booting with an incorrectly supplied payload, the energy-intensive flash operations will have already occurred. As a result, these operations can diminish the lifespan of the devices, making battery-powered IoT devices particularly susceptible to such attacks. For further discussion on IoT devices using flash memory, see Section 9.
Including the digest of the encrypted payload in the manifest enables the device to detect a battery exhaustion attack before energy-consuming decryption and flash memory copy or swap operations take place.
IANA Considerations
IANA is asked to add the following value to the SUIT Parameters registry established by Section 11.5 of [I-D.ietf-suit-manifest]:

Label      Name                 Reference
-----------------------------------------
TBD19      Encryption Info      Section 4

RFC Editor's Note (TBD19): The value for the Encryption Info parameter is set to 19, as the proposed value.

Normative References
[RFC2119]

Key words for use in RFCs to Indicate Requirement Levels
S. Bradner
March 1997
BCP 14
RFC 2119
DOI 10.17487/RFC2119
[RFC3394]

Advanced Encryption Standard (AES) Key Wrap Algorithm
J. Schaad
R. Housley
September 2002
RFC 3394
DOI 10.17487/RFC3394
[RFC9052]

CBOR Object Signing and Encryption (COSE): Structures and Process
J. Schaad
August 2022
STD 96
RFC 9052
DOI 10.17487/RFC9052
[RFC9053]

CBOR Object Signing and Encryption (COSE): Initial Algorithms
J. Schaad
August 2022
RFC 9053
DOI 10.17487/RFC9053
[RFC8174]

Ambiguity of Uppercase vs Lowercase in RFC 2119 Key Words
B. Leiba
May 2017
BCP 14
RFC 8174
DOI 10.17487/RFC8174
[I-D.ietf-suit-manifest]

A Concise Binary Object Representation (CBOR)-based Serialization Format for the Software Updates for Internet of Things (SUIT) Manifest
Brendan Moran
Arm Limited
Hannes Tschofenig
Henk Birkholz
Fraunhofer SIT
Koen Zandberg
Inria
Øyvind Rønningstad
Nordic Semiconductor
21 October 2024
Internet-Draft draft-ietf-suit-manifest-28
[RFC9459]

CBOR Object Signing and Encryption (COSE): AES-CTR and AES-CBC
R. Housley
H. Tschofenig
September 2023
RFC 9459
DOI 10.17487/RFC9459
[I-D.ietf-suit-trust-domains]

SUIT Manifest Extensions for Multiple Trust Domains
Brendan Moran
Arm Limited
Ken Takayama
SECOM CO., LTD.
21 October 2024
Internet-Draft draft-ietf-suit-trust-domains-08

Informative References
[RFC9019]

A Firmware Update Architecture for Internet of Things
B. Moran
H. Tschofenig
D. Brown
M. Meriac
April 2021
RFC 9019
DOI 10.17487/RFC9019
[RFC9124]

A Manifest Information Model for Firmware Updates in Internet of Things (IoT) Devices
B. Moran
H. Tschofenig
H. Birkholz
January 2022
RFC 9124
DOI 10.17487/RFC9124
[RFC8937]

Randomness Improvements for Security Protocols
C. Cremers
L. Garratt
S. Smyshlyaev
N. Sullivan
C. Wood
October 2020
RFC 8937
DOI 10.17487/RFC8937
[RFC5652]

Cryptographic Message Syntax (CMS)
R. Housley
September 2009
STD 70
RFC 5652
DOI 10.17487/RFC5652
[RFC5280]

Internet X.509 Public Key Infrastructure Certificate and Certificate Revocation List (CRL) Profile
D. Cooper
S. Santesson
S. Farrell
S. Boeyen
R. Housley
W. Polk
May 2008
RFC 5280
DOI 10.17487/RFC5280
[RFC5869]

HMAC-based Extract-and-Expand Key Derivation Function (HKDF)
H. Krawczyk
P. Eronen
May 2010
RFC 5869
DOI 10.17487/RFC5869
[iana-suit]

IANA SUIT Manifest Registry
Internet Assigned Numbers Authority
2023
[ROP]

Return-Oriented Programming
Wikipedia
March 2023
[SP800-56]

Recommendation for Pair-Wise Key Establishment Schemes Using Discrete Logarithm Cryptography, NIST Special Publication 800-56A Revision 3
NIST
April 2018
Full CDDL
The following CDDL must be appended to the SUIT Manifest CDDL. The SUIT CDDL is defined in Appendix A of [I-D.ietf-suit-manifest]

SUIT_Encryption_Info = #6.96(COSE_Encrypt)

$$SUIT_Parameters //= (suit-parameter-encryption-info =>
    bstr .cbor SUIT_Encryption_Info)

suit-parameter-encryption-info = 19

Acknowledgements
We would like to thank Henk Birkholz for his feedback on the CDDL description in this document. Additionally, we would like to thank Michael Richardson, Øyvind Rønningstad, Dave Thaler, Laurence Lundblade, Christian Amsüss, Ruud Derwig, Martin Thomson and Carsten Bormann for their review feedback. Finally, we would like to thank Dick Brooks for making us aware of the challenges encryption imposes on binary analysis.
Reviews from the IESG include Deb Cooley and Roman Danyliw.