Repository navigation
Conversation
Quest-Claim: e5f93fd162d41627
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…om above Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Collaborator
Author
|
Closing without merging. Maintainer decision, 2026-11-07 (/quest-spawn): copies of one identity disagree only when the publisher broke the identity rule, which hurts only its own broadcast, so moq-net spends no cycles detecting it. moq-dev/moq#8242 adds that rule to AGENTS.md and deletes (Written by Claude Opus 5.5) |
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.
Closes the quest
quest/m1/copy-identity.md.Problem
Two copies of the same broadcast+track+group (another route, a FETCH answer, a re-offer, a mid-frame recovery) could disagree on what a reader sees while both stayed accepted. Shared content rows (
rs/moq-net/src/model/group/content.rs) and the mid-frame recovery (frame.rs) compared only size,inflated, and overlapping bytes. Nothing compared a frame's timestamp, its IETF object properties, or where the group ends, so a copy with one more frame could raiselargestafterfinish_largestdeclared the group settled. A resumed group read could also end cleanly on a replacement that finished before frames the earlier copy had already delivered.Approach
Rust (
moq-net):RandomState) of its object properties. A copy that disagrees on either getsProtocolViolationand fails, as a byte conflict already did.Contentrecords the group's end:fin(set by a copy's own finish) andreached(one past the furthest frame position any copy opened). A frame at or pastfinfails its copy. So does a finish short ofreachedor at a differentfin. Positions are the frame's key (Object ID, which a frame without one shares with its ordinal). A copy whose IDs left its ordinals (sparse) declares no end, and neither does a copy a transport bound cut short (range_end). An empty copy that starts past frame 0 only bounds the end from above: it says nothing lies past its start.activate_contentcarries the end of a copy that finished before any other copy shared its content.track::Info::unchecked, lite-05/06), via a newGroupState::unchecked(struct size unchanged at 384 bytes).ProtocolViolationwhen the replacement finishes before frames an earlier copy held. It counts only frames a copy actually committed, so a reader whose range starts past the group's end still ends cleanly.JS (
js/net): JS has no shared content rows; copies meet only at recovery.group.tsnow refuses a replacement that finishes before frames an earlier copy held, matching the Rust recovery check.The end is kept as one
finvalue onContent, which leaves room for the plannedquest/m1/explicit-state/track-end.mdoutcome enum to replace it.Impact
ProtocolViolation. Before, it was accepted and readers of each copy saw different content under one identity.model::tracktest fixtures wrote contradictory copies (for example, a whole-group fill finishing at 1 frame while the live copy held frame 3). They now write consistent groups. None of them asserted the contradiction.Choices made without asking
Arc<Fields>in the row would compare exactly, but it pins one copy's metadata unbilled after that copy goes away.Frame(i)orObject(id), so a lite copy without records and an IETF copy never share a row. That limit already existed and this PR does not change it.poll_resumedonOk(None)and JSreadFrame). A consumer'sclosed/donestill reports the clean end until a read is attempted.Validation
just cion 909653b: pass.cargo nextest run -p moq-net --all-features --no-fail-fast: 3700 passed.copies_disagreeing_on_a_timestamp_fail,copies_disagreeing_on_object_properties_fail,a_copy_past_the_declared_end_fails,a_copy_finishing_short_fails(group.rs);a_half_read_frame_refuses_a_replacement_with_another_timestamp,a_resumed_group_refuses_a_replacement_ending_before_what_was_read(resume.rs). With every new check disabled at once, all six fail.group.test.ts: a short replacement is refused (fails when the check is removed), and a reader of a copy that held nothing takes the replacement's end (fails when the check counts the reader's start instead of held frames).bench/lock.shandquest gate):session_delivery_group_cost/session_delivery_datagramwithSESSION_ALLOCS=1, pinned to one CPU, two base/head pairs: user instructions per viewer-group or datagram are at or below base in 38 of 40 cells (-0.05% to -1.3%). The other two are +0.12% and +0.98%, inside the base-to-base spread of those cells.group_write_frames,group_roundtrip,group_relay_objects,canonical_storage, paired in both orders: wall-clock deltas swing ±10-20% with load and flip sign between orderings. The write path is unchanged when no content is shared, and the instruction counts above show no added work.Caused by
inflatedFollow-ups
content_for_copyactivates content on only the first existing copy of a sequence, so a third copy that already held frames is never compared. Recommend planning a quest if a route can hold two pre-existing copies of one group; otherwise drop it.Models
Size: M
Implementer: Claude Code, claude-opus-5-5, high effort
(Written by Claude Opus 5.5 with high)
Review
Rewritten by
quest reviewafter each round.01a1b8e6-49a9-7af3-b440-aa8db245748d, round 1The head needs rework to preserve copy end bounds and propagate recovered-end violations to terminal observers.rs/moq-net/src/model/group/content.rs:214:Retain the upper bound from an empty late-starting copyjs/net/src/group.ts:1608:Validate recovered ends before settling the closed handlers/moq-net/src/model/group.rs:3763:Apply end-consistency validation to finished()