Skip to content

BundleIO: Preserve channels-last input and output layouts - #23482

Closed
Erik-Lundell wants to merge 4 commits into
pytorch:mainfrom
Erik-Lundell:fix-bundled-tensor
Closed

Erik-Lundell wants to merge 4 commits into
pytorch:mainfrom
Erik-Lundell:fix-bundled-tensor

Conversation

@Erik-Lundell

@Erik-Lundell Erik-Lundell commented Oct 6, 2026 •

Copy link
Copy Markdown
Collaborator

TensorSpec.from_tensor(..., const=True) makes test tensors contiguous, discarding channels-last strides and reordering their bytes. Bundled inputs can then have incorrect values, while output verification can fail its stride check.

Preserve the layout of bundled test tensors. Construct ATen tensors with strides derived from the serialized dimension order before copying their bytes.

Cover channels-last inputs and outputs, offset views, and non-dense views.

Additionally, a small type hint fix in tensor.py

cc @Gasoonjia @digantdesai @freddan80 @per @zingo @oscarandersson8218 @mansnils @Sebastian-Larsson @robell @rascani

TensorSpec.from_tensor(..., const=True) makes test tensors
contiguous, discarding channels-last strides and reordering their
bytes. Bundled inputs can then have incorrect values, while output
verification can fail its stride check.

Preserve the layout of bundled test tensors. Construct ATen tensors
with strides derived from the serialized dimension order before
copying their bytes.

Cover channels-last inputs and outputs, offset views, and non-dense
views.

Additionally, a small type hint fix in tensor.py

Validation: bundled-program suite (10 tests)

Signed-off-by: Erik Lundell <erik.lundell@arm.com>
Change-Id: I4d05a144aafbb0fbd25bfbbd161c4eebc8dc2b0f
@pytorch-bot

pytorch-bot Bot commented Oct 6, 2026 •

Copy link
Copy Markdown

🔗 Helpful Links

🧪 See artifacts and rendered test results at hud.pytorch.org/pr/pytorch/executorch/23482

Note: Links to docs will display an error until the docs builds have been completed.

⏳ No Failures, 1 Pending

As of commit ded0066 with merge base aee0a33 (image):
💚 Looks good so far! There are no failures yet. 💚

This comment was automatically generated by Dr. CI and updates every 15 minutes.

@meta-cla meta-cla Bot added the CLA Signed This label is managed by the Facebook bot. Authors need to sign the CLA before a PR can be reviewed. label Oct 6, 2026
@Erik-Lundell Erik-Lundell added ciflow/trunk release notes: none Do not include this in the release notes help wanted Extra attention is needed partner: arm For backend delegation, kernels, demo, etc. from the 3rd-party partner, Arm module: devtools Issues related to developer tools and code under devtools/ labels Oct 6, 2026
@Erik-Lundell
Erik-Lundell marked this pull request as draft October 7, 2026 18:29
@zingo
zingo marked this pull request as ready for review October 13, 2026 14:38
Copilot AI balanced review requested due to automatic review settings October 13, 2026 14:38

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🟡 Changes recommended

The updated dim_order_from_stride signature retains an incorrect return type contract.

1 open finding
What changed in this PR

Preserves bundled tensor layouts so channels-last inputs and outputs serialize and load correctly.

Changes:

  • Adds layout-preserving tensor serialization.
  • Reconstructs ATen tensors using serialized dimension-order strides.
  • Adds coverage for channels-last tensors and views.
File Description
extension/​pybindings/​test/​test_pybindings.py Adds end-to-end channels-last bundle verification.
exir/​tests/​test_tensor.py Tests layout-preserving TensorSpec creation.
exir/​tensor.py Adds optional layout preservation.
devtools/​bundled_program/​test/​test_bundle_data.py Tests serialized layouts and view data.
devtools/​bundled_program/​core.py Preserves bundled input/output layouts.
devtools/​bundled_program/​bundled_program.cpp Reconstructs tensors with serialized strides.

🧠 Review effort: Balanced


💡 Add a code-review agent skill or configure MCP servers for context-aware, tailored reviews. Learn more in the docs.

