Repository navigation
Strategy::Frag panics with a subtract overflow on the i16 engine #88
Copy link
Copy link
Closed
Description
Summary
The last of the eight overlays in this program panics. Every coordinate fits i16.
Steps to reproduce
use i_float::int::point::IntPoint;
use i_overlay::core::fill_rule::FillRule;
use i_overlay::core::overlay::Overlay;
use i_overlay::core::overlay_rule::OverlayRule;
use i_overlay::core::solver::{Solver, Strategy};
const PTS: [(i32, i32); 3] = [(0, 0), (0, 9854), (129, -23169)];
fn main() {
let c32: Vec<Vec<IntPoint<i32>>> =
vec![PTS.iter().map(|&(x, y)| IntPoint::new(x, y)).collect()];
let c16: Vec<Vec<IntPoint<i16>>> =
vec![PTS.iter().map(|&(x, y)| IntPoint::new(x as i16, y as i16)).collect()];
for (name, strategy) in [
("List", Strategy::List),
("Tree", Strategy::Tree),
("Auto", Strategy::Auto),
("Frag", Strategy::Frag),
] {
let solver = Solver { strategy, ..Default::default() };
let r = Overlay::<i32>::with_contours_custom(&c32, &[], Default::default(), solver)
.overlay(OverlayRule::Subject, FillRule::EvenOdd);
let pts: Vec<Vec<(i32, i32)>> =
r.iter().flatten().map(|c| c.iter().map(|p| (p.x, p.y)).collect()).collect();
println!("i32 engine, {}: {:?}", name, pts);
let r = Overlay::<i16>::with_contours_custom(&c16, &[], Default::default(), solver)
.overlay(OverlayRule::Subject, FillRule::EvenOdd);
let pts: Vec<Vec<(i16, i16)>> =
r.iter().flatten().map(|c| c.iter().map(|p| (p.x, p.y)).collect()).collect();
println!("i16 engine, {}: {:?}", name, pts);
}
}Expected behavior
Strategy::Frag on the i16 engine to return the same contour as the other three strategies do, and as it does on a release build.
Actual behavior
On a debug build:
i32 engine, List: [[(0, 9854), (0, 0), (129, -23169)]]
i16 engine, List: [[(0, 9854), (0, 0), (129, -23169)]]
i32 engine, Tree: [[(0, 9854), (0, 0), (129, -23169)]]
i16 engine, Tree: [[(0, 9854), (0, 0), (129, -23169)]]
i32 engine, Auto: [[(0, 9854), (0, 0), (129, -23169)]]
i16 engine, Auto: [[(0, 9854), (0, 0), (129, -23169)]]
i32 engine, Frag: [[(0, 9854), (0, 0), (129, -23169)]]
thread 'main' panicked at src/split/grid_layout.rs:146:29:
attempt to subtract with overflow
Frag on the i32 engine and every other strategy on the i16 engine return the same contour. On a release build there is no panic and the i16 Frag overlay prints that contour too.
Environment
- iOverlay version: 8.1.0, and current
main(0022b34) - Rust version: 1.98.0 (88d9e12ae 2026-08-18)
- OS: macOS 26.6.2, aarch64
Additional context
The reproduction also depends on i_float for IntPoint.
BTW, this bug was found using hegel. Happy to contribute the tests if you're interested.
Reactions are currently unavailable
Metadata
Metadata
Assignees
Labels
No labels
Activity
NailxSharipov commentedon Sep 4, 2026
This case is expectable.
i16:
-32_767...32_768(-2^15...2^15)the library use operation like a + b or a - b without extending dimension that why the correct coordinate is in range
i16:
−16_384...16_383(-2^14...2^14)which is already valid for float convertation but not properly verified/documented for int api
NailxSharipov commentedon Sep 6, 2026
Add int range explanation in #90