…aces #1195) (#1253)
## What this is
This is #1195 (`fix(runtime): infer Compress output shapes for large
conditions`) rebased onto current `main` (which now includes #1251, the
replacement for its stacked base #1159), plus a follow-up commit that
adds the falsifying test the original was missing. Opened as a
replacement branch because the original `fix/compress-condition-shapes`
was stacked on a `split/*` branch, which makes `gh pr merge` 403. Closes
#1195.
## The bug
A dynamic `Compress` output shape is the count of selected entries, so
the executor must read the boolean condition tensor to size the output.
The dynamic-shape reader (`resolve_node_outputs`) admitted a shape input
only if it passed `bounded_shape_input`, whose cap is
`MAX_SHAPE_DATA_ELEMS = 1024` — sized for scalar/vector shape metadata.
A vision graph whose `Compress` condition spans a full image is longer
than 1024, so it was rejected, `dynamic_output_shapes` received a `None`
condition, and the run failed with `UnresolvedShape { op: "Compress" }`
(a 500).
## The fix
- `geometry.rs`: add `bounded_compress_condition` — a 1-D `Bool` tensor
up to `MAX_COMPRESS_CONDITION_ELEMS = 1 << 20`.
- `dispatch.rs`: route the `Compress` condition input (default domain,
`op_type == "Compress"`, input index 1) through a new
`compress_condition_i64` that uses the larger bound, while every other
shape input still goes through the ordinary `shape_input_i64`. So the
one operand `Compress` genuinely needs is materialized, and an unrelated
large tensor still is not.
## Test-discipline gap I closed
The PR shipped `compress_condition_allows_image_sized_boolean_vectors`,
which only asserts the `bounded_compress_condition` **predicate**.
Reverting the `dispatch.rs` routing (the behavioural half of the fix)
leaves that test green — it cannot catch a regression of the fix. I
added:
1. `compress_runs_with_image_sized_condition_including_empty_and_full` —
builds a `Compress` graph whose `Bool` condition initializer is
`MAX_SHAPE_DATA_ELEMS + 500` (1524) elements and runs it end to end on
the CPU EP, asserting the output shape resolves and exactly the selected
rows are gathered. Covers the all-false (empty output) and all-true
(full output) boundaries through the real resolve + kernel path.
2. `dynamic_output_shapes_compress_boundary_counts` — the selected-count
sizer at its boundaries: condition longer than the axis (clamped),
shorter than the axis, all-false, all-true.
## Falsification (revert -> RED -> restore -> GREEN)
Reverting only the `dispatch.rs` routing back to `shape_input_i64`
(keeping the helper + method so it stays a clean behavioural RED, not a
compile error) makes
`compress_runs_with_image_sized_condition_including_empty_and_full` fail
with exactly:
```
UnresolvedShape { value: "y", op: "Compress" }
```
while the shipped predicate-only test and the counting test stay green
(confirming they do not cover the routing). Restoring the routing
returns all 4 Compress tests to green.
## Validation
- `cargo test -p onnx-runtime-session --lib`: **185 passed, 0 failed**
on current `main`.
- Compress subset: 4 passed (shipped predicate test + shipped counting
test + my 2 new tests).
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
---------
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Copilot-Session: 0190e2eb-abe4-451f-b36d-44a035a99b7e
Problem
A dynamic
Compressoutput shape is the count of selected entries, so computing it requires reading the condition tensor. The dynamic shape reader only admitted the small tensors that normally carry shape data, so a vision graph whose condition spans a full image failed shape inference:Serving a 448x448 image through the Muse vision encoder returned HTTP 500 as a result.
Fix
Read a
Compresscondition through its own bounded path, so the one operand the shape genuinely depends on is materialized while an unrelated large tensor still is not. The bound is an explicit element cap rather than the general shape-data limit.Testing
cargo test -p onnx-runtime-session --lib compresspasses.Note
Stacked on #1159, which introduces the Compress shape-inference path this extends.