Test builds: Neural Engine-compilable conv-cache slices for M2 (FluidAudio #1141)
#3
by alexwengg - opened
- test-1141/README.md +30 -0
- test-1141/encoder-split/2240ms/encoder_body_0_11.mlmodelc/analytics/coremldata.bin +3 -0
- test-1141/encoder-split/2240ms/encoder_body_0_11.mlmodelc/coremldata.bin +3 -0
- test-1141/encoder-split/2240ms/encoder_body_0_11.mlmodelc/metadata.json +147 -0
- test-1141/encoder-split/2240ms/encoder_body_0_11.mlmodelc/model.mil +0 -0
- test-1141/encoder-split/2240ms/encoder_body_0_11.mlmodelc/weights/weight.bin +3 -0
- test-1141/encoder-split/2240ms/encoder_body_12_23.mlmodelc/analytics/coremldata.bin +3 -0
- test-1141/encoder-split/2240ms/encoder_body_12_23.mlmodelc/coremldata.bin +3 -0
- test-1141/encoder-split/2240ms/encoder_body_12_23.mlmodelc/metadata.json +181 -0
- test-1141/encoder-split/2240ms/encoder_body_12_23.mlmodelc/model.mil +0 -0
- test-1141/encoder-split/2240ms/encoder_body_12_23.mlmodelc/weights/weight.bin +3 -0
- test-1141/multilingual/1120ms/encoder.mlmodelc/analytics/coremldata.bin +3 -0
- test-1141/multilingual/1120ms/encoder.mlmodelc/coremldata.bin +3 -0
- test-1141/multilingual/1120ms/encoder.mlmodelc/model.mil +0 -0
- test-1141/multilingual/1120ms/encoder.mlmodelc/weights/weight.bin +3 -0
- test-1141/multilingual/2240ms/encoder.mlmodelc/analytics/coremldata.bin +3 -0
- test-1141/multilingual/2240ms/encoder.mlmodelc/coremldata.bin +3 -0
- test-1141/multilingual/2240ms/encoder.mlmodelc/model.mil +0 -0
- test-1141/multilingual/2240ms/encoder.mlmodelc/weights/weight.bin +3 -0
- test-1141/multilingual/560ms/encoder.mlmodelc/analytics/coremldata.bin +3 -0
- test-1141/multilingual/560ms/encoder.mlmodelc/coremldata.bin +3 -0
- test-1141/multilingual/560ms/encoder.mlmodelc/model.mil +0 -0
- test-1141/multilingual/560ms/encoder.mlmodelc/weights/weight.bin +3 -0
- test-1141/patch_mlmodelc.py +116 -0
test-1141/README.md
ADDED
|
@@ -0,0 +1,30 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
# Test builds for FluidAudio #1141 (not for production)
|
| 2 |
+
|
| 3 |
+
https://github.com/FluidInference/FluidAudio/issues/1141
|
| 4 |
+
|
| 5 |
+
On M2-generation Neural Engines, the compiler refuses the shipped multilingual encoders. The trigger is the conv-cache
|
| 6 |
+
update in each Conformer layer, `concat(cache_time[l], x)[:, :, T:T+8]`, and Core ML then runs the whole encoder on the CPU.
|
| 7 |
+
|
| 8 |
+
Each model here is the shipped `.mlmodelc` from `main` with only those slices rewritten. Each slice of the concat becomes
|
| 9 |
+
a slice of the concat's inputs: `x[:, :, T-8:T]` for 1120/2240 ms, and `concat(cache[:, :, 7:], x)` for 560 ms.
|
| 10 |
+
`weight.bin` is byte-identical to `main`. `patch_mlmodelc.py` is the script that made them
|
| 11 |
+
(`python3 patch_mlmodelc.py <shipped.mlmodelc> <out.mlmodelc>`).
|
| 12 |
+
|
| 13 |
+
| Path | Replaces |
|
| 14 |
+
|---|---|
|
| 15 |
+
| `multilingual/560ms/encoder.mlmodelc` | `multilingual/560ms/encoder.mlmodelc` (24 slices) |
|
| 16 |
+
| `multilingual/1120ms/encoder.mlmodelc` | `multilingual/1120ms/encoder.mlmodelc` (24 slices) |
|
| 17 |
+
| `multilingual/2240ms/encoder.mlmodelc` | `multilingual/2240ms/encoder.mlmodelc` (24 slices) |
|
| 18 |
+
| `encoder-split/2240ms/encoder_body_0_11.mlmodelc` | same path on `main` (12 slices) |
|
| 19 |
+
| `encoder-split/2240ms/encoder_body_12_23.mlmodelc` | same path on `main` (12 slices) |
|
| 20 |
+
|
| 21 |
+
The split front end has no such slice; use `encoder-split/2240ms/encoder_frontend.mlmodelc` from `main`.
|
| 22 |
+
Inputs, outputs and the rest of each tier folder (preprocessor, decoder, joint, tokenizer, metadata) are unchanged.
|
| 23 |
+
|
| 24 |
+
Checked on M5 Pro, macOS 27.0, over 86 s of FLEURS en+es streamed with the caches fed back:
|
| 25 |
+
|
| 26 |
+
- Outputs are byte-identical to `main` on both `.cpuAndNeuralEngine` and `.cpuOnly`, for all tiers and the split chain.
|
| 27 |
+
- Latency: 560 ms goes from 8.1 to 8.5 ms per step (one extra concat per layer); 1120 ms, 2240 ms and the split are unchanged.
|
| 28 |
+
- Load and memory footprint are unchanged.
|
| 29 |
+
|
| 30 |
+
The Neural Engine compile has not been checked on M1, M2 or M3 yet. That is what these builds are for.
|
test-1141/encoder-split/2240ms/encoder_body_0_11.mlmodelc/analytics/coremldata.bin
ADDED
|
@@ -0,0 +1,3 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
version https://git-lfs.github.com/spec/v1
|
| 2 |
+
oid sha256:c6a9212467d1fead00b74855bcbea0a197eead90e7f4100816c04aaad69e9c11
|
| 3 |
+
size 243
|
test-1141/encoder-split/2240ms/encoder_body_0_11.mlmodelc/coremldata.bin
ADDED
|
@@ -0,0 +1,3 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
version https://git-lfs.github.com/spec/v1
|
| 2 |
+
oid sha256:780807c03fe6b8f858e6d20450e5ca411a85d4b4ddd57be32a2d52ff1948711c
|
| 3 |
+
size 651
|
test-1141/encoder-split/2240ms/encoder_body_0_11.mlmodelc/metadata.json
ADDED
|
@@ -0,0 +1,147 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
[
|
| 2 |
+
{
|
| 3 |
+
"metadataOutputVersion" : "3.0",
|
| 4 |
+
"shortDescription" : "Nemotron-3.5 ASR streaming multilingual 2240ms encoder [body_0_11], LAYERPOS [42,13]",
|
| 5 |
+
"outputSchema" : [
|
| 6 |
+
{
|
| 7 |
+
"hasShapeFlexibility" : "0",
|
| 8 |
+
"isOptional" : "0",
|
| 9 |
+
"dataType" : "Float32",
|
| 10 |
+
"formattedType" : "MultiArray (Float32 1 × 28 × 1024)",
|
| 11 |
+
"shortDescription" : "",
|
| 12 |
+
"shape" : "[1, 28, 1024]",
|
| 13 |
+
"name" : "hidden",
|
| 14 |
+
"type" : "MultiArray"
|
| 15 |
+
},
|
| 16 |
+
{
|
| 17 |
+
"hasShapeFlexibility" : "0",
|
| 18 |
+
"isOptional" : "0",
|
| 19 |
+
"dataType" : "Float32",
|
| 20 |
+
"formattedType" : "MultiArray (Float32 1 × 12 × 42 × 1024)",
|
| 21 |
+
"shortDescription" : "",
|
| 22 |
+
"shape" : "[1, 12, 42, 1024]",
|
| 23 |
+
"name" : "cache_channel_out",
|
| 24 |
+
"type" : "MultiArray"
|
| 25 |
+
},
|
| 26 |
+
{
|
| 27 |
+
"hasShapeFlexibility" : "0",
|
| 28 |
+
"isOptional" : "0",
|
| 29 |
+
"dataType" : "Float32",
|
| 30 |
+
"formattedType" : "MultiArray (Float32 1 × 12 × 1024 × 8)",
|
| 31 |
+
"shortDescription" : "",
|
| 32 |
+
"shape" : "[1, 12, 1024, 8]",
|
| 33 |
+
"name" : "cache_time_out",
|
| 34 |
+
"type" : "MultiArray"
|
| 35 |
+
}
|
| 36 |
+
],
|
| 37 |
+
"storagePrecision" : "Mixed (Float16, Int8, Palettized (6 bits))",
|
| 38 |
+
"modelParameters" : [
|
| 39 |
+
|
| 40 |
+
],
|
| 41 |
+
"specificationVersion" : 8,
|
| 42 |
+
"mlProgramOperationTypeHistogram" : {
|
| 43 |
+
"Ios17.reshape" : 72,
|
| 44 |
+
"Ios17.logicalAnd" : 3,
|
| 45 |
+
"Ios16.softmax" : 12,
|
| 46 |
+
"Ios17.matmul" : 36,
|
| 47 |
+
"Ios17.transpose" : 113,
|
| 48 |
+
"Split" : 12,
|
| 49 |
+
"Select" : 36,
|
| 50 |
+
"Ios17.expandDims" : 5,
|
| 51 |
+
"Ios17.add" : 86,
|
| 52 |
+
"Tile" : 1,
|
| 53 |
+
"Ios17.sliceByIndex" : 74,
|
| 54 |
+
"Ios16.sigmoid" : 12,
|
| 55 |
+
"Pad" : 12,
|
| 56 |
+
"Ios17.logicalNot" : 2,
|
| 57 |
+
"Ios17.layerNorm" : 72,
|
| 58 |
+
"Ios16.constexprAffineDequantize" : 69,
|
| 59 |
+
"Ios17.less" : 1,
|
| 60 |
+
"Ios17.cast" : 6,
|
| 61 |
+
"Ios16.silu" : 36,
|
| 62 |
+
"Ios17.conv" : 36,
|
| 63 |
+
"Ios16.constexprLutToDense" : 75,
|
| 64 |
+
"Ios17.linear" : 96,
|
| 65 |
+
"Ios17.concat" : 36,
|
| 66 |
+
"Ios17.greaterEqual" : 1,
|
| 67 |
+
"Stack" : 2,
|
| 68 |
+
"Ios17.mul" : 49
|
| 69 |
+
},
|
| 70 |
+
"computePrecision" : "Mixed (Float16, Float32, Int32)",
|
| 71 |
+
"isUpdatable" : "0",
|
| 72 |
+
"stateSchema" : [
|
| 73 |
+
|
| 74 |
+
],
|
| 75 |
+
"availability" : {
|
| 76 |
+
"macOS" : "14.0",
|
| 77 |
+
"tvOS" : "17.0",
|
| 78 |
+
"visionOS" : "1.0",
|
| 79 |
+
"watchOS" : "10.0",
|
| 80 |
+
"iOS" : "17.0",
|
| 81 |
+
"macCatalyst" : "17.0"
|
| 82 |
+
},
|
| 83 |
+
"modelType" : {
|
| 84 |
+
"name" : "MLModelType_mlProgram"
|
| 85 |
+
},
|
| 86 |
+
"inputSchema" : [
|
| 87 |
+
{
|
| 88 |
+
"hasShapeFlexibility" : "0",
|
| 89 |
+
"isOptional" : "0",
|
| 90 |
+
"dataType" : "Float32",
|
| 91 |
+
"formattedType" : "MultiArray (Float32 1 × 28 × 1024)",
|
| 92 |
+
"shortDescription" : "",
|
| 93 |
+
"shape" : "[1, 28, 1024]",
|
| 94 |
+
"name" : "pre_encoded",
|
| 95 |
+
"type" : "MultiArray"
|
| 96 |
+
},
|
| 97 |
+
{
|
| 98 |
+
"hasShapeFlexibility" : "0",
|
| 99 |
+
"isOptional" : "0",
|
| 100 |
+
"dataType" : "Int32",
|
| 101 |
+
"formattedType" : "MultiArray (Int32 1)",
|
| 102 |
+
"shortDescription" : "",
|
| 103 |
+
"shape" : "[1]",
|
| 104 |
+
"name" : "pre_encoded_length",
|
| 105 |
+
"type" : "MultiArray"
|
| 106 |
+
},
|
| 107 |
+
{
|
| 108 |
+
"hasShapeFlexibility" : "0",
|
| 109 |
+
"isOptional" : "0",
|
| 110 |
+
"dataType" : "Float32",
|
| 111 |
+
"formattedType" : "MultiArray (Float32 1 × 12 × 42 × 1024)",
|
| 112 |
+
"shortDescription" : "",
|
| 113 |
+
"shape" : "[1, 12, 42, 1024]",
|
| 114 |
+
"name" : "cache_channel",
|
| 115 |
+
"type" : "MultiArray"
|
| 116 |
+
},
|
| 117 |
+
{
|
| 118 |
+
"hasShapeFlexibility" : "0",
|
| 119 |
+
"isOptional" : "0",
|
| 120 |
+
"dataType" : "Float32",
|
| 121 |
+
"formattedType" : "MultiArray (Float32 1 × 12 × 1024 × 8)",
|
| 122 |
+
"shortDescription" : "",
|
| 123 |
+
"shape" : "[1, 12, 1024, 8]",
|
| 124 |
+
"name" : "cache_time",
|
| 125 |
+
"type" : "MultiArray"
|
| 126 |
+
},
|
| 127 |
+
{
|
| 128 |
+
"hasShapeFlexibility" : "0",
|
| 129 |
+
"isOptional" : "0",
|
| 130 |
+
"dataType" : "Int32",
|
| 131 |
+
"formattedType" : "MultiArray (Int32 1)",
|
| 132 |
+
"shortDescription" : "",
|
| 133 |
+
"shape" : "[1]",
|
| 134 |
+
"name" : "cache_len",
|
| 135 |
+
"type" : "MultiArray"
|
| 136 |
+
}
|
| 137 |
+
],
|
| 138 |
+
"userDefinedMetadata" : {
|
| 139 |
+
"com.github.apple.coremltools.conversion_date" : "2026-11-08",
|
| 140 |
+
"com.github.apple.coremltools.source" : "torch==2.7.0",
|
| 141 |
+
"com.github.apple.coremltools.version" : "9.0",
|
| 142 |
+
"com.github.apple.coremltools.source_dialect" : "TorchScript"
|
| 143 |
+
},
|
| 144 |
+
"generatedClassName" : "body_0_11",
|
| 145 |
+
"method" : "predict"
|
| 146 |
+
}
|
| 147 |
+
]
|
test-1141/encoder-split/2240ms/encoder_body_0_11.mlmodelc/model.mil
ADDED
|
The diff for this file is too large to render.
See raw diff
|
|
|
test-1141/encoder-split/2240ms/encoder_body_0_11.mlmodelc/weights/weight.bin
ADDED
|
@@ -0,0 +1,3 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
version https://git-lfs.github.com/spec/v1
|
| 2 |
+
oid sha256:48d03ce9838198de9d7929f9cfac6bee7206b7b868dbd6538a1632352d90d4c2
|
| 3 |
+
size 242596992
|
test-1141/encoder-split/2240ms/encoder_body_12_23.mlmodelc/analytics/coremldata.bin
ADDED
|
@@ -0,0 +1,3 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
version https://git-lfs.github.com/spec/v1
|
| 2 |
+
oid sha256:4573c654d466a4a77343d78b389a45e084a83f448f33936a3501d2ac7046fea4
|
| 3 |
+
size 243
|
test-1141/encoder-split/2240ms/encoder_body_12_23.mlmodelc/coremldata.bin
ADDED
|
@@ -0,0 +1,3 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
version https://git-lfs.github.com/spec/v1
|
| 2 |
+
oid sha256:e6bc3f11214d1c2d912180b3050071952e10a2784934ae9804c7efd9568e8d5b
|
| 3 |
+
size 729
|
test-1141/encoder-split/2240ms/encoder_body_12_23.mlmodelc/metadata.json
ADDED
|
@@ -0,0 +1,181 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
[
|
| 2 |
+
{
|
| 3 |
+
"metadataOutputVersion" : "3.0",
|
| 4 |
+
"shortDescription" : "Nemotron-3.5 ASR streaming multilingual 2240ms encoder [body_12_23], LAYERPOS [42,13]",
|
| 5 |
+
"outputSchema" : [
|
| 6 |
+
{
|
| 7 |
+
"hasShapeFlexibility" : "0",
|
| 8 |
+
"isOptional" : "0",
|
| 9 |
+
"dataType" : "Float32",
|
| 10 |
+
"formattedType" : "MultiArray (Float32 1 × 1024 × 28)",
|
| 11 |
+
"shortDescription" : "",
|
| 12 |
+
"shape" : "[1, 1024, 28]",
|
| 13 |
+
"name" : "encoded",
|
| 14 |
+
"type" : "MultiArray"
|
| 15 |
+
},
|
| 16 |
+
{
|
| 17 |
+
"hasShapeFlexibility" : "0",
|
| 18 |
+
"isOptional" : "0",
|
| 19 |
+
"dataType" : "Int32",
|
| 20 |
+
"formattedType" : "MultiArray (Int32 1)",
|
| 21 |
+
"shortDescription" : "",
|
| 22 |
+
"shape" : "[1]",
|
| 23 |
+
"name" : "encoded_length",
|
| 24 |
+
"type" : "MultiArray"
|
| 25 |
+
},
|
| 26 |
+
{
|
| 27 |
+
"hasShapeFlexibility" : "0",
|
| 28 |
+
"isOptional" : "0",
|
| 29 |
+
"dataType" : "Float32",
|
| 30 |
+
"formattedType" : "MultiArray (Float32 1 × 12 × 42 × 1024)",
|
| 31 |
+
"shortDescription" : "",
|
| 32 |
+
"shape" : "[1, 12, 42, 1024]",
|
| 33 |
+
"name" : "cache_channel_out",
|
| 34 |
+
"type" : "MultiArray"
|
| 35 |
+
},
|
| 36 |
+
{
|
| 37 |
+
"hasShapeFlexibility" : "0",
|
| 38 |
+
"isOptional" : "0",
|
| 39 |
+
"dataType" : "Float32",
|
| 40 |
+
"formattedType" : "MultiArray (Float32 1 × 12 × 1024 × 8)",
|
| 41 |
+
"shortDescription" : "",
|
| 42 |
+
"shape" : "[1, 12, 1024, 8]",
|
| 43 |
+
"name" : "cache_time_out",
|
| 44 |
+
"type" : "MultiArray"
|
| 45 |
+
},
|
| 46 |
+
{
|
| 47 |
+
"hasShapeFlexibility" : "0",
|
| 48 |
+
"isOptional" : "0",
|
| 49 |
+
"dataType" : "Int32",
|
| 50 |
+
"formattedType" : "MultiArray (Int32 1)",
|
| 51 |
+
"shortDescription" : "",
|
| 52 |
+
"shape" : "[1]",
|
| 53 |
+
"name" : "cache_len_out",
|
| 54 |
+
"type" : "MultiArray"
|
| 55 |
+
}
|
| 56 |
+
],
|
| 57 |
+
"storagePrecision" : "Mixed (Float16, Int8, Palettized (6 bits))",
|
| 58 |
+
"modelParameters" : [
|
| 59 |
+
|
| 60 |
+
],
|
| 61 |
+
"specificationVersion" : 8,
|
| 62 |
+
"mlProgramOperationTypeHistogram" : {
|
| 63 |
+
"Ios17.reshape" : 72,
|
| 64 |
+
"Ios17.logicalAnd" : 3,
|
| 65 |
+
"Ios16.softmax" : 12,
|
| 66 |
+
"Identity" : 1,
|
| 67 |
+
"Ios17.matmul" : 36,
|
| 68 |
+
"Ios17.transpose" : 114,
|
| 69 |
+
"Split" : 12,
|
| 70 |
+
"Ios17.expandDims" : 6,
|
| 71 |
+
"Select" : 39,
|
| 72 |
+
"Ios17.add" : 90,
|
| 73 |
+
"Tile" : 2,
|
| 74 |
+
"Ios17.sliceByIndex" : 74,
|
| 75 |
+
"Ios16.sigmoid" : 12,
|
| 76 |
+
"Pad" : 12,
|
| 77 |
+
"Ios17.logicalNot" : 2,
|
| 78 |
+
"Ios17.gather" : 1,
|
| 79 |
+
"Ios17.layerNorm" : 72,
|
| 80 |
+
"Ios16.constexprAffineDequantize" : 72,
|
| 81 |
+
"Ios17.less" : 1,
|
| 82 |
+
"Ios17.cast" : 12,
|
| 83 |
+
"Ios16.constexprLutToDense" : 53,
|
| 84 |
+
"Ios16.silu" : 36,
|
| 85 |
+
"Ios17.conv" : 36,
|
| 86 |
+
"Ios17.linear" : 98,
|
| 87 |
+
"Ios17.concat" : 37,
|
| 88 |
+
"Ios17.greaterEqual" : 4,
|
| 89 |
+
"Stack" : 2,
|
| 90 |
+
"Ios17.clip" : 1,
|
| 91 |
+
"Ios16.relu" : 1,
|
| 92 |
+
"Ios17.mul" : 49
|
| 93 |
+
},
|
| 94 |
+
"computePrecision" : "Mixed (Float16, Float32, Int16, Int32)",
|
| 95 |
+
"isUpdatable" : "0",
|
| 96 |
+
"stateSchema" : [
|
| 97 |
+
|
| 98 |
+
],
|
| 99 |
+
"availability" : {
|
| 100 |
+
"macOS" : "14.0",
|
| 101 |
+
"tvOS" : "17.0",
|
| 102 |
+
"visionOS" : "1.0",
|
| 103 |
+
"watchOS" : "10.0",
|
| 104 |
+
"iOS" : "17.0",
|
| 105 |
+
"macCatalyst" : "17.0"
|
| 106 |
+
},
|
| 107 |
+
"modelType" : {
|
| 108 |
+
"name" : "MLModelType_mlProgram"
|
| 109 |
+
},
|
| 110 |
+
"inputSchema" : [
|
| 111 |
+
{
|
| 112 |
+
"hasShapeFlexibility" : "0",
|
| 113 |
+
"isOptional" : "0",
|
| 114 |
+
"dataType" : "Float32",
|
| 115 |
+
"formattedType" : "MultiArray (Float32 1 × 28 × 1024)",
|
| 116 |
+
"shortDescription" : "",
|
| 117 |
+
"shape" : "[1, 28, 1024]",
|
| 118 |
+
"name" : "hidden",
|
| 119 |
+
"type" : "MultiArray"
|
| 120 |
+
},
|
| 121 |
+
{
|
| 122 |
+
"hasShapeFlexibility" : "0",
|
| 123 |
+
"isOptional" : "0",
|
| 124 |
+
"dataType" : "Int32",
|
| 125 |
+
"formattedType" : "MultiArray (Int32 1)",
|
| 126 |
+
"shortDescription" : "",
|
| 127 |
+
"shape" : "[1]",
|
| 128 |
+
"name" : "pre_encoded_length",
|
| 129 |
+
"type" : "MultiArray"
|
| 130 |
+
},
|
| 131 |
+
{
|
| 132 |
+
"hasShapeFlexibility" : "0",
|
| 133 |
+
"isOptional" : "0",
|
| 134 |
+
"dataType" : "Float32",
|
| 135 |
+
"formattedType" : "MultiArray (Float32 1 × 12 × 42 × 1024)",
|
| 136 |
+
"shortDescription" : "",
|
| 137 |
+
"shape" : "[1, 12, 42, 1024]",
|
| 138 |
+
"name" : "cache_channel",
|
| 139 |
+
"type" : "MultiArray"
|
| 140 |
+
},
|
| 141 |
+
{
|
| 142 |
+
"hasShapeFlexibility" : "0",
|
| 143 |
+
"isOptional" : "0",
|
| 144 |
+
"dataType" : "Float32",
|
| 145 |
+
"formattedType" : "MultiArray (Float32 1 × 12 × 1024 × 8)",
|
| 146 |
+
"shortDescription" : "",
|
| 147 |
+
"shape" : "[1, 12, 1024, 8]",
|
| 148 |
+
"name" : "cache_time",
|
| 149 |
+
"type" : "MultiArray"
|
| 150 |
+
},
|
| 151 |
+
{
|
| 152 |
+
"hasShapeFlexibility" : "0",
|
| 153 |
+
"isOptional" : "0",
|
| 154 |
+
"dataType" : "Int32",
|
| 155 |
+
"formattedType" : "MultiArray (Int32 1)",
|
| 156 |
+
"shortDescription" : "",
|
| 157 |
+
"shape" : "[1]",
|
| 158 |
+
"name" : "cache_len",
|
| 159 |
+
"type" : "MultiArray"
|
| 160 |
+
},
|
| 161 |
+
{
|
| 162 |
+
"hasShapeFlexibility" : "0",
|
| 163 |
+
"isOptional" : "0",
|
| 164 |
+
"dataType" : "Int32",
|
| 165 |
+
"formattedType" : "MultiArray (Int32 1)",
|
| 166 |
+
"shortDescription" : "",
|
| 167 |
+
"shape" : "[1]",
|
| 168 |
+
"name" : "prompt_id",
|
| 169 |
+
"type" : "MultiArray"
|
| 170 |
+
}
|
| 171 |
+
],
|
| 172 |
+
"userDefinedMetadata" : {
|
| 173 |
+
"com.github.apple.coremltools.conversion_date" : "2026-11-08",
|
| 174 |
+
"com.github.apple.coremltools.source" : "torch==2.7.0",
|
| 175 |
+
"com.github.apple.coremltools.version" : "9.0",
|
| 176 |
+
"com.github.apple.coremltools.source_dialect" : "TorchScript"
|
| 177 |
+
},
|
| 178 |
+
"generatedClassName" : "body_12_23",
|
| 179 |
+
"method" : "predict"
|
| 180 |
+
}
|
| 181 |
+
]
|
test-1141/encoder-split/2240ms/encoder_body_12_23.mlmodelc/model.mil
ADDED
|
The diff for this file is too large to render.
See raw diff
|
|
|
test-1141/encoder-split/2240ms/encoder_body_12_23.mlmodelc/weights/weight.bin
ADDED
|
@@ -0,0 +1,3 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
version https://git-lfs.github.com/spec/v1
|
| 2 |
+
oid sha256:ab6283745c243e083a532b4ea960986747c23cafaa2d8ac7b750adb6e4070ba5
|
| 3 |
+
size 318141952
|
test-1141/multilingual/1120ms/encoder.mlmodelc/analytics/coremldata.bin
ADDED
|
@@ -0,0 +1,3 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
version https://git-lfs.github.com/spec/v1
|
| 2 |
+
oid sha256:5488ed81fa1e370dd5411218d9b0e0562d01ca33c45b9ea1935bab6c8e8dc943
|
| 3 |
+
size 243
|
test-1141/multilingual/1120ms/encoder.mlmodelc/coremldata.bin
ADDED
|
@@ -0,0 +1,3 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
version https://git-lfs.github.com/spec/v1
|
| 2 |
+
oid sha256:93d7f1b6412b965b379f3359e38f9c4330099b5b41f9d30b85bf7286b098a78d
|
| 3 |
+
size 572
|
test-1141/multilingual/1120ms/encoder.mlmodelc/model.mil
ADDED
|
The diff for this file is too large to render.
See raw diff
|
|
|
test-1141/multilingual/1120ms/encoder.mlmodelc/weights/weight.bin
ADDED
|
@@ -0,0 +1,3 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
version https://git-lfs.github.com/spec/v1
|
| 2 |
+
oid sha256:e3dbd37659c7ef51d2dc691afac42fbdd1f04998fa62816ff0f2eebec5cc3d01
|
| 3 |
+
size 564646848
|
test-1141/multilingual/2240ms/encoder.mlmodelc/analytics/coremldata.bin
ADDED
|
@@ -0,0 +1,3 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
version https://git-lfs.github.com/spec/v1
|
| 2 |
+
oid sha256:af569fd95237bdf8b91d38094691bfc990fcf3534316fa615bac5964c02809e4
|
| 3 |
+
size 243
|
test-1141/multilingual/2240ms/encoder.mlmodelc/coremldata.bin
ADDED
|
@@ -0,0 +1,3 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
version https://git-lfs.github.com/spec/v1
|
| 2 |
+
oid sha256:d5471a4edf55ce02dab51e5d01c86b419a7659bcdd6aac216ba6f0b795eae8bf
|
| 3 |
+
size 573
|
test-1141/multilingual/2240ms/encoder.mlmodelc/model.mil
ADDED
|
The diff for this file is too large to render.
See raw diff
|
|
|
test-1141/multilingual/2240ms/encoder.mlmodelc/weights/weight.bin
ADDED
|
@@ -0,0 +1,3 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
version https://git-lfs.github.com/spec/v1
|
| 2 |
+
oid sha256:2e00be98049a22e095452c020f183d2b23728e145cc814ba031436931b4f2e8f
|
| 3 |
+
size 565336640
|
test-1141/multilingual/560ms/encoder.mlmodelc/analytics/coremldata.bin
ADDED
|
@@ -0,0 +1,3 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
version https://git-lfs.github.com/spec/v1
|
| 2 |
+
oid sha256:3409887ed9eadc8689bd4c64754d95e4119152dc0b9ee1650664d2a6a689c783
|
| 3 |
+
size 243
|
test-1141/multilingual/560ms/encoder.mlmodelc/coremldata.bin
ADDED
|
@@ -0,0 +1,3 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
version https://git-lfs.github.com/spec/v1
|
| 2 |
+
oid sha256:269d7188428298be3d0b2803c0e42bf6d44f7b4a9371030ae690beac443afbfa
|
| 3 |
+
size 572
|
test-1141/multilingual/560ms/encoder.mlmodelc/model.mil
ADDED
|
The diff for this file is too large to render.
See raw diff
|
|
|
test-1141/multilingual/560ms/encoder.mlmodelc/weights/weight.bin
ADDED
|
@@ -0,0 +1,3 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
version https://git-lfs.github.com/spec/v1
|
| 2 |
+
oid sha256:0e994440ed6c936ac375d375eaab16eb445881ff2d9bc62384de991b411e234e
|
| 3 |
+
size 564307200
|
test-1141/patch_mlmodelc.py
ADDED
|
@@ -0,0 +1,116 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
#!/usr/bin/env python3
|
| 2 |
+
"""FluidAudio #1141 path 2b: apply the uncut-concat rewrite to a compiled .mlmodelc's model.mil text.
|
| 3 |
+
|
| 4 |
+
python3 patch_mlmodelc.py <src.mlmodelc> <dst.mlmodelc> [--dry-run]
|
| 5 |
+
Same rewrite as the reporter's uncut_concat.py (slice of a concat -> concat of slices of its inputs), but
|
| 6 |
+
on the shipped compiled model, so it needs no .mlpackage and no coremltools. The weights are hard-linked,
|
| 7 |
+
not rewritten. Only slices along the concat's axis, with unit stride and no squeeze, are touched.
|
| 8 |
+
"""
|
| 9 |
+
import os
|
| 10 |
+
import re
|
| 11 |
+
import shutil
|
| 12 |
+
import sys
|
| 13 |
+
from pathlib import Path
|
| 14 |
+
|
| 15 |
+
LINE = re.compile(r"^(\s*)tensor<(\w+), \[([^\]]*)\]> (\w+) = (\w+)\((.*)\)\[name = tensor<string, \[\]>\(\"([^\"]*)\"\)\];$")
|
| 16 |
+
CONST = re.compile(r"^\s*tensor<\w+, \[[^\]]*\]> (\w+) = const\(\)")
|
| 17 |
+
VAL = re.compile(r"val = tensor<\w+, \[[^\]]*\]>\((.*)\)\]")
|
| 18 |
+
|
| 19 |
+
|
| 20 |
+
def ints(s):
|
| 21 |
+
return [int(v) for v in s.strip("[]").split(", ")] if s.strip("[]") else []
|
| 22 |
+
|
| 23 |
+
|
| 24 |
+
def patch(text):
|
| 25 |
+
lines = text.split("\n")
|
| 26 |
+
defs, consts = {}, {}
|
| 27 |
+
for i, l in enumerate(lines):
|
| 28 |
+
if (c := CONST.match(l)) and (v := VAL.search(l)):
|
| 29 |
+
consts[c[1]] = v[1]
|
| 30 |
+
continue
|
| 31 |
+
m = LINE.match(l)
|
| 32 |
+
if not m:
|
| 33 |
+
continue
|
| 34 |
+
ind, dt, shp, var, op, args, name = m.groups()
|
| 35 |
+
defs[var] = dict(i=i, ind=ind, dt=dt, shape=ints(shp), op=op, args=dict(re.findall(r"(\w+) = (\([^)]*\)|\w+)", args)),
|
| 36 |
+
name=name)
|
| 37 |
+
out_lines, n = {}, 0
|
| 38 |
+
for var, d in defs.items():
|
| 39 |
+
if d["op"] != "slice_by_index" or defs.get(d["args"].get("x"), {}).get("op") != "concat":
|
| 40 |
+
continue
|
| 41 |
+
a, cat = d["args"], defs[d["args"]["x"]]
|
| 42 |
+
if "stride" in a and set(consts.get(a["stride"], "?").strip("[]").split(", ")) != {"1"}:
|
| 43 |
+
continue
|
| 44 |
+
if "squeeze_mask" in a and "true" in consts.get(a["squeeze_mask"], "true"):
|
| 45 |
+
continue
|
| 46 |
+
if consts.get(cat["args"]["interleave"]) != "false":
|
| 47 |
+
continue
|
| 48 |
+
rank, ishape = len(cat["shape"]), cat["shape"]
|
| 49 |
+
axis = int(consts[cat["args"]["axis"]]) % rank
|
| 50 |
+
begin, end = ints(consts[a["begin"]]), ints(consts[a["end"]])
|
| 51 |
+
bm = consts.get(a.get("begin_mask"), "[" + ", ".join(["false"] * rank) + "]").strip("[]").split(", ")
|
| 52 |
+
em = consts.get(a.get("end_mask"), "[" + ", ".join(["false"] * rank) + "]").strip("[]").split(", ")
|
| 53 |
+
span, ok = None, True
|
| 54 |
+
for k in range(rank):
|
| 55 |
+
b = 0 if bm[k] == "true" else min(max(begin[k] + ishape[k] * (begin[k] < 0), 0), ishape[k])
|
| 56 |
+
e = ishape[k] if em[k] == "true" else min(max(end[k] + ishape[k] * (end[k] < 0), 0), ishape[k])
|
| 57 |
+
if k == axis:
|
| 58 |
+
span = (b, e)
|
| 59 |
+
elif (b, e) != (0, ishape[k]):
|
| 60 |
+
ok = False
|
| 61 |
+
if not ok or span[0] >= span[1]:
|
| 62 |
+
continue
|
| 63 |
+
lo, hi = span
|
| 64 |
+
parts, at = [], 0
|
| 65 |
+
for v in cat["args"]["values"].strip("()").split(", "):
|
| 66 |
+
w = defs[v]["shape"][axis]
|
| 67 |
+
s, z = max(lo, at), min(hi, at + w)
|
| 68 |
+
if s < z:
|
| 69 |
+
parts.append((v, s - at, z - at, w))
|
| 70 |
+
at += w
|
| 71 |
+
ind, dt = d["ind"], d["dt"]
|
| 72 |
+
new, pieces = [], []
|
| 73 |
+
for j, (v, s, z, w) in enumerate(parts):
|
| 74 |
+
if (s, z) == (0, w):
|
| 75 |
+
pieces.append(v)
|
| 76 |
+
continue
|
| 77 |
+
vs = defs[v]["shape"]
|
| 78 |
+
b = [0] * rank; e = list(vs); b[axis], e[axis] = s, z
|
| 79 |
+
pv, shp = f"{var}_uncut{j}", list(vs); shp[axis] = z - s
|
| 80 |
+
new += [f'{ind}tensor<int32, [{rank}]> {pv}_begin = const()[name = tensor<string, []>("{pv}_begin"), val = tensor<int32, [{rank}]>([{", ".join(map(str, b))}])];',
|
| 81 |
+
f'{ind}tensor<int32, [{rank}]> {pv}_end = const()[name = tensor<string, []>("{pv}_end"), val = tensor<int32, [{rank}]>([{", ".join(map(str, e))}])];',
|
| 82 |
+
f'{ind}tensor<{dt}, [{", ".join(map(str, shp))}]> {pv} = slice_by_index(begin = {pv}_begin, end = {pv}_end, x = {v})[name = tensor<string, []>("{pv}")];']
|
| 83 |
+
pieces.append(pv)
|
| 84 |
+
oshape = ", ".join(map(str, d["shape"]))
|
| 85 |
+
if len(pieces) == 1 and pieces[0].startswith(f"{var}_uncut"):
|
| 86 |
+
# rename the single slice to the original var/name
|
| 87 |
+
new[-1] = new[-1].replace(f"> {pieces[0]} = ", f"> {var} = ").replace(f'("{pieces[0]}")]', f'("{d["name"]}")]')
|
| 88 |
+
elif len(pieces) == 1:
|
| 89 |
+
new.append(f'{ind}tensor<{dt}, [{oshape}]> {var} = identity(x = {pieces[0]})[name = tensor<string, []>("{d["name"]}")];')
|
| 90 |
+
else:
|
| 91 |
+
new.append(f'{ind}tensor<{dt}, [{oshape}]> {var} = concat(axis = {cat["args"]["axis"]}, interleave = {cat["args"]["interleave"]}, '
|
| 92 |
+
f'values = ({", ".join(pieces)}))[name = tensor<string, []>("{d["name"]}")];')
|
| 93 |
+
out_lines[d["i"]] = new
|
| 94 |
+
n += 1
|
| 95 |
+
print(f" {var} = {cat['args']['values']}{ishape} [{lo}:{hi}] axis {axis} -> {', '.join(f'{v}[{s}:{z}]' for v, s, z, _ in parts)}")
|
| 96 |
+
res = []
|
| 97 |
+
for i, l in enumerate(lines):
|
| 98 |
+
res.extend(out_lines.get(i, [l]))
|
| 99 |
+
return "\n".join(res), n
|
| 100 |
+
|
| 101 |
+
|
| 102 |
+
def main():
|
| 103 |
+
src, dst = Path(sys.argv[1]), Path(sys.argv[2])
|
| 104 |
+
text, n = patch((src / "model.mil").read_text())
|
| 105 |
+
print(f"{n} slices rewritten")
|
| 106 |
+
if "--dry-run" in sys.argv:
|
| 107 |
+
return
|
| 108 |
+
if dst.exists():
|
| 109 |
+
shutil.rmtree(dst)
|
| 110 |
+
shutil.copytree(src, dst, copy_function=os.link) # hard links: weights untouched
|
| 111 |
+
(dst / "model.mil").unlink()
|
| 112 |
+
(dst / "model.mil").write_text(text)
|
| 113 |
+
|
| 114 |
+
|
| 115 |
+
if __name__ == "__main__":
|
| 116 |
+
main()
|