Skip to content

Fix overflow when a parameter range ends at the numeric type's maximum - #905

Closed
santhreal wants to merge 1 commit into
sharkdp:masterfrom
santhreal:fix/parameter-scan-range-overflow
Closed

Fix overflow when a parameter range ends at the numeric type's maximum#905
santhreal wants to merge 1 commit into
sharkdp:masterfrom
santhreal:fix/parameter-scan-range-overflow

Conversation

@santhreal

Copy link
Copy Markdown

Problem

RangeStep::next yields the current value and then unconditionally computes state + step:

let return_val = self.state;
self.state += self.step;
Some(return_val)

When end is at (or within step of) the numeric type's maximum, that final increment overflows. RangeStep::new allows such a range through as long as it's small enough (the size check passes), e.g. --parameter-scan x 2147483645 2147483647:

  • debug builds: panics with attempt to add with overflow
  • release builds: state wraps around (to i32::MIN), so state > end stays false and the iterator runs far past end instead of terminating.

Fix

Track a done flag and only advance state while state + step stays within end; otherwise the current value is the last element. end - state is non-negative (state <= end is already checked) and step is positive (validated in new), so the guard itself can't overflow.

Tests

Adds test_range_reaching_type_max_terminates (a range ending at i32::MAX), which panics on the old code and passes now. Existing range_step tests are unchanged and still pass; cargo fmt --check is clean.

`RangeStep::next` yielded the final in-range value and then unconditionally
computed `state + step`. When `end` is at (or within `step` of) the numeric
type's maximum — e.g. `--parameter-scan x 2147483645 2147483647` — that final
increment overflows: it panics in debug builds and wraps around in release,
causing the iterator to run far past `end`.

Track a `done` flag and only advance `state` while `state + step` stays within
`end`, so the last element is yielded without an overflowing increment.
`end - state` is non-negative (state <= end) and `step` is positive (validated
in `new`), so the guard itself never overflows.

Add a regression test covering a range that ends at `i32::MAX`.
@santhreal santhreal closed this Jul 28, 2026
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.

1 participant