<?xml version='1.0' encoding='utf-8'?>
<!DOCTYPE rfc [
  <!ENTITY nbsp    "&#160;">
  <!ENTITY zwsp   "&#8203;">
  <!ENTITY nbhy   "&#8209;">
  <!ENTITY wj     "&#8288;">
]>
<?xml-stylesheet type="text/xsl" href="rfc2629.xslt" ?>
<!-- generated by https://github.com/cabo/kramdown-rfc version 1.7.21 (Ruby 3.3.6) -->
<rfc xmlns:xi="http://www.w3.org/2001/XInclude" ipr="trust200902" docName="draft-barnes-mls-appsync-01" category="info" consensus="true" submissionType="IETF" tocInclude="true" sortRefs="true" symRefs="true" version="3">
  <!-- xml2rfc v2v3 conversion 3.25.0 -->
  <front>
    <title abbrev="MLS App API">A Safe Application Interface to Messaging Layer Security</title>
    <seriesInfo name="Internet-Draft" value="draft-barnes-mls-appsync-01"/>
    <author initials="J." surname="Alwen" fullname="Joel Alwen">
      <organization>Amazon</organization>
      <address>
        <email>alwenjo@amazon.com</email>
      </address>
    </author>
    <author initials="R." surname="Barnes" fullname="Richard Barnes">
      <organization>Cisco</organization>
      <address>
        <email>rlb@ipv.sx</email>
      </address>
    </author>
    <author initials="R." surname="Mahy" fullname="Rohan Mahy">
      <organization>Rohan Mahy Consulting Services</organization>
      <address>
        <email>rohan.ietf@gmail.com</email>
      </address>
    </author>
    <author initials="M." surname="Mularczyk" fullname="Marta Mularczyk">
      <organization>Amazon</organization>
      <address>
        <email>mulmarta@amazon.com</email>
      </address>
    </author>
    <date year="2024" month="December" day="12"/>
    <area>Security</area>
    <workgroup>Messaging Layer Security</workgroup>
    <keyword>messaging layer security</keyword>
    <keyword>end-to-end encryption</keyword>
    <abstract>
      <?line 44?>

<t>The Messaging Layer Security protocol enables a group of participants to
negotiate a common cryptographic state.  While the primary function of MLS is to
establish shared secret state for the group, an MLS group also captures
authentication information for group participants and information on which the
group has confirmed agreement.  This document defines an interface interface by
which multiple uncoordinated application functions may safely reuse the
cryptographic state of an MLS group for application purposes.</t>
    </abstract>
    <note removeInRFC="true">
      <name>About This Document</name>
      <t>
        The latest revision of this draft can be found at <eref target="https://bifurcation.github.io/mls-appsync/draft-barnes-mls-appsync.html"/>.
        Status information for this document may be found at <eref target="https://datatracker.ietf.org/doc/draft-barnes-mls-appsync/"/>.
      </t>
      <t>
        Discussion of this document takes place on the
        Messaging Layer Security Working Group mailing list (<eref target="mailto:mls@ietf.org"/>),
        which is archived at <eref target="https://mailarchive.ietf.org/arch/browse/mls/"/>.
        Subscribe at <eref target="https://www.ietf.org/mailman/listinfo/mls/"/>.
      </t>
      <t>Source for this draft and an issue tracker can be found at
        <eref target="https://github.com/bifurcation/mls-appsync"/>.</t>
    </note>
  </front>
  <middle>
    <?line 54?>

<section anchor="introduction">
      <name>Introduction</name>
      <t>The Messaging Layer Security protocol (MLS) is designed to be integrated into
applications, in order to provide security services that the application
requires <xref target="RFC9420"/>.  There are two questions to answer when designing such an
integration:</t>
      <ol spacing="normal" type="1"><li>
          <t>How does the application provide the services that MLS requires?</t>
        </li>
        <li>
          <t>How does the application use MLS to get security benefits?</t>
        </li>
      </ol>
      <t>The MLS Architecture describes the requirements for the first of these questions
<xref target="I-D.mls-architecture"/>, namely the structure of the Delivery Service and
Authentication Service that MLS requires.  This document is focused on the
second question.</t>
      <t>MLS itself offers some basic functions that applications can use, such as the
secure message encapsulation (PrivateMessage), the MLS exporter, and the epoch
authenticator.  Current MLS applications make use of these mechanisms to acheive
a variety of confidentiality and authentication properties.</t>
      <t>As application designers become more familiar with MLS, there is increasing
interest in leveraging other cryptographic tools that an MLS group provides:</t>
      <ul spacing="normal">
        <li>
          <t>HPKE and signature key pairs for each member, where the private key is known
only to that member, and the public key is authenticated to the other members.</t>
        </li>
        <li>
          <t>A pre-shared key mechanism that can allow an application to inject data into
the MLS key schedule.</t>
        </li>
        <li>
          <t>An exporter mechanism that allows applications to derive secrets from the MLS
key schedule.</t>
        </li>
        <li>
          <t>Association of data with Commits as a synchronization mechanism.</t>
        </li>
        <li>
          <t>Binding of information to the GroupContext to confirm group agreement.</t>
        </li>
      </ul>
      <t>There is also interest in exposing an MLS group to multiple loosely-coordinated
components of an application.  To accommodate such cases, the above mechanisms
need to be exposed in such a way that different components' usage will not
conflict with each other, or with MLS itself.</t>
      <t>This document defines a set of mechanisms that application components can use to
ensure that their use of these facilities is properly domain-separated from MLS
itself, and from other application components that might be using the same MLS
group.</t>
    </section>
    <section anchor="conventions-and-definitions">
      <name>Conventions and Definitions</name>
      <t>The key words "<bcp14>MUST</bcp14>", "<bcp14>MUST NOT</bcp14>", "<bcp14>REQUIRED</bcp14>", "<bcp14>SHALL</bcp14>", "<bcp14>SHALL
NOT</bcp14>", "<bcp14>SHOULD</bcp14>", "<bcp14>SHOULD NOT</bcp14>", "<bcp14>RECOMMENDED</bcp14>", "<bcp14>NOT RECOMMENDED</bcp14>",
"<bcp14>MAY</bcp14>", and "<bcp14>OPTIONAL</bcp14>" in this document are to be interpreted as
described in BCP 14 <xref target="RFC2119"/> <xref target="RFC8174"/> when, and only when, they
appear in all capitals, as shown here.</t>
      <?line -18?>

<t>We make heavy use of the terminology in the MLS specification <xref target="RFC9420"/>.</t>
      <dl>
        <dt>Application:</dt>
        <dd>
          <t>The system that instantiates, manages, and uses an MLS group.  Each MLS group
is used by exactly one application, but an application may maintain multiple
groups.</t>
        </dd>
        <dt>Application component:</dt>
        <dd>
          <t>A subsystem of an application that has access to an MLS group.</t>
        </dd>
        <dt>Component ID:</dt>
        <dd>
          <t>An identifier for an application component.  These identifiers are assigned by
the application.</t>
        </dd>
      </dl>
    </section>
    <section anchor="protocol-overview">
      <name>Protocol Overview</name>
      <t>The mechansms in this document take MLS mechanisms that are either not
inherently designed to be used by applications, or not inherently designed to be
used by multiple application components, and adds a domain separator that
separates application usage from MLS usage, and application components' usage
from each other:</t>
      <ul spacing="normal">
        <li>
          <t>Signing operations are tagged so that signatures will only verify in the
context of a given component.</t>
        </li>
        <li>
          <t>Public-key encryption operations are similarly tagged so that encrypted data
will only decrypt in the context of a given component.</t>
        </li>
        <li>
          <t>Pre-shared keys are identified as originating from a specific component, so
that differnet components' contributions to the MLS key schedule will not
collide.</t>
        </li>
        <li>
          <t>Exported values include an identifier for the component to which they are
being exported, so that different components will get different exported
values.</t>
        </li>
      </ul>
      <t>We also define new general mechanisms that allow applications to take advantage
of the extensibility mechanisms of MLS without having to define extensions
themselves:</t>
      <ul spacing="normal">
        <li>
          <t>An <tt>application_data</tt> extension type that associates application data with MLS
messages, or with the state of the group.</t>
        </li>
        <li>
          <t>An ApplicationData proposal type that enables arbitrary application data to
be associated to a Commit.</t>
        </li>
        <li>
          <t>An ApplicationDataUpdate proposal type that enables efficient updates to
an <tt>application_data</tt> GroupContext extension.</t>
        </li>
      </ul>
      <t>As with the above, information carried in these proposals and extension marked
as belonging to a specific application component, so that components can manage
their information independently.</t>
      <t>The separation between components is acheived by the application assigning each
component a unique component ID number.  These numbers are then incorporated
into the appopriate calculations in the protocol to achieve the required
separation.</t>
      <section anchor="component-ids">
        <name>Component IDs</name>
        <t>A component ID is a four-byte value that uniquely identifies a component within
the scope of an application.</t>
        <t><tt>
uint32 ComponentID;
</tt></t>
        <ul empty="true">
          <li>
            <t>TODO: What are the uniqueness requirements on these?  It seems like the more
diversity, the better.  For example, if a ComponentID is reused across
applications (e.g., via an IANA registry), then there will be a risk of replay
across applications.  Maybe we should include a binder to the group/epoch as
well, something derived from the key schedule.</t>
          </li>
        </ul>
        <ul empty="true">
          <li>
            <t>TODO: It might be better to frame these in terms of "data types" instead of
components, to avoid presuming software architecture.  Though that makes less
sense for the more "active" portions of the API, e.g., signing and encryption.</t>
          </li>
        </ul>
        <t>When a label is required for an operation, the following data structure is used.
