TLS 1.3 Cipher Suites with Alternative Key-Schedule Profiles
draft-sullivan-tls-xof-ciphers-00
This document is an Internet-Draft (I-D).
Anyone may submit an I-D to the IETF.
This I-D is not endorsed by the IETF and has no formal standing in the
IETF standards process.
| Document | Type | Active Internet-Draft (individual) | |
|---|---|---|---|
| Author | Nick Sullivan | ||
| Last updated | 2026-07-06 | ||
| RFC stream | (None) | ||
| Intended RFC status | (None) | ||
| Formats | |||
| Stream | Stream state | (No stream defined) | |
| Consensus boilerplate | Unknown | ||
| RFC Editor Note | (None) | ||
| IESG | IESG state | I-D Exists | |
| Telechat date | (None) | ||
| Responsible AD | (None) | ||
| Send notices to | (None) |
draft-sullivan-tls-xof-ciphers-00
TLS N. Sullivan
Internet-Draft Cryptography Consulting LLC
Intended status: Standards Track 6 July 2026
Expires: 7 January 2027
TLS 1.3 Cipher Suites with Alternative Key-Schedule Profiles
draft-sullivan-tls-xof-ciphers-00
Abstract
TLS 1.3 builds its key schedule on HKDF over the cipher suite's hash.
This document defines TLS 1.3 cipher suites that build it on a deck
function over a single permutation instead, the one a deployment
already carries when it uses SHA-3, ML-KEM, or ML-DSA. One
permutation then runs the whole schedule, and a full handshake takes
about a third of the permutation calls an HKDF schedule over that
permutation would. Such a cipher suite names an AEAD algorithm
together with a schedule profile that defines every key-schedule
function the connection uses. The profile follows from the
negotiated cipher suite alone, so no new extension is defined and the
TLS 1.3 state machine and wire format are unchanged. Two profiles
are defined, one on the standard SHA-3 function and one on a faster
reduced-round variant of it.
Discussion Venues
This note is to be removed before publishing as an RFC.
Discussion of this document takes place on the Transport Layer
Security Working Group mailing list (tls@ietf.org), which is archived
at https://mailarchive.ietf.org/arch/browse/tls/.
Source for this draft and an issue tracker can be found at
https://github.com/grittygrease/draft-sullivan-tls-xof-ciphers.
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/.
Sullivan Expires 7 January 2027 [Page 1]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
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 7 January 2027.
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. Design Goals . . . . . . . . . . . . . . . . . . . . . . 4
1.2. Scope . . . . . . . . . . . . . . . . . . . . . . . . . . 5
2. Conventions and Definitions . . . . . . . . . . . . . . . . . 5
2.1. Transcript Hash . . . . . . . . . . . . . . . . . . . . . 7
3. Schedule Profiles . . . . . . . . . . . . . . . . . . . . . . 7
4. The Governing Profile . . . . . . . . . . . . . . . . . . . . 9
5. Keyed Derivations . . . . . . . . . . . . . . . . . . . . . . 10
5.1. Expanding a Retained Secret . . . . . . . . . . . . . . . 10
5.2. MAC . . . . . . . . . . . . . . . . . . . . . . . . . . . 11
5.3. Record Keys . . . . . . . . . . . . . . . . . . . . . . . 12
5.4. Key Update . . . . . . . . . . . . . . . . . . . . . . . 12
5.5. Finished and PSK Binder MACs . . . . . . . . . . . . . . 13
5.6. Exporters . . . . . . . . . . . . . . . . . . . . . . . . 14
5.7. Resumption PSK . . . . . . . . . . . . . . . . . . . . . 14
5.8. ECH Acceptance Confirmations . . . . . . . . . . . . . . 15
5.9. PSK Import Derivation . . . . . . . . . . . . . . . . . . 15
6. Cipher Suites and Code Points . . . . . . . . . . . . . . . . 16
7. The Deck Schedule . . . . . . . . . . . . . . . . . . . . . . 17
7.1. The Deck Schedule Interface . . . . . . . . . . . . . . . 18
7.1.1. Operations . . . . . . . . . . . . . . . . . . . . . 18
7.1.2. One-Shot Equivalence . . . . . . . . . . . . . . . . 19
7.2. Derivation Shapes . . . . . . . . . . . . . . . . . . . . 19
7.3. Key Schedule . . . . . . . . . . . . . . . . . . . . . . 20
7.3.1. Absent and Empty Inputs . . . . . . . . . . . . . . . 22
Sullivan Expires 7 January 2027 [Page 2]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
7.3.2. Suite Binding and Stage Secrets . . . . . . . . . . . 22
8. The TLS13-TURBOSHAKE256 Profile . . . . . . . . . . . . . . . 22
8.1. Instantiation . . . . . . . . . . . . . . . . . . . . . . 23
8.1.1. Required API Surface . . . . . . . . . . . . . . . . 23
8.2. MAC . . . . . . . . . . . . . . . . . . . . . . . . . . . 23
9. The TLS13-SHAKE256 Profile . . . . . . . . . . . . . . . . . 24
9.1. Instantiation . . . . . . . . . . . . . . . . . . . . . . 24
9.1.1. Required API Surface . . . . . . . . . . . . . . . . 25
9.2. MAC . . . . . . . . . . . . . . . . . . . . . . . . . . . 25
10. PSK Importer . . . . . . . . . . . . . . . . . . . . . . . . 25
11. Zero-RTT and Early Data . . . . . . . . . . . . . . . . . . . 26
12. Alerts . . . . . . . . . . . . . . . . . . . . . . . . . . . 26
13. Companion Mechanisms . . . . . . . . . . . . . . . . . . . . 27
13.1. Out of Scope . . . . . . . . . . . . . . . . . . . . . . 27
14. IANA Considerations . . . . . . . . . . . . . . . . . . . . . 27
15. Security Considerations . . . . . . . . . . . . . . . . . . . 28
15.1. Schedule-Profile Separation . . . . . . . . . . . . . . 28
15.2. PSK Profile Binding . . . . . . . . . . . . . . . . . . 28
15.3. Downgrade Resistance . . . . . . . . . . . . . . . . . . 29
15.4. PSK Entropy . . . . . . . . . . . . . . . . . . . . . . 29
15.5. Authentication Is Out of Scope . . . . . . . . . . . . . 29
15.6. Retained RFC 8446 Properties . . . . . . . . . . . . . . 30
15.7. TLS13-TURBOSHAKE256 Considerations . . . . . . . . . . . 30
15.7.1. Cryptographic Analysis . . . . . . . . . . . . . . . 30
15.7.2. Erasure Boundaries and One-Wayness . . . . . . . . . 33
15.7.3. Domain Separation . . . . . . . . . . . . . . . . . 34
15.7.4. Related Constructions . . . . . . . . . . . . . . . 34
15.8. TLS13-SHAKE256 Considerations . . . . . . . . . . . . . 35
15.9. Test Vectors . . . . . . . . . . . . . . . . . . . . . . 35
15.10. Out of Scope . . . . . . . . . . . . . . . . . . . . . . 35
16. References . . . . . . . . . . . . . . . . . . . . . . . . . 35
16.1. Normative References . . . . . . . . . . . . . . . . . . 35
16.2. Informative References . . . . . . . . . . . . . . . . . 36
Appendix A. Comparison with RFC 8446 . . . . . . . . . . . . . . 38
A.1. Invocation Count . . . . . . . . . . . . . . . . . . . . 40
Appendix B. Implementation Considerations . . . . . . . . . . . 43
Appendix C. Test Vectors . . . . . . . . . . . . . . . . . . . . 44
C.1. TLS13-TURBOSHAKE256 Vectors . . . . . . . . . . . . . . . 44
C.2. TLS13-SHAKE256 Vectors . . . . . . . . . . . . . . . . . 45
Appendix D. A Fully FIPS-Component Key Schedule (Informative) . 45
Author's Address . . . . . . . . . . . . . . . . . . . . . . . . 46
Sullivan Expires 7 January 2027 [Page 3]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
1. Introduction
Every TLS 1.3 [RFC8446] cipher suite builds its key schedule on HKDF
over the cipher suite's hash. This document defines cipher suites
that build it on a deck function instead, running the whole schedule
on one permutation, the one a deployment already carries when it uses
SHA-3, ML-KEM, or ML-DSA. Instantiating HKDF with a SHA-3 hash would
remove SHA-2 without changing how the schedule works. This document
changes the schedule itself, not the hash.
This document extends the agility TLS 1.3 already has, in which
groups, KEMs, signature schemes, PSKs, and AEAD algorithms are all
negotiated, to the key schedule itself. A TLS 1.3 cipher suite
normally identifies an AEAD algorithm and the hash used with HKDF.
The cipher suites defined here instead identify an AEAD algorithm and
a complete schedule profile:
cipher suite = AEAD algorithm + ScheduleProfile
A schedule profile (Section 3) defines every key-schedule computation
the connection uses: the transcript hash, the secret and key
derivations, the Finished and PSK binder MACs, and the Encrypted
Client Hello acceptance computations. The cipher suite selects the
profile by itself, through the ordinary cipher_suites and
cipher_suite fields, with no separately negotiated extension.
Both profiles express the schedule as one deck function [FARFALLE],
defined once for both in Section 7, and select different permutations
for it: TLS13-TURBOSHAKE256 (Section 8) uses the 12-round
TurboSHAKE256 [RFC9861], and TLS13-SHAKE256 (Section 9) uses the
24-round SHAKE256 [FIPS202]. Finished, PSK binder, and Encrypted
Client Hello acceptance values all use one MAC (Section 5.2).
1.1. Design Goals
A schedule profile turns the whole derivation surface of a connection
into one named, testable object. Every value comes from one
permutation family, every output binds the profile identity and the
governing cipher suite, and every derivation has a byte-exact test
vector (Appendix C). Neither profile uses SHA-2, HMAC, or HKDF in
any role, and the correspondence with RFC 8446 can be audited shape
by shape (Section 7.2). A deployment that already carries a Keccak
permutation for SHA-3, ML-KEM, or ML-DSA reuses it for the entire
schedule.
The alternative is to keep RFC 8446's HKDF schedule and give it a
SHA-3 hash. That inherits RFC 8446's analysis directly, and
Appendix D records a variant close to it.
Sullivan Expires 7 January 2027 [Page 4]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
The deck is faster than that alternative. HKDF is built on HMAC,
which runs every derivation as two nested hash calls, overhead that
exists only to key a hash not built for keying. A keyed sponge needs
no such wrapper: it produces each value in one squeeze, with no
separate extract step between stages.
Over the representative handshake of Appendix A, the deck costs 52
Keccak-f[1600] permutation calls against 156 for a hash-only HKDF-
SHA3-256. That factor of three follows from HKDF's definition over
HMAC, so no HKDF instantiation removes it.
1.2. Scope
This document does not define a new version of TLS. It changes no
wire structure and no state machine: the cipher suite code point is
negotiated in the cipher_suites field and selected in the ServerHello
as always, and the schedule profile is not independently negotiable.
A cipher suite of this document governs only the AEAD and the key
schedule. It does not by itself make a connection free of SHA-2:
certificate-based authentication is negotiated separately and
commonly relies on SHA-2. A deployment that requires a fully SHA-
2-free connection must additionally restrict itself to SHA-2-free
signature schemes and certificate chains, or use PSK-only
authentication (Section 15).
2. Conventions and Definitions
The key words "MUST", "MUST NOT", "REQUIRED", "SHALL", "SHALL NOT",
"SHOULD", "SHOULD NOT", "RECOMMENDED", "NOT RECOMMENDED", "MAY", and
"OPTIONAL" in this document are to be interpreted as described in
BCP 14 [RFC2119] [RFC8174] when, and only when, they appear in all
capitals, as shown here.
This document uses the following terms.
schedule profile: The set of algorithms and encodings, selected by a
TLS 1.3 cipher suite, that defines every key-schedule computation
of a connection (Section 3). Written ScheduleProfile when
referring to the named component of a cipher suite.
selected_cipher_suite: The cipher suite selected in the ServerHello
message, as a 16-bit integer. uint16(selected_cipher_suite)
yields its two-octet RFC 8446 encoding.
recorded cipher suite: For a resumption PSK, the cipher suite of the
ticket; for an imported PSK, target_ciphersuite (Section 10).
governing cipher suite: The cipher suite value a derived output
Sullivan Expires 7 January 2027 [Page 5]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
binds, determined by the rules of Section 4. For an output
computed before the server's selection is known (an early-stage
output when a PSK is offered, a PSK binder, a PSK import), it is
the PSK's recorded cipher suite. For every other output it is
selected_cipher_suite. Stage secrets and other values internal to
a schedule bind no cipher suite (Section 3).
trunk (stage trunk): The running deck accumulator for a schedule
stage (E, H, or T), which absorbs the stage's inputs, is forked
for the stage's leaf outputs, and is ratcheted to produce the
stage secret.
DHE: The (EC)DHE shared secret, computed as in RFC 8446,
Section 7.4.
Nk, Nn: The AEAD key and nonce lengths of the selected cipher suite,
in octets.
FLen: The length of Finished and PSK binder verify_data: 64 octets
in both profiles of this document.
uint16(n): The two-octet big-endian encoding of n, as in the TLS
presentation language.
||: Octet-string concatenation.
x[a..b]: Octets a through b-1 of the octet string x, indexed from
zero.
frame(x): uint16(len(x)) || x, where len(x) is the octet length of
x.
Strings are length-prefixed only: they are not null-terminated or
otherwise padded after x. Both profiles of this document build
every derivation input from framed items, so inputs are
injectively encoded. Inputs longer than 0xFFFE octets do not
occur: variable-length public values are reduced by the transcript
hash or explicitly bounded before framing, and the one variable-
length secret input, an external PSK, is bounded by Section 10.
An empty value contributes frame("") wherever it is framed, encoding
as the two octets 0x0000 with no payload octets. An absent input
omits its framed items entirely. Omitting an input is not the same
as framing an empty value.
Sullivan Expires 7 January 2027 [Page 6]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
2.1. Transcript Hash
The transcript hash is an unkeyed 64-octet hash defined by the
schedule profile of the governing cipher suite (Section 8,
Section 9). TranscriptHash is computed over the handshake transcript
as in RFC 8446, Section 4.4.1: message type and length fields are
included, and record-layer framing is excluded. TranscriptHash
accepts any octet string. The RFC 8446 rules define only how the
handshake transcript is serialized before hashing, and the same
function is applied to non-transcript inputs such as exporter labels
and imported PSK identities. For a HelloRetryRequest, the RFC 8446
Section 4.4.1 synthetic-message construction is retained,
substituting TranscriptHash for Hash. In both profiles of this
document, TranscriptHash takes no cipher suite input, so a client can
compute its checkpoints before the ServerHello. Cipher suite binding
happens at output derivations only.
This document uses the following checkpoint values:
TH_CH0: TranscriptHash of the partial ClientHello transcript of RFC
8446, Section 4.2.11.2: the handshake messages through the
ClientHello, with the ClientHello truncated after the
PreSharedKeyExtension.identities field and the binders list
excluded. After a HelloRetryRequest, this partial transcript
includes the first ClientHello and the HelloRetryRequest via the
synthetic-message construction of Section 2.1, exactly as in RFC
8446.
TH_CH: TranscriptHash(ClientHello).
TH_SH: TranscriptHash(ClientHello up to and including ServerHello).
TH_SF: TranscriptHash(ClientHello up to and including the server
Finished message).
TH_CF: TranscriptHash(ClientHello up to and including the client
Finished message).
For a Finished MAC computed by either peer, the covered transcript is
taken up to but not including the Finished message being computed,
consistent with RFC 8446, Section 4.4.4.
3. Schedule Profiles
A schedule profile is a set of algorithms and encodings selected by a
TLS 1.3 cipher suite. A schedule profile specifies:
Sullivan Expires 7 January 2027 [Page 7]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
* profile_id, a fixed octet string naming the profile, bound into
its derivations;
* SecretLen, the length of stage and traffic secrets;
* FLen, the length of Finished and binder verify_data;
* TranscriptHash(messages), the unkeyed transcript hash of
Section 2.1;
* the derivation of initial and stage secrets from PSK and key-
exchange inputs (an extract operation, a stage accumulator, or an
equivalent construction);
* the derivation of every handshake, application, exporter, and
resumption secret;
* the Finished MAC and PSK binder computations;
* record key and IV derivation;
* traffic-secret update;
* exporter derivation;
* resumption PSK derivation;
* the Encrypted Client Hello acceptance computations; and
* the domain-separation and input-framing rules its derivations use.
A schedule profile is not independently negotiated. It is selected
solely by the negotiated cipher suite: the ClientHello cipher_suites
field offers, and the ServerHello cipher_suite field selects, as in
RFC 8446, Section 4.1. Future specifications may define additional
schedule profiles by registering new TLS 1.3 cipher suites whose
definitions include the complete profile.
Every derivation of a schedule profile MUST bind at least the
following into the input of the underlying primitive: a protocol
identifier (the profiles of this document use profile_id strings
beginning "TLS 1.3"), the profile_id, the governing cipher suite for
any output that leaves the schedule, the derivation label, the output
length (a profile MAY instead fix the length of an internal stage
secret as a profile constant, provided the operation that produces it
is domain-separated from every variable-length operation), the
transcript checkpoint or other public context where applicable, and
the secret input or the stage that carries it. All variable-length
Sullivan Expires 7 January 2027 [Page 8]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
items MUST be length-framed. No two distinct derivation paths may
produce identical encoded inputs to the underlying primitive unless
they intentionally derive the same value.
Both profiles of this document bind the output length as uint16, so
no output longer than 65534 octets is derivable. The one derivation
whose length is caller-chosen is the exporter: an implementation MUST
reject a TLS-Exporter request for more than 65534 octets rather than
reduce the requested length modulo 65536, which would let two
different requested lengths bind the same encoded value. Every other
output length in this document is a profile constant or Nk + Nn, all
far below the bound, so the exporter is the only derivation where
this rejection can occur.
4. The Governing Profile
Every output of a schedule profile binds a governing cipher suite,
and through it a governing profile. The rules are:
* After the ServerHello of a full handshake, the governing cipher
suite is selected_cipher_suite, and the governing profile is the
schedule profile of that suite.
* A PSK binder is computed before the server selects a cipher suite.
Its governing cipher suite is the PSK's recorded cipher suite, and
it is computed and verified under the schedule profile associated
with that PSK. As in RFC 8446, Section 4.2.11, a server MUST
verify the binder of any PSK it selects, and MUST perform that
verification under that PSK's recorded cipher suite.
* Early-stage outputs derived before the ServerHello (early traffic
keys, the early exporter secret) are governed by the offered PSK's
recorded cipher suite.
* After a HelloRetryRequest, an updated binder remains governed by
the PSK's recorded cipher suite. A client SHOULD omit from its
updated ClientHello any PSK whose recorded cipher suite is
incompatible with the cipher suite implied by the
HelloRetryRequest, and MUST recompute binders as required by RFC
8446, Section 4.2.11.2.
* A server MUST NOT select a PSK unless the schedule profile of the
cipher suite it selects is compatible with the schedule profile
associated with the PSK. Two schedule profiles are compatible
only if they have the same profile_id and identical profile
parameters. This document defines no broader compatibility.
Because each profile of this document additionally binds the
recorded cipher suite into the binder, a server MUST NOT select a
Sullivan Expires 7 January 2027 [Page 9]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
PSK whose recorded cipher suite differs from the cipher suite it
selects. This is stricter than RFC 8446, Section 4.2.11, which
requires only that the selected cipher suite share the PSK's Hash.
Because a schedule profile is not independently negotiated,
compatibility requires the full cipher suite, not merely its
transcript hash, to match.
* For 0-RTT, the server MUST require the selected cipher suite to
equal the PSK's recorded cipher suite (Section 11), unless a
future specification defines a narrower compatibility rule.
A PSK that is offered but not selected leaves no trace in the
schedule. If the server does not select the client's PSK, both peers
compute the connection's schedule as a handshake without a PSK: the
client discards any PSK-keyed schedule state it built for the binder
or for early data, along with its outputs, and begins the schedule
again with the empty PSK, applying the destruction rules of its
profile.
Implementations MUST associate every PSK and session ticket with the
cipher suite, and therefore the schedule profile, under which it was
established.
5. Keyed Derivations
Every derivation in this document that is keyed by a retained octet-
string secret, rather than by a live stage of a profile's schedule,
is a deck session rooted at that secret (Section 7), specified once
for both profiles in Section 5.1 since the deck is identical up to
its permutation. MAC computes Finished, PSK binders, and Encrypted
Client Hello acceptance confirmations. Section 5.2 defines it once
as a byte layout over the profile's permutation, and each profile
fixes that permutation (Section 8.2, Section 9.2). Stage schedules
themselves remain profile-specific (Section 8, Section 9). This
section covers everything derived from the octet-string secrets those
schedules produce.
5.1. Expanding a Retained Secret
A value keyed by a retained octet-string secret is produced by a deck
session (Section 7) rooted at that secret. The deck is initialized,
the secret is absorbed, the session is forked under a label and the
governing cipher suite of the output, any context is absorbed, and
the deck is squeezed to the output length. Written with the deck
operations of Section 7.1:
Sullivan Expires 7 January 2027 [Page 10]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
D = Init(); Absorb(D, "secret", secret)
F = Fork(D, label, suite)
Absorb(F, "context", context) # omitted when context is empty
out = Squeeze(F, "out", L)
suite is the governing cipher suite of the output (Section 4), bound
by the Fork; label is an ASCII label; context is an octet string; and
L is the output length in octets. Because every item is length-
framed by the deck (Section 15.7.3), distinct expansions map to
distinct deck inputs. When context is empty its Absorb is omitted
rather than framed as an empty value. The frame of the following
"out" tag delimits the absence, so an omitted context and an empty
one never yield the same input. No two expansions in this document
share the same label unless they intentionally derive the same value,
and L never exceeds 65534 octets (Section 3). This expansion is the
analogue of RFC 8446's HKDF-Expand-Label and carries the same RFC
8446 labels. It is a use of the deck, not a separate construction.
5.2. MAC
MAC(key, suite, label, message, L) computes every tag in this
document: the PSK binder, both Finished values, and the ECH
acceptance confirmation. Both profiles use it. This section defines
it once over the profile's permutation, and each profile fixes that
permutation (Section 8.2, Section 9.2).
MAC builds the octet string mac_input from a key, a positional tuple
X, and a fixed customization string S, then applies the profile's
permutation to mac_input as a sponge, with a 136-octet rate, a
512-bit capacity, and domain-separation byte 0x04 appended in the
manner of TurboSHAKE [RFC9861], squeezing 8 * L bits:
K = key
X = frame(profile_id) || frame(uint16(suite))
|| frame(label) || frame(message)
S = "TLS 1.3 MAC"
mac_input = bytepad(encode_string("KMAC") || encode_string(S), 136)
|| bytepad(encode_string(K), 136)
|| X || right_encode(8 * L)
The four length encoders are byte-oriented. For a non-negative
integer n, let b be the number of octets in its minimal big-endian
form, taking b to be 1 when n is 0. left_encode(n) is the single
octet b followed by n as b octets. right_encode(n) is n as b octets
followed by the single octet b. For an octet string s of len(s)
octets, encode_string(s) is left_encode(8 * len(s)) followed by s.
bytepad(s, w) is left_encode(w) followed by s, then zero octets until
the length is a multiple of w.
Sullivan Expires 7 January 2027 [Page 11]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
The input X is positional. Unlike the deck's Absorb and Fork inputs,
which pair each value with a frame(tag), the MAC fields carry no per-
item tags. Their fixed order and length-framing parse them
unambiguously, and S is the same in every invocation of either
profile.
The two profiles fix the permutation. On the Keccak-p[1600,12] of
TLS13-TURBOSHAKE256 the sponge is TurboSHAKE256(mac_input, 0x04, L),
which this document names TurboKMAC256. On the Keccak-f[1600] of
TLS13-SHAKE256 it is the sponge cSHAKE256 and KMAC256 are built on,
and the result is byte-for-byte NIST KMAC256 [SP800-185]. This
layout and the 0x04 domain byte are the ones cSHAKE and KMAC use, so
those equalities hold by construction. MAC is defined by the layout
above, not by reference to KMAC.
Because right_encode(8 * L) binds the output length into mac_input
before the permutation runs, neither profile is KMACXOF256, and
outputs of different lengths are unrelated. MAC is the analogue of
RFC 8446's HMAC-based Finished and binder MACs and carries the same
RFC 8446 labels. No two invocations share a label unless they derive
the same value, and L never exceeds 65534 octets (Section 3).
5.3. Record Keys
Record keys are derived from a traffic secret in one call, so a
retained traffic secret suffices to re-derive its keys, as in RFC
8446. The governing cipher suite is that of the traffic secret: for
early-data keys, derived before the ServerHello, it is the offered
PSK's recorded cipher suite, whose Nk and Nn apply.
D = Init(); Absorb(D, "secret", traffic_secret)
key_block = Squeeze(Fork(D, "key", suite), "out", Nk + Nn)
write_key = key_block[0..Nk]
write_iv = key_block[Nk..Nk+Nn]
The split is unambiguous: Nk and Nn are fixed by the suite, which is
bound into the derivation together with the output length. The
traffic secret is already specific to one direction and one stage, so
no direction or epoch input is needed. The per-record nonce
construction, record format, and AEAD additional data are unchanged
from RFC 8446.
5.4. Key Update
A key update derives the next traffic-secret generation from the
current one:
Sullivan Expires 7 January 2027 [Page 12]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
D = Init(); Absorb(D, "secret", app_traffic_secret_N)
app_traffic_secret_{N+1} =
Squeeze(Fork(D, "traffic upd", suite), "out", SecretLen)
with record keys re-derived from the new secret as above. Each
generation is an erasure boundary: an implementation MUST destroy the
previous secret, its keys, and any schedule state derived from them
after the new generation is installed, and MUST NOT derive generation
N+1 from anything other than generation N (in particular, not from a
retained stage accumulator or a counter).
5.5. Finished and PSK Binder MACs
Finished and PSK binder verify_data are computed under a dedicated
MAC key, expanded from a stage or traffic secret (Section 5.1),
rather than by MACing that secret directly. This matches RFC 8446,
Section 4.4.4, field for field: finished_key and binder_key take the
roles of RFC 8446's identically named intermediates, and MAC takes
the role of RFC 8446's HMAC.
D = Init(); Absorb(D, "secret", base_key)
finished_key = Squeeze(Fork(D, "finished", suite), "out", SecretLen)
verify_data = MAC(finished_key, suite, label, th, FLen)
For a Finished message, base_key is the sender's handshake traffic
secret, selected as in RFC 8446, Section 4.4; suite is
selected_cipher_suite; label is "finished"; and th covers the
transcript up to but not including the Finished message being
computed. For a PSK binder, the dedicated key is derived in two
steps, as RFC 8446, Section 7.1 derives binder_key and then
finished_key from it:
De = Init(); Absorb(De, "secret", early_secret)
binder_key = Squeeze(Fork(De, ext_or_res_label, suite), "out", 64)
Db = Init(); Absorb(Db, "secret", binder_key)
finished_key = Squeeze(Fork(Db, "finished", suite), "out", SecretLen)
verify_data = MAC(finished_key, suite, label, TH_CH0, FLen)
early_secret is the early-stage secret of the schedule keyed by that
PSK; ext_or_res_label is "ext binder" for an external PSK and "res
binder" for a resumption PSK, and label takes the same value in the
MAC call; suite is the PSK's recorded cipher suite. Both
finished_key and binder_key are 64 octets, the length of every stage
and traffic secret in both profiles (SecretLen, Section 8,
Section 9), matching RFC 8446's use of Hash.length for the same
intermediates. Binder verification follows Section 4.
Sullivan Expires 7 January 2027 [Page 13]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
Appendix A counts every finished_key and binder_key derivation of a
representative full handshake against the corresponding RFC 8446
HKDF-Expand-Label calls.
finished_key and binder_key are dedicated MAC keys: neither is ever
used to derive record keys, an exporter, or any other output. No
joint-security argument about reusing one secret across the deck and
the MAC is therefore needed, and the MAC's security as a keyed
function rests on the same sponge assumptions as the deck itself
([FSKS], [KEYEDDUPLEX]). The structure is otherwise identical to RFC
8446's, field for field: finished_key and binder_key exist for the
same reason in both, and the only substitution is the MAC for HMAC as
the keyed function that consumes them (Section 15.7.1). The RFC 8446
key-schedule analysis of these intermediates therefore transfers
directly, in both profiles of this document.
Binders are computed before the ServerHello. This is possible in
both profiles because stage secrets bind no cipher suite: the client
ratchets a clone of the early trunk to obtain early_secret at
ClientHello time, in either profile (Section 7).
5.6. Exporters
Exporters are keyed by the retained exporter master secret:
TLS-Exporter(label, context, length):
D = Init(); Absorb(D, "secret", exp_master)
F = Fork(D, "exporter", suite)
Absorb(F, "context", frame(TranscriptHash(label))
|| frame(TranscriptHash(context)))
return Squeeze(F, "out", length)
The early exporter is the same construction keyed by e_exp_master,
with the offered PSK's recorded cipher suite as its governing suite.
Hashing the label and the context bounds them and keeps the composite
context injective. An implementation MUST reject a TLS-Exporter
request for more than 65534 octets (Section 3).
5.7. Resumption PSK
The resumption PSK for a NewSessionTicket is:
D = Init(); Absorb(D, "secret", res_master)
F = Fork(D, "resumption", suite); Absorb(F, "context", ticket_nonce)
resumption_psk = Squeeze(F, "out", 64)
Sullivan Expires 7 January 2027 [Page 14]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
5.8. ECH Acceptance Confirmations
For the cipher suites of this document, the ECH acceptance signals of
[RFC9849] are:
accept_confirmation =
MAC(ClientHelloInner.random, selected_cipher_suite,
"ech accept confirmation",
TranscriptHash(ech_conf_messages), 8)
hrr_accept_confirmation =
MAC(ClientHelloInner.random, selected_cipher_suite,
"hrr ech accept confirmation",
TranscriptHash(hrr_ech_conf_messages), 8)
replacing the HKDF-Extract and HKDF-Expand-Label computations of
[RFC9849], with ech_conf_messages and hrr_ech_conf_messages the
handshake message ranges that document identifies for each
confirmation, per RFC 8446, Section 4.4.1.
TranscriptHash(ech_conf_messages) is RFC 9849's transcript_ech_conf,
i.e. the same single transcript-hash operation, applied once. The
selected cipher suite is known to both peers when each confirmation
is computed and checked.
Keying the confirmation on ClientHelloInner.random alone matches
[RFC9849], whose confirmation key is HKDF-Extract(0,
ClientHelloInner.random), with no handshake secret mixed in. This
document computes a single MAC under that same key in place of RFC
9849's extract-then-expand, so the acceptance signal keeps its RFC
9849 properties. Only a server that decrypted the inner ClientHello,
and so learned ClientHelloInner.random, can compute the confirmation,
and no network attacker can forge it. Because the confirmation
transcript covers the ServerHello, it binds its handshake and does
not transplant to another.
5.9. PSK Import Derivation
An external PSK is imported per target cipher suite (Section 10).
The import derivation, for every profile of this document, is:
D = Init(); Absorb(D, "secret", epsk)
F = Fork(D, "derived psk", target_ciphersuite)
Absorb(F, "context", TranscriptHash(ImportedIdentityV2))
ipsk = Squeeze(F, "out", SecretLen)
with target_ciphersuite as the governing suite, following the shape
of the RFC 9258 derivation, with the entire serialized
ImportedIdentityV2 reduced by the transcript hash as the context.
Sullivan Expires 7 January 2027 [Page 15]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
ipsk is an explicit octet string by design: it crosses a system
boundary into the PSK store. epsk is absorbed as the secret of a
deck expansion (Section 5.1) in both profiles, so a low-entropy or
attacker-influenced epsk never keys either profile's underlying
permutation directly.
6. Cipher Suites and Code Points
This document defines five cipher suites. As in TLS 1.3, the code
point is negotiated in the cipher_suites field of the ClientHello and
selected in the ServerHello. The suffix of each name denotes the
complete schedule profile of the suite, not merely a transcript hash
or MAC.
enum {
TLS_AES_128_GCM_TURBOSHAKE256 = {0xTBD, 0xTBD},
TLS_AES_256_GCM_TURBOSHAKE256 = {0xTBD, 0xTBD},
TLS_CHACHA20_POLY1305_TURBOSHAKE256 = {0xTBD, 0xTBD},
TLS_AES_128_GCM_SHAKE256 = {0xTBD, 0xTBD},
TLS_AES_256_GCM_SHAKE256 = {0xTBD, 0xTBD}
} CipherSuite;
+===================================+=================+===================+
|Cipher Suite |AEAD |ScheduleProfile |
+===================================+=================+===================+
|TLS_AES_128_GCM_TURBOSHAKE256 |AES-128-GCM |TLS13-TURBOSHAKE256|
+-----------------------------------+-----------------+-------------------+
|TLS_AES_256_GCM_TURBOSHAKE256 |AES-256-GCM |TLS13-TURBOSHAKE256|
+-----------------------------------+-----------------+-------------------+
|TLS_CHACHA20_POLY1305_TURBOSHAKE256|ChaCha20-Poly1305|TLS13-TURBOSHAKE256|
+-----------------------------------+-----------------+-------------------+
|TLS_AES_128_GCM_SHAKE256 |AES-128-GCM |TLS13-SHAKE256 |
+-----------------------------------+-----------------+-------------------+
|TLS_AES_256_GCM_SHAKE256 |AES-256-GCM |TLS13-SHAKE256 |
+-----------------------------------+-----------------+-------------------+
Table 1: Cipher Suites and Their Schedule Profiles
The suites of a profile differ only in the AEAD algorithm and its key
and nonce lengths. The AEAD algorithms, their Nk and Nn, and the
per-record nonce construction are those of RFC 8446 and its cipher
suites. Code points are to be assigned by IANA (Section 14).
An implementation MUST NOT combine an AEAD algorithm and a schedule
profile that are not registered together as a cipher suite: each
cipher suite is a single negotiated value that determines both.
Sullivan Expires 7 January 2027 [Page 16]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
7. The Deck Schedule
Both schedule profiles of this document express the key schedule as a
deck function. The key schedule is a derivation tree, and a sponge-
based primitive can express a tree natively: absorb inputs into a
running accumulator, fork where the tree branches, and squeeze
outputs at the leaves.
The schedule's normative interface is a deck function [FARFALLE]: a
keyed function with extendable input and incremental output, the
abstraction under which forked-state designs carry security contracts
[JAMMIN]. This section defines the deck operations once, for both
profiles. Section 8 and Section 9 each give a short instantiation
naming the profile's XOF, permutation, and domain-separation
constants.
This document uses the following terms.
deck function: A keyed cryptographic function taking a sequence of
input strings and producing output of arbitrary length, supporting
extendable input and incremental output [FARFALLE].
stage: One of the three phases of the schedule: early (keyed by the
PSK), handshake (adds the key-exchange secrets), and application.
Stages are separated by ratchets, and each key-update generation
adds a further ratchet.
fork: Deriving a leaf value from a stage by extending the stage's
input sequence with a label and the governing cipher suite and
squeezing. In a stateful implementation, a fork is a clone of the
stage accumulator. Forks are only permitted from an accumulator
that has not produced output.
ratchet: Crossing a stage boundary by squeezing an explicit stage
secret directly from the trunk (the Ratchet operation of
Section 7.1) and reinitializing the next stage from it, after
which every accumulator of the completed stage is destroyed
(Section 15.7.2). The squeeze-and-reinitialize pattern follows
the RATCHET operation of [STROBE] and the Ratchet call of Cyclist
[XOODYAK].
The presentation is stateful, but the construction is not. Every
derived value equals one invocation of a profile's deck function over
the framed derivation path from its stage's initialization to that
value, with no extract-then-expand structure, and an implementation
that recomputes each value from its path is as conformant as one that
maintains cloned accumulators. The three stages of Section 7.3 are
protocol phases separated by ratchets, not KDF steps: shared trunks
Sullivan Expires 7 January 2027 [Page 17]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
absorb each input once, the handshake holds only two intermediate
secrets, and the one-way truncations fall at the stage boundaries
where TLS must erase prior state.
The keyed-duplex construction underlying both profiles has concrete
security bounds [FSKS] [KEYEDDUPLEX] [DUPLEXSEC], and the TLS 1.3 key
schedule has a proof framework based on derivation graphs with
explicit intermediate values [TLS13KS]. Section 15.7.1 composes
those lines of work into a handshake-level security argument for the
TLS13-TURBOSHAKE256 profile.
7.1. The Deck Schedule Interface
The schedule is expressed through operations that build input
sequences for the deck function DF(S, L), which maps a completed
sequence S and an output length L to L octets of output. Each
profile's instantiation of DF is given in Section 8.1 and
Section 9.1. Every operation that absorbs data contributes
frame(tag) || frame(value) to the sequence, so distinct input
sequences yield distinct absorbed strings.
7.1.1. Operations
Each operation's effect on a sequence is:
Init() seq = frame(profile_id)
Absorb(S, tag, v) seq(S) = seq(S) || frame(tag) || frame(v)
Fork(S, label, cs) new S' with
seq(S') = seq(S) || frame(label)
|| frame("suite") || frame(uint16(cs))
Squeeze(S, tag, L) seq(S) = seq(S) || frame(tag)
|| frame(uint16(L))
output DF(S, L)
Ratchet(S, label) Squeeze(S, label, SecretLen)
Init(): Begin a session by framing the governing profile's
profile_id (Section 8, Section 9).
Absorb(S, tag, value): Add one tagged input to S, returning S.
Fork(S, label, suite): Branch a new sequence for a single output.
Sullivan Expires 7 January 2027 [Page 18]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
The copy diverges from S under the framed label, and suite, the
governing cipher suite of the output being derived, is bound under
the fixed tag "suite". S is unmodified. An implementation MUST
NOT apply Fork to a sequence that has produced output.
Squeeze(S, tag, L): Terminate S and produce L octets. An
implementation MUST NOT absorb further input into a squeezed S and
MUST NOT fork it. Binding L into the sequence before output
ensures that outputs of different lengths are unrelated rather
than prefixes of one another. L never exceeds 65534 octets for
any derivation in this document.
Ratchet(S, label): Cross a stage boundary: squeeze the 64-octet
stage secret directly from the stage trunk under the stage label,
terminating the trunk. A ratchet output binds no cipher suite:
stage secrets never leave the schedule, and every output that does
binds its governing suite at its own Fork or expansion (Section 4,
Section 5.1). The ratchet labels "early secret" and "main secret"
are reserved: they appear as no absorb tag, fork label, or squeeze
tag elsewhere in either profile.
Leaf derivations keyed by a live stage use Fork and Squeeze.
Derivations keyed by a retained octet-string secret use a deck
expansion (Section 5.1), built from the same Init, Absorb, Fork, and
Squeeze operations over each profile's DF.
7.1.2. One-Shot Equivalence
Because Fork applies only before output and Squeeze, and therefore
Ratchet, terminates a sequence, every derived value is exactly one
deck-function invocation over the framed path from Init to its final
squeeze. Derived values are therefore byte-exact and testable
without reference to any internal state. An implementation MAY
realize forks by cloning a running accumulator or by recomputing each
leaf from its path. Both strategies MUST produce identical octets.
7.2. Derivation Shapes
Every RFC 8446 derivation replaced by this document is an instance of
one of six shapes. This table is the specification frame for
Section 7.3 and makes the RFC 8446 correspondence auditable.
Sullivan Expires 7 January 2027 [Page 19]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
+===============+==========================+======================+
| Shape | RFC 8446 sites | Realization |
+===============+==========================+======================+
| Root absorb | early_secret; PSK import | Init + Absorb secret |
+---------------+--------------------------+----------------------+
| Accumulate | handshake_secret (per | Absorb secret |
| | component) | |
+---------------+--------------------------+----------------------+
| Ratchet | early_secret; | Ratchet or expand |
| | main_secret; key update | |
+---------------+--------------------------+----------------------+
| Branch | traffic/master secrets; | Fork + Squeeze |
| | resumption | |
+---------------+--------------------------+----------------------+
| Expand-to-use | record keys; exporters | Expand from a secret |
+---------------+--------------------------+----------------------+
| Keyed check | Finished; PSK binders | MAC |
+---------------+--------------------------+----------------------+
Table 2: Derivation Shapes and Their Realizations
Shapes 1 through 3 act on the trunk of a stage. Shapes 4 through 6
are forks or self-contained keyed calls. The early_secret of RFC
8446 becomes this document's first ratchet, and the handshake_secret
extract becomes an accumulation into the handshake stage. Both stage
boundaries remain explicit octet-string secrets (Section 15.7.2).
Record keys are derived from their traffic secret by a separate call,
as in RFC 8446, so a retained traffic secret suffices to re-derive
its keys. Deriving them by squeezing alongside the secret would save
a few invocations but break that re-derivability, so the schedule
keeps the separate call.
7.3. Key Schedule
The schedule has three stages separated by two ratchets, and each
key-update generation adds a further ratchet. Stage trunks and stage
secrets bind no cipher suite value, matching the RFC 8446 extracts
they replace: a client offering several cipher suites of this
document computes one schedule, and only leaf derivations differ, in
their framed suffix alone. The governing cipher suite is bound at
each leaf derivation, by Fork or expansion. In the listing below,
suite denotes the governing cipher suite of the leaf being derived:
the offered PSK's recorded cipher suite in the early stage, and
selected_cipher_suite thereafter. This listing is identical for both
profiles. Only each profile's DF and MAC instantiations differ
(Section 8, Section 9).
Sullivan Expires 7 January 2027 [Page 20]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
E = Init()
Absorb(E, "psk", PSK) # root absorb; see {{absent-empty}}
# for the no-PSK encoding
# early-stage leaves (0-RTT only); governing suite: recorded
c_e_traffic = Squeeze(Absorb(Fork(E, "c e traffic", suite),
"th", TH_CH), "out", SecretLen)
e_exp_master = Squeeze(Absorb(Fork(E, "e exp master", suite),
"th", TH_CH), "out", SecretLen)
early_secret = Ratchet(E, "early secret")
# ratchet: E is terminally squeezed; destroy every
# early-stage accumulator
H = Init()
Absorb(H, "early", early_secret)
Absorb(H, "dh", DHE) # accumulate; once per component
Absorb(H, "th", TH_SH) # shared branch context
# governing suite below: selected_cipher_suite
c_hs_traffic = Squeeze(Fork(H, "c hs traffic", suite), "out", SecretLen)
s_hs_traffic = Squeeze(Fork(H, "s hs traffic", suite), "out", SecretLen)
main_secret = Ratchet(H, "main secret")
# ratchet: H is terminally squeezed; destroy every
# handshake-stage accumulator
T = Init()
Absorb(T, "main", main_secret)
Absorb(T, "th", TH_SF)
c_ap_traffic = Squeeze(Fork(T, "c ap traffic", suite), "out", SecretLen)
s_ap_traffic = Squeeze(Fork(T, "s ap traffic", suite), "out", SecretLen)
exp_master = Squeeze(Fork(T, "exp master", suite), "out", SecretLen)
Absorb(T, "th", TH_CF)
res_master = Squeeze(Fork(T, "res master", suite), "out", SecretLen)
# destroy T
When the negotiated group is a hybrid or other multi-component key
exchange, DHE is not one secret. Each component shared secret is
absorbed by its own Absorb(H, "dh", component), in the order that
group defines them, and the components are never concatenated first.
Both peers MUST absorb in that order, so they build the same
handshake-stage input sequence.
Sullivan Expires 7 January 2027 [Page 21]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
7.3.1. Absent and Empty Inputs
A handshake without a PSK still executes Absorb(E, "psk", ""). That
contributes frame("psk") followed by frame(""), that is, 0x0003 ||
"psk" || 0x0000. This is unambiguous because a PSK of this document
is never zero-length (an imported or resumption PSK is 64 octets).
In that case the early stage carries no leaves and early_secret is a
single deterministic, public constant of the profile, as RFC 8446's
early secret is the extract of two known constants. The stage exists
for uniformity across handshake modes, and the schedule's security
does not rest on its secrecy when no PSK is present. A PSK-only
handshake omits Absorb(H, "dh", ...) entirely: the tag "dh" does not
appear in the sequence.
7.3.2. Suite Binding and Stage Secrets
A server never selects a PSK whose recorded cipher suite differs from
the cipher suite it selects (Section 4), so early_secret never feeds
the handshake stage under a suite the transcript does not confirm.
early_secret and main_secret are the schedule's explicit stage
secrets, and like the RFC 8446 extracts they replace they are
interoperable octet strings: an implementation that computes them by
cloned accumulators and one that computes them as one-shot
invocations over the framed path MUST produce identical octets. An
implementation MUST destroy each stage secret once the next stage has
absorbed it (Section 15.7.2). Note that main_secret binds TH_SH
through its trunk, where the corresponding RFC 8446 extract binds no
transcript. This is a strict superset binding, computed identically
by both peers, and is intentional.
8. The TLS13-TURBOSHAKE256 Profile
The TLS13-TURBOSHAKE256 schedule profile instantiates the deck
schedule of Section 7 with TurboSHAKE256 [RFC9861], built on the
12-round Keccak-p[1600,12] permutation of [FIPS202].
The profile parameters are:
profile_id: The fixed ASCII string "TLS 1.3 DeckSchedule v1" (23
octets), absorbed first into every derivation as frame(profile_id)
(Section 7.1).
SecretLen: 64 octets, the length of every stage and traffic secret.
FLen: 64 octets.
Sullivan Expires 7 January 2027 [Page 22]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
8.1. Instantiation
The deck function is:
DF(S, L) = TurboSHAKE256(seq(S), 0x1F, L)
where seq(S) is the concatenation of every framed item of S in order.
TurboSHAKE256's output length is in octets per [RFC9861], so L is
passed unchanged, unlike the SHAKE256 profile, whose bit-oriented
length needs an 8 * L conversion (Section 9.1). The transcript hash
of Section 2.1 is instantiated with the same function:
TranscriptHash(x) = TurboSHAKE256("tls13 hash" || x, 0x1F, 64). The
domain-separation byte for the deck and the transcript hash is fixed
to 0x1F, the RFC 9861 default, so an API without the D parameter
implements both unchanged. The MAC (Section 5.2) requires D = 0x04,
so the TurboSHAKE interface this profile uses MUST expose the domain
byte. TurboSHAKE256 uses the Keccak-p[1600,12] permutation as a
sponge: input is absorbed into a 1600-bit state in rate-sized blocks
of 136 octets, with the permutation applied after each block, and
output is read from the same state. The capacity is the 512-bit
portion of the state that input and output never touch. It is what
the erasure argument of Section 15.7.2 relies on, and the 64-octet
secret, transcript-hash, and MAC lengths used throughout this
document are set to match it. The stateful view of this construction
is analyzed as a duplex [DUPLEX], under the keyed-sponge and keyed-
duplex results [FSKS] [KEYEDDUPLEX] [DUPLEXSEC].
8.1.1. Required API Surface
The required API surface is incremental absorption, cloning of an
unfinalized state, and one-shot squeeze with the output length known
up front. Cloning before any output is incremental input to two
separate invocations, which Section 2.1 of [RFC9861] permits; no
absorb-after-squeeze occurs anywhere in this document, so no access
below the TurboSHAKE interface is required. The clone discipline is
the same one TLS stacks already apply to SHA-2 transcript-hash
checkpoints.
8.2. MAC
This profile's MAC is the construction of Section 5.2 over this
profile's Keccak-p[1600,12] permutation.
Sullivan Expires 7 January 2027 [Page 23]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
9. The TLS13-SHAKE256 Profile
The TLS13-SHAKE256 schedule profile instantiates the deck schedule of
Section 7 with plain SHAKE256 [FIPS202], built on the 24-round
Keccak-f[1600] permutation, in place of TurboSHAKE256's Keccak-
p[1600,12]. This profile mirrors the TLS13-TURBOSHAKE256 profile's
framing exactly: domain separation comes from the same framed-prefix
mechanism the TurboSHAKE profile uses, an absorbed frame(profile_id)
at Init (Section 7.1), not from cSHAKE's function-name and
customization-string inputs. The two profiles' decks therefore
differ only in the underlying permutation, so expansion (Section 5.1)
and the MAC construction (Section 5.2) are shared by both profiles,
each differing only in which permutation it invokes (Section 9.2,
Section 8.2).
The profile parameters are:
profile_id: The fixed ASCII string "TLS 1.3 SHAKESchedule v1" (24
octets), absorbed first into every derivation as frame(profile_id)
(Section 7.1), as in the TLS13-TURBOSHAKE256 profile.
SecretLen: 64 octets, the length of every stage and traffic secret.
FLen: 64 octets.
9.1. Instantiation
The deck function is:
DF(S, L) = SHAKE256(seq(S), 8 * L)
Sullivan Expires 7 January 2027 [Page 24]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
where seq(S) is the concatenation of every framed item of S in order,
SHAKE256(X, L) is the function of [FIPS202] with X the main input and
L the output length in bits, and 8 * L converts this document's
octet-oriented L to the bit-oriented L argument of SHAKE256.
SHAKE256 takes no function-name or customization-string input.
Domain separation for this profile comes entirely from seq(S) itself
beginning with frame(profile_id) (Section 7.1), the same mechanism
the TLS13-TURBOSHAKE256 profile uses in place of a fixed domain-
separation byte. The transcript hash of Section 2.1 is instantiated
with the same function: TranscriptHash(x) = SHAKE256("tls13 hash" ||
x, 512). SHAKE256 uses the Keccak-f[1600] permutation as a sponge
with a 136-octet rate and a 512-bit capacity, the same rate and
capacity as TurboSHAKE256. Input is absorbed in rate-sized blocks
with the permutation applied after each block, and output is read
from the same state. The capacity is what the erasure argument of
Section 15.7.2 relies on, and the 64-octet secret, transcript-hash,
and MAC lengths used throughout this document match it in both
profiles.
9.1.1. Required API Surface
The required API surface is incremental absorption, cloning of an
unfinalized state, and one-shot squeeze with the output length known
up front, as in Section 8.1. No absorb-after-squeeze occurs anywhere
in this document, so no access below the SHAKE256 interface is
required.
9.2. MAC
This profile's MAC is the construction of Section 5.2 over this
profile's Keccak-f[1600] permutation.
10. PSK Importer
TLS 1.3 permits external PSKs [RFC8446], and [RFC9258] imports an
external PSK into a target KDF, producing a PSK bound to its target.
An external PSK used with a cipher suite of this document is imported
per target cipher suite into an ipsk. ImportedIdentityV2 below is
this document's own variant of the ImportedIdentity struct of RFC
9258, Section 4, binding target_ciphersuite where that structure
binds target_kdf:
struct {
opaque external_identity<1..2^16-1>;
opaque context<0..2^16-1>;
uint16 target_protocol; /* 0x0304 for TLS 1.3 */
uint16 target_ciphersuite; /* a cipher suite of this document */
} ImportedIdentityV2;
Sullivan Expires 7 January 2027 [Page 25]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
The client offers the full ImportedIdentityV2 serialization as the
PskIdentity.identity, and a server that recognizes the structure
recomputes ipsk and MUST verify target_ciphersuite equals the cipher
suite it selects (Section 12). A server that does not recognize the
structure treats the entry as an unknown PSK identity, per ordinary
RFC 8446 handling. The import derivation is the generic derivation
of Section 5.9, keyed by epsk under target_ciphersuite.
Binding target_ciphersuite rather than RFC 9258's target_kdf
diversifies the imported PSK per cipher suite. That is one step
finer than RFC 9258's per-KDF granularity, and it matches the per-
suite binding this document uses everywhere else. It reuses the TLS
Cipher Suites registry and registers no TLS KDF Identifier. The five
code points of Section 6 are the only values target_ciphersuite
takes.
An endpoint MUST NOT use the raw external PSK epsk directly as a TLS
PSK for a cipher suite of this document, and MUST NOT import an epsk
longer than 0xFFFE octets, so every framed value fits a single frame.
A client that imports one external PSK for use with more than one
cipher suite of this document MUST produce a separate
ImportedIdentityV2, and hence a separate ipsk, per
target_ciphersuite.
11. Zero-RTT and Early Data
Early data remains PSK-only and remains replayable under the RFC 8446
anti-replay model. This document changes neither. A client MAY send
early data only if the first offered PSK's recorded cipher suite is
among the cipher suites it offers and the remembered ALPN and early-
data policy match the ticket. A server MUST reject early data unless
the selected cipher suite equals the offered PSK's recorded cipher
suite, the selected ALPN equals the ticket's, and all RFC 8446 anti-
replay checks pass. The suite-equality check, not the binder,
prevents redirecting early data to a different AEAD.
12. Alerts
This section lists the alerts an implementation of this document
sends, in addition to those already defined by RFC 8446:
* illegal_parameter: a raw external PSK offered for a cipher suite
of this document without import (Section 10); or an
ImportedIdentityV2 whose target_ciphersuite does not equal the
selected cipher suite.
* decrypt_error: a Finished or PSK binder MAC that fails
verification, as in RFC 8446.
Sullivan Expires 7 January 2027 [Page 26]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
* handshake_failure: no cipher suite of this document is mutually
supported when one is required.
13. Companion Mechanisms
Several deployed mechanisms invoke HKDF-Expand-Label directly. This
document defines the Encrypted Client Hello confirmation for its
cipher suites (Section 5.8), because ECH is pervasive in the
deployments most likely to exercise these schedules. The remaining
mechanisms are out of scope until a companion document defines their
analogues.
13.1. Out of Scope
* DTLS 1.3 [RFC9147] derives a record sequence-number encryption key
(Section 4.2.3) and separates its schedule with the "dtls13" label
prefix (Section 5.9). DTLS-OK is N in Section 14.
* QUIC [RFC9001] derives its Initial secrets and its "quic key",
"quic iv", "quic hp", and "quic ku" values with HKDF-Expand-Label.
* Exported Authenticators [RFC9261] derive their own Finished keys
with HKDF-Expand-Label.
An endpoint negotiating a cipher suite of this document MUST NOT use
these mechanisms with that connection unless a specification defines
their derivations for its schedule profile.
14. IANA Considerations
IANA is requested to register five code points in the TLS Cipher
Suites registry per the procedures of [RFC8447].
+=====+=====================================+=======+=============+
|Value| Description |DTLS-OK| Recommended |
+=====+=====================================+=======+=============+
|TBD | TLS_AES_128_GCM_TURBOSHAKE256 |N | N |
+-----+-------------------------------------+-------+-------------+
|TBD | TLS_AES_256_GCM_TURBOSHAKE256 |N | N |
+-----+-------------------------------------+-------+-------------+
|TBD | TLS_CHACHA20_POLY1305_TURBOSHAKE256 |N | N |
+-----+-------------------------------------+-------+-------------+
|TBD | TLS_AES_128_GCM_SHAKE256 |N | N |
+-----+-------------------------------------+-------+-------------+
|TBD | TLS_AES_256_GCM_SHAKE256 |N | N |
+-----+-------------------------------------+-------+-------------+
Table 3: Requested TLS Cipher Suites Registrations
Sullivan Expires 7 January 2027 [Page 27]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
The reference for each entry is this document. DTLS-OK is N
(Section 13). Recommended is N pending working group consensus.
The ScheduleProfile column of Table 1 is explanatory in this
document. It is not independently negotiated, and no registry of
schedule profiles is created. Future documents that define new TLS
1.3 alternative key-schedule profiles are expected to register new
TLS cipher-suite code points whose definitions include the complete
schedule profile.
OPEN ISSUE: Because every derived output binds the governing cipher
suite value, no final test vector can exist before code points are
assigned. Early code point allocation under RFC 7120 should be
considered once the document is adopted. Until then, the test
vectors of Appendix C use declared placeholder values.
15. Security Considerations
This section follows RFC 3552. It states what the schedules protect,
the assumptions they rest on, the properties common to every schedule
profile of this document, and the analysis specific to each profile.
15.1. Schedule-Profile Separation
Every derivation of both profiles binds the profile_id and, for every
output that leaves the schedule, the governing cipher suite
(Section 3). Labels, output lengths, profile identifiers, cipher
suite values, and context fields are length-framed and bound into
each output. No output of one profile can then collide with an
output of another, or of any future profile with a distinct
profile_id, even when they share a permutation: the profile_id
separates them at the input encoding. Nor can any output be
transplanted between cipher suites, even between two suites of the
same profile: the suite binding separates them. Within each profile,
distinct derivation paths produce distinct primitive inputs.
Section 15.7.3 gives the byte-level argument for TLS13-TURBOSHAKE256.
The same framing, with this profile's own profile_id and lengths,
gives it for TLS13-SHAKE256.
15.2. PSK Profile Binding
A PSK is associated with the schedule profile under which it was
established, and its binder is computed and verified under that
profile and the PSK's recorded cipher suite (Section 4). This
matters because the binder is computed before the server selects a
cipher suite: without the recorded-suite rule, a PSK established
under one profile could key the early stage of another, and the
binder would not detect it. The server-side selection rules ensure
Sullivan Expires 7 January 2027 [Page 28]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
that no secret derived from a PSK ever feeds a schedule other than
the one the PSK is bound to. For 0-RTT the rule is strictest,
requiring the selected cipher suite to equal the PSK's recorded
cipher suite: early-data keys are derived and used before the
server's selection can be confirmed by the transcript, so suite
equality, not the binder, prevents redirecting early data to a
different AEAD or profile.
15.3. Downgrade Resistance
The governing cipher suite is bound into every derived output, and
the selected cipher suite appears in the ServerHello and therefore in
TH_SH. In both profiles, intermediate secrets are suite-independent,
but no output leaves the schedule without a suite binding, and the
server never selects a PSK whose recorded suite differs from its
selected suite (Section 4), so no output is keyed under a suite the
transcript does not confirm. Downgrade among the suites of this
document is prevented by the transcript and the per-output suite
binding, and, for early data, by the suite-equality check. A client
that requires an alternative schedule profile MUST offer only cipher
suites of this document.
The two profiles of this document share the same schedule structure
and the same composed security argument (Section 15.7.1), differing
only in the underlying permutation. Cipher-suite negotiation
integrity guarantees that the selection is authentic. A deployment
that offers suites of both profiles accepts whichever the peer
selects.
15.4. PSK Entropy
As in RFC 8446, binder unforgeability against an attacker who can
guess an external PSK requires the PSK to have adequate entropy,
since such an attacker can recompute the binder offline. External
PSKs SHOULD have at least 64 octets of entropy.
15.5. Authentication Is Out of Scope
A cipher suite of this document governs only the AEAD and the key
schedule. A fully SHA-2-free connection also requires SHA-2-free
authentication: certificate-based authentication is negotiated
separately, through the signature_algorithms and
signature_algorithms_cert extensions, and commonly relies on SHA-2.
A deployment that must avoid SHA-2 entirely MUST restrict those
extensions accordingly, or use PSK-only authentication.
Sullivan Expires 7 January 2027 [Page 29]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
15.6. Retained RFC 8446 Properties
0-RTT replay properties and forward secrecy via key erasure (realized
by each profile's destruction rules) are unchanged from RFC 8446. In
both profiles, hybrid key-exchange components remain separated: each
component secret is absorbed separately, and secrets are not
concatenated before derivation (Section 7).
15.7. TLS13-TURBOSHAKE256 Considerations
The considerations of this subsection apply only to the
TLS13-TURBOSHAKE256 profile.
15.7.1. Cryptographic Analysis
The keyed sponge and keyed duplex have concrete security bounds
[FSKS] [KEYEDDUPLEX], surveyed in [DUPLEXSEC]; deck-function session
modes are analyzed in [JAMMIN]; and the TLS 1.3 key schedule is
proven in a multi-stage derivation framework [TLS13KS]. This
subsection develops the security argument for the schedule of this
document by composing those results.
15.7.1.1. Threat Model and Goals
The adversary model and key-schedule goals are those of [TLS13KS]: an
active network adversary that controls message delivery, may learn
selected stage secrets under compromise predicates, and seeks to
distinguish unseen traffic keys, forge Finished or binder values,
break forward secrecy across ratchet boundaries, or downgrade the
negotiated cipher suite. Authentication of peer identity remains
outside the cipher suite, as in RFC 8446. The schedule must provide
indistinguishability of record keys and exporter outputs under the
chosen AEAD, integrity of the handshake transcript through Finished
and binder verification, forward secrecy from handshake compromise to
application traffic once (EC)DHE is used, and the RFC 8446 0-RTT
replay model when early data is accepted.
15.7.1.2. Primitive Assumptions
The deck function DF is modeled as a sponge over a random permutation
[FIPS202] [DUPLEXSEC]. TranscriptHash is an unkeyed XOF on inputs
prefixed with "tls13 hash" (Section 2.1). Every keyed derivation is
a single call DF(S, L) where seq(S) is an injectively framed byte
string (Section 15.7.3). Section 8.1 fixes the XOF, domain-
separation parameter, and output lengths for the cipher suites
defined here. Under injective framing, distinct derivations map to
distinct sponge inputs, and the keyed-duplex analyses [FSKS]
[KEYEDDUPLEX] bound the adversary's advantage in distinguishing
Sullivan Expires 7 January 2027 [Page 30]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
outputs or forging MAC values as a function of permutation queries
and output length. TurboKMAC256 is introduced by this document and
is not covered by NIST's KMAC security analysis, which is scoped to
the Keccak-f[1600]-based cSHAKE256 of KMAC256. Its security is
treated here as inheriting from the generic keyed-sponge and keyed-
duplex bounds of [FSKS] and [KEYEDDUPLEX], which are stated over an
idealized permutation of any round count, not as a NIST-validated
instance of KMAC256.
15.7.1.3. Security Strength and Round Margin
TLS13-TURBOSHAKE256 targets 256-bit security, the level its 512-bit
capacity supports. Its guarantees at that level all rest on the
12-round Keccak-p[1600,12] permutation of TurboSHAKE256: collision
resistance of the transcript hash, indistinguishability of the stage
and traffic secrets, and unforgeability of the Finished and binder
values. [RFC9861] claims that permutation's security at 256 bits.
The reduced round count is the only structural difference from a
full-permutation instantiation. Capacity, framing, and the
derivation graph match the TLS13-SHAKE256 profile, which reaches the
same target over the full 24-round Keccak-f[1600] permutation. A
deployment that prefers that larger round margin can negotiate
TLS13-SHAKE256, the conservative choice (Section 9).
15.7.1.4. Derivation Graph
Each derived octet string is one leaf of a derivation tree
(Section 7.2). Stage trunks E, H, and T absorb the inputs that RFC
8446 mixes through chained HKDF-Extract and Derive-Secret calls.
Ratchets emit the only stage-boundary secrets, early_secret and
main_secret (Appendix A). finished_key and binder_key are the
schedule's other intermediate secrets. Each is a deck expansion of a
retained secret (Section 5.1), a fresh deck rooted at that secret
rather than a fork of a live stage trunk, and each keys exactly one
MAC invocation and no other output (Section 5.5). Every remaining
leaf equals an expansion, a MAC invocation, or Squeeze(Fork(...)),
and each stage secret equals Ratchet(...), hence one deck-function or
MAC invocation each (Section 5.1, Section 5.2, Section 7.1). The
comparison of Appendix A maps every HKDF-Expand-Label site to a
unique framed path, and no RFC 8446 secret is derived without a
matching leaf here. The mapping is one-to-one on derived values with
one intentional divergence: main_secret binds TH_SH through its trunk
where the RFC 8446 extract binds no transcript. That extra binding
front-loads transcript agreement that RFC 8446 enforces only at
Finished. It removes no binding RFC 8446 requires, but it makes this
tree a strict superset of the proven RFC 8446 derivation graph rather
than an exact image of it.
Sullivan Expires 7 January 2027 [Page 31]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
Under the random-permutation model, each leaf is idealized as an
independent random-oracle call on its framed path, the standard
idealization step for keyed-sponge proofs [FSKS]. It applies at two
levels. A traffic or master secret is forked from a live stage trunk
whose absorbed secrets have, by fork time, mixed across the full
state, so the full-state keyed-duplex bound of [KEYEDDUPLEX] governs
it. A retained-secret expansion of Section 5.1 is instead a fresh
deck rooted at a single secret absorbed through the rate, an outer-
keyed sponge governed by the keyed-sponge bound of [FSKS]. Because
that secret is itself an idealized-uniform ratchet or fork output,
the two levels compose by the standard hybrid over the derivation
tree.
This idealization connects the schedule to the multi-stage framework.
[TLS13KS] is defined over discrete extract-and-expand invocations, so
it does not by itself cover a single running sponge state. The
keyed-sponge idealization, not [TLS13KS] directly, carries this
document's continuous deck into that framework's scope.
15.7.1.5. Multi-Stage Security
[TLS13KS] models TLS 1.3 as a multi-stage authenticated key exchange
whose stages align with Early, Handshake, and Application secrets.
Extract transitions pass an intermediate secret into the next stage
while erasing the prior stage's expandable state. Here, early_secret
and main_secret are explicit ratchet outputs, and the destruction
rules of Section 15.7.2 enforce the same erasure: once H absorbs
early_secret, the early stage MUST NOT remain usable, and likewise
for main_secret into T.
Given (EC)DHE, early_secret and main_secret depend on secrets the
adversary does not know at the ratchet. The 512-bit capacity
withheld at each squeeze prevents recovering pre-ratchet sponge
states from ratchet outputs alone (Section 15.7.2). This matches the
extract semantics on which [TLS13KS] relies: stage t+1 keys are
unpredictable from stage t traffic keys even if stage t was
compromised before the ratchet, provided the fresh key-exchange
contribution was not learned.
Traffic and master secrets within a stage are forks from a common
trunk that already binds TH_SH or TH_SF. Fork labels, suite
bindings, and transcript absorbs are framed separately
(Section 15.7.3), so fork security reduces to the multi-user keyed-
duplex bounds of [KEYEDDUPLEX] on a single stage trunk. Finished and
binder MACs are MAC invocations (Section 5.5, Section 5.2), a
construction independent of expansion, yielding the same PRF-on-
transcript role as HMAC in the [TLS13KS] analysis.
Sullivan Expires 7 January 2027 [Page 32]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
Composing the stage arguments in order E, H, T, under the keyed-
sponge idealization above, gives an argument, in the random-
permutation model, for the same class of multi-stage key-schedule
goals as [TLS13KS] for connections that use this schedule in place of
HKDF, modulo the keyed-sponge and keyed-duplex advantage terms of
[FSKS] and [KEYEDDUPLEX]: record keys, exporter keys, resumption
PSKs, and key-update secrets are argued to inherit the same
indistinguishability and integrity guarantees, conditional on the
AEAD and authentication assumptions of RFC 8446. This document does
not claim a formal reproduction of the [TLS13KS] theorem, whose
statement is proved over discrete extract-and-expand nodes.
The subsections below restate protocol-specific assumptions,
downgrade controls, and implementation obligations that the model
treats as explicit rules rather than derived properties.
15.7.2. Erasure Boundaries and One-Wayness
15.7.2.1. The Invertibility Hazard
A sponge accumulator is built on a permutation (Section 8.1), and
permutations are invertible: an accumulator derived from another by
absorption alone carries its full past with it. Given a state equal
to the permutation of a prior state XORed with a publicly known block
(a label, a transcript hash, a stage marker), anyone holding the
later state recovers the earlier one. This holds for any sponge-
based realization of the deck function, not only the instantiation of
this document. A design that carried a raw accumulator across a
stage boundary would therefore let a post-handshake state compromise
re-derive handshake traffic secrets.
One-wayness comes only from truncation at squeeze time: a squeeze
withholds the capacity, 512 bits in the instantiation of Section 8.1,
so no squeezed output, of any length, permits reconstruction of the
state that produced it. Accordingly, an explicit ratchet sits at
every boundary where TLS requires erasure or compromise isolation:
the early-to-handshake transition (early_secret), the handshake-to-
application transition (main_secret), and every key-update
generation.
15.7.2.2. State-Handling Rules
An implementation MUST destroy every accumulator of a stage when the
stage's ratchet is crossed, MUST NOT retain a forked accumulator as a
successor across a ratchet, and MUST NOT serialize, export, or
compare accumulators. Squeezed octet-string secrets are subject to
the same discipline as their RFC 8446 counterparts: an implementation
MUST destroy handshake-stage traffic secrets and record keys when
Sullivan Expires 7 January 2027 [Page 33]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
their RFC 8446 analogues would be destroyed, and MUST destroy each
stage secret once the next stage has absorbed it.
Every cloned accumulator is a 200-octet copy of secret capacity.
Clones exist from fork to squeeze. An implementation SHOULD keep
that window short and MUST zeroize each clone when it is destroyed,
exactly as it zeroizes key material. Within a stage, retaining
accumulators is equivalent to retaining the stage's secrets:
compromise of a live accumulator yields that stage's underived
leaves, as compromise of a stage secret does in RFC 8446, and no
more.
15.7.3. Domain Separation
Every sequence begins with frame(profile_id) for the fixed profile_id
"TLS 1.3 DeckSchedule v1", separating these derivations from any
other use of the instantiation's XOF. The invariant the analysis
relies on is that distinct derivation paths yield distinct byte
strings as deck-function inputs. The framing rules give this
jointly: every absorbed item carries a framed tag, every fork absorbs
a framed label and the governing cipher suite, output length is bound
before squeezing, the ratchet labels are reserved for ratchets, and
no label is shared between MAC-type and expand-type uses. Absent
inputs are distinguished from empty inputs by the framed tag stream
(Section 2). Unkeyed transcript hashing is separated at the byte
level: a TranscriptHash input begins with the octets of "tls13 hash"
(0x74 0x6c ...), whereas every keyed sequence begins with
uint16(len(profile_id)) = 0x00 0x17. These leading octets cannot
coincide. The MAC (Section 5.2) uses domain byte 0x04 where a deck
derivation uses the instantiation XOF's native byte, so a MAC output
and a deck output over one permutation cannot coincide, and their
input encodings differ.
15.7.4. Related Constructions
Running-state protocol constructions with fork and ratchet operations
have precedent: BLINKER [BLINKER] builds a two-party record protocol
from a single sponge state with domain-separated forks; STROBE
[STROBE] defines KEY, PRF, and RATCHET operations over a duplex, with
RATCHET zeroizing rate bytes against rollback; Cyclist [XOODYAK]
makes the ratchet a first-class call; and Disco [DISCO] composes
STROBE with the Noise handshake, the closest existing analogue of a
handshake key schedule over a forked state. Disco's formal analysis
is thin relative to the Noise literature. This document treats it as
precedent, not assurance.
Sullivan Expires 7 January 2027 [Page 34]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
15.8. TLS13-SHAKE256 Considerations
The TLS13-SHAKE256 profile is structurally identical to the
TLS13-TURBOSHAKE256 profile (Section 7), so the Cryptographic
Analysis, Erasure Boundaries, and Related Constructions arguments of
Section 15.7 apply to it directly, with SHAKE256's Keccak-f[1600]
permutation in place of TurboSHAKE256's Keccak-p[1600,12] and this
profile's own profile_id and lengths in place of the
TLS13-TURBOSHAKE256 profile's (Section 9.1). It does not use raw
keyed SHAKE256 for any keyed operation: expansion is a deck-native
absorb-then-squeeze session over a framed protocol identifier
(Section 5.1), and MAC is the construction of Section 5.2, whose key
block, function name, and customization string provide the keyed-mode
domain separation that bare SHAKE256 lacks (Section 9.2). KMACXOF256
is not used. Every MAC invocation binds its output length, so
outputs of different lengths are unrelated.
15.9. Test Vectors
Each schedule profile requires independent test vectors covering
every derivation it defines. Appendix C provides vectors for both
profiles. Final vectors for both profiles require assigned code
points (Section 14).
15.10. Out of Scope
QUIC, DTLS 1.3, and Exported Authenticators remain out of scope for
both profiles (Section 13): an endpoint negotiating a cipher suite of
this document MUST NOT use those mechanisms with that connection
unless a specification defines their derivations for its schedule
profile.
16. References
16.1. Normative References
[RFC2119] Bradner, S., "Key words for use in RFCs to Indicate
Requirement Levels", BCP 14, RFC 2119,
DOI 10.17487/RFC2119, March 1997,
<https://www.rfc-editor.org/info/rfc2119>.
[RFC8174] Leiba, B., "Ambiguity of Uppercase vs Lowercase in RFC
2119 Key Words", BCP 14, RFC 8174, DOI 10.17487/RFC8174,
May 2017, <https://www.rfc-editor.org/info/rfc8174>.
[RFC8446] Rescorla, E., "The Transport Layer Security (TLS) Protocol
Version 1.3", RFC 8446, DOI 10.17487/RFC8446, August 2018,
<https://www.rfc-editor.org/info/rfc8446>.
Sullivan Expires 7 January 2027 [Page 35]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
[RFC8447] Salowey, J. and S. Turner, "IANA Registry Updates for TLS
and DTLS", RFC 8447, DOI 10.17487/RFC8447, August 2018,
<https://www.rfc-editor.org/info/rfc8447>.
[RFC9258] Benjamin, D. and C. A. Wood, "Importing External Pre-
Shared Keys (PSKs) for TLS 1.3", RFC 9258,
DOI 10.17487/RFC9258, July 2022,
<https://www.rfc-editor.org/info/rfc9258>.
[RFC9849] Rescorla, E., Oku, K., Sullivan, N., and C. A. Wood, "TLS
Encrypted Client Hello", RFC 9849, DOI 10.17487/RFC9849,
March 2026, <https://www.rfc-editor.org/info/rfc9849>.
[RFC9861] Viguier, B., Wong, D., Ed., Van Assche, G., Ed., Dang, Q.,
Ed., and J. Daemen, Ed., "KangarooTwelve and TurboSHAKE",
RFC 9861, DOI 10.17487/RFC9861, October 2025,
<https://www.rfc-editor.org/info/rfc9861>.
[FIPS202] National Institute of Standards and Technology, "SHA-3
Standard: Permutation-Based Hash and Extendable-Output
Functions", FIPS 202, DOI 10.6028/NIST.FIPS.202, August
2015, <https://csrc.nist.gov/pubs/fips/202/final>.
16.2. Informative References
[SP800-185]
National Institute of Standards and Technology, "SHA-3
Derived Functions: cSHAKE, KMAC, TupleHash, and
ParallelHash", NIST SP 800-185,
DOI 10.6028/NIST.SP.800-185, December 2016,
<https://csrc.nist.gov/pubs/sp/800/185/final>.
[RFC9001] Thomson, M., Ed. and S. Turner, Ed., "Using TLS to Secure
QUIC", RFC 9001, DOI 10.17487/RFC9001, May 2021,
<https://www.rfc-editor.org/info/rfc9001>.
[RFC9147] Rescorla, E., Tschofenig, H., and N. Modadugu, "The
Datagram Transport Layer Security (DTLS) Protocol Version
1.3", RFC 9147, DOI 10.17487/RFC9147, April 2022,
<https://www.rfc-editor.org/info/rfc9147>.
[RFC9261] Sullivan, N., "Exported Authenticators in TLS", RFC 9261,
DOI 10.17487/RFC9261, July 2022,
<https://www.rfc-editor.org/info/rfc9261>.
Sullivan Expires 7 January 2027 [Page 36]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
[SP800-133]
National Institute of Standards and Technology,
"Recommendation for Cryptographic Key Generation", NIST SP
800-133r2, DOI 10.6028/NIST.SP.800-133r2, June 2020,
<https://csrc.nist.gov/pubs/sp/800/133/r2/final>.
[SP800-108]
National Institute of Standards and Technology,
"Recommendation for Key Derivation Using Pseudorandom
Functions", NIST SP 800-108r1,
DOI 10.6028/NIST.SP.800-108r1-upd1, August 2024,
<https://csrc.nist.gov/pubs/sp/800/108/r1/upd1/final>.
[SP800-56C]
National Institute of Standards and Technology,
"Recommendation for Key-Derivation Methods in Key-
Establishment Schemes", NIST SP 800-56Cr2,
DOI 10.6028/NIST.SP.800-56Cr2, August 2020,
<https://csrc.nist.gov/pubs/sp/800/56/c/r2/final>.
[DUPLEX] Bertoni, G., Daemen, J., Peeters, M., and G. Van Assche,
"Duplexing the Sponge: Single-Pass Authenticated
Encryption and Other Applications", Selected Areas in
Cryptography SAC 2011, DOI 10.1007/978-3-642-28496-0_19,
2011, <https://keccak.team/files/SpongeDuplex.pdf>.
[FSKS] Mennink, B., Reyhanitabar, R., and D. Vizar, "Security of
Full-State Keyed Sponge and Duplex: Applications to
Authenticated Encryption", ASIACRYPT 2015, 2015,
<https://eprint.iacr.org/2015/541>.
[KEYEDDUPLEX]
Daemen, J., Mennink, B., and G. Van Assche, "Full-State
Keyed Duplex with Built-In Multi-User Support",
ASIACRYPT 2017, DOI 10.1007/978-3-319-70697-9_21, 2017,
<https://eprint.iacr.org/2017/498>.
[DUPLEXSEC]
Mennink, B., "Understanding the Duplex and Its Security",
IACR Transactions on Symmetric Cryptology 2023(2),
DOI 10.46586/tosc.v2023.i2.1-46, 2023,
<https://eprint.iacr.org/2022/1340>.
Sullivan Expires 7 January 2027 [Page 37]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
[FARFALLE] Bertoni, G., Daemen, J., Hoffert, S., Peeters, M., Van
Assche, G., and R. Van Keer, "Farfalle: Parallel
Permutation-Based Cryptography", IACR Transactions on
Symmetric Cryptology 2017(4),
DOI 10.46586/tosc.v2017.i4.1-38, 2017,
<https://keccak.team/farfalle.html>.
[JAMMIN] Bacuieti, N., Daemen, J., Hoffert, S., Van Assche, G., and
R. Van Keer, "Jammin' on the Deck", ASIACRYPT 2022, 2022,
<https://eprint.iacr.org/2022/531>.
[XOODYAK] Daemen, J., Hoffert, S., Peeters, M., Van Assche, G., and
R. Van Keer, "Xoodyak, a Lightweight Cryptographic
Scheme", IACR Transactions on Symmetric
Cryptology 2020(S1), DOI 10.46586/tosc.v2020.iS1.60-87,
2020, <https://keccak.team/xoodyak.html>.
[BLINKER] Saarinen, M.-J. O., "Beyond Modes: Building a Secure
Record Protocol from a Cryptographic Sponge Permutation",
CT-RSA 2014, DOI 10.1007/978-3-319-04852-9_14, 2014,
<https://eprint.iacr.org/2013/772>.
[STROBE] Hamburg, M., "The STROBE Protocol Framework", 2017,
<https://eprint.iacr.org/2017/003>.
[DISCO] Wong, D., "Disco: Modern Session Encryption", 2019,
<https://eprint.iacr.org/2019/180>.
[TLS13KS] Brzuska, C., Delignat-Lavaud, A., Egger, C., Fournet, C.,
Kohbrok, K., and M. Kohlweiss, "Key-Schedule Security for
the TLS 1.3 Standard", ASIACRYPT 2022, 2022,
<https://eprint.iacr.org/2021/467>.
Appendix A. Comparison with RFC 8446
This appendix is non-normative. It compares the RFC 8446 schedule
with the deck schedule of Section 7. Both profiles of this document
share this schedule and differ only in the underlying permutation, so
the comparison applies equally to TLS13-TURBOSHAKE256 and
TLS13-SHAKE256. The figure labels the deck side generically for that
reason. With finished_key and binder_key as dedicated MAC keys
(Section 5.5), the two schedules are close structurally, not only in
the values they produce: both carry the same named intermediates,
binder_key and finished_key, into the same MAC step, and both produce
the same six traffic and master secrets from the same three trunk
inputs. The figure shows the two schedules side by side for a full
handshake, lining up node for node where they agree. The table maps
each RFC 8446 construction to its replacement.
Sullivan Expires 7 January 2027 [Page 38]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
RFC 8446 (HKDF) Deck schedule (this document)
0, PSK PSK
| |
v v
+--------------+ +--------------+
| Early Secret | | E stage |
+--+------+----+ +--+------+----+
| | | |
| +--> binder_key | +--> binder_key
| +--> c e traffic | +--> c e traffic
| +--> e exp master | +--> e exp master
v v ratchet "early secret"
Derive-Secret "derived" +--------------+
| | early_secret | RATCHET 1
| DHE +--+-----------+
| | | re-init; absorb early_secret,
v v | DHE, TH_SH once
+--------------+ v
| Handshake | +--------------+
| Secret | | H stage |
+--+------+----+ +--+------+----+
| | | |
| +--> c hs traffic | +--> c hs traffic
| +--> s hs traffic | +--> s hs traffic
v |
Derive-Secret "derived" v ratchet "main secret"
| +--------------+
| 0 | main_secret | RATCHET 2
| | +--+-----------+
v v | re-init; absorb main_secret,
+--------------+ | TH_SF once
| Main Secret | v
+--+-----------+ +--------------+
| | T stage |
+--> c ap traffic +--+-----------+
+--> s ap traffic |
+--> exp master +--> c ap traffic
+--> res master (TH_CF) +--> s ap traffic
| +--> exp master
v +--> res master (TH_CF)
per traffic secret: |
"key" + "iv" v
Expand-Labels per traffic secret: one call, split
per base_key or per base_key or
binder_key: binder_key:
finished_key = finished_key =
Sullivan Expires 7 January 2027 [Page 39]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
Expand-Label "finished" expand(...,"finished",...,SecretLen)
Figure 1: The Two Schedules Side by Side
expand(...) in the figure denotes a deck expansion (Section 5.1). It
is figure-only shorthand and is not a function name this document
defines.
Both schedules fork binder_key from the same Early Secret analogue,
and both derive finished_key from binder_key or from a traffic secret
by the same "finished" label, feeding the same MAC step (HMAC on the
left, MAC on the right, Section 5.5). The schedules diverge in
topology, not in which named secrets exist: RFC 8446 threads every
stage transition through a discrete HKDF-Extract, salted by a Derive-
Secret("derived") call, where the deck schedule absorbs each stage's
inputs into one running state and crosses the boundary with a single
ratchet. The Finished and binder MACs, record keys, exporters,
resumption PSK, key updates, and PSK import each replace their RFC
8446 counterparts one for one, and Section 7.2 gives the per-shape
rules.
A.1. Invocation Count
The figure of Figure 1 shows structural closeness. This table
quantifies it. Both profiles of this document share the deck
schedule and therefore the same invocation count, differing only in
the underlying permutation, so the count is given once for both. The
handshake counted is one full 1-RTT handshake that offers and selects
a PSK, uses (EC)DHE, accepts 0-RTT early data, issues one
NewSessionTicket, and performs one KeyUpdate in each direction, the
maximal common case both RFC 8446, Section 7.1 and Section 7.3 cover
completely. A deck invocation is one expand, MAC, or Ratchet call,
matching the One-Shot Equivalence of Section 7.1. An RFC 8446
invocation is one HKDF-Extract, HKDF-Expand-Label, or HMAC call.
Fork and Absorb build an input sequence rather than invoking the
primitive and are not separately counted, matching how Section 7.2
already accounts for deck operations.
+===================================+==============+================+
|Derived value |Deck (this | RFC 8446 |
| |document) | |
+===================================+==============+================+
|Early Secret / early_secret |1 (Ratchet) | 1 (HKDF- |
| | | Extract) |
+-----------------------------------+--------------+----------------+
|binder_key |1 (expand) | 1 (Derive- |
| | | Secret) |
+-----------------------------------+--------------+----------------+
Sullivan Expires 7 January 2027 [Page 40]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
|finished_key (binder) |1 (expand) | 1 (Expand- |
| | | Label) |
+-----------------------------------+--------------+----------------+
|PSK binder verify_data |1 (MAC) | 1 (HMAC) |
+-----------------------------------+--------------+----------------+
|client_early_traffic_secret |1 | 1 (Derive- |
| |(Fork+Squeeze)| Secret) |
+-----------------------------------+--------------+----------------+
|early_exporter_master_secret |1 | 1 (Derive- |
| |(Fork+Squeeze)| Secret) |
+-----------------------------------+--------------+----------------+
|early traffic key + iv |1 (expand) | 2 (Expand- |
| | | Label) |
+-----------------------------------+--------------+----------------+
|"derived" salt (to Handshake |0 | 1 (Derive- |
|Secret) | | Secret) |
+-----------------------------------+--------------+----------------+
|Handshake Secret / main_secret |1 (Ratchet) | 1 (HKDF- |
| | | Extract) |
+-----------------------------------+--------------+----------------+
|client_handshake_traffic_secret |1 | 1 (Derive- |
| |(Fork+Squeeze)| Secret) |
+-----------------------------------+--------------+----------------+
|server_handshake_traffic_secret |1 | 1 (Derive- |
| |(Fork+Squeeze)| Secret) |
+-----------------------------------+--------------+----------------+
|client hs traffic key + iv |1 (expand) | 2 (Expand- |
| | | Label) |
+-----------------------------------+--------------+----------------+
|server hs traffic key + iv |1 (expand) | 2 (Expand- |
| | | Label) |
+-----------------------------------+--------------+----------------+
|finished_key (server Finished) |1 (expand) | 1 (Expand- |
| | | Label) |
+-----------------------------------+--------------+----------------+
|server Finished verify_data |1 (MAC) | 1 (HMAC) |
+-----------------------------------+--------------+----------------+
|finished_key (client Finished) |1 (expand) | 1 (Expand- |
| | | Label) |
+-----------------------------------+--------------+----------------+
|client Finished verify_data |1 (MAC) | 1 (HMAC) |
+-----------------------------------+--------------+----------------+
|"derived" salt (to Master Secret) |0 | 1 (Derive- |
| | | Secret) |
+-----------------------------------+--------------+----------------+
|Master Secret (2nd ratchet) |1 (Ratchet) | 1 (HKDF- |
| | | Extract) |
+-----------------------------------+--------------+----------------+
Sullivan Expires 7 January 2027 [Page 41]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
|client_application_traffic_secret_0|1 | 1 (Derive- |
| |(Fork+Squeeze)| Secret) |
+-----------------------------------+--------------+----------------+
|server_application_traffic_secret_0|1 | 1 (Derive- |
| |(Fork+Squeeze)| Secret) |
+-----------------------------------+--------------+----------------+
|exporter_master_secret |1 | 1 (Derive- |
| |(Fork+Squeeze)| Secret) |
+-----------------------------------+--------------+----------------+
|resumption_master_secret |1 | 1 (Derive- |
| |(Fork+Squeeze)| Secret) |
+-----------------------------------+--------------+----------------+
|client ap traffic key + iv (gen 0) |1 (expand) | 2 (Expand- |
| | | Label) |
+-----------------------------------+--------------+----------------+
|server ap traffic key + iv (gen 0) |1 (expand) | 2 (Expand- |
| | | Label) |
+-----------------------------------+--------------+----------------+
|client_application_traffic_secret_1|1 (expand) | 1 (Expand- |
| | | Label) |
+-----------------------------------+--------------+----------------+
|client ap traffic key + iv (gen 1) |1 (expand) | 2 (Expand- |
| | | Label) |
+-----------------------------------+--------------+----------------+
|server_application_traffic_secret_1|1 (expand) | 1 (Expand- |
| | | Label) |
+-----------------------------------+--------------+----------------+
|server ap traffic key + iv (gen 1) |1 (expand) | 2 (Expand- |
| | | Label) |
+-----------------------------------+--------------+----------------+
|resumption PSK (NewSessionTicket) |1 (expand) | 1 (Expand- |
| | | Label) |
+-----------------------------------+--------------+----------------+
|TLS-Exporter output (one request) |1 (expand) | 2 (Derive- |
| | | Secret + |
| | | Expand-Label) |
+-----------------------------------+--------------+----------------+
|Total |29 | 39 |
+-----------------------------------+--------------+----------------+
Table 4: Invocation Count for One Full Handshake
Of the deck total, 3 invocations are MAC (the PSK binder and both
Finished values) and 26 are expand, Ratchet, or Fork+Squeeze. Of the
RFC 8446 total, 3 invocations are HMAC and 36 are HKDF-Extract or
HKDF-Expand-Label. This operation count understates the difference,
because it counts operations rather than the permutation calls that
are the cost unit the two schedules share. Each HKDF or HMAC
Sullivan Expires 7 January 2027 [Page 42]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
operation is two nested hash calls, so over the same 24-round Keccak-
f[1600] permutation a hash-only HKDF-SHA3-256 instantiation of the
RFC 8446 schedule costs 156 permutation calls for this handshake
against the deck's 52, a factor of three. HMAC's nested hashing is
the overhead a keyed sponge does not carry. The deck is lower at the
operation level too, in every row where RFC 8446 needs two Expand-
Label calls, one for "key" and one for "iv", against this document's
single expansion that outputs Nk + Nn octets and splits the result
(Section 5.3), and in the two rows where RFC 8446's chained-extract
structure needs an explicit Derive-Secret("derived") call to salt the
next HKDF-Extract, which this document's ratchet does not need. The
composed security argument of Section 15.7.1 does not rest on either
count.
Appendix B. Implementation Considerations
This appendix is non-normative.
The profile of Section 8.1 requires incremental XOF absorption,
cloning of an unfinalized state, and one-shot squeeze. Output
lengths are always known up front. See Section 8.1 for the concrete
API surface and permutation parameters of that profile. Section 9.1
gives the analogous parameters for the TLS13-SHAKE256 profile.
Stage trunks and stage secrets bind no cipher suite value, so a
client offering several cipher suites of this document maintains one
schedule regardless of how many suites it offers. Only leaf
derivations differ, and only in their framed suffix.
An implementation choosing the one-shot recomputation strategy for
leaves retains raw key-exchange inputs longer than the stateful
strategy. The stateful strategy is the appropriate choice wherever
the erasure semantics of Section 15.7.2 matter. Accumulator clones
follow the lifetime and zeroization rules of Section 15.7.2.
Both ratchets consume a transcript checkpoint that the corresponding
RFC 8446 extracts do not: the handshake stage absorbs TH_SH and the
application stage absorbs TH_SF at initialization. A stack that
mirrors RFC 8446's derivation order and computes its master secret
before the server Finished exists must defer the second ratchet until
that checkpoint is available. In the one stack ported so far this
was code motion within existing functions, with no change to message
flow.
The destruction rules of Section 15.7.2 bound what an implementation
deliberately retains. In garbage-collected runtimes, zeroization is
inherently best effort: the runtime may have copied or moved key
material, and erasing every copy is not achievable from the language.
Sullivan Expires 7 January 2027 [Page 43]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
Such implementations satisfy the destruction rules by ceasing use,
dropping references, and zeroizing the buffers they control, as they
already do for RFC 8446 key material.
A cipher suite is a single negotiated value that determines both the
AEAD algorithm and the schedule profile. There is no mechanism for
combining them independently (Section 6). PSKs and session tickets
carry their originating cipher suite, and therefore their schedule
profile, with them (Section 4). A client that offers PSKs associated
with different schedule profiles computes each binder under its own
PSK's profile, which requires maintaining transcript-hash state per
governing profile for the partial ClientHello transcript.
Appendix C. Test Vectors
This appendix is non-normative.
Complete machine-readable test vectors for both profiles are
published as artifacts in this document's repository, alongside the
reference implementation that generated them and the independent
implementations that reproduced them. Every derived output binds the
governing cipher suite, so no final vector can exist before code
points are assigned (Section 14): the sets use declared private-use
placeholder values (0xFF01 to 0xFF03 for the TLS13-TURBOSHAKE256
suites, 0xFF04 and 0xFF05 for the TLS13-SHAKE256 suites). The
vectors track this document's expansion and MAC operations
(Section 5.1, Section 5.2) and are regenerated whenever that encoding
or the code points change. Each set is generated by one
implementation and reproduced by an independent implementation
constructed from this document alone.
C.1. TLS13-TURBOSHAKE256 Vectors
The published set contains 44 vectors: transcript-hash pins, the no-
PSK early_secret, a full schedule trace with a PSK and a key-exchange
secret (resumption and external binders, early leaves, both stage
secrets, and all six traffic and master secrets), record key blocks
for both key lengths under all three suites, the Finished MAC, two
key-update generations, resumption PSKs with present and empty
nonces, exporters including the early exporter, both ECH
confirmations, a PSK-only trace pinning the omitted "dh" absorb,
suite-binding cross-checks, the HelloRetryRequest synthetic
transcript, and the PSK-importer ipsk in three variants, including an
epsk at the 0xFFFE frame limit.
Sullivan Expires 7 January 2027 [Page 44]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
C.2. TLS13-SHAKE256 Vectors
This profile's vector set tracks the deck schedule of Section 7
instantiated with SHAKE256 (Section 9.1), mirroring the coverage of
Appendix C.1: transcript-hash pins, the no-PSK early_secret, a full
schedule trace with a PSK and a key-exchange secret, record key
blocks for both key lengths, two key-update generations, resumption
PSKs, exporters, both ECH confirmations, suite-binding cross-checks,
the HelloRetryRequest synthetic transcript, and the PSK-importer
ipsk. The published set contains 40 vectors, generated from this
profile and reproduced by an independent implementation built from
this document alone. Within this profile's two suites and single
PSK-importer ipsk, it omits the third-suite cross-checks and the
extra import variants of Appendix C.1. A message-level full-
handshake trace in the style of RFC 8448 has not yet been extracted,
though a reference implementation now wires this profile into a TLS
stack.
Appendix D. A Fully FIPS-Component Key Schedule (Informative)
This appendix is non-normative. It records an extract-and-expand
schedule assembled entirely from FIPS-approved components, for
deployers and future work that need that property before or instead
of the deck schedule of Section 7. This document does not define
this schedule as a profile: it has no code point, no cipher suite,
and no IANA registration, and Section 6 and Section 14 are unaffected
by it.
The TLS13-SHAKE256 profile's deck schedule of Section 7 is built from
FIPS 202 and SP 800-185 functions used in isolation, SHAKE256
[FIPS202] for the deck and KMAC256 [SP800-185] for the MAC, but as a
keyed-duplex key-derivation function the deck is not itself an
approved key-derivation function under any current NIST Special
Publication, and no CAVP or CMVP testing covers it. A deployment
that requires FIPS-approved primitives throughout therefore cannot
use the deck. This appendix records an approved-component
alternative for it, subject to the validation caveats below.
TLS13-TURBOSHAKE256, whose TurboSHAKE256 and TurboKMAC256 are not
approved functions, is not available to such a deployment either.
The schedule is the RFC 8446, Section 7.1 extract-and-expand
structure with its PRF replaced by KMAC256 [SP800-185] throughout,
and its Extract step drawn from NIST SP 800-56C [SP800-56C] rather
than from HKDF-Extract.
Extract: An SP 800-56C two-step randomness-extraction step, PRK =
Sullivan Expires 7 January 2027 [Page 45]
Internet-Draft TLS 1.3 Schedule Profiles July 2026
KMAC256(K = salt, X = IKM, L = 512, S = ""), applied at each of
the three stage transitions of RFC 8446, Section 7.1: Early =
Extract(0, PSK), Handshake = Extract(derived, (EC)DHE), and Master
= Extract(derived, 0), where derived is the RFC 8446 Derive-
Secret("", "derived", "") intermediate at each transition and 0
denotes an all-zero string of the same length as the adjacent
secret.
Expand: An SP 800-108 KBKDF counter-mode expansion with KMAC256 as
the PRF, used for every Derive-Secret and HKDF-Expand-Label site
of RFC 8446, Section 7.1: record keys, traffic secrets, exporter
and resumption secrets, and the Finished and PSK binder keys.
TranscriptHash: An approved SHA-3-family function: SHA3-256,
SHA3-384, or, for a variable-length instantiation with an explicit
output length, SHAKE256 or cSHAKE256 [FIPS202] [SP800-185].
This schedule is structurally RFC 8446, Section 7.1 with its PRF
replaced by another approved PRF. Most of the CMVP approved-CVL
decomposition of the TLS 1.3 KDF therefore transfers directly:
[SP800-133] for the initial all-zero input and [SP800-108] for
Expand, for which SP 800-108 recognizes KMAC as a PRF. The RFC 8446
key-schedule security analysis is likewise modular over the
underlying PRF and re-instantiates with KMAC256. The one component
that does not transfer for free is the [SP800-56C] Extract step: SP
800-56C's approved randomness-extraction functions are HMAC- and AES-
CMAC-based, so whether KMAC256 is approved there, rather than HMAC,
is a point a validation would have to establish, and this document
does not assert it.
This document does not claim that a schedule built this way is fully
FIPS-validated or fully FIPS-validatable today. It is assembled
entirely from FIPS-approved components, and whether a CMVP validation
of the composite reuses existing CAVP test vectors for SP 800-56C and
SP 800-108 or requires its own named CVL entry is a determination for
a validation laboratory and CMVP, not one this document makes. This
appendix records the approvable variant for deployers and future
work. It is not a profile this document defines.
Author's Address
Nick Sullivan
Cryptography Consulting LLC
Email: nicholas.sullivan+ietf@gmail.com
Sullivan Expires 7 January 2027 [Page 46]