fix(cli): overflow-safe ZIP bounds check; env-bash shebangs#812
Open
DeusData wants to merge 3 commits into
Open
fix(cli): overflow-safe ZIP bounds check; env-bash shebangs#812DeusData wants to merge 3 commits into
DeusData wants to merge 3 commits into
Conversation
The truncation check `header_end + (int)comp_size > data_len` was bypassable for comp_size >= 2^31: the int cast turns the size negative, the sum drops below data_len, and the entry is accepted -- authorizing inflate to read up to ~4GB past the downloaded archive buffer during self-update ZIP extraction. Replace it with `header_end > data_len || comp_size > (uint32_t)(data_len - header_end)`, which is overflow-safe and strictly tighter. Regression guard cli_extract_binary_from_zip_rejects_truncated_deflate_size_over_int_max builds a 52-byte archive whose entry claims comp_size=0xFFFF0000 with a self-terminating DEFLATE stream: the old check admits it and extraction returns non-NULL (verified red pre-fix); the new check rejects it. Secondary cppcheck cleanups from the same review: - cli.c: extract zip_read_u16le/zip_read_u32le little-endian helpers (behavior-identical) and widen zip_extract_entry sizes to size_t with an explicit UINT_MAX guard before the zlib uInt narrowing. - cypher.c: drop unreachable IS NULL / IS NOT NULL null guards in eval_condition (resolve_condition_value result is checked earlier). Distilled from PR #784. Co-authored-by: SS-42 <noreply@incogni.to> Signed-off-by: Martin Vogel <martin.vogel.tech@gmail.com>
On NixOS (and other non-FHS systems) /bin/bash does not exist, so scripts with an absolute shebang fail to run. Switch the remaining holdouts to /usr/bin/env bash: eleven scripts/*.sh, test-infrastructure/run.sh, and the three Claude Code hook scripts emitted by src/cli/cli.c (gate, session reminder, subagent reminder). Distilled from PR #674, with parser-test coverage preserved: the infra_parse_shell* fixtures in tests/test_pipeline.c intentionally keep #!/bin/bash so absolute-path shebang extraction stays covered, and tests/repro fixtures are untouched. Also replace the GitHub-PAT-shaped fixture string flagged in the #674 thread with an obviously fake placeholder (ghp_FAKE...) that still matches the ghp_ + 36-alnum secret detector. Co-authored-by: Sandro Jäckel <sandro.jaeckel@gmail.com> Signed-off-by: Martin Vogel <martin.vogel.tech@gmail.com>
Signed-off-by: Martin Vogel <martin.vogel.tech@gmail.com>
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.
distill: overflow-safe ZIP bounds check (#784) + env-bash shebangs (#674)
Two independent review distills sharing
src/cli/cli.c, kept as two separate commits on one branch to avoid conflicts.Commit 1 —
7b93210fix(cli): overflow-safe ZIP entry bounds check in self-update extractionDistilled from #784 (thanks @SS-42, co-authored). Refs #784-review.
The real fix (title, not buried): the self-update ZIP truncation check
is bypassable for
comp_size >= 2^31: theintcast turns the size negative, the sum drops belowdata_len, and the entry is accepted — authorizinginflateto read up to ~4 GB past the downloaded archive buffer (strm.avail_in = comp_size). Replaced with the overflow-safe, strictly tighterRegression guard (red-first, verified via temporary revert of the check):
cli_extract_binary_from_zip_rejects_truncated_deflate_size_over_int_maxbuilds a 52-byte archive whose only entry claimscomp_size = 0xFFFF0000(DEFLATE,uncomp_size = 1, self-terminating 3-byte stream).avail_in = 0xFFFF0000(licensed to read ~4 GB past the buffer); the fixture's DEFLATE stream self-terminates, so extraction succeeds and returns non-NULL — a deterministic assertion failure rather than an ASan-dependent crash, in both directions: the fixed check rejects the entry (NULL), the old one accepts it (non-NULL).cli+cyphersuites 258 passed, 0 failed.Secondary cppcheck cleanups from the same review (audited behavior-neutral):
zip_read_u16le/zip_read_u32lelittle-endian helpers replacing the inline shift pyramids (behavior-identical).zip_extract_entrysizes widened tosize_twith an explicitUINT_MAXguard before the zlibuIntnarrowing.cypher.c eval_condition: removed genuinely unreachableIS NULL/IS NOT NULLnull guards (resolve_condition_valueresult is early-returned on NULL just above);cypher_*_is_nulltests unchanged and green.Commit 2 —
50392a4fix(scripts): use /usr/bin/env bash shebangs (NixOS has no /bin/bash)Distilled fresh from #674 (thanks @SuperSandro2000, co-authored). Refs #674-review.
#!/bin/bash→#!/usr/bin/env bashin the elevenscripts/*.shholdouts,test-infrastructure/run.sh, and the three Claude Code hook scripts emitted bysrc/cli/cli.c(gate, session reminder, and the subagent reminder added since Use /usr/bin/env bash for widely compatible shebang #674 was opened).infra_parse_shell*fixtures intests/test_pipeline.cintentionally keep#!/bin/bash, so absolute-path shebang extraction (r.shebang == "/bin/bash") stays covered.tests/reprofixtures untouched. No test asserts the emitted hook scripts' shebang, so no assertion updates were required.ghp_FAKEFAKEFAKEFAKEFAKEFAKEFAKEFAKEFAKE— obviously fake, stillghp_+ 36 alnum so the secret detector (pass_infrascan.c) keeps firing;envscan_secret_value_exclusiongreen.bash -nclean on all 12 changed scripts.Verification (after both commits)
make -f Makefile.cbm cbm—-Werrorclean.make -f Makefile.cbm lint-ci— cppcheck, clang-format, NOLINT check all green.test-runner pipeline— 209 passed, 0 failed.test-runner cli cypher— 258 passed, 0 failed.Refs #784-review, refs #674-review.