Network Working Group M. K. Yossif Internet-Draft Yuthent Intended status: Standards Track 9 June 2026 Expires: 11 December 2026 PSEA Token Profile: An EAT Profile for Action-Bound, User-Verification- Gated Transaction-Confirmation Evidence draft-yossif-psea-02 Abstract This document defines the PSEA Token Profile, an Entity Attestation Token (EAT) profile for action-bound, user-verification-gated transaction-confirmation Evidence. The profile specifies the canonical encoding, the signed proof-token claim set, the action- payload and cross-replay bindings, an optional hash-chain integrity layer, and the security properties that together constitute a What- You-Sign-Is-What-You-Execute proof that a human, present and verified at an authenticator, approved a specific named action at the moment of execution. The profile binds what is signed to what the Verifier executes; it does not, by itself, bind what a human saw on a potentially compromised display to what was signed (the What-You-See- Is-What-You-Sign problem), which remains out of scope. The strength of the human-presence assurance depends on the authenticator's user- verification enforcement: where the platform attestation conveys that enforcement it is hardware-attested, and otherwise it rests on the authenticator's signed assertion that user verification occurred. The profile does not, by itself, prove a specific human identity. It fills the transaction-confirmation gap left unaddressed by deployed authentication standards and complements OAuth 2.0 Step-Up Authentication by supplying the per-action, cryptographically action- bound Evidence that step-up flows can require. Note to Readers This note is to be removed before publishing as an RFC. This is an individual submission to the IETF. "Standards Track" above is the _intended_ status; this document has not been adopted by any IETF working group and does not represent IETF consensus. The author intends to request dispatch of this work (for example through the SECDISPATCH working group) toward adoption by an appropriate working group. Review and comments are welcome at the repository referenced in the Introduction. Yossif Expires 11 December 2026 [Page 1] Internet-Draft PSEA Token Profile June 2026 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 11 December 2026. Copyright Notice Copyright (c) 2026 IETF Trust and the persons identified as the document authors. All rights reserved. This document is subject to BCP 78 and the IETF Trust's Legal Provisions Relating to IETF Documents (https://trustee.ietf.org/ license-info) in effect on the date of publication of this document. Please review these documents carefully, as they describe your rights and restrictions with respect to this document. Code Components extracted from this document must include Revised BSD License text as described in Section 4.e of the Trust Legal Provisions and are provided without warranty as described in the Revised BSD License. Table of Contents 1. Introduction . . . . . . . . . . . . . . . . . . . . . . . . 4 1.1. Requirements Language . . . . . . . . . . . . . . . . . . 6 1.2. Terminology . . . . . . . . . . . . . . . . . . . . . . . 6 2. Canonical Encoding of Proof Payloads . . . . . . . . . . . . 7 2.1. UTF-8 Serialization . . . . . . . . . . . . . . . . . . . 8 2.2. Object Key Ordering (Case-Sensitive Unicode Code-Point Sort) . . . . . . . . . . . . . . . . . . . . . . . . . . 8 2.3. Array Ordering . . . . . . . . . . . . . . . . . . . . . 8 2.4. String Serialization . . . . . . . . . . . . . . . . . . 9 2.5. Number Serialization (Integers Only) . . . . . . . . . . 9 2.6. Boolean and Null Serialization . . . . . . . . . . . . . 10 2.7. Whitespace . . . . . . . . . . . . . . . . . . . . . . . 10 2.8. Conformance and Cross-Platform Implementer Warning . . . 10 3. Proof Token Format . . . . . . . . . . . . . . . . . . . . . 11 3.1. PSEA as an EAT Profile . . . . . . . . . . . . . . . . . 12 Yossif Expires 11 December 2026 [Page 2] Internet-Draft PSEA Token Profile June 2026 3.1.1. EAT Profile Definition (per RFC 9711, Section 7) . . 12 3.2. Top-Level Structure . . . . . . . . . . . . . . . . . . . 14 3.3. Single Authoritative Payload (No Envelope Duplicates) . . 17 3.4. JOSE Header Hardening (Normative) . . . . . . . . . . . . 17 3.5. JWS Payload Claim Set . . . . . . . . . . . . . . . . . . 18 3.6. Wire Transport Bodies . . . . . . . . . . . . . . . . . . 22 3.7. Human Presence via User-Verification-Gated Signature . . 22 3.7.1. User-Verification Claim (psea_uv) . . . . . . . . . . 24 3.8. Subject Hash (psea_user_hash) . . . . . . . . . . . . . . 25 3.9. Device-State Submodule (submods.psea-device-state) . . . 26 3.10. Counter Model (Monotonic Replay Ordering) . . . . . . . . 27 3.11. Freshness and Expiry . . . . . . . . . . . . . . . . . . 28 3.12. ChainEntry (Deployment-Optional Tamper-Evidence Layer) . 29 3.12.1. Formula (Length-Prefixed Concatenation) . . . . . . 30 3.12.2. Sentinel Value . . . . . . . . . . . . . . . . . . . 31 3.12.3. Verifier Behavior on Mismatch . . . . . . . . . . . 31 3.13. Action Binding (Fail-Closed by Default) . . . . . . . . . 31 3.13.1. Producer Obligations . . . . . . . . . . . . . . . . 32 3.13.2. Verifier Obligations: Fail-Closed Binding (Normative Default) . . . . . . . . . . . . . . . . . . . . . . 32 3.13.3. Relying-Party Obligations . . . . . . . . . . . . . 33 3.13.4. Cross-Replay Binding (psea_tier + psea_op + aud + iss) . . . . . . . . . . . . . . . . . . . . . . . . 33 3.13.5. Caller-Identity Binding (psea_caller_package) . . . 35 3.14. Enrollment Lifecycle and Trust Gate (Verifier) . . . . . 35 3.15. Versioning . . . . . . . . . . . . . . . . . . . . . . . 36 4. Relationship to WebAuthn and FIDO Transaction Confirmation . 36 5. Relationship to OAuth 2.0 Step-Up Authentication . . . . . . 37 5.1. Comparison . . . . . . . . . . . . . . . . . . . . . . . 37 5.2. Complementarity . . . . . . . . . . . . . . . . . . . . . 38 5.3. Out of Scope for This Document . . . . . . . . . . . . . 39 6. Security Considerations . . . . . . . . . . . . . . . . . . . 39 6.1. Scope and Method . . . . . . . . . . . . . . . . . . . . 39 6.2. Attester Assumptions . . . . . . . . . . . . . . . . . . 39 6.3. Enrollment Is the Root of Trust . . . . . . . . . . . . . 40 6.4. STRIDE Threats Addressed . . . . . . . . . . . . . . . . 41 6.4.1. Spoofing . . . . . . . . . . . . . . . . . . . . . . 41 6.4.2. Tampering . . . . . . . . . . . . . . . . . . . . . . 42 6.4.3. Repudiation . . . . . . . . . . . . . . . . . . . . . 42 6.4.4. Information Disclosure . . . . . . . . . . . . . . . 42 6.4.5. Denial of Service . . . . . . . . . . . . . . . . . . 43 6.4.6. Elevation of Privilege . . . . . . . . . . . . . . . 43 6.5. Verifier State Integrity: Sharding and Rollback . . . . . 43 6.6. Future Work: Relying Party Counter-Signature . . . . . . 44 6.7. Threats Out of Scope . . . . . . . . . . . . . . . . . . 44 6.8. Known Open Problems . . . . . . . . . . . . . . . . . . . 45 6.8.1. Coercion and Duress . . . . . . . . . . . . . . . . . 45 6.8.2. What-You-See-Is-What-You-Sign (WYSIWYS) . . . . . . . 46 Yossif Expires 11 December 2026 [Page 3] Internet-Draft PSEA Token Profile June 2026 6.8.3. Subject-Identity Limits . . . . . . . . . . . . . . . 47 7. Privacy Considerations . . . . . . . . . . . . . . . . . . . 47 7.1. UEID Linkability . . . . . . . . . . . . . . . . . . . . 48 7.2. Hashing Is Not Anonymization . . . . . . . . . . . . . . 49 7.3. Data Minimization at the Verifier . . . . . . . . . . . . 50 8. IANA Considerations . . . . . . . . . . . . . . . . . . . . . 50 8.1. Summary of Requested Registrations . . . . . . . . . . . 50 8.2. Media Type Registration . . . . . . . . . . . . . . . . . 51 8.3. URN Sub-namespace Registration (urn:ietf:params:psea) . . 52 9. Algorithm Agility and Operational Defaults . . . . . . . . . 53 9.1. Cryptographic Algorithms . . . . . . . . . . . . . . . . 53 9.1.1. Mandatory-to-Implement (MTI) . . . . . . . . . . . . 53 9.1.2. Post-Quantum Migration . . . . . . . . . . . . . . . 53 9.1.3. Algorithm Negotiation . . . . . . . . . . . . . . . . 54 9.2. Operational Defaults . . . . . . . . . . . . . . . . . . 54 10. References . . . . . . . . . . . . . . . . . . . . . . . . . 54 10.1. Normative References . . . . . . . . . . . . . . . . . . 54 10.2. Informative References . . . . . . . . . . . . . . . . . 56 Appendix A. Canonical Encoding Test Vectors . . . . . . . . . . 57 A.1. Case-Sensitive Key Sort . . . . . . . . . . . . . . . . . 57 A.2. Integer Serialization . . . . . . . . . . . . . . . . . . 57 A.3. Action-Payload Hash (End-to-End Worked Example) . . . . . 57 Appendix B. Conformance . . . . . . . . . . . . . . . . . . . . 58 B.1. Conformance Roles . . . . . . . . . . . . . . . . . . . . 58 B.2. Attester Conformance . . . . . . . . . . . . . . . . . . 58 B.2.1. Requirements . . . . . . . . . . . . . . . . . . . . 58 B.3. Verifier Conformance . . . . . . . . . . . . . . . . . . 59 B.3.1. Requirements . . . . . . . . . . . . . . . . . . . . 59 B.4. Relying Party Conformance . . . . . . . . . . . . . . . . 61 Author's Address . . . . . . . . . . . . . . . . . . . . . . . . 61 1. Introduction Session-based authentication answers "did this entity present valid credentials at some point?"; execution-time authority answers "is an authorized human, present and verified, approving this specific action right now?". The gap between these two questions is where session-hijacking, autonomous malware, and unattended-device risk materialize. This document defines a token profile that fills that gap at the token layer: a signed EAT-profile token whose claim set constitutes cryptographic Evidence of execution authority at the moment of action, independent of prior session state. Yossif Expires 11 December 2026 [Page 4] Internet-Draft PSEA Token Profile June 2026 The signed token is a JSON Web Signature (JWS) Compact Serialization object ([RFC7515]) whose payload is an EAT-JSON claims-set. The profile reuses the registered EAT claims ueid, eat_nonce, submods, and eat_profile ([RFC9711]) alongside JSON Web Token (JWT) registered claims ([RFC7519]) and the PSEA-private psea_* extension claims defined in this document. The profile applies to any authenticator that can generate a hardware-backed, user-verification-gated ES256 signature over a _raw digest_ the host supplies. Conforming authenticator classes include Trusted Execution Environment (TEE)- or Secure-Element-backed mobile keystores (for example Android Keystore keys that require user authentication, or iOS Secure Enclave keys gated by a local- authentication context), PIN-gated Personal Identity Verification (PIV)-class smartcards that expose a user-verification-gated raw ECDSA-over-digest operation, and programmable secure elements. A standard FIDO2/WebAuthn security key does not natively conform: a WebAuthn authenticator signs only its fixed assertion structure (authenticator data concatenated with a hash of the client data) and exposes no primitive to sign an arbitrary digest, so it cannot emit a JWS whose payload is an arbitrary EAT-JSON claims-set. Binding a FIDO assertion into this profile would require a separate FIDO- assertion binding, which is out of scope of this document (Section 4). Where the authenticator exposes only a raw user-verification-gated signing primitive (the typical case for keystore- and smartcard- backed keys), the host application -- the integrating SDK -- assembles the JWS, computes the action-payload hash, maintains the replay counter, and populates the user-verification claim; the hardware authenticator contributes only the hardware-protected, user- verification-gated signature. In this profile the term "Attester" denotes the composite of that host software and the hardware authenticator. The security properties this profile claims rest on the hardware authenticator's protected key and its user-verification gating; the surrounding claim assembly is performed by the host and is itself untrusted until the Verifier validates the resulting signature and cross-checks the claims against the platform attestation. The deployment architecture -- including any operational enforcement model that maps applications to capability or assurance levels, the HTTP verifier endpoints, the attestation-evidence wrapper, the Verifier acknowledgement, and the trust-state model -- is deployment- specific and is out of scope of this profile. Yossif Expires 11 December 2026 [Page 5] Internet-Draft PSEA Token Profile June 2026 The transaction-confirmation gap this profile addresses was previously targeted by the WebAuthn txAuthSimple and txAuthGeneric extensions, both of which were removed in Web Authentication Level 2 without widely deployed successors (Section 4). This profile complements OAuth 2.0 Step-Up Authentication ([RFC9470]) by providing the per-action, cryptographically action-bound Evidence token that a step-up challenge can require and a resource server can verify (Section 5). This document is the protocol-specification revision of PSEA. The earlier revisions draft-yossif-psea-00 and draft-yossif-psea-01 were Informational and described PSEA as a security model and a set of requirements for verifying authority at the moment of action. This revision specifies the concrete wire protocol that realizes that work as an EAT profile ([RFC9711]), with a defined claim set, a canonical encoding, and normative verification rules; the intended status is Standards Track accordingly. 1.1. Requirements Language 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. 1.2. Terminology This document uses the following terms. RATS terminology follows [RFC9334]; PSEA-specific terms are defined here. Attester The entity that generates Evidence by producing a proof token signed with a hardware-protected, user-verification-gated key. Concretely the Attester is the composite of (a) a hardware authenticator that holds the signing key and enforces the user- verification gate -- for example a TEE- or Secure-Element-backed mobile keystore, a PIN-gated PIV-class smartcard, or a programmable secure element -- and (b) the host software that assembles the token claim set around that signature. Where the hardware authenticator exposes only a raw user-verification-gated signing primitive, the host computes psea_payload_hash, maintains psea_counter, and populates psea_uv; the authenticator contributes the signature. A standard FIDO2/WebAuthn security key is not a conforming Attester under this profile (Section 1). A natural person is not an Attester. Verifier The server-side component that appraises Evidence and produces Attestation Results. Yossif Expires 11 December 2026 [Page 6] Internet-Draft PSEA Token Profile June 2026 Relying Party The application server that gates the action on the Verifier's Attestation Result. Subject (of Evidence) The natural person whose presence and intent the Attester's Evidence makes claims about. Evidence The signed proof token an Attester produces per this profile: a user-verification-gated, action-bound execution- authority proof. See Section 3. Attestation Result The integrity-protected artifact the Verifier produces and returns to the Relying Party. Endorsement A trust anchor the Verifier uses to appraise Evidence (for example, an Android Key Attestation root, an Apple App Attest root, a FIDO authenticator vendor root, or a smartcard issuer root). action / action payload The specific operation the Subject approves. The canonical encoding of the action payload is hashed and included in the signed Evidence body (see Section 3.13). capability / assurance level An abstract indicator of the authority or assurance context a proof is produced under, carried in the signed psea_tier claim and bound into the signature (Section 3.13.4). The value space is opaque to this profile and is agreed out of band between producer and Verifier; this profile does not define a fixed set of levels, and the operational mapping of applications to levels is deployment-specific and out of scope of this profile. 2. Canonical Encoding of Proof Payloads The canonical encoding rules in this section apply wherever a PSEA hash is taken over canonical JSON octets. The PSEA proof is carried as JWS Compact Serialization (Section 3), as is any Verifier acknowledgement a deployment defines (that artifact's format is out of scope of this profile); a JWS signature covers the received wire octets directly, so canonical encoding is therefore not load-bearing for verifying those JWS objects. It is normative (a MUST) for exactly one use, in which the producer and the Verifier independently hash canonical JSON bytes with SHA-256 and compare the result: * the action-payload binding -- the SHA-256 over the canonical actionPayload that produces the signed psea_payload_hash claim, which the Verifier independently re-computes and compares (Section 3.13). Yossif Expires 11 December 2026 [Page 7] Internet-Draft PSEA Token Profile June 2026 For this use, implementations that deviate from the rules below will produce byte sequences that fail the payload-binding comparison on peer platforms. The underlying data format is JSON ([RFC8259]). Canonical encoding MUST follow the JSON Canonicalization Scheme (JCS) [RFC8785] in full. This section restates the [RFC8785] rules that are most consequential for cross-platform PSEA implementers and notes the one schema restriction PSEA imposes: PSEA payload schemas use JSON integer numbers only at this revision, so the floating-point number- serialization rules of [RFC8785], Section 3.2.2.3 do not arise (see Section 2.5); in all other respects an implementation MUST conform to [RFC8785]. Implementers MUST read this section in full before relying on a JSON library's default serialization or a third-party JCS implementation; platform defaults frequently diverge from these requirements in ways that are difficult to detect without cross- platform test vectors. This document uses the verb "will" in lowercase to describe deterministic consequences of non-conformance, not as a BCP 14 keyword. 2.1. UTF-8 Serialization The canonical byte sequence MUST be encoded as UTF-8 [RFC3629]. The encoding MUST NOT include a byte-order mark. 2.2. Object Key Ordering (Case-Sensitive Unicode Code-Point Sort) Object members MUST be ordered by case-sensitive ascending Unicode code-point comparison of their keys, byte by byte after UTF-8 encoding. The comparison MUST NOT normalize case, fold Unicode equivalence classes, or apply collation rules. Two keys that differ only in case (for example, "endedAt" and "endReason") MUST order according to the Unicode code-point value of their differing character; in this example, "endReason" (uppercase "R" = U+0052 = 82) sorts before "endedAt" (lowercase "e" at the comparison position = U+0065 = 101) because 82 < 101. This rule is the canonical encoding's most consequential implementer- warning point. See Section 2.8 for cross-platform notes. 2.3. Array Ordering JSON arrays preserve their natural element order; the canonical encoding MUST NOT re-order array elements. The semantics of array order are payload-specific and are defined where applicable in Section 3. Yossif Expires 11 December 2026 [Page 8] Internet-Draft PSEA Token Profile June 2026 2.4. String Serialization String values MUST be serialized following the encoding rules in [RFC8785], Section 3.2.2.2 (Serialization of Strings). In particular: the JSON six- character escape forms for U+0022 (quotation mark), U+005C (reverse solidus), U+0008, U+000C, U+000A, U+000D, and U+0009 MUST be used; the "\uXXXX" form MUST use lowercase hexadecimal digits; surrogate pairs MUST be emitted as written by the producer (canonical encoding does not normalize Unicode form). 2.5. Number Serialization (Integers Only) PSEA payload schemas define numeric fields only as integers. The canonical encoding of an integer N MUST follow [RFC8785], Section 3.2.2.3, which for an integer is its shortest decimal representation (no leading zeros, no "+" sign, no exponent, no decimal point). Because every numeric field defined in this revision is an integer, the floating-point cases of [RFC8785] do not arise; a full RFC 8785 serializer and an implementation of only this integer rule produce identical output for every payload schema defined in this revision. Floating-point numbers, decimal fractions, and exponent notation MUST NOT appear in any PSEA payload field at this revision. A future revision MAY extend the subset; until such an extension is registered, any non-integer numeric value in a signed payload field is non-conformant. This integers-only rule also governs the actionPayload that the action binding hashes (Section 3.13). The actionPayload schema is deployment-defined, but it is hashed under the same canonical encoding, so a JSON floating-point value placed in it would re- introduce exactly the [RFC8785] floating-point serialization divergence this section avoids for the profile's own claims. Accordingly, monetary and other fractional quantities carried in actionPayload MUST be represented as integers in a fixed minor unit (for example, integer cents) or as strings, and MUST NOT be represented as JSON floating-point numbers. The worked example of Appendix A.3 follows this rule (an amount of 2500 minor units, not 25.00). A deployment that places a JSON float in actionPayload falls outside the cross-platform canonicalization guarantee of this section and will observe payload-binding failures between peers whose float serializers differ. Yossif Expires 11 December 2026 [Page 9] Internet-Draft PSEA Token Profile June 2026 2.6. Boolean and Null Serialization The literals true, false, and null MUST be serialized with their lowercase JSON spelling. null as a value SHOULD NOT appear in PSEA payload schemas; absent fields are conveyed by omitting the key rather than by including the key with a null value. 2.7. Whitespace The canonical encoding MUST NOT include whitespace between tokens (no spaces, tabs, newlines, or carriage returns). Whitespace inside string values is preserved verbatim per Section 2.4. 2.8. Conformance and Cross-Platform Implementer Warning Implementations MUST verify their canonical encoder against the test vectors in Appendix A. A canonical encoder that produces output matching the test vectors for every input in that appendix is conformant; an encoder that diverges on any single test vector is non-conformant and will produce signed bytes that fail peer verification. Specific implementer-warning notes on common platform pitfalls: Apple platforms JSONSerialization with the sortedKeys option performs a _case-insensitive_ sort, which diverges from this section's _case-sensitive_ rule (see Section 2.2). Implementations on Apple platforms MUST NOT rely on sortedKeys; they MUST emit canonical bytes via a manual sort using a case- sensitive comparator (for example, Swift's Dictionary.keys.sorted() with the default less-than operator on String, which is case-sensitive). JavaScript / TypeScript platforms Array.prototype.sort() on string keys performs a case-sensitive Unicode code-point sort, matching this section's requirement. JSON.stringify with a comparator option is not standard; use a manual canonicalization pass. Java / Kotlin String.compareTo() performs case-sensitive Unicode code-point comparison; the standard JCS implementations in major libraries (Jackson, Gson) produce conformant output when configured for canonical mode. Python The standard sorted() on strings performs case-sensitive Unicode code-point sort. The json module's sort_keys=True matches this section's rule. Go, Rust Default string comparison on both languages is case- Yossif Expires 11 December 2026 [Page 10] Internet-Draft PSEA Token Profile June 2026 sensitive byte-wise on UTF-8, which matches this section's rule for keys composed entirely of ASCII characters. The most consequential pitfall is an Apple sortedKeys case- insensitive sort silently producing canonical bytes that diverge from a peer using a case-sensitive sort, causing cross-platform signature- verification failures. This is the failure mode the implementer- warning here is specifically designed to prevent. 3. Proof Token Format A PSEA proof is a JWS Compact Serialization object ([RFC7515]): BASE64URL(protected header) || "." || BASE64URL(payload) || "." || BASE64URL(signature). The Attester signs the header.payload octets with its hardware-protected signing key. The payload is an Entity Attestation Token claims-set in EAT-JSON form ([RFC9711]); PSEA defines it as an EAT profile (Section 3.1). The claim set reuses JWT registered claims ([RFC7519]), the registered EAT claims ([RFC9711]) ueid, eat_nonce, submods, and eat_profile for device-state conveyance and profile identification, and the profile's PSEA-private psea_* extension claims. The proof travels in a transport body (Section 3.6) alongside the unsigned cleartext actionPayload that the Verifier independently hashes and compares against the signed payload-hash claim. The integrity flows are: the proof's authenticity and integrity are established by the JWS signature over its received octets; the action binding is established by the Verifier re-hashing the cleartext actionPayload and comparing to the signed psea_payload_hash claim (Section 3.13); the attestation evidence carried in integrityEvidence (contents out of scope) is appraised independently against the platform Endorsement; and, where the deployment-optional chain layer is enabled (Section 3.12), chainEntry is computed deterministically by the Verifier from signed inputs, so its integrity flows from the signature on those inputs. This profile defines a single proof token type: the user- verification-gated, action-bound execution-authority proof. A deployment MAY define additional, lower-assurance signed-token types that reuse the same JWS Compact Serialization representation and the same canonical encoding; such tokens are out of scope of this profile. Yossif Expires 11 December 2026 [Page 11] Internet-Draft PSEA Token Profile June 2026 3.1. PSEA as an EAT Profile The PSEA proof is a profile of the Entity Attestation Token ([RFC9711]), as that term is used in [RFC9711], Section 7. The token is a compact JWS ([RFC7515]) signed with ES256 (ECDSA P-256 with SHA- 256) whose payload is an EAT-JSON claims-set. A conforming PSEA proof MUST carry the eat_profile claim ([RFC9711], Section 4.3.4) with the stable profile identifier urn:ietf:params:psea:eat-profile:1 (or the fallback identifier of Section 8.3 if the URN registration is not granted in the publication stream). A Verifier MUST reject a proof whose eat_profile claim is absent or carries any other value. The profile is composed of three claim families: * *Registered EAT claims ([RFC9711]).* ueid (the per-device identifier, [RFC9711], Section 4.2.1; see the encoding requirement in Section 3.2 and the privacy discussion in Section 7.1), eat_nonce (OPTIONAL freshness nonce), submods (the device-state submodules map), and eat_profile (this profile's identifier). * *Registered JWT claims ([RFC7519]).* jti, aud, iss, iat, and exp. * *Profile extension claims (psea_*).* The properties for which EAT defines no registered claim: psea_payload_hash (action-binding payload hash; Section 3.13), psea_tier (capability/assurance-level binding), psea_counter (monotonic per-counter-scope replay counter; Section 3.10), psea_uv (user-verification claim; Section 3.7.1), psea_op (operation binding; Section 3.13.4), and psea_proof_version. The OPTIONAL extension claims psea_chain_prev (deployment-optional hash-chain anchor; Section 3.12), psea_user_hash, psea_caller_package, and psea_sdk_version MAY also be present. This document does not claim that a generic EAT consumer can fully appraise a PSEA proof without understanding the psea_* extension claims; the extension claims are profile-specific and are defined normatively in Section 3. The eat_profile claim signals to a consumer which extension semantics apply. 3.1.1. EAT Profile Definition (per RFC 9711, Section 7) This subsection states the profile in the form [RFC9711], Section 7 calls for, so the eat_profile commitment is auditable in one place. A token claiming urn:ietf:params:psea:eat-profile:1 MUST satisfy all of the following. Profile identifier The eat_profile claim ([RFC9711], Section 4.3.4) Yossif Expires 11 December 2026 [Page 12] Internet-Draft PSEA Token Profile June 2026 MUST equal the URI urn:ietf:params:psea:eat-profile:1 — or, if the urn:ietf:params:psea registration is not granted in the publication stream, the single fallback URI fixed by the published document (Section 8.3). A published document fixes exactly one value for this claim. Serialization The token MUST be a JWS Compact Serialization ([RFC7515]) whose payload is an EAT-JSON claims-set. A CBOR/COSE representation is out of scope of this profile; a Verifier MUST NOT accept a CBOR/COSE-encoded token as conforming to this profile. Mandatory-to-implement algorithm ES256 (ECDSA on P-256 with SHA-256) is the only mandatory-to-implement signature algorithm (Section 9.1.1). A Verifier MUST reject a token whose JOSE alg is not "ES256" and MUST apply the header hardening of Section 3.4. Freshness Replay freshness is provided by the monotonic psea_counter (Section 3.10), by the iat/exp validity window (Section 3.11), and, when the Verifier issues a challenge, by the OPTIONAL eat_nonce claim ([RFC9711]) carrying that challenge value. A Verifier that issued a challenge MUST reject a token whose eat_nonce is absent or does not equal the issued value. Key confirmation The verification key is resolved out of band from the enrolled record selected by the JOSE kid; a Verifier MUST NOT use any key conveyed in or referenced by the token header (Section 3.4). Claims The full claim set, and which claims are REQUIRED versus OPTIONAL, is defined in Section 3.5. submods content The OPTIONAL submods map ([RFC9711]) carries a single psea-device-state submodule whose contents are out of scope; an authenticator that cannot produce device-state omits submods entirely. Detached EAT Bundles and nested tokens This profile does not use Detached EAT Bundles ([RFC9711], Section 5) and does not use nested tokens ([RFC9711], Section 4.2.18): a conforming PSEA proof is a single, self-contained JWS whose payload is one EAT-JSON claims-set. A Verifier MUST NOT accept a Detached EAT Bundle or a nested token as conforming to this profile. UEID type The ueid claim carries a deterministic per-issuer value under the RFC 9711 RAND type tag (0x01); this is a deliberate, disclosed choice whose rationale and migration path are stated in Section 7.1. Yossif Expires 11 December 2026 [Page 13] Internet-Draft PSEA Token Profile June 2026 Extensibility model This profile is a deliberately strict, lock-step profile rather than an ignore-unknown-claims profile. A conforming Verifier rejects a proof carrying any claim outside this profile's defined set (the claim-set schema sets additionalProperties: false, Section 3.5), any unknown psea_proof_version (Section 3.15), and any unrecognized crit header parameter (Section 3.4). A consequence intended by this design is that a future psea_* claim is rejected by current- revision Verifiers until they are upgraded to a revision that defines it; the wire format is versioned as a whole rather than extended in place. This departs from the ignore-unknown extensibility customary for EAT and JWT consumers, and is chosen so that the set of claims a Verifier appraises is exactly the set the profile revision specifies. 3.2. Top-Level Structure JWS Compact Serialization (value of the transport-body "proof" field) BASE64URL(UTF8(protected header)) || "." || BASE64URL(JCS-canonical-JSON(payload)) || "." || BASE64URL(r || s) ; ES256, see Signature below Protected header (a JSON object; base64url-encoded, no padding) +-- alg ; "ES256" (ECDSA P-256 with SHA-256) +-- kid ; opaque, deployment-internal enrollment-lookup selector, | ; untrusted until verified (a forged kid fails: the wrong | ; key will not validate the signature). The SHA-256 of the | ; signing-key SubjectPublicKeyInfo (SPKI) in standard base64 | ; is one ILLUSTRATIVE derivation; the value space is not | ; constrained by this profile. +-- typ ; "psea-proof+jwt" Payload (the claim set; base64url-encoded, no padding) JWT registered claims (RFC 7519) +-- jti ; action id; also the global-uniqueness key +-- aud ; intended Verifier/audience identifier (RFC 7519) +-- iss ; tenant / deployment id +-- iat ; NumericDate, epoch SECONDS +-- exp ; NumericDate, epoch SECONDS EAT claims (RFC 9711) +-- ueid ; base64url no-pad of the RAND-type UEID byte | ; string: 0x01 || SHA-256(deviceId || iss), | ; 33 bytes; per-issuer (pairwise): the same | ; device yields a distinct ueid per deployment | ; (RFC 9711 Sec 4.2.1; 0x01 = RAND type tag) [+-- eat_nonce] ; OPTIONAL server nonce for push-initiated | ; freshness; omitted entirely when absent Yossif Expires 11 December 2026 [Page 14] Internet-Draft PSEA Token Profile June 2026 [+-- submods] ; OPTIONAL; { "psea-device-state": {...} } -- | ; device-state appraisal input; contents | ; out of scope of this document +-- eat_profile ; "urn:ietf:params:psea:eat-profile:1" | ; (RFC 9711 Sec 4.3.4); REQUIRED PSEA-private extension claims +-- psea_tier ; capability/assurance indicator (opaque; | ; deployment-defined value space) +-- psea_counter ; JSON integer [0, 2^53-1], monotonic per | ; (attester, counter scope) +-- psea_payload_hash ; standard base64 of SHA-256(canonical | ; actionPayload) -- the action binding +-- psea_op ; operation/authority-context discriminator | ; (REQUIRED; see cross-replay binding) +-- psea_uv ; { "verified": bool, "method": string } | ; user-verification (human-presence) claim; | ; REQUIRED; see the psea_uv section +-- psea_proof_version ; "1" [+-- psea_chain_prev] ; OPTIONAL deployment-optional hash-chain | ; anchor; 64-char lowercase hex | ; (sentinel: 64 ASCII '0' for first proof); | ; present only when the deployment enables | ; the chain layer (see ChainEntry section) [+-- psea_caller_package] ; OPTIONAL; reverse-DNS app identifier [+-- psea_sdk_version] ; OPTIONAL; Attester implementation version [+-- psea_user_hash] ; OPTIONAL; base64url no-pad; omitted ; entirely when empty Signature ECDSA P-256 (ES256). The signature is the fixed-width 64-byte concatenation of the (r, s) integers, base64url no-pad, computed over ASCII(headerB64 || "." || payloadB64). This is the JWS ES256 signature encoding (RFC 7518 Sec 3.4), NOT a DER/ASN.1 encoding. Encoding split: ueid uses base64url (no padding) of the 33-byte RAND-type UEID; psea_payload_hash uses standard base64 (with padding); psea_user_hash uses base64url (no padding). NOTE on chainEntry (deployment-optional layer): when a deployment enables the hash-chain tamper-evidence layer, the Attester sends psea_chain_prev IN the signed payload (the prior proof's chainEntry, or the sentinel for the first proof). chainEntry itself is not carried inbound: the Verifier recomputes this proof's chainEntry from the signed inputs (see the ChainEntry section). The mechanism by which the recomputed chainEntry is conveyed back to the Attester for use as the next proof's psea_chain_prev is deployment-specific and out of scope. Deployments that do not enable the chain layer omit psea_chain_prev entirely. Yossif Expires 11 December 2026 [Page 15] Internet-Draft PSEA Token Profile June 2026 Figure 1: PSEA proof as JWS Compact Serialization. *Base64 encoding split (normative):* psea_payload_hash MUST be encoded as standard base64 ([RFC4648], Section 4) with padding (the pattern ^[A-Za-z0-9+/]{42}[AEIMQUYcgkosw048]=$; the restricted final- sextet class rejects non-canonical encodings of the 32-octet digest, whose trailing two bits are always zero). ueid and psea_user_hash MUST be encoded as base64url ([RFC4648], Section 5) without padding. This is a deliberate per-claim encoding split that implementers MUST observe exactly; using base64url for psea_payload_hash or standard base64 for ueid or psea_user_hash produces a non-conformant token. The two encodings are not interchangeable; they carry the same underlying octets and differ only in alphabet and padding. A Verifier validates each claim against the exact pattern in Section 3.5. The operation a proof is presented for determines which psea_tier and psea_op values the Verifier expects in the payload; the expected values are deployment-defined and agreed out of band. The payload's psea_tier, psea_op, aud, and iss claims together close the cross- replay attack surface (Section 3.13.4). The transport body POSTed to the endpoint wraps the JWS in the proof field and carries the cleartext action and evidence alongside it: { "proof": "", "actionPayload": { ... }, // unsigned cleartext; the Verifier // re-canonicalizes, SHA-256s, and // compares against psea_payload_hash "integrityEvidence": { ... }, // OPTIONAL attestation evidence "requestId": "...", // OPTIONAL opaque request id "signalReport": { ... }, // OPTIONAL device-signal report "proofId": "..." // OPTIONAL opaque proof identifier } The actionPayload is unsigned cleartext; the Verifier re- canonicalizes it (Section 2), takes its SHA-256, and compares the result against the signed psea_payload_hash claim. This comparison is the fail-closed action binding (Section 3.13). Because a compact JWS has a single authoritative payload, the proof carries no envelope-level duplicates of the signed claims. Yossif Expires 11 December 2026 [Page 16] Internet-Draft PSEA Token Profile June 2026 3.3. Single Authoritative Payload (No Envelope Duplicates) A compact JWS has a single, cryptographically attested payload. The PSEA proof format therefore carries no envelope-level duplicates of its signed claims, and there is no envelope-versus-signed-body consistency check to perform: the only field a Verifier reads ahead of signature verification is the protected-header kid, which is the untrusted-until-verified enrollment-lookup selector. A forged kid fails verification because the key it selects will not validate the signature, so no separate envelope-body comparison is needed to defend against a substituted routing value. The Verifier looks up the enrollment by kid, verifies the JWS signature with the enrolled key, and only then reads the authentic claim set (including jti, psea_counter, psea_payload_hash, and ueid) directly from the verified payload. There are no pre-signature lookup copies of these values to reconcile. A compact JWS carries a single authoritative payload, so there is no envelope/body pair to reconcile and this profile defines no envelope- body mismatch error codes. A Verifier reads the signed claim set (jti, psea_counter, psea_payload_hash, ueid) directly from the verified payload. 3.4. JOSE Header Hardening (Normative) Because a JWS protected header is attacker-influenceable until the signature is verified, a Verifier MUST apply the following constraints to every PSEA proof JWS before trusting any claim. A deployment that represents its Verifier acknowledgement / Attestation Result as a JWS — that artifact's format is out of scope of this profile (Section 3.13.3) — SHOULD apply equivalent header hardening when the Attester consumes it: * The Verifier MUST reject any JWS whose protected-header alg is not "ES256". ES256 is the only mandatory-to-implement algorithm at this revision (Section 9.1.1); a Verifier that does not implement algorithm negotiation (Section 9.1.3) MUST NOT accept any other alg value. * The Verifier MUST reject any JWS whose protected-header alg is "none". An unsigned token MUST NOT be accepted under any circumstance. Yossif Expires 11 December 2026 [Page 17] Internet-Draft PSEA Token Profile June 2026 * The Verifier MUST ignore any key material embedded in the JWS header, including the jwk, jku, and x5u header parameters. The verification key is resolved *only* from the enrolled record selected by the untrusted-until-verified kid; the Verifier MUST NOT verify a PSEA JWS against any key conveyed in or referenced by the token itself. * The Verifier MUST verify the protected-header typ value. A PSEA proof carries typ = "psea-proof+jwt", and a consumer expecting a proof MUST reject a JWS whose typ is not "psea-proof+jwt". A deployment that defines a Verifier acknowledgement / Attestation Result as a JWS (out of scope of this profile) SHOULD give it a distinct typ — for example "psea-ack+jwt" — applying the explicit- typing guidance of [RFC8725], Section 3.11, so that a proof cannot be processed as an acknowledgement or the reverse. * The Verifier MUST reject any JWS that carries a crit header parameter naming an extension this profile does not define, and MUST reject any JWS that uses the unencoded-payload option (the b64 header parameter set to false, [RFC7797]). A conforming PSEA JWS uses only the base64url-encoded payload form and defines no critical header extensions at this revision. These constraints close the classic JOSE downgrade and key-confusion attacks (algorithm substitution, alg:"none", attacker-supplied verification keys, cross-type confusion between proof and acknowledgement, and unencoded-payload / unknown-critical-header tricks) at the protocol's wire surface, and align with the JSON Web Token Best Current Practices ([RFC8725]); see also Section 6.4.1. 3.5. JWS Payload Claim Set The following JSON Schema describes the claim set carried in the BASE64URL(payload) segment of the PSEA proof JWS. The claims combine JWT registered claims ([RFC7519]), a subset of EAT claims ([RFC9711]), and PSEA-private psea_* claims. eat_nonce and psea_user_hash are optional and, when not applicable, are omitted entirely rather than serialized as empty or null. The schema sets additionalProperties: false. This is deliberate: as stated in the "Extensibility model" entry of Section 3.1.1, this profile is a strict lock-step profile, so a Verifier rejects a proof carrying any claim outside the set below, and a future psea_* claim is by design rejected by current-revision Verifiers until they are upgraded. This departs from the ignore-unknown-claims extensibility customary for EAT and JWT. The three OPTIONAL members psea_chain_pending, psea_last_confirmed_head, and psea_rp_context_hash are registered in the schema below as opaque, Yossif Expires 11 December 2026 [Page 18] Internet-Draft PSEA Token Profile June 2026 non-appraised extension members: they are permitted so that proofs carrying deployment-defined diagnostic context are not rejected by additionalProperties: false, but they carry no Verifier appraisal obligation, and a Verifier that does not recognize them ignores them. { "$schema": "https://json-schema.org/draft/2020-12/schema", "title": "PseaProofClaims", "description": "The JWS payload claim set for the PSEA proof.", "type": "object", "required": [ "jti", "aud", "iss", "iat", "exp", "ueid", "eat_profile", "psea_tier", "psea_op", "psea_counter", "psea_payload_hash", "psea_uv", "psea_proof_version" ], "properties": { "jti": { "type": "string", "minLength": 1, "maxLength": 128, "pattern": "^[A-Za-z0-9._-]+$", "description": "Action id; also the global-uniqueness key. Alphanumeric/dot/underscore/hyphen only. UUID RECOMMENDED." }, "aud": { "type": "string", "minLength": 1, "maxLength": 256, "description": "JWT audience (RFC 7519): identifier of the intended Verifier/audience. See cross-replay binding." }, "iss": { "type": "string", "minLength": 1, "maxLength": 128, "description": "Tenant / deployment identifier; verified against the deployment/tenant the Verifier resolves for the request. See cross-replay binding." }, "iat": { "type": "integer", "minimum": 0, "description": "NumericDate; epoch SECONDS." }, "exp": { "type": "integer", "minimum": 0, "description": "NumericDate; epoch SECONDS." }, "ueid": { "type": "string", "pattern": "^[A-Za-z0-9_-]{44}$", "description": "RFC 9711 Sec 4.2.1 RAND-type UEID: base64url (no padding) of the 33-byte string 0x01 || SHA-256(deviceId || iss). Per-issuer (pairwise): the same device yields a distinct ueid per iss, preventing cross-deployment correlation. The leading 0x01 is the RAND type tag. See Privacy Considerations." }, "eat_nonce": { "type": "string", "description": "OPTIONAL. Server nonce for push-initiated freshness. Omitted entirely when absent." }, "submods": { "type": "object", "properties": { "psea-device-state": { "type": "object", "description": "Reserved placeholder extension point; Yossif Expires 11 December 2026 [Page 19] Internet-Draft PSEA Token Profile June 2026 contributes nothing wire-normative in this revision (contents out of scope)." } }, "description": "OPTIONAL EAT submodules map. The psea-device-state submodule is a reserved, deployment-specific placeholder; an authenticator that cannot produce device-state omits submods entirely." }, "eat_profile": { "type": "string", "enum": ["urn:ietf:params:psea:eat-profile:1"], "description": "EAT profile identifier (RFC 9711 Sec 4.3.4). REQUIRED. The enum value is the requested primary identifier; if the urn:ietf:params:psea registration is not granted in the publication stream, the published document fixes the single fallback URI instead (see the IANA URN sub-namespace section). A published document fixes exactly one value." }, "psea_tier": { "type": "string", "minLength": 1, "maxLength": 128, "description": "Capability/assurance-level binding. Opaque to this profile; deployment-defined value space agreed out of band. The Verifier rejects the proof if it does not match the level expected for the operation. See cross-replay binding." }, "psea_op": { "type": "string", "minLength": 1, "maxLength": 128, "description": "Operation / authority-context discriminator the proof is bound to. Opaque to this profile; the Verifier rejects the proof if it does not match the operation being performed. See cross-replay binding." }, "psea_counter": { "type": "integer", "minimum": 0, "maximum": 9007199254740991, "description": "Monotonic per (attester, counter scope). JSON integer in [0, 2^53-1]; see counter model." }, "psea_payload_hash": { "type": "string", "pattern": "^[A-Za-z0-9+/]{42}[AEIMQUYcgkosw048]=$", "description": "Standard base64 (with padding) of SHA-256(canonical actionPayload); the action binding. The restricted final-sextet class rejects non-canonical encodings (the digest's trailing two bits are always zero). See action binding." }, "psea_chain_prev": { "type": "string", "pattern": "^[0-9a-f]{64}$", "description": "OPTIONAL deployment-optional hash-chain anchor. 64-char lowercase hex; sentinel 64 ASCII '0' for the first proof. Present only when the deployment enables the chain tamper-evidence layer. See ChainEntry." }, Yossif Expires 11 December 2026 [Page 20] Internet-Draft PSEA Token Profile June 2026 "psea_uv": { "type": "object", "required": ["verified", "method"], "properties": { "verified": { "type": "boolean", "description": "Whether a contemporaneous user- verification event gated this signature." }, "method": { "type": "string", "description": "User-verification method. Extensible string; suggested baseline values include \"biometric\", \"pin\", \"fido_uv\" (no IANA registry is defined). Unknown values MUST be tolerated." } }, "description": "User-verification claim. REQUIRED on the PSEA proof. The Verifier MUST require verified==true and MUST cross-check it against the authenticator's attested UV-enforcement where the attestation conveys it. See the user-verification claim section." }, "psea_proof_version": { "type": "string", "enum": ["1"] }, "psea_caller_package": { "type": "string", "minLength": 1, "maxLength": 256, "description": "OPTIONAL profile-extension claim. Reverse-DNS identifier of the calling application." }, "psea_sdk_version": { "type": "string", "maxLength": 64, "description": "OPTIONAL profile-extension claim. Attester implementation version." }, "psea_user_hash": { "type": "string", "pattern": "^[A-Za-z0-9_-]{42}[AEIMQUYcgkosw048]$", "description": "OPTIONAL. base64url (no padding) of SHA-256(subject_id); audit-attribution only. The restricted final-sextet class rejects non-canonical encodings. Omitted entirely when empty. MUST be derived pairwise per issuer (see Privacy Considerations)." }, "psea_chain_pending": { "description": "OPTIONAL registered opaque profile-extension member; empty schema (any JSON value). Semantics are deployment-defined and out of scope; the member carries no Verifier appraisal obligation, and a Verifier that does not recognize it ignores it. Present only when the deployment's chain gap-tolerance layer emits it." }, "psea_last_confirmed_head": { "description": "OPTIONAL registered opaque profile-extension member; empty schema (any JSON value). Semantics are deployment-defined and out of scope; the member carries no Verifier appraisal obligation, and a Verifier that does not recognize it ignores it. Present only when the deployment's Yossif Expires 11 December 2026 [Page 21] Internet-Draft PSEA Token Profile June 2026 chain gap-tolerance layer emits it." }, "psea_rp_context_hash": { "description": "OPTIONAL registered opaque profile-extension member; empty schema (any JSON value). Semantics are deployment-defined and out of scope; the member carries no Verifier appraisal obligation, and a Verifier that does not recognize it ignores it. Present only when the deployment binds a relying-party request context." } }, "additionalProperties": false } 3.6. Wire Transport Bodies A PSEA proof is submitted to the Verifier in a transport body of the form { proof, actionPayload, integrityEvidence?, requestId?, signalReport?, proofId? }, where proof is the compact JWS (Section 3.2), actionPayload is the unsigned cleartext action bound by psea_payload_hash (Section 3.13), and integrityEvidence is an OPTIONAL attestation evidence block whose contents are out of scope of this profile. The concrete transport (HTTP method and path) is deployment-specific and out of scope. Of the transport-body fields, only proof is signed, and actionPayload is cryptographically bound to it through psea_payload_hash (Section 3.13). The remaining fields — integrityEvidence, requestId, signalReport, and proofId — are unsigned and attacker-mutable in transit. A Verifier MUST NOT use any unsigned transport-body field as an input to a security decision. integrityEvidence is appraised on its own cryptographic merits against the platform Endorsement (its appraisal does not trust the envelope framing); requestId, signalReport, and proofId are correlation and operational hints only and confer no authority. 3.7. Human Presence via User-Verification-Gated Signature This profile establishes the human-presence requirement through the signing operation itself rather than through a separate wire-level presence block. The Attester's hardware-protected signing key MUST be gated by a platform user-verification event such that the signing operation cannot complete without a successful, contemporaneous user- verification ceremony. The signed proof body is therefore implicit Evidence that a user-verification event occurred at the moment of signing; the signature itself is the presence commitment. *Per-operation gating (normative).* The user-verification gate MUST be enforced _per signing operation_: each proof signature MUST be preceded by its own fresh user-verification event. A configuration Yossif Expires 11 December 2026 [Page 22] Internet-Draft PSEA Token Profile June 2026 in which a single user-verification event authorizes signing for a time window or for multiple subsequent signatures (duration- or window-based authentication) is NOT RECOMMENDED for any signing and is non-conformant for proof signing: it would let a compromised host pre-compute a batch of proofs from one ceremony (see Section 6.4.1, Paragraph 3). A conforming Attester binds exactly one user- verification event to exactly one proof signature. This rules out "authenticate-once-then-reuse" key configurations. By way of example, the following common platform configurations are non- conformant for proof signing, and only their per-operation counterparts conform: a PIV-class smartcard in PIN-once mode (only a PIN-always / per-signature PIN policy conforms); an Android Keystore key with a non-zero user-authentication validity timeout (only a timeout of 0 — authentication required for every use — conforms); and an iOS authentication context reused across multiple signing operations (a fresh, non-reused authentication context per signature is required). The specific platform mechanism is out of scope; the normative requirement is the one-verification-per-signature binding above. The user-verification mechanisms that gate the signing key — for example, a platform biometric subsystem (fingerprint or face match), a Secure Enclave PIN entry, a hardware-token PIN, a smartcard with PIN, a magnetic-stripe credential combined with a PIN, or any equivalent platform user-verification primitive — are out of scope of this specification. The specific per-authenticator mechanism is mechanism-agnostic; what is normative is that the signing operation cannot complete without a contemporaneous user-verification event and that the proof carries an explicit psea_uv claim asserting that fact (Section 3.7.1). The Verifier MUST NOT infer presence silently from the bare existence of a signature from the hardware-protected signing key. For the PSEA proof it MUST require the explicit psea_uv claim and, where the authenticator's attestation conveys a UV-enforcement property, cross- check the claim against that attested property (appraised through the authenticator attestation and the deployment's Reference Values). The detailed normative rule, and the statement of where this property is attested versus where it rests on a documented trust assumption, are given in Section 3.7.1. Yossif Expires 11 December 2026 [Page 23] Internet-Draft PSEA Token Profile June 2026 This design uses a single, compact user-verification claim rather than a parallel wire-level presence block whose other fields would duplicate information already carried by the attestation evidence (in integrityEvidence) for platforms that bundle user-verification into the attestation chain. The cryptographic anchor for "a human was present at the moment of signing" is the psea_uv claim covered by the proof signature plus the hardware-protected-key attestation against which it is cross-checked. 3.7.1. User-Verification Claim (psea_uv) Every PSEA proof MUST carry a signed psea_uv claim: * psea_uv.verified — a boolean asserting that a contemporaneous user-verification event gated the signing operation that produced this proof. * psea_uv.method — a string identifying the user-verification method. The value space is extensible; suggested baseline values are "biometric", "pin", and "fido_uv" (this document defines no IANA registry for them). A Verifier MUST tolerate an unknown method value (treat it as an opaque label) rather than rejecting solely on the method string. A token that makes no human-presence claim (such tokens are out of scope of this profile) does not carry psea_uv. The claim is part of the JWS payload and is therefore covered by the proof's ES256 signature, so it is tamper-evident: an intermediary cannot flip verified from false to true without invalidating the signature. Normative Verifier rule: the Verifier MUST require psea_uv.verified == true and MUST reject the proof otherwise. Beyond that, anchoring of the claim is conditional on what the authenticator's attestation conveys: * Where the platform attestation conveys a UV-enforcement property, the Verifier MUST cross-check psea_uv against it and MUST reject the proof if the attested key properties contradict the claim (for example, the claim asserts verified == true but the attested signing key is not user-authentication-gated). The Verifier MUST NOT accept such a psea_uv as merely self-asserted when it could have been cross-checked against the attestation. * Where the attestation does not convey a UV-enforcement property, the Verifier MUST NOT treat the human-presence assurance as attested — the claim is signed but rests on a documented trust assumption (see below) — and for high-assurance operations SHOULD reject the proof or require an additional independent factor. Yossif Expires 11 December 2026 [Page 24] Internet-Draft PSEA Token Profile June 2026 This rule is device-agnostic: any conforming Attester emits psea_uv, and the Verifier anchors it wherever the authenticator's attestation permits. Examples of the per-authenticator cross-check (informative, NOT normative — the specific mechanism is out of scope): a phone with an attested UV-gated hardware key whose key attestation conveys an auth- enforced / user-authentication-required property; a PIN-gated smartcard whose attested key properties indicate a PIN-verified signing operation. In each case the conforming Attester emits psea_uv and the Verifier cross-checks it against that authenticator's own attested UV-enforcement. The FIDO/WebAuthn user-verified (UV) flag carried in signed authenticator data is the same idea in a different envelope, but a FIDO authenticator does not itself emit a PSEA proof (Section 1); consuming a FIDO assertion's UV signal would require the separate, out-of-scope FIDO-assertion binding. Verification depth (known limitation): where the authenticator's platform attestation conveys UV-enforcement (for example, a hardware- key attestation carrying an auth-enforced field), the Verifier cross- checks psea_uv against it and the user-verification property is *attested*. Where the platform attestation cannot convey UV- enforcement, conformance rests on a *documented trust assumption* in the authenticator's user-verification enforcement; in that case the psea_uv claim is required and signed, but it is not independently attested. Authenticator-signed user-verification evidence — for example, a FIDO-style UV flag carried in signed authenticator data — is the path to full verifiability and is the RECOMMENDED direction for authenticators that can produce it. This document does not claim the property is fully solved on every platform; it normatively requires the claim and the cross-check, and documents the residual trust assumption where the attestation surface does not yet permit the cross-check. The rationale for the unattested case above is that such a psea_uv is advisory only — a signed boolean the host populated, with no independent cryptographic backing for the user-verification event — so it cannot be relied upon as an attested human-presence assurance for high-assurance operations. 3.8. Subject Hash (psea_user_hash) The OPTIONAL psea_user_hash claim (Section 3.5) is an Attester-signed subject-binding commitment: the SHA-256 of an opaque, deployment- issued subject identifier, encoded as base64url without padding. The claim cryptographically attributes the action to a subject identifier for the audit trail. Yossif Expires 11 December 2026 [Page 25] Internet-Draft PSEA Token Profile June 2026 When present, psea_user_hash MUST be derived so that it does not function as a cross-deployment correlator, mirroring the pairwise ueid derivation (Section 7.1): the subject identifier MUST be bound to the deployment before hashing — for example by salting the hash input with a per-issuer (iss) secret not published with the proofs, or by deriving a per-issuer subject identifier. A deployment MUST NOT emit a bare SHA-256 of a globally stable subject identifier (see Section 7.2). A Verifier MUST NOT make an authorization decision based on the per- proof psea_user_hash claim of a PSEA proof. Subject attribution is for ledger and audit purposes only. The cryptographic chain of authorization at the Verifier rests on the device-bound signature, the monotonic counter, and the presence Evidence (Section 3.7); the Attester's commitment to a subject identifier is an additional audit- trail property, not a security gate. The per-proof psea_user_hash is distinct from any enrollment-bound subject binding a deployment records at enrollment time; that binding, and its use in decision-bearing checks, is deployment- specific and out of scope. The per-proof signed value on the PSEA proof is a commitment whose role is solely audit-trail attribution. 3.9. Device-State Submodule (submods.psea-device-state) The OPTIONAL psea-device-state submodule of the EAT submods map (Section 3.5) carries an opaque device-posture commitment from the Attester. Its contents and the Verifier's appraisal logic are out of scope of this document. An authenticator that cannot produce device- state omits submods entirely. On the wire, the psea-device-state submodule is a JSON object whose internal structure is not constrained by this specification. The Verifier appraises the commitment as part of the deployment's policy evaluation; the wire surface visible to the Attester is binary -- the Verifier either accepts the commitment (the proof proceeds through subsequent appraisal steps) or rejects the proof through the deployment's policy verdict. The appraisal mechanism the Verifier applies, the categorical properties the commitment may carry, and any operator-side controls over appraisal sensitivity are deployment- specific and outside the scope of this specification. Because the submodule travels inside the signed JWS payload, its bytes are covered by the proof signature as written; a future revision of this document MAY define a normative sealed commitment form for the submodule, but until such a revision is published, conforming implementations treat submods.psea-device-state as an opaque deployment-specific object whose contents are out of scope. Yossif Expires 11 December 2026 [Page 26] Internet-Draft PSEA Token Profile June 2026 3.10. Counter Model (Monotonic Replay Ordering) The signed psea_counter claim is a monotonic replay-ordering anchor. The Verifier compares the submitted value against the last-accepted counter value it holds for the same Attester and the same counter scope (see below); a value that is not strictly greater than the stored value for that scope MUST cause the Verifier to reject the proof. An Attester MAY maintain a single counter or several independent counter scopes, and emits in psea_counter the value of the scope the proof is produced under. The number of scopes, and the mapping of an application's actions to scopes, is deployment-specific and out of scope of this profile. Independent scopes serve only to preserve independent offline progress: if proofs produced offline under different scopes drew every value from one shared sequence, an offline-signed proof would collide on submission with a proof signed under another scope after the first was composed but before it was synced. Independent scopes let each progress without colliding. *Scope selection (normative).* When a deployment uses more than one counter scope, the value that identifies the scope a proof was produced under MUST be cryptographically bound to that proof — either carried as a signed claim (for example psea_tier) or carried in the action payload and therefore covered by the signed psea_payload_hash (Section 3.13). A Verifier MUST select the stored counter value to compare against using only such a bound scope identifier, and MUST NOT derive the scope from any field that is not covered by the signature or by the action-binding hash. This closes the otherwise- exploitable case in which an attacker steers the comparison toward a stale bucket by altering an unbound scope selector. Because the action-binding check (Section 3.13.2) MUST run and fail-closed before the counter comparison is reached, a scope identifier conveyed in the action payload is fully bound at the point the Verifier selects the bucket. A deployment that maintains a single counter has no scope to select and emits one monotonic sequence. Yossif Expires 11 December 2026 [Page 27] Internet-Draft PSEA Token Profile June 2026 The cross-scope replay surface that a single counter _would_ defend against (a captured proof submitted under a different scope) is closed instead by a global action-identifier uniqueness check the Verifier MUST maintain (each jti action identifier finalizes exactly once) plus the cross-replay binding of Section 3.13.4 (the signed psea_tier + psea_op bindings force operation-correctness independent of counter scope). The Verifier MUST retain each finalized jti for at least as long as a proof bearing it could still be within its exp validity window (that is, at least until the maximum exp the Verifier will accept has passed); a jti MAY be evicted once no proof carrying it could still pass the exp freshness check. A Verifier that retains finalized jti values for less than the exp window reopens the replay surface this check exists to close. *Atomicity (normative).* A Verifier MUST perform the counter comparison-and-advance and the jti finalization atomically — serialized per (Attester, counter scope) — within a single transaction: read the stored counter, compare, and conditionally advance in one atomic step that also records the jti. The counter value compared MUST be the value read inside that transaction (not a value read earlier), and the stored value MUST be advanced only when the submitted counter is strictly greater than it. A blind last- write-wins advance is non-conformant. This guarantees that two concurrent or out-of-order submissions cannot both commit and cannot lower (regress) the stored high-water mark: of any set of submissions racing at a given scope, at most one advances, and a later-arriving lower counter is rejected rather than overwriting a higher stored value. *Interoperability bound (normative):* Producers MUST emit psea_counter as a JSON integer in the range [0, 2^53 − 1] (inclusive) so that the value round-trips losslessly through IEEE 754 double- precision JSON parsers. Verifiers MUST treat the claim as a 64-bit unsigned integer for comparison purposes. This profile does not string-encode the counter; a string-valued psea_counter is non- conformant. At any reasonable operational rate a producer never approaches the 2^53 bound, but producers MUST enforce this bound explicitly. 3.11. Freshness and Expiry The signed iat and exp claims ([RFC7519]) bound the time window in which a proof is acceptable. Both are NumericDate values in epoch seconds and are REQUIRED (Section 3.5). A producer MUST set iat to the time of signing and exp to a value no later than iat plus the deployment's maximum proof lifetime. Yossif Expires 11 December 2026 [Page 28] Internet-Draft PSEA Token Profile June 2026 A Verifier MUST reject a proof whose exp is at or before the current time, and MUST reject a proof whose iat is implausibly in the future. The Verifier MAY allow a small clock-skew tolerance when applying these checks; the tolerance SHOULD NOT exceed 60 seconds. The Verifier SHOULD additionally enforce a bounded maximum acceptable proof lifetime (the interval between iat and exp); a RECOMMENDED bound is given in Section 9.2. These checks MUST be applied after signature verification and before any state mutation. The iat/exp window complements, but does not replace, the replay defenses of Section 3.10: the monotonic psea_counter provides ordering, the global jti uniqueness check ensures each action finalizes exactly once, and the OPTIONAL eat_nonce (when the Verifier issued a challenge) binds the proof to that challenge. A deployment that produces proofs offline for deferred submission MUST choose an exp margin wide enough to cover its expected offline-to-sync interval; the freshness anchor for such proofs is then the counter and the jti uniqueness check rather than a narrow exp window. When a Verifier issued a challenge, it MUST correlate the returned proof to the issued challenge using only the signed eat_nonce claim value read from the verified payload — for example, by looking up its outstanding-challenge state keyed on the nonce value itself. A Verifier MUST NOT rely on any unsigned transport-body field (for example requestId, Section 3.6) to decide which issued challenge a proof answers, because an unsigned field is attacker-mutable in transit and a mismatched correlation could let a proof carrying one (signed) nonce be accepted against a different outstanding challenge. The eat_nonce value is covered by the proof signature, so keying the correlation on it keeps the challenge-to-proof binding within the signed surface. 3.12. ChainEntry (Deployment-Optional Tamper-Evidence Layer) The chainEntry is a deterministic hash-chain anchor that links each proof to the prior proof from the same Attester. It provides a per- Attester tamper-evident ledger of accepted proofs *in addition to* the monotonic ordering already provided by psea_counter (Section 3.10); its value is detecting after-the-fact alteration or omission within a stored proof sequence, not freshness, which the counter and the action-binding already supply. Yossif Expires 11 December 2026 [Page 29] Internet-Draft PSEA Token Profile June 2026 The chain is a *deployment-optional* layer. A deployment MAY enable it; when enabled, the Attester carries the prior proof's chainEntry inbound as the psea_chain_prev claim and the Verifier behaves as specified in Section 3.12.3. A deployment that does not enable the chain MUST omit psea_chain_prev entirely (the claim is OPTIONAL in Section 3.5), and a Verifier that does not implement the chain ignores it. Completing the chain loop requires the Verifier to convey each recomputed chainEntry back to the Attester so it can serve as the next proof's psea_chain_prev. That conveyance rides on the Verifier acknowledgement / Attestation Result, whose format is deployment- specific and out of scope of this profile. Two independent implementations therefore interoperate on the chain only after they additionally agree on that out-of-scope acknowledgement format; the chain is consequently specified here as an optional deployment feature rather than a mandatory wire element, and a self-contained conforming Verifier (Appendix B.3) is not required to implement it. 3.12.1. Formula (Length-Prefixed Concatenation) For each PSEA proof, the chainEntry is computed over a length- prefixed concatenation of the three input fields, where actionId is the jti claim, counter is psea_counter, and chainPrev is psea_chain_prev. Length-prefixing guarantees domain separation: for any two distinct tuples (actionId, counter, chainPrev) the encoded inputs are byte-distinct regardless of whether any field contains a : character, NUL bytes, or any other character. This is the standard cryptographic pattern for unambiguous hash-input encoding. encode(s) = u32_be(len(utf8(s))) || utf8(s) input = encode(actionId) || encode(decimal(counter)) || encode(chainPrev) chainEntry = lowercase_hex( SHA-256( input ) ) where u32_be(n) is the 4-byte big-endian unsigned-32-bit encoding of the integer n, utf8(s) is the UTF-8 byte sequence of the string s, decimal(counter) is the digit-only decimal representation of counter per Section 2.5 (the byte length of any field encoded by encode in this revision fits comfortably in u32), and the output is the lowercase-hex representation of the SHA-256 digest [FIPS180-4]. Byte layout (worked example) for actionId="550e8400-e29b- 41d4-a716-446655440000", counter=42, chainPrev = 64 '0' characters: Yossif Expires 11 December 2026 [Page 30] Internet-Draft PSEA Token Profile June 2026 Offset Bytes Description ───────────────────────────────────────────────────────────────────── [00–03] 00 00 00 24 u32_be(36) = len(actionId) [04–39] 35 35 30 65 38 34 30 30 ... actionId UTF-8 (36 bytes) [40–43] 00 00 00 02 u32_be(2) = len("42") [44–45] 34 32 "42" UTF-8 (2 bytes) [46–49] 00 00 00 40 u32_be(64) = len(chainPrev) [50–113] 30 30 30 30 ... chainPrev UTF-8 (64 bytes) ───────────────────────────────────────────────────────────────────── Total: 114 bytes → SHA-256 → 64 hex chars 3.12.2. Sentinel Value For the first proof from an Attester since enrollment (i.e., when the Attester has no prior chain entry stored locally), the Attester MUST use the sentinel value 64 ASCII '0' characters ("0000000000000000000000000000000000000000000000000000000000000000") as psea_chain_prev. The Verifier MUST accept this sentinel value when its stored prior chain entry for the Attester is empty. 3.12.3. Verifier Behavior on Mismatch A Verifier that has enabled the chain layer performs a strict- equality linkage check on every proof that carries psea_chain_prev: if the inbound signed psea_chain_prev does not equal the chainEntry of the last proof the Verifier accepted for the Attester — or the sentinel of Section 3.12.2 when the Verifier holds no prior chain entry for the Attester — the Verifier MUST reject the proof. A Verifier MAY, as a local operational policy out of scope of this profile, additionally accept a bounded class of out-of-order or backfilled proofs; any such tolerance MUST preserve the tamper- evidence of the chain by accepting only chainEntry values the Verifier has itself previously computed and accepted for that Attester. A Verifier that has not enabled the chain layer ignores psea_chain_prev if present and performs no linkage check; the proof's freshness and replay resistance then rest on psea_counter (Section 3.10), the jti uniqueness check, and the action binding. 3.13. Action Binding (Fail-Closed by Default) PSEA's execution-authority guarantee requires that an approved action be cryptographically bound to a specific action payload. Without this binding, a captured proof from one execution can be replayed against a different payload at the Verifier. Yossif Expires 11 December 2026 [Page 31] Internet-Draft PSEA Token Profile June 2026 3.13.1. Producer Obligations A PSEA proof producer (a conforming Attester) MUST compute the action payload hash over the canonical encoding defined in Section 2 and include the resulting digest as the psea_payload_hash claim of the signed execution-authority proof. The proof MUST be signed by the hardware-protected signing key that holds the active user- verification binding for the originating action. A producer MUST NOT emit a proof whose signed psea_payload_hash claim is absent, empty, or computed over input other than the canonical encoding of the actual action payload being authorized by the human. 3.13.2. Verifier Obligations: Fail-Closed Binding (Normative Default) A conforming Verifier MUST, on every per-action proof submission, perform the following steps in order: 1. Decode the signed token and validate its cryptographic signature against the device- anchored public key bound to the active enrollment. 2. Compute the canonical encoding of the request's action payload using Section 2 and hash the result with SHA-256. 3. Compare the computed hash, byte-for-byte, against the psea_payload_hash claim decoded from the signed proof in step 1. 4. If step 3 produces a mismatch, OR if the request omits the action payload entirely while the signed proof carries a psea_payload_hash claim, the Verifier MUST reject the proof and MUST NOT return any Attestation Result or other wire response that a Relying Party could interpret as approval. The Verifier MUST emit this rejection before producing any wire response that could be interpreted by the Relying Party as an approval. A rejection MUST NOT carry a success-bearing Attestation Result. The action-binding obligation in this subsection applies identically to every PSEA proof, regardless of the capability or assurance level under which it was produced; a Verifier that enforces the binding for some levels but not others is non-conformant. Yossif Expires 11 December 2026 [Page 32] Internet-Draft PSEA Token Profile June 2026 3.13.3. Relying-Party Obligations On a successful appraisal, a Verifier that is not co-located with the Relying Party MUST convey the outcome as an integrity-protected Attestation Result. A Relying Party that receives a success-bearing, integrity-protected Attestation Result from a conforming Verifier MAY treat the action binding as enforced and is not required to re- perform the payload-hash computation. This is the central simplification that PSEA's normative fail-closed binding enables: the Relying Party can trust the Verifier's integrity-protected result without performing client-side binding enforcement. The concrete encoding of the Attestation Result, the Verifier-to- Relying-Party transport, and the enrollment ceremony that binds a kid to an enrolled key are deployment-specific and out of scope of this profile. The extent of what a second party can build from this document alone should be stated precisely. The proof-token validation core is fully specified here: from this document alone a second party can build a conforming Attester that emits byte- conformant proofs, and the Verifier-side validation core — JWS signature verification, the JOSE header hardening (Section 3.4), the fail-closed payload-hash action binding (Section 3.13.2), the cross- replay binding (Section 3.13.4), the monotonic counter (Section 3.10), the jti uniqueness check, and freshness (Section 3.11). A _deployable_ Verifier additionally requires two inputs this profile deliberately leaves out of scope: the enrollment binding that resolves kid to an enrolled public key (without which no signature can be verified), and — for human presence to be _attested_ rather than merely signed — the appraisal of the out-of-scope attestation evidence against which psea_uv is cross-checked (Section 3.7.1). Interoperating on those two interfaces, and on the Verifier-to-Relying-Party Attestation Result, additionally requires a companion deployment profile that fixes them. 3.13.4. Cross-Replay Binding (psea_tier + psea_op + aud + iss) In addition to the payload binding of Section 3.13.2, every PSEA proof MUST carry the following cross-replay binding claims in its signed JWS payload. These close attack surfaces where a captured signed proof could be replayed across operations, across authority levels, or across deployments without the signature alone catching the mismatch. Yossif Expires 11 December 2026 [Page 33] Internet-Draft PSEA Token Profile June 2026 * psea_tier — capability / assurance-level binding: an abstract indicator of the authority or assurance context the proof is produced under. The value space is opaque to this profile and agreed out of band between producer and Verifier. The Verifier MUST reject any proof whose signed psea_tier does not match the level expected for the operation being performed. * psea_op — operation / authority-context binding: a string identifying the operation the proof is presented for. The producer and Verifier agree on the value space out of band; the values are opaque to this profile. The Verifier MUST reject any proof whose signed psea_op does not equal the operation identifier for the operation being performed. This is the discriminator that prevents a proof minted for one operation from being accepted for another. * aud — the JWT audience claim ([RFC7519]): an identifier of the intended Verifier / audience. This profile restricts aud to a single case-sensitive string value; the array form that [RFC7519] otherwise permits is non-conformant in a PSEA proof, and a Verifier MUST reject a proof whose aud is an array or is absent. The Verifier MUST reject any proof whose signed aud does not identify it. * iss — the JWT issuer claim ([RFC7519]): the deployment / tenant identifier the Attester has locally available at sign time. The Verifier MUST reject any proof whose signed iss does not match the deployment / tenant the Verifier resolves for the request. All four checks MUST fire after the signed body's signature has been verified (so the bytes are confirmed authentic) and before any state mutation (counter consumption, ledger write, acknowledgement signing). The checks are byte-equality string comparisons; comparisons MUST NOT normalize case or whitespace. The expected psea_tier and psea_op values for a given operation are deployment-defined and agreed out of band; the proof also carries the aud and iss bindings above. Any additional, lower-assurance signed- token types a deployment defines (out of scope of this profile) carry the same binding claims under the same claim names with their own values. Yossif Expires 11 December 2026 [Page 34] Internet-Draft PSEA Token Profile June 2026 These bindings together close: (a) cross-operation replay (a captured proof for one operation presented for another), (b) cross-level downgrade (a higher-assurance proof processed as a lower-assurance one), and (c) cross-deployment replay (a captured proof presented to a different deployment's Verifier). The bindings are locally derivable at sign time without server round-trips, preserving the offline-capable property of proofs produced offline. The scope of this protection should not be over-read. The cross- replay binding defends against _capture-replay_ of an existing proof — a proof minted for one operation, level, audience, or deployment being presented for a different one. It does _not_ defend against a compromised host minting a _fresh_ proof for the wrong operation: because the host chooses the claim values it asks the user- verification-gated key to sign, a compromised host that obtains a user-verification ceremony can sign a proof carrying whatever psea_op / psea_tier / actionPayload it wishes. The user-verification gate constrains _that signing can occur_, not _what content is signed_. That compromised-host case is the What-You-See-Is-What-You-Sign problem and is treated in Section 6.8.2. 3.13.5. Caller-Identity Binding (psea_caller_package) When a deployment has enrolled an expected caller identity for the operation, a conforming Verifier MUST reject a proof whose signed psea_caller_package is absent or does not byte-exactly equal the expected value, before any state mutation. A deployment that has not enrolled an expected caller identity MUST NOT treat the claim's absence as failure. The binding is covered by the JWS signature; the comparison is a byte-equality string comparison that MUST NOT normalize case or whitespace. 3.14. Enrollment Lifecycle and Trust Gate (Verifier) The enrollment ceremony that binds a kid to an enrolled signing key and to a subject is deployment-specific and out of scope of this profile (Section 3.13.3). The enrollment _lifecycle states_ that the Verifier enforces on every proof are, by contrast, in scope and normative, because they are the trust gate that makes the rest of the profile meaningful: a valid signature from an enrolled key is necessary but not sufficient for acceptance. A conforming Verifier MUST maintain an authoritative, server-side enrollment lifecycle for each enrolled Attester with at least the states active, suspended, and revoked, and MUST reject any proof whose enrollment is not in the active state. This enrollment-status check is authoritative: this profile carries no self-asserted wire trust-state field, and a Verifier MUST NOT derive the trust state Yossif Expires 11 December 2026 [Page 35] Internet-Draft PSEA Token Profile June 2026 from any value the Attester supplies. The check MUST be applied after signature verification and before any state mutation. The transitions between these states, and the events that trigger them, are deployment-specific; the requirement here is only that the three states exist and gate acceptance. The Elevation-of-Privilege analysis in Section 6.4.6 relies on this requirement. 3.15. Versioning The psea_proof_version claim identifies the wire-format revision the producer targets. This revision uses "1". Future revisions MAY extend the value space; a Verifier MUST reject a proof carrying an unknown version value. Conforming implementations at this revision emit only "1"; the version field is included in the signed payload so that the wire-version commitment is cryptographically anchored. 4. Relationship to WebAuthn and FIDO Transaction Confirmation WebAuthn and FIDO2 provide phishing-resistant, hardware-backed authentication for the login boundary. Their transaction- confirmation features do not provide the per-action execution-time action-binding this profile defines, for the following specific reason. Web Authentication Level 1 ([WebAuthn-L1]) defined two transaction- confirmation extensions: txAuthSimple (display a text prompt and bind the user's approval of that exact text into the signed assertion) and txAuthGeneric (the same for a hashed content blob). These were the mechanism by which a WebAuthn assertion could attest that the user approved a specific transaction -- a What-You-See-Is-What-You-Sign (WYSIWYS) binding. No browser implemented these extensions, and they were removed in Web Authentication Level 2 ([WebAuthn-L2]). A current WebAuthn assertion therefore attests that an authenticator holding a given credential was exercised with user presence (and optionally user verification), but it does not cryptographically bind the assertion to a specific application-level action or to human- readable transaction content. Consequently, the transaction-binding / WYSIWYS property -- proof that a present, verified human approved a specific named action, with specific content, at the moment of execution -- is not provided by any deployed authentication standard today. PSEA addresses precisely this gap: a PSEA proof binds the action identity and a SHA-256 hash of the action payload (the fail-closed action-binding defined later in this document) into a hardware-signed Attestation produced at execution time. PSEA is complementary to WebAuthn and FIDO rather than a replacement: WebAuthn and FIDO2 remain appropriate for establishing the session and verifying the human's credential, while Yossif Expires 11 December 2026 [Page 36] Internet-Draft PSEA Token Profile June 2026 PSEA supplies the per-action execution-time Evidence that the transaction-confirmation extensions were intended to provide but, in deployed form, do not. 5. Relationship to OAuth 2.0 Step-Up Authentication OAuth 2.0 Step-Up Authentication Challenge [RFC9470] defines a mechanism by which an OAuth-protected resource server signals to a client that the bearer access token presented does not satisfy the resource's authentication requirements. The resource server responds with HTTP 401 and a WWW-Authenticate challenge carrying a required Authentication Context Class Reference (acr_values) and/or a maximum authentication age (max_age). The client then drives the user through re-authentication and obtains a new access token that satisfies the requirement. RFC 9470 and PSEA address adjacent but distinct points in the access- control chain. Both react to the same operational gap: an access token or session that was sufficient at issuance time may be insufficient at the moment a higher-risk action is requested. They differ in the unit of escalation and in the cryptographic properties of the artifact produced. 5.1. Comparison +================+=====================+=========================+ | Property | RFC 9470 step-up | PSEA | +================+=====================+=========================+ | Unit of | The access token | The individual action | | escalation | (session-scoped). | (action-scoped). | +----------------+---------------------+-------------------------+ | Artifact | A new bearer access | Evidence (signed proof | | produced | token, possibly | token; see Section 3) | | | with refreshed acr | cryptographically bound | | | / auth_time claims. | to the specific action | | | | payload. | +----------------+---------------------+-------------------------+ | Scope of | Subsequent requests | The single action whose | | authority | within the resource | payload is bound by the | | granted | server's session | Evidence. No | | | policy, until the | subsequent action | | | new token expires | inherits authority. | | | or fails its own | | | | freshness check. | | +----------------+---------------------+-------------------------+ | Connectivity | Re-authentication | Deployment-dependent: a | | requirement | requires | proof MAY be produced | | | reachability of the | offline with deferred | Yossif Expires 11 December 2026 [Page 37] Internet-Draft PSEA Token Profile June 2026 | | authorization | Verifier interaction, | | | server. | or require synchronous | | | | Verifier interaction, | | | | per deployment policy | | | | (out of scope). | +----------------+---------------------+-------------------------+ | Action-payload | Not defined. The | Required for every PSEA | | binding | new token does not | proof. The Evidence | | | bind to any | body contains the | | | specific resource | action's payload hash; | | | or operation. | see Section 3.13. | +----------------+---------------------+-------------------------+ | Authentication | Conveyed via | Conveyed via the | | context | acr_values; | abstract capability/ | | | identifiers are | assurance indicator and | | | registry-managed | other fields in the | | | and opaque to OAuth | Evidence. | | | itself. | | +----------------+---------------------+-------------------------+ Table 1 5.2. Complementarity RFC 9470 step-up and PSEA MAY be composed: the first to signal that a per-action authority check is required; the second to produce the cryptographically action-bound Evidence that satisfies that check. 1. An OAuth-protected resource server, acting as a Relying Party, receives a request whose access token does not satisfy the resource's per-action policy. 2. The resource server returns HTTP 401 with a WWW-Authenticate challenge per [RFC9470], indicating the required step-up. 3. The client drives the step-up flow on a device hosting a PSEA Attester. The Attester produces fresh Evidence at the capability level the resource's policy demands, cryptographically bound to the specific action that triggered the 401. 4. The client re-submits the request, conveying the Evidence to the Verifier. The Verifier appraises the Evidence and produces an Attestation Result. The resource server gates the action on both the OAuth access token (session validity) and the Attestation Result (per-action authority). Yossif Expires 11 December 2026 [Page 38] Internet-Draft PSEA Token Profile June 2026 In this composition, OAuth supplies the session and identity context; PSEA supplies the per- action cryptographic authority proof. Neither mechanism replaces the other. 5.3. Out of Scope for This Document This section identifies architectural complementarity. It does not define a normative integration profile between PSEA and [RFC9470]. A normative integration profile (specifying the precise WWW- Authenticate challenge syntax, the acr_values registration for PSEA capability/assurance levels, the error-mapping table between RFC 9470 challenges and PSEA error codes, and the conveyance of the Evidence in the re-submitted request) is deferred to a future document. 6. Security Considerations 6.1. Scope and Method This section enumerates the threats this document addresses, the assumptions on which the protocol's security properties rest, and the residual risks. The method is a STRIDE decomposition (Spoofing, Tampering, Repudiation, Information Disclosure, Denial of Service, Elevation of privilege) applied to the protocol's wire surface; threats specific to a particular deployment's policy or non-protocol implementation choices are out of scope. 6.2. Attester Assumptions The protocol's security properties depend on the following assumptions about a conforming Attester: A1. Hardware-protected signing key The Attester's signing key is generated in and never leaves a hardware-protected key store (for example a TEE, a Secure Enclave, a StrongBox, a smartcard secure chip, or a programmable secure element). The authenticator's attestation chain, verified by the Verifier against a trust anchor (Section 6.2), provides cryptographic evidence of this property. A2. Contemporaneous user-verification gating The Attester's signing key is gated by a platform user-verification ceremony such that signing cannot complete without a successful, contemporaneous user-verification event (see Section 3.7). The mechanism by which the platform implements this gating is out of scope; the Attester's assertion of the property is appraised through the platform attestation. A3. Platform user-verification subsystem integrity The Attester Yossif Expires 11 December 2026 [Page 39] Internet-Draft PSEA Token Profile June 2026 relies on the integrity of the platform user-verification subsystem (for example, a platform biometric subsystem, PIN entry into a Secure Enclave, hardware-token PIN handling, smartcard or magnetic-stripe-with-PIN reader logic). This is a platform guarantee; PSEA does not attempt to verify platform user- verification subsystem internals. A4. Authenticator attestation as a trust anchor The Verifier holds the authenticator's attestation root (for example an Android Key Attestation root, an Apple App Attest root, a hardware-token vendor root, or a smartcard issuer root) as a trust anchor. The Verifier's appraisal of attestation chains is bounded by the authenticator's published chain-validation rules. 6.3. Enrollment Is the Root of Trust Every security property in this document is conditional on one out- of-scope step: the enrollment ceremony that binds an enrolled signing key (selected at verification time by kid) to the correct device and the correct subject. This is stated as an out-of-scope assumption in O3 (Section 6.7), but its consequence is foundational and is called out here explicitly so it is not understated: if enrollment binds the wrong key, the entire chain of guarantees is anchored to the wrong hardware, and every downstream check in this profile still passes. Concretely, an adversary who can complete the deployment's enrollment ceremony with hardware the adversary controls — enrolling the adversary's own hardware-protected key as if it were the victim's device — thereafter produces proofs that are valid in every respect this profile can check: the signature verifies against the enrolled key, the attestation chain is genuine (it attests the adversary's real hardware), the user-verification gate fires (on the adversary), the action binding holds, and the counter and jti checks pass. The Verifier has no in-protocol signal that the enrolled key belongs to the wrong person, and the substitution persists for the lifetime of the enrollment. The forged-binding cannot be detected by the wire protocol; it can be detected only by the strength of the enrollment ceremony and by out-of-band identity proofing. Deployments therefore MUST treat enrollment as the security-critical root of the whole system and apply identity-proofing, attestation freshness, and binding controls commensurate with the authority the resulting proofs will carry. No property claimed elsewhere in this document is stronger than the enrollment binding it rests on. Yossif Expires 11 December 2026 [Page 40] Internet-Draft PSEA Token Profile June 2026 6.4. STRIDE Threats Addressed 6.4.1. Spoofing S1. _Attacker forging Evidence on behalf of an Attester._ Mitigated by hardware-protected signing keys (A1) and the Verifier's appraisal of the attestation chain. An attacker without access to the hardware key store cannot produce a valid signature, so the Verifier rejects the proof. The JOSE header hardening of Section 3.4 additionally closes algorithm- substitution, alg:"none", and attacker-supplied-key (jwk / jku / x5u) forgery vectors: the Verifier accepts only ES256 and resolves the verification key solely from the enrolled record selected by kid. S2. _Attacker presenting a recorded user-verification artifact._ Mitigated by contemporaneous gating (A2): the platform user- verification ceremony is required at the moment of signing. The Attester delegates user-verification to platform mechanisms; the attestation chain proves the gating is in place. Residual risk: bounded by the platform's user-verification anti-spoofing capability (e.g., presentation-attack detection in biometric subsystems, tamper resistance of hardware-token / smartcard readers, PIN-shoulder- surfing mitigations). S3. _Compromised host pre-minting a batch of proofs from a single user-verification event._ If the signing key were gated by a duration- or window-based user-verification policy (one ceremony unlocking the key for an interval), a compromised host could sign a stack of future proofs — each with a distinct jti, an increasing psea_counter, and a distant exp — from one ceremony, and every such proof would pass the wire checks. Mitigated by the per-operation gating requirement of Section 3.7: each proof signature MUST be preceded by its own fresh user-verification event, so the number of valid proofs is bounded by the number of ceremonies and pre-minting is not reachable. This mitigation is subject to the same attestation-conditionality as the psea_uv claim (Section 3.7.1): the Verifier can confirm that the signing key is gated per operation (rather than under a duration- or window-based policy that would permit pre-minting) only where the platform attestation conveys the key's user-verification-gating configuration. Where the attestation conveys it, the Verifier MUST reject a proof whose attested key properties show a duration- or window-based gating policy, and pre- minting is attested-closed. Where the attestation does not convey the gating configuration, per-operation gating rests on a documented trust assumption in the Attester rather than an attested property, and a compromised host that configures window-based authentication could pre-mint without the Verifier detecting it from the attestation; for high-assurance operations a Verifier SHOULD reject Yossif Expires 11 December 2026 [Page 41] Internet-Draft PSEA Token Profile June 2026 or require an additional independent factor in that case, as for psea_uv. Residual risk: a host that subverts the platform user- verification subsystem itself (O1) is out of scope. 6.4.2. Tampering T1. _Attacker modifying Evidence in transit._ Mitigated by the signed body's ECDSA P-256 signature. Any tampering of the signed octets causes signature verification to fail and the Verifier to reject the proof. T2. _Attacker swapping action payloads between proof and request._ Mitigated by the action-binding fail-closed check (Section 3.13.2): the Verifier recomputes the payload hash and rejects the proof on mismatch. T3. _Attacker re-using a captured proof against a different request._ Mitigated by the monotonic counter (Section 3.10) and by the action- binding (T2). The counter prevents re-issuance with the same counter value; the action-binding prevents reuse of a proof against a different payload. 6.4.3. Repudiation R1. _Subject claims they did not approve an action._ Mitigated by the device-bound signature (binding to a specific physical device) plus the contemporaneous user-verification ceremony (binding to a human at that moment). The per-proof psea_user_hash claim (Section 3.8) provides an additional Attester commitment to subject identifier for audit-trail purposes; it does not affect the cryptographic non- repudiability, which rests on the device-bound key and the presence Evidence binding. 6.4.4. Information Disclosure I1. _User-verification template leakage._ Out of scope (the user- verification template is platform-internal; PSEA does not transit or store it). I2. _Subject identifier leakage via wire fields._ Reduced — not eliminated — by hashing: the wire carries SHA-256 hashes of subject identifiers, not the raw identifiers, so the raw value and the biometric template never transit. Hashing is not anonymization; an unsalted hash of a low-entropy identifier is reversible and linkable. See Section 7.2 for the treatment and the salt / pairwise-derivation mitigations. Yossif Expires 11 December 2026 [Page 42] Internet-Draft PSEA Token Profile June 2026 I3. _Wire-protocol leak via verbose error responses._ Mitigated by constraining rejection responses to a fixed set of abstract outcomes without leaking deployment-internal diagnostic detail to the Attester. 6.4.5. Denial of Service D1. _Rate-flooding of Verifier endpoints._ Mitigated by per- deployment rate limiting. D2. _Quota exhaustion of Verifier processing._ Mitigated by per- deployment rate limiting and by implementation-specific quota controls (an exhausted-quota rejection is out of scope for this protocol and is not assigned a PSEA wire response code). 6.4.6. Elevation of Privilege E1. _Attester signing a proof while it should be locally untrusted._ Mitigated by the authoritative server-side enrollment lifecycle the Verifier maintains, specified normatively in Section 3.14: the Verifier rejects any proof whose enrollment is not in the active state. This server-side enrollment-status / revocation check is the trust gate, so a misbehaving or compromised Attester that signs a proof it should have withheld cannot bypass a suspended or revoked state. This profile carries no self-asserted wire trust-state field; the Verifier's enrollment record, not any Attester self-assertion, is authoritative. E2. _Attester emitting proofs after local-state revocation._ Mitigated by the Verifier's enrollment lifecycle: even if a misbehaving Attester continues to emit proofs after local revocation, the Verifier rejects them. 6.5. Verifier State Integrity: Sharding and Rollback The replay defenses of Section 3.10 — the strictly-increasing psea_counter compared-and-advanced atomically per (Attester, counter scope), and the global jti uniqueness check that finalizes each action identifier exactly once — are stated as logical, single-domain guarantees. A horizontally-scaled (sharded) Verifier deployment and the durability of the Verifier's state both bear on whether those guarantees actually hold, and neither is closed by the wire format alone. _Sharding / distributed serialization._ The atomic compare-and- advance of Section 3.10 assumes a single transactional domain per (Attester, counter scope), and the jti uniqueness check assumes a globally consistent index. A deployment that spreads verification Yossif Expires 11 December 2026 [Page 43] Internet-Draft PSEA Token Profile June 2026 across multiple nodes MUST preserve these assumptions: all submissions for a given (Attester, counter scope) MUST be serialized to a single authority (for example by routing or partitioning on the Attester identity, or by a shared transactional store that serializes per scope), and the jti finalization index MUST be globally consistent across all nodes that can accept proofs for the deployment. A design in which two nodes can independently advance the same scope's counter, or independently finalize the same jti, without a serializing authority is non-conformant: it reopens the concurrent-double-accept and counter-regression surfaces that the atomicity requirement of Section 3.10 exists to close, this time at the storage tier rather than at the single-node transaction. _Rollback / durability._ Section 3.10 prevents an Attester from regressing its counter; the symmetric risk is the Verifier regressing its own stored high-water mark and jti set. If the Verifier's counter / jti state is restored from an older backup or otherwise rolled back, counter values and jti values consumed since that backup become acceptable again, reopening the replay surface for proofs still within their exp window. A conforming Verifier MUST protect its replay state (the per-scope high-water-mark counters and the finalized-jti set) against rollback, such that a restore or failover does not lower a stored high-water mark or forget a finalized jti that could still be replayed within the exp window. This is the server-side mirror of the client-side regression the counter model forbids; durability of the replay state is part of the replay defense, not an operational afterthought. 6.6. Future Work: Relying Party Counter-Signature The current protocol provides cryptographic action-binding between the Attester and the Verifier. A future extension MAY introduce a Relying-Party counter-signature primitive in which the Relying Party countersigns the Attestation Result, producing a three-party signed artifact that binds the action approval to (a) the Subject (via the Attester's hardware key + user- verification), (b) the Verifier's appraisal, and (c) the Relying Party's policy acceptance. This three-party binding would close the residual risk that a compromised Relying Party accepts an Attestation Result it should have rejected on policy grounds. The wire-level primitive is informative-only at this revision; a normative specification is deferred to a future document. 6.7. Threats Out of Scope The following threats are acknowledged but are out of scope of the wire protocol: Yossif Expires 11 December 2026 [Page 44] Internet-Draft PSEA Token Profile June 2026 O1. Platform user-verification subsystem compromise Compromise of the platform user-verification subsystem (biometric subsystem, Secure Enclave, hardware-token reader, smartcard reader, or equivalent). Bounded by platform vendor guarantees; PSEA appraises the resulting attestation but does not verify platform internals. O2. Insider threat at the Verifier or Relying Party An insider with administrative access to the Verifier or Relying Party can subvert appraisal regardless of the wire protocol. Deployments SHOULD apply standard operational controls (separation of duties, audit logging, key custodianship). O3. Pre-enrollment trust establishment The protocol assumes that an enrollment ceremony validly binds an Attester to a subject identity. Deployment-specific enrollment policies are out of scope. This is the root-of-trust assumption for the entire profile and its consequence (a forged enrollment binding yields fully-valid proofs anchored to the wrong hardware) is treated explicitly in Section 6.3. 6.8. Known Open Problems The following are attack surfaces that PSEA does not solve and that remain unsolved at the authenticator/platform layer at the time of writing. They are documented so that deployers and reviewers can assess residual risk in their own deployment context, and each is a candidate for future research and protocol evolution. 6.8.1. Coercion and Duress An attacker physically present with the legitimate subject can compel the subject to perform the user-verification ceremony. The resulting proof is cryptographically indistinguishable from a freely-given approval: the signed body shows the correct hardware key, the contemporaneous user-verification event happened, and the action payload binds correctly. Why this is hard for any authenticator: the platform user- verification APIs do not expose which finger was used, which face geometry matched, which PIN was entered, or whether the subject appeared distressed. The Attester sees only a binary "verification succeeded." A duress-code scheme (e.g., a specific finger reserved for duress, a specific PIN suffix) would require either (a) platform- level API changes to surface which credential was used so the Attester can interpret it, or (b) the application binding distinct credentials to distinct server-side meanings — but on face-based verification this is effectively impossible because there is no way Yossif Expires 11 December 2026 [Page 45] Internet-Draft PSEA Token Profile June 2026 to enroll a "duress face." This remains an open problem; deployments that require duress detection today rely on out-of-band mechanisms (transaction-monitoring rules, behavioral analytics, secondary channels) that lie outside this protocol. 6.8.2. What-You-See-Is-What-You-Sign (WYSIWYS) The property PSEA guarantees, for every PSEA proof, is *action- binding*: what is signed is what the Verifier executes. The fail- closed action-binding check (Section 3.13.2) ties the signed proof to the exact action payload via psea_payload_hash, so the signature-to- execution binding is cryptographically enforced and a captured proof cannot be replayed against a different payload. What PSEA does not guarantee on a compromised device is the eye-to- signature binding — that what the human actually saw on screen at the moment of the user-verification ceremony is identical to what was signed. A compromised UI layer or a malicious overlay can display "Approve $10 transfer to Alice" while the underlying action payload submitted to the Verifier is "$10,000 transfer to Mallory." The hardware key signs the payload it was given, not the pixels the human saw. PSEA binds signature to execution; it does not, by itself, bind the human's perception to either. It is important to state the degraded-mode value plainly rather than leave it implied. On a fully compromised display — or, equivalently, where a compromised Relying Party or in-path modifier substitutes a plausible-but-tampered payload that the human did not intend — PSEA does _not_ prevent execution of the unintended action: the tampered payload is signed by the genuine hardware key under a genuine user- verification event, so the action-binding check passes on it. What PSEA retains in that case is forensic / non-repudiation value: the signed proof is durable, hardware-anchored evidence of exactly what was signed (and that a user-verification event gated the signing), establishing after the fact what the device actually committed to. PSEA's contribution on a compromised display/RP is therefore non- repudiation, not prevention; prevention of the eye-to-signature mismatch requires the trusted-display path below, which is out of scope. Why this is hard for any authenticator: full WYSIWYS requires a trusted display path the application cannot influence — pixels rendered by a trusted execution path (for example a Trusted Execution Environment), with the user-verification ceremony tied to a render- of-record that the platform attests to. Some platforms have partial support (e.g., trusted-UI on certain TEEs), but the API surface for application developers to express "render THIS exact content in trusted UI before signing" is not generally available across Yossif Expires 11 December 2026 [Page 46] Internet-Draft PSEA Token Profile June 2026 authenticator platforms in a way that survives platform UI redesigns. *Trusted-display / secure-UI is out of scope of this specification* (it is platform-dependent and not universally available) and remains the open problem. Mitigation for high-consequence actions: for high-consequence operations, deployments SHOULD use a server-signed confirmation round-trip. In this RECOMMENDED pattern the Verifier signs the canonical action it is about to execute and returns it to the authenticator for display and a user-verification step before the action commits, giving the signed content an independent, server- anchored origin rather than one chosen entirely by a potentially- compromised client UI. This is a SHOULD / RECOMMENDED measure for high-consequence operations, not a universal MUST, and it reduces but does not eliminate the residual risk on a fully compromised display. Out-of-band channels vulnerable to SIM-swap or one-time-passcode interception (for example, SMS OTP) are NOT RECOMMENDED as a WYSIWYS mitigation: they reintroduce exactly the channel-interception and credential-replay weaknesses PSEA exists to eliminate, and a deployment that layers them on does not obtain a trusted-display guarantee. Trusted display remains an open problem. 6.8.3. Subject-Identity Limits PSEA proves _a_ human was present and approved this action. It does not identify _which_ human, beyond the deployment-issued subject identifier the Attester commits to (psea_user_hash — an opaque commitment, not a cryptographic identity binding). Subject identity attribution — KYC, anti-money-laundering, multi-user-on-one-device scenarios — is the responsibility of the deployment's enrollment ceremony and out-of-band identity proofing. A device legitimately enrolled to user A whose user-verification credential is then re- enrolled to user B will produce proofs that the platform attests contemporaneously gated by user B's verification; PSEA cannot detect this. Deployments requiring strong subject identity binding rely on enrollment-time mechanisms (in-person ceremony, document verification, etc.) outside the wire protocol. 7. Privacy Considerations This section follows the guidance of [RFC6973]. PSEA Evidence is, by design, a device-bound and (via the user-verification gate) human- presence-bearing artifact; that same binding creates privacy exposure that deployers MUST understand. The principal concerns are the linkability of the stable per-device identifier (ueid) and the common but incorrect assumption that hashing an identifier anonymizes it. Yossif Expires 11 December 2026 [Page 47] Internet-Draft PSEA Token Profile June 2026 7.1. UEID Linkability The ueid claim (Section 3.2) is, within one deployment, a stable per- device identifier: it is the same value across every action a given device attests to a given issuer (iss). A Verifier therefore can, and by construction does, link all of a given device's proofs to one another within its deployment. This intra-deployment linkability is an inherent property of a device-bound attestation identifier, not a defect; this profile depends on the Verifier being able to bind successive proofs to one enrollment. To prevent the same physical device from being correlated _across_ deployments, the ueid MUST be derived pairwise per issuer: the UEID byte string is 0x01 || SHA-256(deviceId || iss) (Section 3.2), so the same device yields a different ueid for each distinct iss. Because iss is itself a signed claim bound into the proof, the derivation is verifiable: a Verifier recomputes the expected ueid for its own iss from the enrolled device-id input. The privacy rationale is that a single, globally-shared device identifier would let independent Relying Parties and deployments correlate one person's device activity across unrelated services; binding the identifier to iss confines linkability to the single deployment that legitimately requires it. This profile carries a deterministic per-issuer value under the RFC 9711 RAND type tag (0x01). This is a deliberate, disclosed design choice, not an oversight, and it warrants an explicit justification because the RAND type tag nominally denotes a randomly generated UEID ([RFC9711], Section 4.2.1), whereas the value this profile places under that tag is the deterministic derivation SHA-256(deviceId || iss). The cross-issuer unlinkability this profile requires is supplied here by the per-issuer derivation (a distinct, non- correlatable value per iss), not by randomness; within a single issuer the value is intentionally stable, because this profile depends on binding a device's successive proofs to one enrollment. The semantically purer vehicle for a stable-but-pairwise identifier of this kind is the EAT semipermanent UEID (sueids) claim ([RFC9711]), which is defined precisely for non-random, semipermanent per-relationship identifiers. The trade-off this revision weighed is the following. The sueids claim is the more exact EAT semantics, but adopting it adds a second identifier claim to the wire with its own array structure and per- entry labelling semantics, which every conforming Attester and every conforming Verifier must then produce and appraise. The RAND-tagged ueid reuses a single, already-specified 33-octet UEID encoding that all parties already implement, and the per-issuer derivation gives the required cross-issuer confinement (Section 7.1) without a second Yossif Expires 11 December 2026 [Page 48] Internet-Draft PSEA Token Profile June 2026 claim. This revision therefore chose one stable per-issuer ueid over introducing sueids handling, accepting the looser fit against the RAND tag's "randomly generated" connotation as the cost of that simplicity. The choice is recorded here so a consumer is not misled into treating the value as random: it is a per-issuer pseudonym, deterministic by construction and verifiable from the enrolled deviceId input. A future revision MAY migrate the per-issuer (and per-Relying-Party) identifier to the sueids form; that migration is the recommended direction for aligning the wire encoding with the EAT identifier semantics, and it composes with the per-Relying-Party unlinkability direction noted below. Per-issuer derivation does not provide per-Relying-Party unlinkability _within_ a single deployment, nor does it defeat correlation by other shared fields. A future revision MAY define a pairwise / sueids-style per-Relying-Party identifier derivation (in the spirit of the EAT semipermanent-UEID concept, [RFC9711]) so that one device presents a distinct, unlinkable identifier to each Relying Party within a deployment; this is the path to per-RP unlinkability and is RECOMMENDED as the direction for deployments with strong unlinkability requirements. The same "hashing is not anonymization" caution that applies to psea_user_hash (Section 7.2) applies to the deviceId input of the ueid derivation. If deviceId is a low-entropy or enumerable value (for example a hardware serial number or other guessable platform identifier), then SHA-256(deviceId || iss) with a known iss is recoverable by brute force, defeating the confinement the per-issuer derivation is meant to provide. A deployment SHOULD use a high- entropy, per-enrollment random value as deviceId (a value generated at enrollment and not derived from a stable hardware identifier), so that the derived ueid is not recoverable from guessable inputs and is not a globally stable value computable by any other party. 7.2. Hashing Is Not Anonymization PSEA wire fields carry SHA-256 hashes of identifiers (the device-id hash inside ueid, and the OPTIONAL psea_user_hash subject hash) rather than the identifiers themselves. Hashing reduces casual exposure of the raw value, but it MUST NOT be relied upon as a privacy or anonymization guarantee. An *unsalted* hash of a *low- entropy* identifier — a phone number, an account number, an email address, a national ID, or any identifier drawn from a small or enumerable space — is reversible by brute-force or dictionary attack: an adversary who can compute the same hash function over candidate inputs recovers the input, and two systems that hash the same identifier produce the same digest, making the hash a stable, globally linkable identifier in its own right. Yossif Expires 11 December 2026 [Page 49] Internet-Draft PSEA Token Profile June 2026 Where linkability or re-identification of the hashed identifier matters, a deployment SHOULD either (a) salt or pepper the hash input with a per-deployment secret that is not published with the proofs, so the digest is not a globally stable value computable by any other party, or (b) derive a pairwise identifier per Relying Party (see Section 7.1), so the hashed value is not a single stable identifier shared across contexts. A deployment MUST NOT treat a bare SHA-256 of a user or device identifier as sufficient to claim the wire field is non-identifying. The minimization PSEA does provide is that the _raw_ identifier and the biometric template never transit the wire (Section 6.4.4); that is a reduction in exposure, not anonymization. 7.3. Data Minimization at the Verifier The Verifier and Relying Party necessarily retain proof records to serve PSEA's audit-trail purpose, and those records are linkable per Section 7.1. Deployments SHOULD apply retention limits, access controls, and purpose limitation to stored proofs and Attestation Results consistent with their regulatory environment, and SHOULD NOT retain the OPTIONAL psea_user_hash beyond the audit-trail need it serves. Correlation of proofs with out-of-band identity (which natural person a ueid or psea_user_hash corresponds to) is established only at enrollment and is a deployment responsibility outside the wire protocol. 8. IANA Considerations 8.1. Summary of Requested Registrations This document requests IANA to register one media type and register a URN sub-namespace: * One media-type registration (Section 8.2). * Registration of the urn:ietf:params:psea URN sub-namespace (Section 8.3). Yossif Expires 11 December 2026 [Page 50] Internet-Draft PSEA Token Profile June 2026 This document does not request registration of the psea_* claims in the JSON Web Token Claims registry ([RFC7519], Section 10.1) or in the CBOR Web Token (CWT) Claims registry. The psea_* claims are profile-private extension claims whose semantics are meaningful only to a consumer that understands this eat_profile (Section 3.1); their names are scoped by the eat_profile claim rather than by a global registry, consistent with the strict, profile-scoped extensibility model of this document (Section 3.1.1). A future revision MAY register one or more psea_* claims in the JWT Claims registry should cross-profile reuse warrant a globally-managed name; this revision intentionally does not, to avoid reserving global names for semantics that are defined only relative to this profile. 8.2. Media Type Registration This document requests registration of the media type application/ psea+jwt in the "Media Types" registry, following the procedures of [RFC6838] and using the registered +jwt structured syntax suffix ([RFC7519]). The subtype carries the PSEA proof defined by this profile (protected-header typ = "psea-proof+jwt") per Section 3. The media type application/psea+jwt labels the object at the transport layer, and a consumer expecting a proof MUST verify the protected- header typ value (Section 3.4). The Verifier acknowledgement / Attestation Result is out of scope of this profile (Section 3.13.3); a deployment that represents that artifact as a JWS MAY reuse this media type with a distinct protected-header typ value (for example "psea-ack+jwt"), applying the explicit-typing guidance of [RFC8725], Section 3.11 so the two object types are not confused, but this document does not define that artifact. Type name application Subtype name psea+jwt Required parameters N/A Optional parameters N/A Encoding considerations 8bit; a PSEA token is a JWS Compact Serialization ([RFC7515]): a series of base64url-encoded values separated by period (".") characters. Security considerations See Section 6 of this document and the Security Considerations of [RFC7515] and [RFC7519]. In particular, a consumer MUST apply the JOSE header hardening of Section 3.4 (ES256 only; reject alg:"none"; ignore jwk/jku/x5u; verify typ; reject unknown crit parameters and the unencoded- payload option). Yossif Expires 11 December 2026 [Page 51] Internet-Draft PSEA Token Profile June 2026 Interoperability considerations See Section 3 and Section 2. Published specification This document. Applications that use this media type PSEA Attesters, Verifiers, and Relying Parties exchanging action-bound, user-verification-gated execution-authority Evidence and the corresponding Attestation Results. Fragment identifier considerations N/A Additional information Deprecated alias names for this type: N/A; Magic number(s): N/A; File extension(s): N/A; Macintosh file type code(s): N/A. Person & email address to contact for further information Mohamad Khalil Yossif Intended usage COMMON Restrictions on usage None Author Mohamad Khalil Yossif Change controller IETF A CWT/COSE representation ([RFC9052]) carrying the same EAT ([RFC9711]) and psea_* claim set is future work; this revision does not register a +cose media type. 8.3. URN Sub-namespace Registration (urn:ietf:params:psea) This document requests that IANA register the psea sub-namespace within the urn:ietf:params hierarchy, per the procedures of [RFC3553] (BCP 73). The registration enables stable, IANA-managed identifiers under urn:ietf:params:psea, of which the EAT profile identifier urn:ietf:params:psea:eat-profile:1 (Section 3.1) is the first assignment. The registration template (per [RFC3553], Section 4.3) is: Registry name PSEA (Post-Session Execution Assurance) Specification This document. Repository Identifier strings assigned under urn:ietf:params:psea by this and future PSEA documents. Yossif Expires 11 December 2026 [Page 52] Internet-Draft PSEA Token Profile June 2026 Index value Sub-strings of the form urn:ietf:params:psea:: are assigned by Specification Required [RFC8126]. The initial assignment is urn:ietf:params:psea:eat-profile:1. The urn:ietf:params hierarchy is managed conservatively and its sub- namespace registrations are normally associated with the IETF document stream. If this document is published on a stream for which a urn:ietf:params:psea sub-namespace registration is not granted, or if the registration is otherwise not completed, the profile identifier MUST fall back to the stable HTTPS URI https://yuthent.com/psea/eat-profile/1, under a namespace the author controls, carrying identical semantics. Conforming implementations MUST treat whichever single value this document's final published form fixes as the canonical eat_profile value; the two forms are not interchangeable on the wire within one deployment. The remainder of this document uses the urn:ietf:params:psea:eat-profile:1 form as the requested primary identifier. 9. Algorithm Agility and Operational Defaults 9.1. Cryptographic Algorithms 9.1.1. Mandatory-to-Implement (MTI) Conforming Attesters and Verifiers MUST implement: * Signature: ECDSA on the P-256 curve with SHA-256 ([FIPS180-4], [RFC7518]). * Hash: SHA-256 ([FIPS180-4]). * Encoding: canonical JSON per Section 2. 9.1.2. Post-Quantum Migration This revision does not specify a post-quantum signature suite. A future revision MAY add a ML-DSA-based suite ([FIPS204]) as an alternate or successor signature algorithm. The PSEA proof and the Verifier acknowledgement are JWS objects that carry the signature algorithm in the JWS protected alg header (ES256 is the mandatory-to- implement algorithm at this revision) and a protected kid header that provides the key-selection and key-rotation story; no PSEA JWS uses a fixed out-of-header algorithm. A dedicated rejection outcome for an unsupported algorithm is reserved for a future revision that admits more than one signature algorithm. Yossif Expires 11 December 2026 [Page 53] Internet-Draft PSEA Token Profile June 2026 9.1.3. Algorithm Negotiation Algorithm negotiation between Attester and Verifier is out of scope at this revision; the MTI algorithm is the only conforming choice. A future revision MAY introduce negotiation via a Verifier-published algorithm preference list at a deployment-specific well-known URL. 9.2. Operational Defaults The following operational defaults are RECOMMENDED for conforming deployments: Nonce TTL Deployment-defined; RECOMMENDED 60-300 seconds. Maximum proof lifetime (exp - iat) Deployment-defined (Section 3.11); RECOMMENDED 300 seconds for synchronously- submitted proofs, extended only as far as a deployment's offline- to-sync interval requires for proofs produced offline. Clock-skew tolerance Deployment-defined; SHOULD NOT exceed 60 seconds (Section 3.11). Operational grace window after enrollment Deployment-defined; RECOMMENDED 24 hours during which the Verifier accepts proofs from a freshly-enrolled Attester before requiring strict policy enforcement. Counter range The counter is a JSON integer in [0, 2^53 − 1] (Section 3.10); exhaustion is not a practical concern at any reasonable operational rate. 10. References 10.1. Normative References [RFC2119] Bradner, S., "Key words for use in RFCs to Indicate Requirement Levels", BCP 14, RFC 2119, March 1997, . [RFC3629] Yergeau, F., "UTF-8, a transformation format of ISO 10646", RFC 3629, November 2003, . [RFC4648] Josefsson, S., "The Base16, Base32, and Base64 Data Encodings", RFC 4648, October 2006, . Yossif Expires 11 December 2026 [Page 54] Internet-Draft PSEA Token Profile June 2026 [RFC3553] Mealling, M., Masinter, L., Hardie, T., and G. Klyne, "An IETF URN Sub-namespace for Registered Protocol Parameters", BCP 73, RFC 3553, June 2003, . [RFC6838] Freed, N., Klensin, J., and T. Hansen, "Media Type Specifications and Registration Procedures", BCP 13, RFC 6838, January 2013, . [RFC7515] Jones, M., Bradley, J., and N. Sakimura, "JSON Web Signature (JWS)", RFC 7515, May 2015, . [RFC7518] Jones, M., "JSON Web Algorithms (JWA)", RFC 7518, May 2015, . [RFC7519] Jones, M., Bradley, J., and N. Sakimura, "JSON Web Token (JWT)", RFC 7519, May 2015, . [RFC7797] Jones, M., "JSON Web Signature (JWS) Unencoded Payload Option", RFC 7797, February 2016, . [RFC8126] Cotton, M., Leiba, B., and T. Narten, "Guidelines for Writing an IANA Considerations Section in RFCs", BCP 26, RFC 8126, June 2017, . [RFC8174] Leiba, B., "Ambiguity of Uppercase vs Lowercase in RFC 2119 Key Words", BCP 14, RFC 8174, May 2017, . [RFC8259] Bray, T., Ed., "The JavaScript Object Notation (JSON) Data Interchange Format", STD 90, RFC 8259, December 2017, . [RFC8725] Sheffer, Y., Hardt, D., and M. Jones, "JSON Web Token Best Current Practices", BCP 225, RFC 8725, February 2020, . [RFC8785] Rundgren, A., Jordan, B., and S. Erdtman, "JSON Canonicalization Scheme (JCS)", RFC 8785, June 2020, . Yossif Expires 11 December 2026 [Page 55] Internet-Draft PSEA Token Profile June 2026 [RFC9334] Birkholz, H., Thaler, D., Richardson, M., Smith, N., and W. Pan, "Remote ATtestation procedureS (RATS) Architecture", RFC 9334, January 2023, . [RFC9711] Lundblade, L., Mandyam, G., O'Donoghue, J., and C. Wallace, "The Entity Attestation Token (EAT)", RFC 9711, December 2024, . [FIPS180-4] National Institute of Standards and Technology, "Secure Hash Standard (SHS)", FIPS 180-4, August 2015, . 10.2. Informative References [RFC6973] Cooper, A., Tschofenig, H., Aboba, B., Peterson, J., Morris, J., Hansen, M., and R. Smith, "Privacy Considerations for Internet Protocols", RFC 6973, July 2013, . [RFC9052] Schaad, J., "CBOR Object Signing and Encryption (COSE): Structures and Process", RFC 9052, August 2022, . [RFC9470] Bertocci, V. and B. Campbell, "OAuth 2.0 Step Up Authentication Challenge Protocol", RFC 9470, September 2023, . [FIPS204] National Institute of Standards and Technology, "Module- Lattice-Based Digital Signature Standard (ML-DSA)", FIPS 204, August 2024, . [WebAuthn-L1] W3C, "Web Authentication: An API for accessing Public Key Credentials Level 1", W3C Recommendation, March 2019, . [WebAuthn-L2] W3C, "Web Authentication: An API for accessing Public Key Credentials Level 2", W3C Recommendation, April 2021, . Yossif Expires 11 December 2026 [Page 56] Internet-Draft PSEA Token Profile June 2026 Appendix A. Canonical Encoding Test Vectors This appendix provides test vectors for verifying canonical-encoding implementations. An implementation that produces output matching every vector in this appendix is conformant with Section 2. Implementations SHOULD construct their own canonical-encoding test suite covering the canonical-JSON input that PSEA hashes (the action payload bound by psea_payload_hash) plus boundary cases for case- sensitive sort, mixed-case keys, integer serialization, escape forms, and UTF-8 multi-byte sequences. The PSEA proof and the acknowledgement are JWS objects verified over their received octets and so do not depend on canonical encoding for signature verification; only the action-payload hash is taken over canonical JSON octets. Implementations SHOULD maintain machine-readable golden vectors covering these dimensions; consulting or publishing them is informative and not a normative requirement of this specification. A representative subset, demonstrating the case-sensitive sort rule of Section 2.2, is reproduced here: A.1. Case-Sensitive Key Sort Input object (logical): { "endReason": "TtlExpired", "endedAt": 1700000060, "sessionId": "abc-123", "startedAt": 1700000000 } Canonical bytes (the keys ordered by case-sensitive Unicode code- point sort: 'R' = U+0052 = 82 sorts before 'e' = U+0065 = 101, so "endReason" precedes "endedAt"): {"endReason":"TtlExpired","endedAt":1700000060,"sessionId":"abc-123","startedAt":1700000000} A.2. Integer Serialization The integer 0 is serialized as the single character 0; the integer 42 as 42; the integer 1700000000000 as 1700000000000; no leading zeros, no decimal point, no exponent. A.3. Action-Payload Hash (End-to-End Worked Example) This vector demonstrates the one normative use of canonical encoding (Section 2): the action-payload binding. Given the logical actionPayload: Yossif Expires 11 December 2026 [Page 57] Internet-Draft PSEA Token Profile June 2026 { "amount": 2500, "actionType": "transfer", "to": "alice", "currency": "EUR" } the canonical encoding orders the keys by case-sensitive Unicode code-point sort (actionType < amount < currency < to), removes all inter-token whitespace, and serializes the integer with no decimal point or exponent, yielding the 69 canonical octets: {"actionType":"transfer","amount":2500,"currency":"EUR","to":"alice"} SHA-256 of those octets is, in lowercase hex: f0f8eb390ecdb3b312765cfe3a888c39ad4571bb94ddfc553230a4b85171e942 The psea_payload_hash claim is that digest in standard base64 with padding (Section 3.2): 8PjrOQ7Ns7MSdlz+OoiMOa1FcbuU3fxVMjCkuFFx6UI= A Verifier re-canonicalizes the received actionPayload, recomputes this digest, and compares it byte-for-byte against the signed psea_payload_hash (Section 3.13.2). The same 32-byte digest encoded as base64url without padding — the encoding used by ueid and psea_user_hash, not by psea_payload_hash — is 8PjrOQ7Ns7MSdlz- OoiMOa1FcbuU3fxVMjCkuFFx6UI; the difference (+ versus -, trailing = versus none) illustrates why the per-claim encoding split of Section 3.2 must be observed exactly. Appendix B. Conformance This appendix specifies conformance requirements for Attester, Verifier, and Relying Party implementations. B.1. Conformance Roles This document defines conformance for three roles: Attester, Verifier, Relying Party. B.2. Attester Conformance B.2.1. Requirements A conforming Attester: * MUST implement the canonical encoding (Section 2) and produce byte-identical canonical output for every test vector in Appendix A. Yossif Expires 11 December 2026 [Page 58] Internet-Draft PSEA Token Profile June 2026 * MUST generate its signing key in a hardware-backed key store and MUST NOT permit key extraction. * MUST gate signing on a fresh, per-operation platform user- verification event for any proof that carries a human-presence (psea_uv) claim — binding exactly one user-verification event to exactly one proof signature, never a duration- or window-based authorization (Section 3.7) — and MUST compute psea_payload_hash over the canonical action payload per Section 3.13.1. * MUST emit a signed proof body only when its internal trust state permits proof emission for the requested operation; MUST fail fast locally and emit no proof body otherwise. * MUST treat a revoking-class rejection from the Verifier as an instruction to transition local state to revoked. B.3. Verifier Conformance B.3.1. Requirements A conforming Verifier MUST perform every check below. The list is the authoritative enumeration of the Verifier obligations stated normatively in the body; an implementation that omits any item is non-conforming. Where ordering matters it is stated; in all cases the signature MUST be verified before any claim is trusted, and all binding/freshness checks MUST complete before any state mutation (counter advance, ledger write, acknowledgement signing). * MUST apply the JOSE header hardening of Section 3.4 before trusting any claim: accept only alg = "ES256", reject alg = "none", ignore any jwk / jku / x5u header key material, resolve the verification key only from the enrolled record selected by kid, verify the protected-header typ equals "psea-proof+jwt", and reject any unrecognized crit header parameter or an unencoded- payload ([RFC7797] b64:false) header. * MUST verify the ECDSA P-256 / SHA-256 signature against the enrolled public key, and thereafter read claims only from the verified payload. * MUST reject a proof whose eat_profile claim is absent or is not urn:ietf:params:psea:eat-profile:1 (Section 3.1), and a proof whose psea_proof_version is an unknown value (Section 3.15). Yossif Expires 11 December 2026 [Page 59] Internet-Draft PSEA Token Profile June 2026 * MUST validate freshness per Section 3.11: reject a proof whose exp is in the past or whose iat is implausibly in the future, applying only a small bounded clock-skew tolerance (SHOULD NOT exceed 60 seconds) and a bounded maximum proof lifetime (Section 9.2). * MUST, when it issued a challenge, reject a proof whose eat_nonce is absent or does not equal the issued value (Section 3.1.1), and MUST correlate the proof to the issued challenge using only the signed eat_nonce value, never an unsigned transport-body field (Section 3.11). * MUST require psea_uv.verified == true and reject otherwise, and MUST anchor the psea_uv claim to the authenticator's attested UV- enforcement where the attestation conveys it; where it cannot, MUST NOT treat human presence as attested and SHOULD reject for high-assurance operations (Section 3.7.1). * MUST implement the fail-closed action-binding check of Section 3.13.2: re-canonicalize the actionPayload, hash it with SHA-256, byte-compare against psea_payload_hash, and reject on mismatch or on a missing payload, before producing any approval- bearing response. This check MUST precede the counter comparison. * MUST verify the cross-replay binding of Section 3.13.4 (psea_tier, psea_op, aud, iss) by case- and whitespace-exact comparison, after signature verification and before any state mutation. * MUST, when the deployment has enrolled an expected caller identity for the operation, reject a proof whose signed psea_caller_package is absent or does not byte-exactly equal the expected value, before any state mutation (Section 3.13.5); a deployment that has not enrolled an expected caller identity MUST NOT treat the claim's absence as failure. * MUST enforce the monotonic psea_counter (Section 3.10): select the comparison bucket using only a cryptographically bound scope identifier, reject a value not strictly greater than the stored value for that scope, and treat the claim as a 64-bit unsigned integer. * MUST maintain the global jti uniqueness check (Section 3.10), finalizing each jti exactly once and retaining finalized jti values for at least the exp validity window. Yossif Expires 11 December 2026 [Page 60] Internet-Draft PSEA Token Profile June 2026 * MUST, in a horizontally-scaled deployment, serialize all submissions for a given (Attester, counter scope) to a single authority and keep the jti finalization index globally consistent across all nodes, so that the counter atomicity and jti uniqueness guarantees hold under sharding (Section 6.5). * MUST protect its replay state (per-scope high-water-mark counters and the finalized-jti set) against rollback, so a backup restore or failover does not lower a stored high-water mark or forget a finalized jti still replayable within the exp window (Section 6.5). * MUST, when the deployment-optional chain layer (Section 3.12) is enabled, perform the strict-equality psea_chain_prev linkage check of Section 3.12.3; a Verifier that does not enable the chain layer is not required to implement it. * MUST maintain an authoritative enrollment lifecycle (at minimum: active, suspended, revoked) as the trust gate, and MUST reject proofs whose enrollment is not active (Section 3.14). * MUST NOT use any unsigned transport-body field (for example requestId, proofId, signalReport) as an input to any security decision (Section 3.6). * MUST reject non-conforming proofs; the concrete rejection vocabulary is deployment-specific. * MUST produce integrity-protected Attestation Results for non-co- located Relying Parties (Section 3.13.3). B.4. Relying Party Conformance A conforming Relying Party: * MUST gate the action on the Verifier's Attestation Result. * MUST verify the integrity of the Attestation Result for non-co- located Verifiers. Author's Address Mohamad Khalil Yossif Yuthent Email: mohamad@yuthent.com URI: https://yuthent.com/psea Yossif Expires 11 December 2026 [Page 61]