Open bifurcation opened 3 months ago
FWIW, I have gotten the following flavor of AnnotatedCommit working in MLSpp:
struct AnnotatedCommit {
MLSMessage commit_message;
bytes tree_hash_after;
TreeSlice sender_membership_proof_before;
TreeSlice sender_membership_proof_after;
TreeSlice receiver_membership_proof_after;
optional<uint32_t> resolution_index;
};
Working in the sense of:
The DS logic to figure out which node in a Commit belongs to a given receiver is slightly non-trivial, but not terrible. It mostly worked on the first try, except for one bug that didn't show up until pretty far into the random-commits test vector.
All in all, this seems like a worthwhile thing to write up, at least as a transitional measure from a domain where clients don't produce GroupInfo already. (Note that it's possible to support LightCommit and AnnotatedCommit at the same time; the state in a light client is the same.) I'll work on some text.
The above structure might not be minimal. Or might not be secure! (But it seems OK?) Suggestions for improvement welcome. I already stripped out the extensions
and psks
fields, because you can get those from proposals.
The current LightCommit struct has some drawbacks. It seems simple on the surface because it's just a GroupInfo, but:
tree_info
validation / production logic than WelcomeIt seems to me that a better approach would be something like the following:
This re-uses the GroupInfo with
tree_info
scheme (including the current/prior epoch weirdness), but moves the other information outside the signed envelope so that the DS can add it. The information is ultimately confirmed by theconfirmation_tag
in the GroupInfo, so it should be safe for the DS to add.Option B is still a little unfortunate because it requires a committer to send both a GroupInfo and a Commit. This could be challenging for incremental deployment in a setting where committers aren't already sending GroupInfo alongside Commit, since it would require a behavior change at the committer as well as the light client. Another option that avoids that drawback would be something like:
This can be generated by the DS based only on a Commit, and it avoids the
tree_info
old/new epoch weirdness. It also gets anextensions
field in case of GroupContextExtensions proposals. (Theconfirmed_transcript_hash
can be computed as usual.) The light client locates its HPKECiphertext in the UpdatePath by finding the first / lowest-level overlap with the direct path in its membership proof, then using theresolution_index
to select from the individual encryptions. Obviously this is no longer really "light", though, because it carries the whole Commit, which can get heavy.It seems like either B or C would be an update for the current state. It might be worth defining both, since they can cleanly coexist, and address different use cases.