Internet-Draft OASNT-CAID July 2026
Thallapelly Expires 25 January 2027 [Page]
Workgroup:
Network Working Group
Internet-Draft:
draft-thallapelly-oasnt-caid-00
Published:
Intended Status:
Standards Track
Expires:
Author:
A. Thallapelly
OmniArx

OASNT-CAID: Canonical Action Identifier Derivation and the Named-Human Binding

Abstract

This document profiles OASNT tokens for consumption by executor-side processing models. It fixes one normative derivation of a Canonical Action Identifier (CAID) from the OASNT action digest, so that every executor checks the same derivation rather than each integration defining its own, and it specifies the semantics of the token's named-human binding, including a subject-to-enrollment check whose absence this profile makes a refusal.

Status of This Memo

This Internet-Draft is submitted in full conformance with the provisions of BCP 78 and BCP 79.

Internet-Drafts are working documents of the Internet Engineering Task Force (IETF). Note that other groups may also distribute working documents as Internet-Drafts. The list of current Internet-Drafts is at https://datatracker.ietf.org/drafts/current/.

Internet-Drafts are draft documents valid for a maximum of six months and may be updated, replaced, or obsoleted by other documents at any time. It is inappropriate to use Internet-Drafts as reference material or to cite them other than as "work in progress."

This Internet-Draft will expire on 25 January 2027.

Table of Contents

1. Introduction

[I-D.thallapelly-oasnt] (hereafter "the core document") defines the OASNT token: a compact JWS in which a hardware-bound device key attests that a specific human authorized one specific action, with the disclosure the human was shown bound into the signature. The core document deliberately stops at the token. It does not define how an executor, having decided to admit evidence of several kinds, identifies the action that evidence authorizes.

Executor-side processing models such as [I-D.schrock-action-evidence-boundary] work in terms of a Canonical Action Identifier: a value the executor derives for the effect it is about to perform and matches against the identifiers derived from admissible evidence. Left unspecified, that derivation would be reinvented by every executor-to-OASNT integration, and two integrations that disagreed on any detail would disagree silently.

This document fixes the derivation once. It also specifies the named-human binding of the token: what a validated token asserts about the human it names, the subject-to-enrollment check a verifier is required to make, and what the binding deliberately does not assert.

This profile is written from a running implementation. The subject verification requirement in Section 5 exists because implementing this profile exposed its absence; see Section 6.3.

2. Conventions and Definitions

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.

"The core document" refers to [I-D.thallapelly-oasnt]. "Action", "canonical action", "disclosure", and the claim names adg, dsp, rqf, sub, and cnf have the meanings the core document gives them.

"Effect" refers to the concrete operation an executor is about to perform, in the executor's own representation.

3. The Canonical Action Identifier

3.1. Syntax

caid          = "oasnt:caid:" version ":" digest
version       = 1*DIGIT
digest        = 43base64url-char
base64url-char = ALPHA / DIGIT / "-" / "_"

A CAID is an opaque octet string. It is not a URI under [RFC3986], it MUST NOT be dereferenced, and no registration of the leading literal is requested or implied.

This document defines version 1.

3.2. Derivation

For an action with type T and parameters P, the version 1 CAID is:

CAID(T, P) = "oasnt:caid:1:" || BASE64URL(SHA-256(canonical-action(T, P)))

where canonical-action is the canonical action encoding of the core document, under its escaping rules and its UTF-8-octet key ordering; SHA-256 is [RFC6234]; and BASE64URL is the URL-safe alphabet of [RFC4648] without padding, yielding exactly 43 characters.

The digest octets are, by construction, identical to the value of the adg claim of an OASNT token minted for the same action. A conforming derivation therefore has two equivalent forms:

  • Recomputed. Derive from a representation of the action the deriving party itself holds, by computing the canonical action encoding and its digest. This is the form an executor uses for its effect, and the form a verifier that recomputed adg during token validation uses for the evidence.

  • Carried. Prefix the adg value of a validated token. This form is only meaningful after the token's signature has verified under an enrolled key, and it carries only the strength of that signature: it proves what the device signed, not what the executor is about to do. A carried value that is not exactly 43 characters of the base64url alphabet MUST be refused rather than prefixed.

Every CAID comparison in Section 4 is an octet-string equality. Nothing is ever parsed out of a CAID.

3.3. Versioning

Version 1 pins the canonicalization rules of the core document as of this writing: the escaping of structural delimiters and the UTF-8-octet key ordering. Any change to those rules is a new version, never a silent change under the same one.

