Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Extensions #473

Closed
raphaelrobert opened this issue May 20, 2021 · 2 comments · Fixed by #479
Closed

Extensions #473

raphaelrobert opened this issue May 20, 2021 · 2 comments · Fixed by #479

Comments

@raphaelrobert
Copy link
Member

After a thorough review of the current MLS extension system, there are a few questions and we also have a few suggestions for changes.

How we interpret the spec currently:

  • The total set of extensions is fixed and cannot be changed during the lifetime of a group.
  • The set of extensions that is associated with a group is decided by the group creator.
  • All extension types from the set have to be supported by all clients and must therefore be advertised in their capabilities extension.
  • The implementation needs to validate the support in 4 instances: When creating a new group, when joining a group, when creating an add proposal, when parsing someone else's add proposal as part of a Commit.
  • Key package extensions are simple and well-understood, in that they never leave the KeyPackage and there is group consensus through the tree hash.
  • The other kind of extension seems to be called a Group Info Extension (GIE).
  • GIEs can come in two flavours: a) they must be included in the group context, b) they must not be included in the group context.
  • The ratchet tree extensions is an example of type b).
  • GIEs of type a) are essentially just passed from the Adder to the New Joiner, using Welcome messages as an E2EE pipe.

Open questions:

  • The spec does not explicitly introduce the notion of a GIE, it is only mentioned in 16.2. Should the spec be more explicit here?
  • Should the flavour of a GIE (as described above) be reflected in the Extension struct in the spec? E.g. a message type that indicates whether a GIE should be included in the GroupContext (see proposal below).
  • Can the content of a GIE be dynamic (i.e. it can change during the lifetime of a group)? The ratchet tree extension seems to validate that assumption, it is a bit unclear if this is true for all kinds of GIE. We should be more explicit in the spec.
  • If the content of GIEs is indeed dynamic, should those GIEs always be excluded from the GroupContext? Or optionally? If they are to be included in the GroupContext, how do clients agree on the changes? (See proposal below)

We need more guidance regarding extensions in order to keep implementations aligned and capable of interop.

Concrete proposed improvements:

A first suggestion would be to allow for the creation of extensions that have dynamic content. This would allow them to use MLS to agree on arbitrary data.

The requirement would be to make GIEs with dynamic content more robust by introducing a new proposal type to update the content of extensions:

struct {
  Extension extension;
} ExtensionUpdate;

Another improvement to the current extension system would be to be more clear about the kinds of extensions by introducing a dedicated MessageType field for every extension:

enum {
    reserved(0),
    KeyPackage(1),
    GroupContext(2), // GIEs that are to be included in the group context
    GroupInfo(3), // GIEs that should not be included in the group context, like the ratchet tree extension
    (255)
} MessageType;

struct {
    ExtensionId extension_id;
    MessageType message_type;
    opaque extension_data<0..2^16-1>;
} Extension;

This would allow generic GroupInfo extensions, which in turn allow committers of Add proposals to communicate arbitrary data to new group members in a robust fashion.

@bifurcation
Copy link
Collaborator

Thanks for the analysis here. To your point about “dynamic GIEs” — My initial concept here was that the GIEs included in the GroupContext would be fixed for all time. The ratchet tree extension would not be included in the GroupContext; as you say, it just uses the Welcome for E2E tunneling.

Boiling this down a bit, it seems like there are a few problems to solve here:

  • Clarifying which extensions in the GroupInfo go into the GroupContext and which are just used for tunneling E2E
  • Allowing for updates to the group’s extensions

For the former, there's a pretty simple solution available: Just have separate fields in the GroupContext for permanent and ephemeral extensions.

struct {
  // ...
  Extension group_context_extensions<0..2^32-1>;
  Extension other_extensions<0..2^32-1>;
  // ...
} GroupInfo;

The joiner processing would then place the group_context_extensions into the MLS state / GroupContext, and use/discard the other_extensions. We could also then update the IANA considerations to reflect these additional categories for where an extension can appear.

For the latter problem, I think your ExtensionUpdate is about the right approach. It might be simpler just to have the update proposal provide wholesale replacement to the extensions, so that we don't have to design a merge algorithm. I'm not totally sure this is worth doing right now, since it seems easy to do as an extension. But especially if we keep it simple, I'm not strongly opposed.

@bifurcation
Copy link
Collaborator

@kkohbrok @raphaelrobert and I discussed real-time, propose to do the following:

  1. Split out the GroupContext extensions as above
  2. Define a new proposal type to update the group's extensions:
struct {
    Extension new_extensions<0..2^32-1>;
} ExtensionUpdate;

// Processing:
// group_context.extensions = ext_update.new_extensions;

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Development

Successfully merging a pull request may close this issue.

2 participants