# ggml 1.0.0: 13 APIs gone, CPU speed unchanged

> Source: <https://dev.to/frankchu/ggml-100-13-apis-gone-cpu-speed-unchanged-4n79>
> Published: 2026-11-15 01:40:44+00:00

ggml 1.0.0 deletes 13 public API functions, removes two ops, and bumps the RPC protocol to v9. I built it and its predecessor from source and benched both on CPU: text generation is identical — 19.8 tokens a second on both — and prompt processing is inside the noise everywhere I measured. The first 1.x release is a cleanup release, not a speed release, at least on a CPU-only box.

ggml 1.0.0 landed on November 13, 2026, nine days after v0.29.0. The diff between the two tags is 299 files changed, 16,891 lines added and 6,801 removed. Most of the additions are GPU backends: few-row quantized matmuls and MoE fusion on CUDA, a Vulkan prefill FlashAttention path, a device-side MoE scheduler on SYCL, decomposed Adreno FlashAttention in OpenCL, new WebGPU kernels. The headline CPU changes are smaller: MUL_MAT switched to F32 src1, FlashAttention V now accumulates in F32, and the scheduler skips uploading inputs that no op reads.

The breaking part is the API. `include/ggml.h` shrank by 276 lines (7 added). I counted 13 removed `GGML_API` declarations:

| Removed | Status | 
|---|---|
| `ggml_diag_mask_inf` ,`ggml_diag_mask_inf_inplace` | Deleted outright, with the `GGML_OP_DIAG_MASK_INF` op | 
| `ggml_diag_mask_zero` ,`ggml_diag_mask_zero_inplace` | Deleted outright, with the `GGML_OP_DIAG_MASK_ZERO` op | 
| `ggml_type_sizef` | Deleted outright | 
| `ggml_rope_yarn_corr_dims` | Deleted outright | 
| `ggml_add1` ,`ggml_add1_inplace` | Deprecated, now removed | 
| `ggml_mul_mat_set_prec` | Deprecated, now removed — replaced by `ggml_prec_set_acc` | 
| `ggml_rope_custom` ,`ggml_rope_custom_inplace` | Deprecated, now removed | 
| `ggml_upscale_ext` ,`ggml_flash_attn_ext_set_prec` | Deprecated, now removed | 

New in their place: `ggml_rope_set_truncate` / `ggml_rope_get_truncate` for YaRN correction-bound rounding, and a backward pass for the `TRI` op. The RPC protocol went to v9, and the release notes say it rejects incompatible peers — an old `llama-server` talking to a new one will fail the handshake instead of silently misbehaving.

I built llama.cpp twice from source with identical flags (`cmake -DGGML_NATIVE=ON -DCMAKE_BUILD_TYPE=Release`, GNU 13.3.0): master at commit `3de52ac` (November 4, 2026, version string `0.9.0-dev`) and master at commit `e574a17` (November 15, version string `1.0.0-dev`). Before trusting the comparison I checked that the old tree's `ggml.h` is byte-identical to the ggml v0.29.0 tag and the new tree's is byte-identical to the v1.0.0 tag. Both diffs came back empty — the bench really is 0.29.0 vs 1.0.0.

Machine: AMD EPYC 9D25, 4 vCPUs, no GPU. Model: Qwen2.5-0.5B-Instruct Q4_K_M, 491,400,032 bytes — I verified the size against Hugging Face's content-length exactly, and parsed the GGUF header myself (`general.file_type` 15, which `llama.h` defines as `MOSTLY_Q4_K_M`). llama.cpp counts 630.17M parameters, not 494M, because the file carries an untied `output.weight` alongside `token_embd.weight` — both 151,936 × 896. Each config ran through `llama-bench` at 4 threads, first in 3 repetitions, then again in 5, and I report both rounds.

Prompt processing (pp) and generation (tg), tokens per second, mean ± stddev across repetitions:

| Test | 0.29.0 (3 reps) | 1.0.0 (3 reps) | 0.29.0 (5 reps) | 1.0.0 (5 reps) | 
|---|---|---|---|---|
| pp128 | 76.90 ± 4.06 | 74.19 ± 5.48 | 77.78 ± 14.65 | 70.43 ± 21.87 | 
| pp512 | 83.71 ± 3.85 | 93.68 ± 0.90 | 87.73 ± 4.39 | 91.14 ± 10.64 | 
| tg128 | 19.45 ± 0.86 | 20.05 ± 2.23 | 19.62 ± 0.86 | 19.95 ± 5.49 | 
| tg128 (2nd config) | 20.99 ± 0.66 | 19.36 ± 3.14 | 19.30 ± 2.89 | 19.75 ± 2.86 | 

Pooled across both rounds: generation is 19.84 tok/s on 0.29.0 and 19.78 on 1.0.0 — a 0.3% difference on four measurements each, which is no difference at all. Prompt processing at 128 tokens is pure noise (pooled 77.3 vs 72.3, with standard deviations up to ±21.9). At 512 tokens the pooled means are 85.7 vs 92.4, about +7.8% — but the error bars overlap in both rounds, so I won't call it a win. If you squint, the F32 src1 change plausibly helps compute-bound prompt processing at longer contexts; generation on CPU is memory-bandwidth-bound, so nothing there was ever going to move.

On this box, 1.0.0 buys you nothing in speed and costs you 13 API functions. That's not a complaint — it's what a 1.0 is for. The deprecated functions had been deprecated for a reason, the DIAG_MASK ops were legacy, and the RPC bump is the kind of break you want to take exactly once, at a major version. The performance work in this release is real, it's just almost all on GPU backends this machine doesn't have. If you run llama.cpp on CPU, upgrade for the cleanup and the YaRN truncation controls, not for tokens per second. If you build on ggml's public API, grep for `diag_mask`, `add1`, `rope_custom`, `upscale_ext`, and `mul_mat_set_prec` before you upgrade — and if you run RPC workers, upgrade both ends together, because v9 will not talk to v8.

Caveats, stated plainly: one small model (0.5B, quantized), one 4-vCPU shared VM, 3–5 repetitions per config. A 70B model or a GPU would tell a different story about the backend work — the CUDA few-row matmul and Metal MoE fusion changes are exactly the kind of thing that shows up there and not here.

Sources: ggml v1.0.0 release notes (github.com/ggml-org/ggml/releases/tag/v1.0.0, November 13, 2026); ggml v0.29.0 tag (November 4, 2026). All bench numbers are my own runs on the machine and builds described above; the API counts are from `git diff v0.29.0 v1.0.0` on the ggml repository.