The <tt>label</tt> field identifies the operation being performed.  The <tt>component_id</tt>
field identifies the component performing the operation.  The <tt>context</tt> field is
specified by the operation in question.</t>
        <sourcecode type="tls"><![CDATA[
struct {
  opaque label<V>;
  ComponentID component_id;
  opaque context<V>;
} ComponentOperationLabel;
]]></sourcecode>
      </section>
    </section>
    <section anchor="hybrid-public-key-encryption-hpke-keys">
      <name>Hybrid Public Key Encryption (HPKE) Keys</name>
      <t>This component of the API allows components to make use of the HPKE key pairs
generated by MLS. An component identified by an CompnentID can use any HPKE
key pair for any operation defined in <xref target="RFC9180"/>, such as encryption,
exporting keys and the PSK mode, as long as the <tt>info</tt> input to <tt>Setup&lt;MODE&gt;S</tt>
and <tt>Setup&lt;MODE&gt;R</tt> is set to ComponentOperationLabel with <tt>component_id</tt> set
to the appopriate ComponentID. The <tt>context</tt> can be set to an arbitrary Context
specified by the application designer and can be empty if not needed. For
example, a component can use a key pair PublicKey, PrivateKey to encrypt data
as follows:</t>
      <sourcecode type="tls"><![CDATA[
SafeEncryptWithContext(ComponentID, PublicKey, Context, Plaintext) =
    SealBase(PublicKey, ComponentOperationLabel, "", Plaintext)

SafeDecryptWithContext(ComponentID, PrivateKey, Context, KEMOutput, Ciphertext) =
    OpenBase(KEMOutput, PrivateKey, ComponentOperationLabel, "", Ciphertext)
]]></sourcecode>
      <t>Where the fields of ComponentOperationLabel are set to</t>
      <sourcecode type="tls"><![CDATA[
label = "MLS 1.0 Application"
component_id = ComponentID
context = Context
]]></sourcecode>
      <ul empty="true">
        <li>
          <t>TODO: Should this use EncryptWithLabel / DecryptWithLabel?  That wouldn't
cover other modes / exports, but you could say "mutatis mutandis".</t>
        </li>
      </ul>
      <t>For operations involving the secret key, ComponentID <bcp14>MUST</bcp14> be set to the
ComponentID of the component performing the operation, and not to the ID of
any other component. In particular, this means that a component cannot decrypt
data meant for another component, while components can encrypt data that other
components can decrypt.</t>
      <t>In general, a ciphertext encrypted with a PublicKey can be decrypted by any
entity who has the corresponding PrivateKey at a given point in time according
to the MLS protocol (or application component). For convenience, the following
list summarizes lifetimes of MLS key pairs.</t>
      <ul spacing="normal">
        <li>
          <t>The key pair of a non-blank ratchet tree node. The PrivateKey of such a key pair
is known to all members in the node’s subtree. In particular, a PrivateKey of a
leaf node is known only to the member in that leaf. A member in the subtree
stores the PrivateKey for a number of epochs, as long as the PublicKey does not
change. The key pair of the root node <bcp14>SHOULD NOT</bcp14> be used, since the external key
pair recalled below gives better security.</t>
        </li>
        <li>
          <t>The external_priv, external_pub key pair used for external initialization. The
external_priv key is known to all group members in the current epoch. A member
stores external_priv only for the current epoch. Using this key pair gives
better security guarantees than using the key pair of the root of the ratchet
tree and should always be preferred.</t>
        </li>
        <li>
          <t>The init_key in a KeyPackage and the corresponding secret key. The secret key
is known only to the owner of the KeyPackage and is deleted immediately after it
is used to join a group.</t>
        </li>
      </ul>
    </section>
    <section anchor="signature-keys">
      <name>Signature Keys</name>
      <t>MLS session states contain a number of signature keys including the ones in the
LeafNode structs. Application components can safely sign content and verify
signatures using these keys via the SafeSignWithLabel and SafeVerifyWithLabel
functions, respectively, much like how the basic MLS protocol uses SignWithLabel
and VerifyWithLabel.</t>
      <t>In more detail, a component identified by ComponentID should sign and verify
using:</t>
      <sourcecode type="tls"><![CDATA[
SafeSignWithLabel(ComponentID, SignatureKey, Label, Content) =
    SignWithLabel(SignatureKey, "ComponentOperationLabel", ComponentOperationLabel)

SafeVerifyWithLabel(ComponentID, VerificationKey, Label, Content, SignatureValue) =
    VerifyWithLabel(VerificationKey, "ComponentOperationLabel", ComponentOperationLabel, SignatureValue)
]]></sourcecode>
      <t>Where the fields of ComponentOperationLabel are set to</t>
      <sourcecode type="tls"><![CDATA[
label = Label
component_id = ComponentID
context = Content
]]></sourcecode>
      <t>For signing operations, the ComponentID <bcp14>MUST</bcp14> be set to the ComponentID of the
component performing the signature, and not to the ID of any other component.
This means that a component cannot produce signatures in place of other
component. However, components can verify signatures computed by other
components. Domain separation is ensured by explicitly including the ComponentID
with every operation.</t>
    </section>
    <section anchor="pre-shared-keys">
      <name>Pre-Shared Keys</name>
      <t>PSKs represent key material that is injected into the MLS key schedule when
creating or processing a commit as defined in <xref section="8.4" sectionFormat="of" target="RFC9420"/>. Its
injection into the key schedule means that all group members have to agree on
the value of the PSK.</t>
      <t>While PSKs are typically cryptographic keys which due to their properties add to
the overall security of the group, the PSK mechanism can also be used to ensure
that all members of a group agree on arbitrary pieces of data represented as
octet strings (without the necessity of sending the data itself over the wire).
For example, a component can use the PSK mechanism to enforce that all group
members have access to and agree on a password or a shared file.</t>
      <t>This is achieved by creating a new epoch via a PSK proposal. Transitioning to
the new epoch requires using the information agreed upon.</t>
      <t>To facilitate using PSKs in a safe way, this document defines a new PSKType for
application components. This provides domain separation between pre-shared keys
used by the core MLS protocol and applications, and between those used by
different components.</t>
      <sourcecode type="tls-presentation"><![CDATA[
enum {
  // ...
  application(3),
  (255)
} PSKType;

struct {
  PSKType psktype;
  select (PreSharedKeyID.psktype) {
    // ...
    case application:
      ComponentID component_id;
      opaque psk_id<V>;
  };
  opaque psk_nonce<V>;
} PreSharedKeyID;
]]></sourcecode>
      <ul empty="true">
        <li>
          <t>TODO: It seems like you could also do this by structuring the <tt>external</tt>
PSKType as (component_id, psk_id).  I guess this approach separates this API
from other external PSKs.</t>
        </li>
      </ul>
    </section>
    <section anchor="exported-secrets">
      <name>Exported Secrets</name>
      <t>An application component can use MLS as a group key agreement protocol by
exporting symmetric keys.  Such keys can be exported (i.e. derived from MLS key
material) in two phases per epoch: Either at the start of the epoch, or during
the epoch. Derivation at the start of the epoch has the added advantage that the
source key material is deleted after use, allowing the derived key material to
be deleted later even during the same MLS epoch to achieve forward secrecy. The
following protocol secrets can be used to derive key from for use by application
components:</t>
      <ul spacing="normal">
        <li>
          <t><tt>exporter_secret</tt> at the beginning of an epoch</t>
        </li>
        <li>
          <t><tt>application_export_secret</tt> during an epoch</t>
        </li>
      </ul>
      <t>The <tt>application_export_secret</tt> is an additional secret derived from the
<tt>epoch_secret</tt> at the beginning of the epoch in the same way as the other
secrets listed in Table 4 of <xref target="RFC9420"/> using the label "application_export".</t>
      <t>Any derivation performed by an application component either from the
<tt>exporter_secret</tt> or the <tt>application_export_secret</tt> has to use the following
function:</t>
      <sourcecode type="tls"><![CDATA[
DeriveApplicationSecret(Secret, Label) =
  ExpandWithLabel(Secret, "ApplicationExport " + ComponentID + " " + Label)
]]></sourcecode>
      <t>Where ExpandWithLabel is defined in <xref section="8" sectionFormat="of" target="RFC9420"/> and where
ComponentID <bcp14>MUST</bcp14> be set to the ComponentID of the component performing the
export.</t>
      <ul empty="true">
        <li>
          <t>TODO: This section seems over-complicated to me.  Why is it not sufficient to
just use the <tt>exporter_secret</tt>?  Or the <tt>MLS-Exporter</tt> mechanism with a
label structured to include the ComponentID?</t>
        </li>
      </ul>
    </section>
    <section anchor="attaching-application-data-to-mls-messages">
      <name>Attaching Application Data to MLS Messages</name>
      <t>The MLS GroupContext, LeafNode, KeyPackage, and GroupInfo objects each have an
<tt>extensions</tt> field that can carry additional data not defined by the MLS
specification.  The <tt>application_data</tt> extension provides a generic container
that applications can use to attach application data to these messages.  Each
usage of the extension serves a slightly different purpose:</t>
      <ul spacing="normal">
        <li>
          <t>GroupContext: Confirms that all members of the group agree on the application
data, and automatically distributes it to new joiners.</t>
        </li>
        <li>
          <t>KeyPackage and LeafNode: Associates the application data to a particular
client, and advertises it to the other members of the group.</t>
        </li>
        <li>
          <t>GroupInfo: Distributes the application data confidentially to the new joiners
for whom the GroupInfo is encrypted (as a Welcome message).</t>
        </li>
      </ul>
      <t>The content of the <tt>application_data</tt> extension is a serialized
ApplicationDataDictionary object:</t>
      <sourcecode type="tls-presentation"><![CDATA[
struct {
    ComponentID component_id;
    opaque data<V>;
} ComponentData;

struct {
    ComponentData component_data<V>;
} ApplicationDataDictionary;
]]></sourcecode>
      <t>The entries in the <tt>component_data</tt> <bcp14>MUST</bcp14> be sorted by <tt>component_id</tt>, and there
<bcp14>MUST</bcp14> be at most one entry for each <tt>component_id</tt>.</t>
      <t>An <tt>application_data</tt> extension in a LeafNode, KeyPackage, or GroupInfo can be
set when the object is created.  An <tt>application_data</tt> extension in the
GroupContext needs to be manage using the tools available to update GroupContext
extensions: The creator of the group can set extensions unilaterally, and
thereafter, the GroupContextExtensions proposal can be used to update
extensions.  The ApplicationDataUpdate proposal described in
<xref target="appdataupdate"/> provides a more efficient way to update the
<tt>application_data</tt> extension.</t>
    </section>
    <section anchor="appdataupdate">
      <name>Updating Application Data in the GroupContext</name>
      <t>Updating the <tt>application_data</tt> with a GroupContextExtensions proposal is
cumbersome.  The application data needs to be transmitted in its entirety, along
with any other extensions, whether or not they are being changed.  And a
GroupContextExtensions proposal always requires an UpdatePath, which updating
application state never should.</t>
      <t>The ApplicationDataUpdate proposal allows the <tt>application_data</tt> extension to
be updated without these costs.  Instead of sending the whole value of the
extension, it sends only an update, which is interpreted by the application to
provide the new content for the <tt>application_data</tt> extension.  No other
extensions are sent or updated, and no UpdatePath is required.</t>
      <t>```
enum {
    invalid(0),
    update(1),
    remove(2),
    (255)
} ApplicationDataUpdateOperation;</t>
      <t>struct {
    ComponentID component_id;
    ApplicationDataUpdateOperation op;</t>
      <artwork><![CDATA[
select (ApplicationDataUpdate.op) {
    case update: opaque update<V>;
    case remove: struct{}
} } ApplicationDataUpdate; ```
]]></artwork>
      <t>An ApplicationDataUpdate proposal is invalid if its <tt>component_id</tt> references a
component that is not known to the application, or if it specifies the removal
of state for a <tt>component_id</tt> that has no state present.  A proposal list is
invalid if it includes multiple ApplicationDataUpdate proposals that <tt>remove</tt>
state for the same <tt>component_id</tt>, or proposals that both <tt>update</tt> and <tt>remove</tt>
state for the same <tt>component_id</tt>.  In other words, for a given <tt>component_id</tt>,
a proposal list is valid only if it contains (a) a single <tt>remove</tt> operation or
(b) one or more <tt>update</tt> operation.</t>
      <ul empty="true">
        <li>
          <t>TODO: Deconflict with GroupContextExtensions.</t>
        </li>
      </ul>
      <t>ApplicationDataUpdate proposals are processed after any default proposals (i.e., those
defined in <xref target="RFC9420"/>), and any ApplicationData proposals.</t>
      <t>A client applies ApplicationDataUpdate proposals by component ID.  For each
<tt>component_id</tt> field that appears in an ApplicationDataUpdate proposal in the
Commit, the client assembles a list of ApplicationDataUpdate proposals with that
<tt>component_id</tt>, in the order in which they appear in the Commit, and processes
them in the following way:</t>
      <ul spacing="normal">
        <li>
          <t>If the list comprises a single proposal with the <tt>op</tt> field set to <tt>remove</tt>:  </t>
          <ul spacing="normal">
            <li>
              <t>If there is an entry in the <tt>component_states</tt> vector in the
<tt>application_state</tt> extension with the specified <tt>component_id</tt>, remove
it.</t>
            </li>
            <li>
              <t>Otherwise, the proposal is invalid.</t>
            </li>
          </ul>
        </li>
        <li>
          <t>If the list comprises one or more proposals, all with <tt>op</tt> field set to
<tt>update</tt>:  </t>
          <ul spacing="normal">
            <li>
              <t>Provide the application logic registered to the <tt>component_id</tt> value with
the content of the <tt>update</tt> field from each proposal, in the order
specified.</t>
            </li>
            <li>
              <t>The application logic returns either an opaque value <tt>new_data</tt> that will be
stored as the new application data for this component, or else an
indication that it considers this update invalid.</t>
            </li>
            <li>
              <t>If the application logic considers the update invalid, the MLS client <bcp14>MUST</bcp14>
consider the proposal list invalid.</t>
            </li>
            <li>
              <t>If no <tt>application_data</tt> extension is present in the GroupContext, add one
to the end of the <tt>extensions</tt> list in the GroupContext.</t>
            </li>
            <li>
              <t>If there is an entry in the <tt>component_data</tt> vector in the
<tt>application_data</tt> extension with the specified <tt>component_id</tt>, then set
its <tt>data</tt> field to the specified <tt>new_data</tt>.</t>
            </li>
            <li>
              <t>Otherwise, insert a new entry in the <tt>component_states</tt> vector with the
specified <tt>component_id</tt> and the <tt>data</tt> field set to the <tt>new_data</tt>
value.  The new entry is inserted at the proper point to keep the
<tt>component_states</tt> vector sorted by <tt>component_id</tt>.</t>
            </li>
          </ul>
        </li>
        <li>
          <t>Otherwise, the proposal list is invalid.</t>
        </li>
      </ul>
      <ul empty="true">
        <li>
          <t>NOTE: An alternative design here would be to have the <tt>update</tt> operation
simply set the new value for the <tt>application_data</tt> GCE, instead of sending a
diff.  This would be simpler in that the MLS stack wouldn't have to ask the
application for the new state value, and would discourage applications from
storing large state in the GroupContext directly (which bloats Welcome
messages).  It would effectively require the state in the GroupContext to be a
hash of the real state, to avoid large ApplicationDataUpdate proposals.  This
pushes some complexity onto the application, since the application has to
define a hashing algorithm, and define its own scheme for initializing new
joiners.</t>
        </li>
      </ul>
    </section>
    <section anchor="attaching-application-data-to-a-commit">
      <name>Attaching Application Data to a Commit</name>
      <t>The ApplicationData proposal type allows an application component to associate
application data to a Commit, so that the member processing the Commit knows
that all other group members will be processing the same data.  ApplicationData
proposals are ephemeral in the sense that they do not change any persistent
state related to MLS, aside from their appearance in the transcript hash.</t>
      <t>The content of an ApplicationData proposal is the same as an <tt>application_data</tt>
extension.  The proposal type is set in <xref target="iana-considerations"/>.</t>
      <sourcecode type="tls-presentation"><![CDATA[
struct {
    ComponentID component_id;
    opaque data<V>;
} ApplicationData;
]]></sourcecode>
      <t>An ApplicationData proposal is invalid if it contains a <tt>component_id</tt> that is
unknown to the application, or if the <tt>application_data</tt> field contains any
<tt>ComponentData</tt> entry whose <tt>data</tt> field is considered invalid by the
application logic registered to the indicated <tt>component_id</tt>.</t>
      <t>ApplicationData proposals <bcp14>MUST</bcp14> be processed after any default proposals (i.e.,
those defined in <xref target="RFC9420"/>), but before any ApplicationDataUpdate proposals.</t>
      <t>A client applies an ApplicationData proposal by providing the contents of the
<tt>application_data</tt> field to the component identified by the <tt>component_id</tt>.  If
a Commit references more than one ApplicationData proposal for the same
<tt>component_id</tt> value, then they <bcp14>MUST</bcp14> be processed in the order in which they are
specified in the Commit.</t>
    </section>
    <section anchor="security-considerations">
      <name>Security Considerations</name>
      <t>The API defined in this document provides the following security guarantee: If
