Repository navigation
DDIR: restrict on chunks, and the reduce reads each retire's history through it once - #1072
Open
frankmcsherry wants to merge 2 commits into
Open
frankmcsherry wants to merge 2 commits into
frankmcsherry wants to merge 2 commits into
Conversation
…d their keys Each `CorgiChunk` now keeps the first and last identifiers of its rows (the integer key, or the hash lane of a compound key) beside its columns. Readers use them through three methods: `find` searches only the needles inside a chunk's bounds, `rows_before` answers a seek without a binary search when the target is past either end, and `may_hold` rules out a chunk whose bounds miss a range. The reduce's key search, the join's seeks, block ends and probes, and the half join's chunk filter go through them; their results are unchanged. The bounds are what a page index and Bloom filters would sit beside, and they stay readable once a chunk's key column is not. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01H6wB4H99TLw4tqu4x48pXL
…y through it once `CorgiChunk::restrict(needles)` returns an in-core chunk holding every row whose identifier is among the sorted, distinct needles, and possibly other rows. While chunks are uncompressed and in memory it returns the chunk itself, an `Rc` clone, so behavior is unchanged. It is the one call readers need once a chunk is a list of pages: a reader that touches a few rows of a large chunk gets back only the pages its keys can be in, and keeps searching within them. The reduce backend calls it once per retire, at the first window: each prior input chunk and each output chunk is restricted to the retire's keys, and the novel chunks, which define the keys, stay as they are. The retire keeps these chunk lists, and later windows read them instead of rebuilding the lists from the instance, so positions into them (the input matches, the value pools, the key columns, the output keys) mean the same rows in every window. `finish` releases the chunks, the pools and the key columns, which used to stay until the next retire replaced them. The join and half join are left for after TimelyDataflow#1069 and the half-join rewrite land. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01H6wB4H99TLw4tqu4x48pXL
This branch has not been deployed
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.
Stacked on #1071: the first commit here is #1071's, and only the second is new, since upstream can't use the fork's
ddir-chunk-boundsbranch as a base.CorgiChunk::restrict(needles)returns an in-core chunk holding every row whose identifier is among a sorted, distinct set of needles, and possibly other rows.Today it returns the chunk itself, an
Rcclone, so behavior is unchanged.The reduce now restricts its prior input and its output once per retire, reads those chunks in every window, and releases them at
finish.This is the one call readers need once a chunk is a list of independently decompressed pages: a reader that touches a few rows of a large chunk will bring in only the pages its keys can be in, as an ordinary in-core chunk, and keep searching within it as it does today.
What changes
chunk.rs:CorgiChunk::restrict(&self, needles: &[i64]) -> CorgiChunk, documented with that contract. It debug-asserts that the needles are sorted and distinct, and returnsself.clone().reduce.rs:Retirekeeps the chunk lists:in_chunks(prior then novel),prior, andout_chunks.next_windowno longer rebuilds its lists from the instance on every call; the key search, the value pools, the key columns, the output matches, the colliding-key checks andfinishall read these.finishreleases the retire's chunks, both pools, the output keys and the key columns. Before, they stayed until the next retire replaced them.search,presentandsplit_real_keystake&[CorgiChunk]rather than&[&CorgiChunk], as the retire owns its chunks.half_join/backend.rs, so wiringrestrictinto them now would conflict; they come after those land.Why positions stay consistent
Every position into a chunk indexes
Retire's lists: the input matches found at the first window, the pools'(column, row)references, the output keys, and the key rowsemitrecords forfinish.The lists are built once, at the first window, and nothing replaces them until
finish.Once
restrictbuilds new chunks, calling it in each window could give each window different chunks, and an output id recorded in one window would name a row of the wrong chunk in the next; building the lists once rules that out.Measurements
One run each, mini-01, one worker, diagnostics off, against
16bf76f9(#1071) built the same way.Instructions and CPU are within noise.
The LDBC pair ran three times, as another job shared the machine during the first two base runs; the table has the third pair, on an idle machine.
LDBC's peak footprint was lower in all three pairs, by 41 to 152 MiB; releasing the pools at
finishis the only change that could lower it, but I have not measured what the difference consists of.SCC's and reachability's peak footprints moved by under 1.2%, in opposite directions.
Answer and physical digests are identical on all 808 LDBC ticks in every run, and SCC's and reachability's initial and final peeks are identical.
Tests
windows_partition_a_retirenow also checks thatfinishleaves the backend holding no chunks and no columns.cargo test -p differential-dataflow -p differential-dogs3 -p interactive: 459 passed, 0 failed, 22 ignored; no warnings.Implemented and measured by a Claude Opus subagent; reviewed and opened by Claude Code.
🤖 Generated with Claude Code
https://claude.ai/code/session_01H6wB4H99TLw4tqu4x48pXL