test: cover fp8 block-scale dequantization - #40
Conversation
|
Reviewed. The test is good and I checked it by trying to break it rather than
Two things before this comes out of draft. 1. It never runs, on any machine that tests this project
It skips in CI too, and that is the part that decides it: the Linux Confirmed the fix, with the if ! command -v uv >/dev/null 2>&1; then
sk "fp8 block-scale mapping" "uv not installed"
else
out=$(run_uv run --quiet --with torch --no-project \
python tests/test_fp8_blocks.py 2>&1); rc=$?
2. One reader's guard is uncovered
Smaller
Nothing here is structural, and the mutation results say the core is right. |
Two things on top of tomatotomata's checks, which are unchanged and were right: the mutants I planted in unblock_scale — returning q untouched, transposing the block dims, dropping the [:M, :N] crop, removing the shape guard — were all caught, and expected_dequant being an independent index-array implementation rather than a second call to the code under test is what gives it that. It never ran. run.sh invoked it as bare `python3`, and torch is not a system package on the machines that test this: CLAUDE.md says it is never a repo dependency and every other torch checker goes through uv. So the whole thing reported "torch not installed" and skipped everywhere, CI included — where the Linux job is the one that installs uv, which is to say the one place it does get to run. Through run_uv now, with the guard on uv rather than python3, since without uv run_uv exits 127 and the catch-all would report FAIL where a SKIP is meant. 56 passed / 0 failed / 2 skipped becomes 57 / 0 / 2. And the missing-companion check exercised ST only. Deleting ShardReader's own `raise` in convert.py, so it returns the tensor unscaled instead, kept the suite green — a silent wrong answer in the reader sqliteai#26's description called out as "a second reader and was easy to miss". Both readers now, and that mutant is killed. The same mutation against ST survives, and should: without its guard, raw() still raises KeyError naming weight_scale_inv, so the contract the test asserts — refuses, and says which tensor — holds either way. That guard buys a better message, not a different decision, and asserting its exact prose would test the wording rather than the behaviour. Also wrote down the case nothing here can catch, which is the reason the tile size is read from config rather than inferred: 300 rows against 3 scale rows admits both 128 and 100, both pass every shape check, and the wrong one applies each scale to the wrong rows. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
|
Both points fixed and pushed to this branch — 1. It now runs. Through That line did not exist before. Under bare 2. Both readers. One thing I checked and deliberately did not change: the same mutation I also wrote down the case nothing here can catch, since #26 described it and CI is 9/9 on the branch. I approved the workflow run — it needed a maintainer Over to you to take it out of draft; I did not want to flip that on your For the record, your checks were the right ones and they were right on the |
|
Merged, and #39 closed with it. CI 9/9 on the merge commit, and the check runs rather than skips on the Linux job — which was the whole difference between this being coverage and being a file. Thanks. Filed in the morning, correct checks by the afternoon, and the mutation results were the part that made it easy to take: four planted bugs in |
Resolves #39
What changed
tests/test_fp8_blocks.pywith aligned tiles, a partial final row and column, missing scale companions, and gross shape mismatch cases.mxfp4.STandconvert.ShardReaderagree when both read the configured block size.tests/run.sh, with an explicit SKIP when torch is unavailable.Validation
python tests/test_fp8_blocks.pypasses all 5 checks.python tests/test_convert_resume.pypasses.python tests/test_convert_chat.pypasses.git diff --checkpasses.The test stays synthetic and does not require model weights or a multi-hour conversion.