an application uses MLS and all its components use this API, then the security
guarantees of the base MLS protocol and the security guarantees of the
components, each analyzed in isolation, still hold for the composed protocol. In
other words, the API protects applications from careless
component developers. As long as all the components use this API, it is not
possible that some combination of components  (the developers of which did not know
about each other) impedes the security of the base MLS protocol or any used
component. No further analysis of the combination is necessary. This also means
that any security vulnerabilities introduced by one component do not spread to
other component or the base MLS protocol.</t>
    </section>
    <section anchor="iana-considerations">
      <name>IANA Considerations</name>
      <t>TODO:</t>
      <ul spacing="normal">
        <li>
          <t>Register <tt>application_data</tt> extension</t>
        </li>
        <li>
          <t>Register ApplicationData proposal</t>
        </li>
        <li>
          <t>Register ApplicationDataUpdate proposal</t>
        </li>
      </ul>
    </section>
  </middle>
  <back>
    <references anchor="sec-combined-references">
      <name>References</name>
      <references anchor="sec-normative-references">
        <name>Normative References</name>
        <reference anchor="RFC9420">
          <front>
            <title>The Messaging Layer Security (MLS) Protocol</title>
            <author fullname="R. Barnes" initials="R." surname="Barnes"/>
            <author fullname="B. Beurdouche" initials="B." surname="Beurdouche"/>
            <author fullname="R. Robert" initials="R." surname="Robert"/>
            <author fullname="J. Millican" initials="J." surname="Millican"/>
            <author fullname="E. Omara" initials="E." surname="Omara"/>
            <author fullname="K. Cohn-Gordon" initials="K." surname="Cohn-Gordon"/>
            <date month="July" year="2023"/>
            <abstract>
              <t>Messaging applications are increasingly making use of end-to-end security mechanisms to ensure that messages are only accessible to the communicating endpoints, and not to any servers involved in delivering messages. Establishing keys to provide such protections is challenging for group chat settings, in which more than two clients need to agree on a key but may not be online at the same time. In this document, we specify a key establishment protocol that provides efficient asynchronous group key establishment with forward secrecy (FS) and post-compromise security (PCS) for groups in size ranging from two to thousands.</t>
            </abstract>
          </front>
          <seriesInfo name="RFC" value="9420"/>
          <seriesInfo name="DOI" value="10.17487/RFC9420"/>
        </reference>
        <reference anchor="RFC2119">
          <front>
            <title>Key words for use in RFCs to Indicate Requirement Levels</title>
            <author fullname="S. Bradner" initials="S." surname="Bradner"/>
            <date month="March" year="1997"/>
            <abstract>
              <t>In many standards track documents several words are used to signify the requirements in the specification. These words are often capitalized. This document defines these words as they should be interpreted in IETF documents. This document specifies an Internet Best Current Practices for the Internet Community, and requests discussion and suggestions for improvements.</t>
            </abstract>
          </front>
          <seriesInfo name="BCP" value="14"/>
          <seriesInfo name="RFC" value="2119"/>
          <seriesInfo name="DOI" value="10.17487/RFC2119"/>
        </reference>
        <reference anchor="RFC8174">
          <front>
            <title>Ambiguity of Uppercase vs Lowercase in RFC 2119 Key Words</title>
            <author fullname="B. Leiba" initials="B." surname="Leiba"/>
            <date month="May" year="2017"/>
            <abstract>
              <t>RFC 2119 specifies common key words that may be used in protocol specifications. This document aims to reduce the ambiguity by clarifying that only UPPERCASE usage of the key words have the defined special meanings.</t>
            </abstract>
          </front>
          <seriesInfo name="BCP" value="14"/>
          <seriesInfo name="RFC" value="8174"/>
          <seriesInfo name="DOI" value="10.17487/RFC8174"/>
        </reference>
        <reference anchor="RFC9180">
          <front>
            <title>Hybrid Public Key Encryption</title>
            <author fullname="R. Barnes" initials="R." surname="Barnes"/>
            <author fullname="K. Bhargavan" initials="K." surname="Bhargavan"/>
            <author fullname="B. Lipp" initials="B." surname="Lipp"/>
            <author fullname="C. Wood" initials="C." surname="Wood"/>
            <date month="February" year="2022"/>
            <abstract>
              <t>This document describes a scheme for hybrid public key encryption (HPKE). This scheme provides a variant of public key encryption of arbitrary-sized plaintexts for a recipient public key. It also includes three authenticated variants, including one that authenticates possession of a pre-shared key and two optional ones that authenticate possession of a key encapsulation mechanism (KEM) private key. HPKE works for any combination of an asymmetric KEM, key derivation function (KDF), and authenticated encryption with additional data (AEAD) encryption function. Some authenticated variants may not be supported by all KEMs. We provide instantiations of the scheme using widely used and efficient primitives, such as Elliptic Curve Diffie-Hellman (ECDH) key agreement, HMAC-based key derivation function (HKDF), and SHA2.</t>
              <t>This document is a product of the Crypto Forum Research Group (CFRG) in the IRTF.</t>
            </abstract>
          </front>
          <seriesInfo name="RFC" value="9180"/>
          <seriesInfo name="DOI" value="10.17487/RFC9180"/>
        </reference>
      </references>
      <references anchor="sec-informative-references">
        <name>Informative References</name>
        <reference anchor="I-D.mls-architecture">
          <front>
            <title>*** BROKEN REFERENCE ***</title>
            <author>
              <organization/>
            </author>
            <date/>
          </front>
        </reference>
      </references>
    </references>
    <?line 582?>

<section numbered="false" anchor="acknowledgments">
      <name>Acknowledgments</name>
      <ul empty="true">
        <li>
          <t><strong>TODO:</strong> Acknowledgements.</t>
        </li>
      </ul>
    </section>
  </back>
  <!-- ##markdown-source:
H4sIAAAAAAAAA61c63Ibx5X+30/Ry/wIqYCQ5Ti1Dm1LpkU65lq3NeWoUltb
RgNoAG0OZpDpGdKwSql9jf23z7KPsk+y59a3AUDKVUnFJWIw3X369Ll859I4
PT1Vnesqe6aPzvW1WVh9vtlUbmY619T6qu5suzAzq7tGv7Tem6Wrl/qF2dpW
X9tZ37pue6TMdNraW5ji5YtrHK/P31wdKZjDLpt2e6ZdvWiUmjez2qxhpXlr
Ft3p1LS19afryp+azcZv69npJ0+U76dr5z0s3m038O7V5dtvVd2vp7Y9U3OY
8UzNmtrb2vf+THdtbxUs/EdlWmuAgETTXdPeLNum3yBZBym/sVt4cX6m9Kle
x7cqesvLW/idreenXXMK/8Cfs3a7QfaoW1v3QJDWDy+kNe/n6B3QhS/8BYfg
87VxFTwHPnztbLcYN+0SH5t2toLHq67b+LPHj/EtfORu7Ti89hgfPJ62zZ23
j2H8Yxy3dN2qn8LIqVv0LZ/j44zJ+E4FfPRdNnv27pgnGLsmH/X40JmNV926
OlLK9N2qaYmPfMj/1thKn1d3toYFNVB7pvX52vza0GfLu9YGX/i5+drQN+NZ
s04z/OBmK9PO9Te0aJzlufOzJpujraZfu83t2P+SDW1WptYvzWqbFk/P9HOQ
oL7q8BiubXvrZjx9IKrFN4nLXy/xUUnWS9N2Rr/s8Th+3d7ct7t1X63x7Xx7
qm7aNXD6FgRHoWKkT+r09FSbqe9aM+uUeruyB3VOb9qma2ZNBeJoppX12rAQ
6mahN7Cmm7mNqTsPiqtqUMPOwZnDS0DCGhSbRLhZtmazcjPtO/hyrPW7latA
1WHdTeuA8q1e9PWMLAFMi8rtaEIQHljU+ZX2cEJ2jqrS2o7n0bAlmoPoGWlk
Ooxk6kzlGz0zm65vgecoNLbugrWJ3IC/cRIeUuzGgALmr8H/72AHK1xQ8fsr
42GX9cK1a6DMLFtr17AIbO/tCsgHK9TjZz23C1cj43DhYObSX9Ot4pnXKCkb
4AuwogFb4WrYJEycmcnAJQ/KvNUerGi11a3tPTFT7WE28rNgDO43n3LTt5vG
Wz9mqVi7+byySv0OTXLbzHta72Nl5BjWOcGzm1vvljVQD+Z8yrsFsnA78Gej
MgL8CB6BYM9hQngZprp1cxttIvzBegMbNB0ddzZYtfbvvYMT1u/f/8sP3z7/
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
QBPmyZvsMtfC2PtodyOYPD2vt0yvNLaHYpoUafarpTR8ZfsbHoPkKu7jHsl2
Ez17Ss2FKDQL6khZbBYms+k45n8kXOKoCKwLeJgsfJNXjrLRbIH0kf5DYar/
AE/wmYRtWeAzmJRVbB/4LKAnuTrqqVe/OUY5mHoWE5eVmslxe6GAXQFiq1Oc
oUr992u++0UZKtdRbOP72K4Cyv9U/9z7Lh7IzqE+0/q1HCtYgFMx4+0kA2Sc
HIaZWOZieXfO7fpccx9s+Bn6hPOuQ0MCW8xzIRfcqUMGR26H+HQpJ2+fARGQ
rMooSwYx2KD3rgBf6WaKUYDnvj2GhrWapF6nUOWNNw+w02abazgBWM7M8/EL
8MFWpqLjNdSP72uVimDLcNad+uEosQSafvBmDRldYte+riZJAIWmKumOVdzm
WHaFkbS0t9wAX2GzArb/RQwmd9NACx8VrD7DyBwvHmTxUhZPxNgkAe1BMRKU
FIkdhYs1DcJeDpTm2OuBPX6WZBS2g+gVM3R8X+TRMNMXTv0s3r/Yc9ErsMZk
+XNMRleOcivcOXqLoZeP60aTu3dv48gUlKszfZHRvXf1/E5RymFmmwN60OXd
raStJAmt81n15ZhQ0Dtb8c0iuTElHVchPyiU3it7jq89tJTStvO8vRm17sKR
OcEokJXm7AAOzxD1Q7hXwC1SMmxlwCVLeK7LL7PpsvEHiRaITOl+7BqNyde8
EM8sidaYsSDoc1mrj/ebwIqHd7GppsELfjXPv01XqcrB5GAfOAiM4vYbL5gz
iQHjJYVO404aoeRo8CwpMqUWmI9YD71I0XuIxX8vfdrc45fBB75nZm7xajpC
DfTZ3AeZz6GSFeV+fqKoaUuTQBltmzU7euxCI6iJekG8VsRrQq6jpAqyzGUa
GLswB0iSicvoEVP8QC9nfotEvX8PLETO8WTgyjNbTbnr1OhJF5YiTwgO3cN/
ioBo7b3OTqS0OJ33vyuJUSqOP6DmUqN9iHHOqxl3SjZrK1zasVy5bHSY1li7
TqAn3mpDkwbgAI8Oq3+cLExp0nQKdLuQnknPfycd1dLGxaVBlmCwx+oh4qX2
FFMpIAR8pG9MtxpJfq0XRhVJD24trjGjKUUFsZ8PSIg0RT1oWjmO4sOa6ywv
5tFEe8y16KvY41fkx8D8V2VqMcnxCD0Tvuy5DoZogNYIm6XkaroZtacLCCjL
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
qvTqXAAA

-->

</rfc>
