Skip to content

mlx 0.32.x can't find its metallib inside the PyInstaller bundle (blocks unpinning mlx) #515

Description

@ruzin

Split out of #514, which pinned mlx==0.31.2 to stop the bleeding. The pin is a tourniquet, not a fix — this issue is the actual root cause, and it has to be answered before the pin can ever move forward.

What happens

A bundle built against mlx 0.32.2 dies on the first Parakeet load:

$ dist/stenoai/stenoai spike-parakeet
{"event": "error", "stage": "import_parakeet",
 "message": "Failed to load the default metallib. library not found library not found library not found library not found "}

The same commit, same stenoai.spec, built against 0.31.2, transcribes normally. Parakeet is the default macOS engine, so this is a total failure of the primary path.

What has been ruled out

  • The file is present. _internal/mlx/lib/mlx.metallib exists in both bundles (182 MB on 0.32.2, 158 MB on 0.31.2).
  • The layout is identical. Both bundles have the same four libmlx.dylib copies in the same places (_internal/, _internal/mlx/lib/, and Ollama's two mlx_metal_v*/ runner dirs), so the Ollama/pip ABI-collision split that verify_mlx_bundle.py guards is not what changed.
  • Not the artifact round-trip. First seen in a downloaded CI artifact, but reproduced by a clean local pyinstaller stenoai.spec --noconfirm — it is the dependency version, nothing about transport or exec bits.
  • Not the machine. Same Mac runs 0.31.2 fine.

What is not known

Why 0.32.x fails to resolve a file that is sitting at the expected path. The repeated library not found (4x) suggests MLX tries several candidate paths and rejects all of them — worth finding out what those candidates are in 0.32.x versus 0.31.2, and whether it now resolves relative to the loaded libmlx.dylib (which under PyInstaller may be the flattened _internal/libmlx.dylib, with no metallib beside it) rather than to the package directory.

Why it matters beyond the pin

parakeet-mlx floors mlx at >=0.22.1 and has no upper bound, so every unpinned build was a coin flip. The pin makes builds deterministic, but it also freezes the app on an mlx that will age out — losing upstream fixes and eventually Python/macOS compatibility.

Definition of done

  • The resolution mechanism in 0.32.x is understood and written down.
  • Either the spec is fixed so current mlx works in the bundle, or an upstream issue is filed and linked here.
  • The pin in requirements.txt moves forward, verified by a real rebuild plus stenoai spike-parakeet on Apple Silicon.

Do not move the pin on a green CI run alone. No CI job can load Metal — see the companion coverage issue.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    bugSomething isn't working

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions