Draft: draft-ietf-mls-protocol

Commentary: I would like to remove the UserAdd functionality that 's in the current document , and the GroupInitKey construct that supports it . We will need to support a flow where a device can join without an explicit invite . But that mechanism will also have to be limited , since it leaks information out of the group . It will be cleaner to get a GroupAdd - only system working first , then figure out how to add this back in . 
 I think the ( temporary ) simplification makes sense . LGTM except for the missing definitions mentioned in - line . Small claritifcation questions .. otherwise LGTM
Paragraph (version A):
A short-lived Diffie-Hellman key pair used to introduce a new
member to a group.  Initialization keys can be published for both
individual participants (UserInitKey) and groups (GroupInitKey).
Paragraph (version B):
A short-lived Diffie-Hellman key pair used to introduce a new
member to a group.  Initialization keys are published for
individual participants (UserInitKey).
Paragraph (version A):
When a participant A wants to establish a group with B and C, it
first downloads InitKeys for B and C.  It then initializes a group
state containing only itself and uses the InitKeys to compute
GroupAdd messages to add B and C, in a sequence chosen by A.  These
messages are broadcasted to the Group, and processed in sequence by B
and C.  Messages received before a participant has joined the group
are ignored.  Only after A has received its GroupAdd messages back
from the server does it update its state to reflect their addition.
Paragraph (version A):
Subsequent additions of group members proceed in the same way.  Any
member of the group can download an InitKey for a new participant and
broadcast a GroupAdd which the current group can use to update their
state and the new participant can use to initialize its state.
Paragraph (version A):
It is sometimes necessary for a new participant to join without an
explicit invitation from a current member.  For example, if a user
that is authorized to be in the group logs in on a new device, that
device will need to join the group as a new participant, but will not
have been invited.
Paragraph (version A):
In these "user-initiated join" cases, the "InitKey + Add message"
flow is reversed.  We assume that at some previous point, a group
member has published a GroupInitKey reflecting the current state of
the group (A, B, C).  The new participant Z downloads that
GroupInitKey from the directory, generates a UserAdd message, and
broadcasts it to the group.  Once current members process this
message, they will have a shared state that also includes Z.
Paragraph (version B):
When a participant A wants to establish a group with B and C, it
first downloads InitKeys for B and C.  It then initializes a group
state containing only itself and uses the InitKeys to compute Add
messages to add B and C, in a sequence chosen by A.  These messages
are broadcasted to the Group, and processed in sequence by B and C.
Messages received before a participant has joined the group are
ignored.  Only after A has received its Add messages back from the
server does it update its state to reflect their addition.
Paragraph (version B):
Subsequent additions of group members proceed in the same way.  Any
member of the group can download an InitKey for a new participant and
broadcast an Add which the current group can use to update their
state and the new participant can use to initialize its state.
Paragraph (version A):
For UserAdd or GroupAdd, the new user does not know the prior epoch
init secret.  Instead, entropy from the prior epoch is added via the
update secret, and an all-zero vector with the same length as a hash
output is used in the place of the init secret.
Paragraph (version B):
For Add, the new user does not know the prior epoch init secret.
Instead, entropy from the prior epoch is added via the update secret,
and an all-zero vector with the same length as a hash output is used
in the place of the init secret.
Paragraph (version A):
In order to facilitate asynchronous addition of participants to a
group, it is possible to pre-publish initialization keys that provide
some public information about a user or group.  UserInitKey messages
provide information about a potential group member, that a group
member can use to add this user to a group asynchronously.
GroupInitKey messages provide information about a group that a new
user can use to join the group without any of the existing members of
the group being online.
Paragraph (version B):
In order to facilitate asynchronous addition of participants to a
group, it is possible to pre-publish initialization keys that provide
some public information about a user.  UserInitKey messages provide
information about a potential group member, that a group member can
use to add this user to a group asynchronously.
Paragraph (version A):
A GroupInitKey object specifies the aspects of a group's state that a
new member needs to initialize its state (together with an identity
key and a fresh leaf key pair).
Paragraph (version A):
GroupInitKey messages are not themselves signed.  A GroupInitKey
should not be published "bare"; instead, it should be published by
constructing a handshake message with type "none", which will include
a signature by a member of the group and a proof of membership in the
group.
Paragraph (version A):
A signature by a member of the group, together with a Merkle
inclusion proof that demonstrates that the signer is a legitimate
member of the group.
Paragraph (version B):
An MLS handshake message encapsulates a specific message that
accomplishes a change to the group state.  It also includes a
signature by a member of the group, together with a Merkle inclusion
proof that demonstrates that the signer is a legitimate member of the
group.
Paragraph (version A):
A GroupAdd message is sent by a group member to add a new participant
to the group.
Paragraph (version B):
An Add message is sent by a group member to add a new participant to
the group.
Paragraph (version A):
The public key of the ephemeral key pair is placed in the "ephemeral"
field of the GroupAdd message.  The computed direct path is placed in
the "add_path" field.
Paragraph (version B):
The public key of the ephemeral key pair is placed in the "ephemeral"
field of the Add message.  The computed direct path is placed in the
"add_path" field.  The frontiers of the identity and ratchet trees
before the addition of the new member are placed in the
"identity_frontier" and "ratchet_frontier".
Paragraph (version A):
A UserAdd message is sent by a new group participant to add themself
to the group, based on having already had access to a GroupInitKey
for the group.
Paragraph (version A):
Compute the direct path from the new participant's leaf in the new
ratchet tree (the add_path).
Paragraph (version A):
The update secret resulting from this change is the output of a DH
computation between the private key for the root of the ratchet tree
and the add public key from the previous epoch.