Because the version participates in the octet-string comparison, identifiers derived under different versions never compare equal. A version mismatch therefore manifests as an ordinary CAID mismatch and fails closed. No version negotiation exists or is needed.

4. CAID Matching

An executor admitting an OASNT token as evidence for an effect MUST proceed as follows.

  1. Validate the token as the core document's verification procedure requires. A token that fails validation yields no CAID and no further processing.

  2. Derive CAID-effect from the executor's own representation of the effect it is about to perform, using the recomputed form of Section 3.2. The executor MUST NOT construct CAID-effect from any value carried in the token or supplied by the party presenting it.

  3. Derive CAID-evidence from the validated token: the recomputed form where the validator recomputed adg against an expected action, the carried form otherwise.

  4. The evidence identifies the effect only if CAID-effect and CAID-evidence are equal as octet strings. Any other outcome, including a refused carried derivation in step 3, MUST be treated as a refusal (caid-mismatch) and MUST NOT be downgraded to a warning.

Note that step 2 makes the comparison self-strengthening: equality between a self-derived CAID-effect and a carried-basis CAID-evidence is itself a recomputation of the token's adg against the executor's view of the effect. The carried basis is weak only where matching does not happen, for example when a CAID is stored or forwarded for audit without being compared; such a value retains only signature strength and MUST be marked as carried wherever that distinction is visible.

5. The Named-Human Binding

5.1. What a validated token asserts

The core document records, at enrollment, a subject identifier bound to the enrolled key, and requires the sub claim in every token. This profile makes the linkage load-bearing. A token validated under this profile asserts:

the subject recorded at enrollment and named by sub, in control of the enrolled hardware-bound key identified by cnf.jkt, approved the specific action identified by the CAID, having been shown the disclosure whose digest dsp carries, on a device whose runtime integrity was assessed as the int claim reports.

5.2. Subject verification

A verifier operating under this profile MUST refuse a token (sub-mismatch) when sub is absent, is not a string, or is not equal to the subject identifier recorded at enrollment for the key that verified the signature.

This check is REQUIRED. Without it, a token signed by one enrolled key may assert any subject whatsoever: every cryptographic check passes, the key is authorized, and the named human is fiction. Section 6.3 records the implementation experience behind this requirement.

5.3. What the binding does not assert

The binding deliberately asserts nothing beyond the statement above. In particular:

  • It is not a per-signature user-verification ceremony. The approval step precedes the signature; no claim attests a biometric or knowledge-factor ceremony for each individual signature. A relying party that requires per-signature user verification composes it alongside this profile; this profile will not fold it into the core semantics.

  • It does not assert comprehension or legal consent. A valid dsp proves which octets were displayed and signed, not that they were understood. This limit is inherited from the core document unchanged.

  • It does not strengthen the int claim. A device-asserted integrity verdict retains exactly the limits the core document states.

6. Security Considerations

6.1. One derivation or none

The interoperability property this profile buys is deliberately fragile in one direction: two implementations that disagree on any canonicalization detail, escaping, ordering, or version, produce disjoint CAID spaces and refuse each other's identifiers. The failure mode of divergence is caid-mismatch, which denies. Nothing about the construction can turn a divergence into an acceptance.

6.2. Carried derivations

The carried form of Section 3.2 is a convenience for parties that cannot recompute, and it is exactly as strong as the signature over the token that carried it. The matching procedure of Section 4 restores recomputation strength wherever it is actually applied. Deployments SHOULD treat an unmatched carried CAID, for example in logs or forwarded evidence, as a claim by the device rather than a fact about any effect.

6.3. The subject check

The reference implementation, prior to this profile, validated enrollment, signature, thumbprint, freshness, replay, all three bindings, and the integrity claim, and did not compare sub against the enrollment record. A token signed by an enrolled key claiming a different subject passed every check. The defect was found while implementing this profile's named-human semantics, was fixed by the refusal Section 5.2 requires, and is now exercised by a published refusal vector (the named-human substitution case in the implementation's adversarial corpus, and Appendix A).

The lesson generalizes: the named-human binding is precisely as strong as the weakest link between sub, the enrollment record, and the key. A deployment that enrolls keys without recording a verified subject identifier has nothing for this check to bind, and the assertion of Section 5 silently degrades to "some enrolled key approved this". Enrollment procedures SHOULD therefore verify the subject identifier they record.

6.4. Namespace separation

The fixed leading literal exists so that an OASNT-derived identifier can never be confused with an identifier derived by another evidence profile that also feeds an executor. Executors handling multiple evidence profiles SHOULD treat the full octet string, prefix included, as the identifier and compare nothing shorter.

7. IANA Considerations

This document has no IANA actions. The literal oasnt:caid: is a fixed string defined by this document; it is not a URI scheme, not a URN namespace, and no registration is requested.

8. References

8.1. Normative References

[I-D.thallapelly-oasnt]
Thallapelly, A., "OASNT: Attested Action Authorization Tokens", Work in Progress, Internet-Draft, draft-thallapelly-oasnt-01, , <https://datatracker.ietf.org/doc/html/draft-thallapelly-oasnt-01>.
[RFC2119]
Bradner, S., "Key words for use in RFCs to Indicate Requirement Levels", BCP 14, RFC 2119, DOI 10.17487/RFC2119, , <https://www.rfc-editor.org/rfc/rfc2119>.
[RFC4648]
Josefsson, S., "The Base16, Base32, and Base64 Data Encodings", RFC 4648, DOI 10.17487/RFC4648, , <https://www.rfc-editor.org/rfc/rfc4648>.
[RFC6234]
Eastlake 3rd, D. and T. Hansen, "US Secure Hash Algorithms (SHA and SHA-based HMAC and HKDF)", RFC 6234, DOI 10.17487/RFC6234, , <https://www.rfc-editor.org/rfc/rfc6234>.
[RFC8174]
Leiba, B., "Ambiguity of Uppercase vs Lowercase in RFC 2119 Key Words", BCP 14, RFC 8174, DOI 10.17487/RFC8174, , <https://www.rfc-editor.org/rfc/rfc8174>.

8.2. Informative References

[I-D.schrock-action-evidence-boundary]
Schrock, I., "The Action Evidence Boundary for Consequential Agent Effects", Work in Progress, Internet-Draft, draft-schrock-action-evidence-boundary-00, , <https://datatracker.ietf.org/doc/html/draft-schrock-action-evidence-boundary-00>.
[RFC3986]
Berners-Lee, T., Fielding, R., and L. Masinter, "Uniform Resource Identifier (URI): Generic Syntax", STD 66, RFC 3986, DOI 10.17487/RFC3986, , <https://www.rfc-editor.org/rfc/rfc3986>.

Appendix A. Test Vectors

The derivation vectors below are byte-reproducible: they are generated from the shipped canonicalization by docs/ietf/caid/gen-vectors-caid.mjs in the implementation repository, and unlike the signature vectors of the core document they involve no randomness. The named-human refusal vector involves an ECDSA signature and is verified rather than compared.

A.1. P1: CAID derivation

Action type payment.transfer, parameters amount=100.00, payee=acct_9.

canonical action  payment.transfer|amount=100.00&payee=acct_9
adg               YlHp3M4JIWFPPZIVAwAmYOBOMfUyb2bjE6ve3AD2iaQ
CAID              oasnt:caid:1:YlHp3M4JIWFPPZIVAwAmYOBOMfUyb2bjE6ve3AD2iaQ

This vector is deterministic: any conforming implementation reproduces these exact octets.

A.2. P2: CAID mismatch

The evidence above is presented for a different effect: amount=9000.00, payee=acct_EVIL.

executing canonical action  payment.transfer|amount=9000.00&payee=acct_EVIL
CAID-effect                 oasnt:caid:1:EWy_PVFw3FxdZIk6AEpEJ5HxhAsCJQnSq7P1jPHg6gc
CAID-evidence               oasnt:caid:1:YlHp3M4JIWFPPZIVAwAmYOBOMfUyb2bjE6ve3AD2iaQ

The octet strings differ; the outcome is a refusal (caid-mismatch).

A.3. P3: carried-form refusals

Each of the following values MUST be refused by the carried form of the derivation rather than prefixed:

""                                             (empty)
"short"                                        (wrong length)
42 or 44 characters of the base64url alphabet  (wrong length)
43 characters ending in "="                    (padding)
any character outside ALPHA / DIGIT / "-" / "_"

A.4. P4: named-human refusal (verified, not compared)

A token signed by the core document's published test key, with every claim valid except sub, which names mallory while enrollment records agent-1 for the key. Verification refuses with sub-mismatch and no other reason. The signature is not byte-reproducible; regenerate and verify with the tool named above.

Acknowledgments

The composition questions raised by Iman Schrock on the WIMSE mailing list, in particular whether the adg-to-CAID derivation should be fixed normatively or left to each executor adapter, prompted this profile.

Author's Address

Arun Thallapelly
OmniArx