Skip to content

core: a checkpoint's pages out of the page cache once a loader is done with them - #766

Merged
ashhart merged 1 commit into
ashhart:mainfrom
Bizuayeu:pr/page-cache
Oct 16, 2026
Merged

ashhart merged 1 commit into
ashhart:mainfrom
Bizuayeu:pr/page-cache

Conversation

@Bizuayeu

@Bizuayeu Bizuayeu commented Oct 13, 2026 •

Copy link
Copy Markdown
Contributor

What this changes

A GLM-5.3-Flash rank reads about half of the 183 GB checkpoint through the mapping, and its column cuts touch whole
tensors. On GB10's unified memory the page cache holds memory the rank's device allocations need.
safetensors.File.release drops a file's pages from the mapping (madvise) and the page cache
(fadvise DONTNEED), and Checkpoint.release does every file; the mapping stays valid and refaults on a later
read. Linux only (a no-op elsewhere). The GLM-5.3-Flash CUDA family (#548) calls it after each layer it loads.

Receipt

  • Environment: TensorFold 1.0.9 (c36b536d) plus this change; one GB10 (DGX Spark, sm_121, CUDA 13.3).
  • Exactness, decode and prompt speed: not applicable (loading only).
  • Tests run:
    • zig build test: 662 passed, 5 skipped, 0 failed; the new "after release the mapping stays readable: a later
      read faults the same bytes back in" needs this change.
    • zig build test-cuda-host: 430 passed, 0 failed. zig fmt --check: clean. lean_check: 538, as main.
  • Not run, and why: macOS (the call is a no-op there). No test checks that the pages actually leave the page
    cache: mincore() could ask, but fadvise(DONTNEED) is advisory and skips dirty pages (a test's file has just
    been written), so the answer would depend on the kernel and on writeback, and the test would be flaky in CI. The
    test checks what must not break instead: the mapping stays valid and a later read faults the same bytes in.

Checklist

  • Every token still goes through the lane rounds. No serial path, and nothing that needs drafts off.
  • Drafted output equals "draft": false, a resumed prompt equals a fresh one, and concurrent equals solo.
  • No precision traded for speed. If the bits change, the description says which sums change and why.
  • Prompt processing is no slower than the last release.
  • The description says which platforms I ran, Metal M1 to M5 and CUDA, and which I could not.
  • New tests fail before the change, pass after it, and skip cleanly without their dependency.
  • Comments and docstrings are one line. No measurements or history in the source.
  • No personal data, machine names, internal hosts or local paths. No AI attribution lines.

…e with them

A GLM-5.3-Flash rank reads about half of the 183 GB checkpoint through the mapping, and its
column cuts touch whole tensors. On GB10's unified memory the page cache holds memory the
rank's device allocations need (our Python serving engine drops it with posix_fadvise for
the same reason). safetensors.File.release drops a file's pages from the mapping (madvise)
and the page cache (fadvise DONTNEED); Checkpoint.release does every file. The mapping stays
valid and refaults on a later read, which a test checks. The GLM-5.3-Flash CUDA family
(ashhart#548) calls it after each layer it loads.
@Bizuayeu

Copy link
Copy Markdown
Contributor Author

Rebased onto 1.0.9 (c36b536d), the commit's lines unchanged. Host tests 430/430, zig build test 662 passed, 5 skipped.

@ashhart
ashhart merged commit 3996ba4 into ashhart:main Oct 16, 2026
4 checks passed
ashhart added a commit that referenced this pull request Oct 16, 2026
ashhart added a commit that referenced this pull request Oct 16, 2026
The contributor's five GLM commits landed above, with our fixes after them; the head's first seven commits are the same changes as #757, #758, #766, #762, #764 and #763, which the candidate already has from their own heads. This keeps the PR's head in the history with no change to the tree.
@ashhart

ashhart commented Oct 16, 2026

Copy link
Copy Markdown
Owner

Thank you, @Bizuayeu. Dropping a checkpoint's pages once a loader is done with them matters on a GB10's unified memory, and keeping the mapping valid, so a later read faults the bytes back, is the right shape.

It ships in TensorFold 1.0.12 under your name (646119d2f), and our 55a7e9373 is a fix you will want: Zig's File.MemoryMap falls back to a heap copy when mmap fails or mapping is off, and madvise(MADV_DONTNEED) on that copy would zero every tensor. release now advises the mapping only when it is one; fadvise still drops the file's pages. Its test fails without the guard and passes with it. Your head is merged after them with no change to the tree (3996ba463), so this pull request shows as merged.

On a GB10, a cold read of Nemotron 3.5 Lightning NVFP4's 52 files (21.56 GB) left 20.1 GiB cached; Checkpoint.release dropped all of it in 0.26 s, and a second read took 14.6 s. Nemotron's own loader uses direct I/O, so its load time and peak are unchanged. The saving shows for a loader that reads the mapping, as your GLM-5.3-Flash family does (#804).

Posted by Ash's AI Assistant Synthena

BlivionIaG pushed a commit to BlivionIaG/TensorFold that referenced this pull request Oct 20, 2026
BlivionIaG pushed a commit to BlivionIaG/TensorFold that referenced this pull request Oct 20, 2026
The contributor's commit landed above with the same code; this keeps the PR's head in the history with no change to the tree.
BlivionIaG pushed a commit to BlivionIaG/TensorFold that referenced this pull request Oct 20, 2026
BlivionIaG pushed a commit to BlivionIaG/TensorFold that referenced this pull request Oct 20, 2026
…date

The contributor's five GLM commits landed above, with our fixes after them; the head's first seven commits are the same changes as ashhart#757, ashhart#758, ashhart#766, ashhart#762, ashhart#764 and ashhart#763, which the candidate already has from their own heads. This keeps the PR's head in the history with no change to the tree.
@Bizuayeu
Bizuayeu deleted the pr/page-cache branch October 25, 2026 07:27
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants