Subject: [Suit] Manifest authentication field ordering

From: Brendan Moran <[email-masked]>
Date: Mon, 25 Nov 2019 12:10:57 +0000

I’ve been looking at PQC authentication primitives, particularly HSS/LMS [1]  and XMSS [2]. These signature schemes require the processing of quite large signature blocks: I expect a Winternitz parameter of w=8 to be common, which makes the signature size 1088 bytes just for the Winternitz signature, without the Merkle tree components.

These large signatures can easily cause the manifest to violate REQ.SEC.MFST.CONST if the authentication section and the manifest are treated as a single unit, specifically:

the manifest MUST fit within an internal memory or a secure memory, such as encrypted memory

However, I think we should apply a slightly more relaxed approach here: Only the manifest itself, not the authentication wrapper, needs to fit in internal memory. Conveniently, most of these signature schemes can support a modular processing scheme, where the whole signature does not need to be loaded into RAM at once in order to validate a signature, with no loss of security.

The issue I see here is that a manifest that uses this approach faces an implementation challenge. The manifest would need to be processed in this order:

  1.  Parse COSE_Sign/COSE_Sign1 object
  2.  Construct & digest the Sig_structure
  3.  Validate the Sig_structure digest with the COSE_Signature object

1 can be processed up to the COSE_Signature without difficulty (consumed data can be discarded).
2 requires a “seek” past the, potentially large, COSE_Signature, then retention of that manifest in order to satisfy REQ.SEC.MFST.CONST.
3 can be processed gradually, storing or discarding the components of the signature that are consumed.

Currently, any key claim CWTs come after the manifest as well. This causes further “seek” actions.

Eliminating seek operations is important for two reasons:

  1.  Some designs may discard the signature after verification and replace it with a local MAC for re-verification
  2.  It limits the RAM requirements for writing only verified data to non-volatile storage

We could move the CWTs to the start, so that a validated public key is resident in memory when the COSE_Sign block is encountered. This does not resolve the manifest, however. We could move the manifest to prevent the seek, however this would just mean that the manifest must be held in memory during signature validation in order to fulfil REQ.SEC.MFST.CONST.

Both the manifest and any data extracted from it MUST be held immutable between its authenticity verification (time of check) and its use (time of use).

There is another option, but it inflates the size of the authentication wrapper by one digest: instead of using COSE_Sign in detached mode, we place a digest in the COSE_Sign as the payload. That digest is, in turn, the digest of the manifest.

My recommendation is to make two changes:

  1.  Order of fields:
     *   CWT List
     *   List of COSE_Sign/COSE_Sign1/COSE_Mac
     *   Manifest
  2.  COSE_Sign contains a SUIT_Digest of the Manifest.

This would allow seek-free, fully modular processing of the manifest, without the need to hold both the manifest and any signature primitives in RAM at the same time.

Best Regards,
Brendan

[1]: https://tools.ietf.org/html/draft-ietf-cose-hash-sig-07
[2]: https://tools.ietf.org/html/rfc8391
IMPORTANT NOTICE: The contents of this email and any attachments are confidential and may also be privileged. If you are not the intended recipient, please notify the sender immediately and do not disclose the contents to any other person, use it for any purpose, or store or copy the information in any medium. Thank you.

---

From: Michael Richardson <[email-masked]>
Date: Tue, 26 Nov 2019 00:16:08 +0100

Brendan Moran <[email-masked]> wrote:
    > I’ve been looking at PQC authentication primitives, particularly
    > HSS/LMS [1] and XMSS [2]. These signature schemes require the
    > processing of quite large signature blocks: I expect a Winternitz
    > parameter of w=8 to be common, which makes the signature size 1088
    > bytes just for the Winternitz signature, without the Merkle tree
    > components.

    > These large signatures can easily cause the manifest to violate
    > REQ.SEC.MFST.CONST if the authentication section and the manifest are
    > treated as a single unit, specifically:

Thank you for thinking about this now!

    > However, I think we should apply a slightly more relaxed approach here:
    > Only the manifest itself, not the authentication wrapper, needs to fit
    > in internal memory. Conveniently, most of these signature schemes can
    > support a modular processing scheme, where the whole signature does not
    > need to be loaded into RAM at once in order to validate a signature,
    > with no loss of security.

I agree with this idea.

    > 3.  Validate the Sig_structure digest with the COSE_Signature object

I suspect that many will need an illustration.

    > There is another option, but it inflates the size of the authentication
    > wrapper by one digest: instead of using COSE_Sign in detached mode, we
    > place a digest in the COSE_Sign as the payload. That digest is, in
    > turn, the digest of the manifest.

So, we would run a digest (say, SHA256) of the manifest, and then sign that.
The signining operation would (implicitely) create a second digest in the
signature block, which is why you are saying it costs an extra digest.

The problem that I see with this is that we are forced to select a digest at
least as strong as the security of the HSS/LMS/XMSS or future PQC primitive.
With the doubly-signed COSE_Sign payload (once with ECDSA+SHA256, the second
time with the PQC method), then we don't have any specific dependancy in
the PQC path on the SHA256.

Is this a serious concern?  I don't know, because I don't know if SHA256 will
survive.  I think that it will, and there are hash-based signatures that
assume it will, but it seems imprudent to assume this.

    > This would allow seek-free, fully modular processing of the manifest,
    > without the need to hold both the manifest and any signature primitives
    > in RAM at the same time.

This seems reasonable to me.

--
Michael Richardson <[email-masked]>, Sandelman Software Works
 -= IPv6 IoT consulting =-

---

From: Russ Housley <[email-masked]>
Date: Tue, 26 Nov 2019 16:25:10 -0500

This proposal makes sense to me.

Russ

> On Nov 25, 2019, at 7:10 AM, Brendan Moran <[email-masked]> wrote:
> 
> Parse COSE_Sign/COSE_Sign1 object
> Construct & digest the Sig_structure
> Validate the Sig_structure digest with the COSE_Signature object
> 
> Some designs may discard the signature after verification and replace it with a local MAC for re-verification
> It limits the RAM requirements for writing only verified data to non-volatile storage
> 
> 
> Order of fields:
> CWT List
> List of COSE_Sign/COSE_Sign1/COSE_Mac
> Manifest
> COSE_Sign contains a SUIT_Digest of the Manifest.
> 
> [1]: https://tools.ietf.org/html/draft-ietf-cose-hash-sig-07 <https://tools.ietf.org/html/draft-ietf-cose-hash-sig-07>
> [2]: https://tools.ietf.org/html/rfc8391 <https://tools.ietf.org/html/rfc8391>IMPORTANT NOTICE: The contents of this email and any attachments are confidential and may also be privileged. If you are not the intended recipient, please notify the sender immediately and do not disclose the contents to any other person, use it for any purpose, or store or copy the information in any medium. Thank you.
> _______________________________________________
> Suit mailing list
> [email-masked]
> https://www.ietf.org/mailman/listinfo/suit