Comment thread exir/tensor.py

def dim_order_from_stride(
stride: Tuple[int], sizes: Optional[Tuple[int]] = None
stride: Tuple[int, ...], sizes: Optional[Tuple[int, ...]] = None
@zingo

zingo commented Oct 13, 2026

Copy link
Copy Markdown
Collaborator

Hi @rascani and @digantdesai this is in the general code and need a non Arm review :)

@zingo
zingo requested review from digantdesai and rascani October 14, 2026 09:16
@rascani

rascani commented Oct 14, 2026

Copy link
Copy Markdown
Contributor

@Gasoonjia - do you think you could take a look?

@rascani

rascani commented Oct 14, 2026

Copy link
Copy Markdown
Contributor

@claude - Review this PR.

@claude

claude Bot commented Oct 14, 2026 •

Copy link
Copy Markdown

Claude finished @rascani's task in 1m 22s —— View job


PR Review: #23482

Summary: Bundled test tensors now keep their eager strides, so channels-last inputs and outputs load correctly. However, any dense non-contiguous expected output (for example the result of permute or transpose) now aborts verification. Before this PR those outputs worked.

Detailed review

Backward Compatibility

  • devtools/bundled_program/core.py:114,129: the layout comes from the eager tensor, not from the program's I/O dim order. clone(memory_format=torch.preserve_format) keeps the exact strides of any dense, non-overlapping tensor, not just channels-last ones. Most callers build expected outputs by running the eager model (model(*inputs)). Take a model ending in x.permute(0, 2, 3, 1) or x.transpose(1, 2):

    • The eager output is a dense permuted view, so it gets serialized with dim order (0, 2, 3, 1) (or similar).
    • The ExecuTorch program's output comes from permute_copy, so it has the default dim order.
    • tensors_are_close then hits ET_CHECK_MSG(... same strides) and aborts (bundled_program.cpp:182 in ATen mode, :200 in lean mode).

    Before this PR, .contiguous() made those cases pass. Inputs have the same problem: a permuted test input used to be normalized to the program's contiguous input and now arrives with a non-default dim order.

    The cleaner design is to normalize each test tensor to the dim order the program declares for that input/output. That is the layout the runtime compares against, and the method's I/O TensorSpecs carry it. At minimum, limit preservation to tensors whose dim order is default or channels-last, and make everything else contiguous as before.

    Please add a test with a permute/transpose eager output, which would have caught this. Fix this →

API Design

  • exir/tensor.py:214: preserve_layout is a boolean switch on a widely used constructor, and it only matters when const=True. If you take the normalization approach above, the conversion can happen in BundledProgram before calling from_tensor, and the flag can go. Separately, the "type hint fix" leaves dim_order_from_stride's return type as Tuple[bytes] (Copilot already raised this).

Testing

  • extension/pybindings/test/test_pybindings.py:346: the end-to-end test skips non-ATen kernel modes. The lean impl_like / tensors_are_close path is the one used on device, so it should also get an end-to-end channels-last check.

Recommendation

Request Changes. The arbitrary-permutation regression should be fixed before merge. The channels-last fix itself is correct.

@Erik-Lundell
Erik-Lundell marked this pull request as draft October 15, 2026 15:02
@Erik-Lundell

Copy link
Copy Markdown
Collaborator Author

Sorry, this is not quite ready

@zingo

zingo commented Oct 15, 2026 •

Copy link
Copy Markdown
Collaborator

Yeah I was overrideing @Erik-Lundell s origina draft as I needed part of this fix for something else and undrafted sorry for the extra work.

@zingo

zingo commented Oct 16, 2026

Copy link
Copy Markdown
Collaborator

Replaced with this #23927

@zingo zingo closed this Oct 16, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

ciflow/trunk CLA Signed This label is managed by the Facebook bot. Authors need to sign the CLA before a PR can be reviewed. help wanted Extra attention is needed module: devtools Issues related to developer tools and code under devtools/ partner: arm For backend delegation, kernels, demo, etc. from the 3rd-party partner, Arm release notes: none Do not include this in the release notes

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants