fix: select state resolution algorithm by room version#231
Merged
Conversation
state_res::resolve hardcoded the v12 variant (state-res v2.1) for every room. vela supports v6-v11 rooms over federation, so a fork in one of those rooms was resolved with the wrong algorithm and could settle on a different state than Synapse/Dendrite — permanent state divergence that doesn't self-heal. Thread the room version into resolve and branch where v12 differs from classic state-res v2: the iterative auth checks start from the unconflicted state map (v2) versus empty (v12), and the conflicted state subgraph is folded into the full conflicted set (v12 only). Gate the create-event seed to v12, where the room_id is the create hash; pre-v12 gets create from auth_events (v6-v10) or the unconflicted map (v11), so a v11 fork no longer loses its create event and drops all conflicted state. Both call sites look up the room's version and warn if it can't be resolved rather than silently defaulting a pre-v12 fork to v2.1.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
state_res::resolvehardcoded the room-version-12 algorithm (state-res v2.1) for every room. vela deliberately supports v6–v11 rooms over federation, so a fork in one of those rooms was resolved with the wrong algorithm and could settle on a different state than Synapse/Dendrite — permanent, non-self-healing state divergence (disagreement on membership/power, undecryptable timelines).Thread the room version into
resolveand branch at the two points where v12 differs from classic state-res v2:Everything else (both ordering algorithms, the auth rules invoked, the final unconflicted overlay) is identical across versions; the per-version auth-rule differences are already handled inside
check_auth.Also gate the create-event seed to v12, where
room_idis the create event's hash. Pre-v12 gets the create event fromauth_events(v6–v10) or from the unconflicted map (v11). This fixes a latent bug: before, v11 forks used empty-init, create isn't in a v11 event'sauth_events, and the seed can't derive create from an opaque v11room_id— so the create was absent during resolution and every conflicted event was dropped.Both call sites (
state_before_event,compute_state_at_event) look up the room version andwarn!if it can't be resolved rather than silently defaulting a pre-v12 fork to v2.1.Tests: the
uses_state_res_v21version boundary; a fork where a subgraph-only node resolves under v12 but not v6; and a v11-shaped fork whose topics resolve under v2 (unconflicted-init supplies create) but are dropped under v2.1 (empty-init) — pinning both halves of the branch.