Skip to content

Remove the MPS backend from the Apple demos - #259

Merged
shoumikhin merged 1 commit into
mainfrom
remove-mps-backend
Aug 27, 2026
Merged

Remove the MPS backend from the Apple demos#259
shoumikhin merged 1 commit into
mainfrom
remove-mps-backend

Conversation

@shoumikhin

@shoumikhin shoumikhin commented Aug 27, 2026

Copy link
Copy Markdown
Contributor

Remove the MPS backend from the Apple demos

The MPS delegate was removed from ExecuTorch in pytorch/executorch#22181. After that
change the mv3 demo failed to build, because its Xcode project still bundled a model
file that no longer gets produced:

error: .../Resources/Models/MobileNet/mv3_mps_float16.pte:
No such file or directory (in target 'App' from project 'ExecuTorchDemo')

That is the build-demo-ios job on executorch main, which has been red since #22181
landed.

Why the file goes missing is worth stating precisely, because it is not this repo's
own exporter. The build-demo-ios job runs executorch's .ci/scripts/test_ios_ci.sh,
which clones this repo at depth 1 and exports the models with executorch's own
scripts, then moves them into the app:

python3 -m examples.portable.scripts.export --model_name=mv3 ...
python3 -m examples.apple.coreml.scripts.export --model_name=mv3
python3 -m examples.xnnpack.aot_compiler --model_name=mv3 --delegate
mv mv3*.pte -> Resources/Models/MobileNet/

#22181 removed the MPS export step from that script, so mv3_mps_float16.pte stopped
being staged while the project still demanded it. This repo's own mv3/python/export.py
was a second, independent producer of the same file, and it was already misleading:
the MPS partitioner had been commented out and the program was re-exported with
portable ops under an mps name, so that path ran the same graph as the portable build
while claiming to be GPU accelerated.

This change drops, across both Apple demo projects:

  • the backend_mps SwiftPM product reference (cleanup; see the note below on why this
    was not itself the build break),
  • the mv3_mps_float16.pte resource and the MPS case in the mv3 picker,
  • the MPS export from this repo's export.py and the file name from the export
    workflow's artifact list.

The Metal references under voxtral_realtime/ are left alone on purpose. Those are
TORCHAO_BUILD_EXPERIMENTAL_MPS, a torchao Metal-kernel flag the Metal backend still
uses upstream, not the removed delegate. execuwhisper/macos/ and the top-level metal/
tree reference the Metal backend for the same reason and are also untouched. A third
Xcode project, voxtral_realtime/macos/VoxtralRealtime.xcodeproj, declares no
ExecuTorch SwiftPM products, so it had nothing to remove.

Test Plan:

No MPS reference remains outside voxtral_realtime/. Checked with a plain substring
grep (not a word-boundary grep: underscore is a word character, so \bmps\b matches
neither backend_mps nor mv3_mps_float16.pte and would pass on the unfixed tree). On
the base the substring grep finds 26 hits across the .pbxproj files and 0 at head,
after excluding the unrelated words timestamp, dumps, lampshade and bmpSegmentation.

Both Xcode projects were checked with a real plist parser (plutil -convert json), not
a regex over the text. Object counts at head: 109 in mv3, 99 in etLLM. The earlier
"63 in etLLM" figure was wrong: it counted only the 24-character ids and missed the
entire etLLM-macOS target, whose ids are 25 characters (MAC0001...) and which include
both objects this change deletes on the macOS side. Re-run keyed on the parsed object
keys, both projects have zero ids referenced but not defined and zero defined but
never referenced, before and after, so the edit preserved an already-intact graph.
backend_coreml and backend_xnnpack survive in both. plutil -lint passes on both.

ClassificationController.swift parses with swiftc, and the switch over Mode is still
exhaustive over the two remaining cases. Nothing else referenced Mode.mps;
MobileNetClassifierTest covers portable, Core ML and XNNPACK and never had an MPS
case. export.py compiles and the workflow artifact list no longer names the file it
stopped producing.

Notes, none blocking:

  • "no backend_mps SwiftPM product is published" was too strong. Both projects pin the
    swiftpm-1.1.0 branch of pytorch/executorch, which still declares backend_mps. So the
    product reference was not what broke the build; removing it is cleanup that keeps the
    project honest about what it links.
  • The README embeds a screenshot (demo_ios_app.png) that still shows the old
    three-button XNNPACK / CoreML / MPS selector. That image lives in the executorch repo
    and cannot be updated here; it will be stale until refreshed upstream.
  • The MPS picker case is deleted rather than repointed at the portable mv3.pte. Keeping
    a third "portable" comparison would have been one line, but the demo is about
    delegated backends, so two real ones is the cleaner story.

The MPS delegate was removed from ExecuTorch in pytorch/executorch#22181, so
nothing produces mv3_mps_float16.pte any more and no backend_mps SwiftPM product
is published. The mv3 demo still declared both, which fails the build before it
starts:

  error: .../Resources/Models/MobileNet/mv3_mps_float16.pte:
  No such file or directory (in target 'App' from project 'ExecuTorchDemo')

That is the build-demo-ios job on executorch main, which has been red since that
change landed.

Drop the product references from both Xcode projects, the model resource and the
picker case from the mv3 demo, and the export that produced the file. The export
was already misleading: the MPS path had been commented out and the program was
re-exported with portable ops under an mps name, so the option ran the same graph
as the portable build while claiming to be GPU accelerated.

The Metal references under voxtral_realtime/ are deliberately left alone. Those
are TORCHAO_BUILD_EXPERIMENTAL_MPS, a torchao Metal-kernel flag that the Metal
backend still uses upstream, not the removed delegate.

Test Plan:
No MPS reference remains outside voxtral_realtime/, checked with a word-boundary
grep over every file type.

Both Xcode projects lint clean with plutil, and their object graphs are intact:
109 objects in mv3 and 63 in etLLM, with zero ids referenced but not defined and
zero defined but never referenced. The originals measured the same way, so the
edit preserved the property rather than happening to satisfy it. Confirmed
backend_coreml and backend_xnnpack survive in both.

ClassificationController.swift parses with swiftc, and the switch over Mode is
still exhaustive over the two remaining cases. Nothing else referenced Mode.mps;
MobileNetClassifierTest covers portable, Core ML and XNNPACK and never had an MPS
case. export.py compiles and the workflow artifact list no longer names the file
it stopped producing.
@meta-cla meta-cla Bot added the CLA Signed This label is managed by the Meta Open Source bot. label Aug 27, 2026
@shoumikhin
shoumikhin merged commit 809f8a4 into main Aug 27, 2026
15 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

CLA Signed This label is managed by the Meta Open Source bot.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants