Repository navigation
Conversation
* pick up fix-custom-io from mlx-c - I/O callbacks now return number of bytes read/written to indicate failure or success
* fix MLXLogger - fix ml-explore#491 - OSLog.Logger.isEnabled(type:) is not actually available since macOS 11 (and friends) - this causes crashes on iOS/macOS before 26.4 - use different API
…l-explore#489) * be able to trigger workflows on main. notes about upcoming releases Co-authored-by: Nick Henderson <525247+nwh@users.noreply.github.com>
- give me an easy way to trigger dry runs - the build failed because JIT wasn't available on TVOS - this isn't new, so I suspect it was a change on the mlx side that we are now seeing - the guard wasn't wide enough -- just visionOS and iOS, widen to IPHONE (which covers all iOS based OS targets)
ml-explore#499) - globalStreams could take the evalLock - evalLock could take the globalStreams lock (dispatch_once) - break the cycle by making the no-args init lock free
Upstream since the 0.32.2 merge-base 9019419: ml-explore#499 evalLock / globalStreams lock inversion, ml-explore#495 xcframework builds, ml-explore#489, ml-explore#496 float16 attention mask, ml-explore#493 MLXLogger (cLogSupport), ml-explore#402 exclude mlx/build, ml-explore#476 mlx-c fix-custom-io (mlx-c -> ebc88f10). Conflicts: - Source/MLX/Logging.swift: keep the fork's osLogType(for:) (warning -> .default) and metadata suffix; take upstream's is_os_log_enabled(osLog, level) check from ml-explore#493. - Source/Cmlx/include-framework/Metal.hpp: generated header (metal-cpp commit stamp only); keep ours, it matches the still-vendored core d5da0546 and is regenerated by tools/update-mlx.sh in the next commit. Source/Cmlx/mlx-c takes upstream's pointer ebc88f10 (ours, c74db530, is an ancestor).
…-qat#282); regenerate mlx-c: numen-tech/mlx-c numen/0.7.0-gather-qmm-global-scale (cfc471f4 = v0.7.0 + ml-explore/mlx-c#137).
… for the new core (gemma4-qat#282) - tools/fix-metal-includes.sh: add spec_decode.metal (the core builds it unconditionally; GPU spec_decode_verify looked it up in the default library and failed). Regenerated with LC_ALL=C tools/update-mlx.sh; two runs byte-identical. - Package.swift (Linux CUDA): exclude the Windows-only cuda/wddm.cpp and link cusolver, as the core CMake does (cuda/CMakeLists.txt:189-190, :299). Not built here (no CUDA host). - prism_readme.md: describe the current qmv_fast gate and name the dev version. fence.metal stays out: the core builds it only for Metal >= 3.2 and only MLX_METAL_FAST_SYNCH=1 uses it (upstream mlx-swift omits it too).
Codex Review SummaryThis comment shows the latest Codex review activity on this pull request.
ℹ️ About Codex in GitHubYour team has set up Codex to review pull requests in this repo. Reviews are triggered when you
Codex reacts with 👀 while any review is running, comments if it has suggestions, and reacts with 👍 once all reviews finish with no findings. |
There was a problem hiding this comment.
💡 Codex Review
Here are some automated review suggestions for this pull request.
Reviewed commit: b721fdd8f3
ℹ️ About Codex in GitHub
Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you
- Open a pull request for review
- Mark a draft as ready
- Comment "@codex review".
If Codex has suggestions, it will comment; otherwise it will react with 👍.
Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".
| C35EA5643054AC8E00281871 /* MLXNN.framework in Embed Frameworks */ = {isa = PBXBuildFile; fileRef = C3CBE6B52EAC14DE0029A645 /* MLXNN.framework */; settings = {ATTRIBUTES = (CodeSignOnCopy, RemoveHeadersOnCopy, ); }; }; | ||
| C35EA5673054AC8E00281871 /* MLXOptimizers.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = C3CBE6CF2EAC15310029A645 /* MLXOptimizers.framework */; }; | ||
| C35EA5683054AC8E00281871 /* MLXOptimizers.framework in Embed Frameworks */ = {isa = PBXBuildFile; fileRef = C3CBE6CF2EAC15310029A645 /* MLXOptimizers.framework */; settings = {ATTRIBUTES = (CodeSignOnCopy, RemoveHeadersOnCopy, ); }; }; | ||
| C37BFFFA306C6138006C8EBC /* cLogSupport.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = C37BFFEC306C60EE006C8EBC /* cLogSupport.framework */; platformFilters = (ios, maccatalyst, macos, xros, ); }; |
There was a problem hiding this comment.
Add tvOS to cLogSupport's platform filters
When the Xcode project is built for tvOS, Logging.swift can import OSLog and therefore imports cLogSupport, but this framework link and the corresponding PBXTargetDependency both omit tvos from their platform filters. Since tools/create-xcframework.sh explicitly archives tvOS, the resulting tvOS build can lack the required Clang module/dependency; include tvos in both filters.
Useful? React with 👍 / 👎.
Merges upstream ml-explore/mlx-swift
mainintoprismand re-vendors the core from the rebased numen-tech/mlx fork (numen-tech/mlx#10: upstream ml-explore/mlxmain06eb7483fplus the fork's 10-patch series and review fixes). Tracking: numen-tech/gemma4-qat#282.Commits
084da487Merge ml-explore/mlx-swift main 1e61d9c into prism. Upstream since the 0.32.2 merge-base90194196: fix lock inversion between evalLock and dispatch_once on globalStreams ml-explore/mlx-swift#499 (evalLock / globalStreams lock inversion), fix xcframework builds ml-explore/mlx-swift#495, be able to trigger workflows on main. notes about upcoming releases ml-explore/mlx-swift#489, Fix attention mask forfloat16ml-explore/mlx-swift#496 (float16 attention mask), fix MLXLogger ml-explore/mlx-swift#493 (MLXLogger, newcLogSupporttarget), package: exclude mlx/build cmake artifacts from Cmlx target ml-explore/mlx-swift#402 (excludemlx/build), pick up fix-custom-io from mlx-c ml-explore/mlx-swift#476 (mlx-cfix-custom-io, mlx-c moves toebc88f10). Two conflicts:Source/MLX/Logging.swift: keeps the fork'sosLogType(for:)(a warning maps to.default) and its metadata suffix, and takes upstream'sis_os_log_enabled(osLog, level)check from fix MLXLogger ml-explore/mlx-swift#493.Source/Cmlx/include-framework/Metal.hpp: a generated header whose conflict is only the metal-cpp commit stamp. Kept ours; the next commit regenerates it.8b127c7bump numen-tech/mlx to 2fc35a34 (upstream main + fork patches, gemma4-qat#282); regenerate.Source/Cmlx/mlx:d5da0546(the 0.32.2 fork line) moves to2fc35a34, the head offork/282-sync-upstream-main. This includes the review fixes87d00a604(shorter NAX-gate comment indevice.cpp) and2fc35a344(spec_decode_verifyrejects non-integerdraft_tokens, inmlx/fast.cpp).Source/Cmlx/mlx-c:ebc88f10moves tocfc471f4, from numen-tech/mlx-c. See the mlx-c section below.mlx-generated/andinclude-framework/are regenerated withLC_ALL=C tools/update-mlx.sh.MLX_VERSIONis0.32.4, frommlx/version.hat06eb7483f. It is set inPackage.swiftandxcode/xcconfig/Cmlx.xcconfig.031fd87prism_readme: mlx-c comes from the numen-tech/mlx-c fork.b721fddCmlx: build spec_decode into the metallib; fix the Linux CUDA sources for the new core. From review: addsspec_decode.metaltoKERNEL_LIST(regenerated, two runs byte-identical); in the Linux CUDA branch, excludes the Windows-onlycuda/wddm.cppand linkscusolver, as the core CMake does; refreshes the qmv_fast paragraph and version wording inprism_readme.md.Fork patches kept
affine_sym) exposuremlx-generated/quantized*.cppandmetal/quantized*.h. No Swift-side code.spec_decode_verifymlx/fast.his unchanged fromd5da0546through2fc35a34;2fc35a344only adds input validation inmlx/fast.cpp. Here: the regeneratedinclude-framework/mlx-fast.hdeclaration and, sinceb721fdd, the kernel in the SwiftPM metallib. No Swift binding.MLX.GPUCountersand themlx_counters_*extern "C" shimSource/MLX/GPUCounters.swiftandSource/Cmlx/mlx-counters/mlx_counters.cpp, both unchanged.mlx::core::metal::Counters/counters()/reset()inmetal.hare identical at2fc35a34.QuantizedEmbeddinggatherSource/MLXNN/Quantized.swift:234, unchanged.FMT_CONSTEVALprism(6db5272: fmt 12.1.0). Nothing to keep.global_scale699f32fe, which passedstd::nulloptfor unboundglobal_scalearguments) was subsumed by upstream mlx-c. The same class of fix is needed again forgather_qmm; it is now the mlx-c pincfc471f4.mlx-c decision
Pinned to numen-tech/mlx-c
numen/0.7.0-gather-qmm-global-scale(cfc471f4 = v0.7.0 + ml-explore/mlx-c#137). Re-pin to upstream once ml-explore#137 is in a release.Why a pin was needed:
xcrun swift buildwith mlx-c at upstream'sebc88f10fails.cbb4059d8("[Metal] global scale for qmm", #4458, in 0.32.3), which insertedglobal_scalebeforesorted_indicesingather_qmm.a341b49) does not help:ebc88f10..v0.7.0only bumps the version inCMakeLists.txtanddocs/src/conf.py. No released mlx-c builds against MLX ≥ 0.32.3.ops.cppchange. UnderMLX_VERSION_NUMERIC >= 32003it passesstd::nulloptfor the new argument. The C API is unchanged, so no Swift changes are needed.Regeneration check
LC_ALL=C tools/update-mlx.shtwice gives byte-identicalmlx-generated/,include-framework/andinclude/(diff -ron snapshots: no output). This holds at both78bdb20eand2fc35a34.78bdb20eand2fc35a34generate the same output. Neitherdevice.cppnorfast.cppis a generator input, somlx-generated/has no diff between them.ebc88f10and atcfc471f4.include-framework/Metal.hpp. metal-cpp'sMakeSingleHeader.pystamps the superprojectHEADsha (Autogenerated from commit …). That line follows the commit the script runs on, not the submodule. The committed stamp is the merge084da487. This is an upstream generator property; it is not patched.mlx-generated/metal/Xhas a changedmlx/backend/metal/kernels/Xind5da0546..2fc35a34. Every modified JIT.cppembeds at least one header that changed in that range.compiled_preamble.cppandcuda/cuda_jit_sources.hfollow the core's CPU and CUDA device headers.quantized.cpp.quantized.hsection ofmlx-generated/quantized.cpp(after#line 1 "mlx/backend/metal/kernels/quantized.h") is identical toSource/Cmlx/mlx/mlx/backend/metal/kernels/quantized.h.mlx-generated/metal/quantized.his identical to that header.affine_sym2/2,sym_derived_bias3/3,qmv_wide4/4,implied_bias61/61,bits == 117/17.Build plumbing for new core files
tools/fix-metal-includes.sh(generator change).KERNEL_LISTmirrors the core's unconditionalbuild_kernel()set, which now also hasgated_delta_update,gated_delta_update_vjp,gather_mm_offsetsandscaled_dot_product_attention_vjp. Without them those kernels are missing from the SwiftPM metallib at runtime.gather_mmdispatchesgather_mm_offsets.b721fddadds the fork'sspec_decodeas well.default.metallibnow containsgather_mm_offsets,sdpa_vjp_*,gated_delta_update*andspec_decode_verify.fence.metalstays out (see Known gaps).Package.swift..cppfiles (cusolver_utils,wddm) on Apple and Linux CPU builds; the macOS build fails without this (cuda_runtime.hnot found). The Linux CUDA branch compilescusolver_utilsand linkscusolver, and excludes the Windows-onlywddm(b721fdd)..cppfiles (cross_entropy,gated_delta_update, and the fork'sspec_decode, which was previously missing) from the no-Metal Linux builds.mlx/CODE_OF_CONDUCT.md, which the core deleted.xcode/MLX.xcodeproj. Adds membership exceptions for:kernels/andcuda/files;tests/cuda_tests.cpp;metal/*.hheaders;tests/metal_counters_tests.cppandtests/metal_kernel_tests.cpp. These already broke the xcodeproj build onprism631cdf9e.Tests/MLXTests/FP8Tests.swift. Since Fix mx.from_fp8 E4M3FN NaN decode with branchless carry ml-explore/mlx#4376 (in the jump from 0.32.2 to06eb7483f),0x7Fand0xFFdecode to NaN, which is correct for E4M3FN. The test's reference model expected ±480, so it now expects NaN and compares withequalNaN: true.Verification (macOS, Xcode 27.0 / Swift 6.4)
Core at
2fc35a34, mlx-c atcfc471f4, headb721fdd(build and tests rerun after the review fixes, same counts):xcrun swift build:Build complete!The remaining Swift warnings are all in code identical to upstream orprism:withValuedeprecations inStream.swift/State.swift, plusMLXArray+maskFill.swiftandMLXNN/Module.swift.xcodebuild test -scheme mlx-swift-Package -destination 'platform=macOS' -skipPackagePluginValidation -parallel-testing-enabled NO:** TEST SUCCEEDED **.78bdb20e,xcodebuild build-for-testing -scheme MLX -destination 'platform=macOS'reported** TEST BUILD SUCCEEDED **andxctestpassed MLXTests (389 XCTest, 2 skipped; 8 Swift Testing) and MLXIntegrationTests (669). Rebuilt atb721fdd:** TEST BUILD SUCCEEDED **. The2fc35a34delta adds no files.xcodebuild build -scheme mlx-swift-Package -destination 'generic/platform=iOS'atb721fdd:** BUILD SUCCEEDED **.Known gaps
spec_decode_verifyhas no Swift or mlx-c binding; it never had one onprism. Sinceb721fddits kernel is in the SwiftPM metallib, so a C++ caller in Cmlx works on GPU.fence.metalis not in the metallib, as in upstream mlx-swift. The core builds it only for Metal ≥ 3.2, and onlyMLX_METAL_FAST_SYNCH=1(default off) uses it, so setting that variable fails with a missing kernel.CMakeLists.txtbuild, which still fetches upstream mlxv0.32.2and mlx-cebc88f10, as onprism. It is untouched here.Codex round
spec_decode.metalmissing from the metallib. GPUspec_decode_verifywould fail with "Unable to load kernel". Fixed inb721fdd.fence.metalmissing from the metallib. Pre-existing, and the same in upstream mlx-swift. Kept as a known gap (above).wddm.cppand did not linkcusolver. Fixed inb721fdd.