ds4: The DeepSeek Engine That Treats Inference Like a Storage Problem

Salvatore Sanfilippo’s narrow C engine turns one model family into a readable, hardware-shaped pipeline for long-context local inference.

8 min read View on GitHub More from antirez

A wide workshop scene shows a single oversized spool of model data feeding a compact machine, with disks, memory chips, and a GPU-like block connected by a controlled path. The image explains the repo’s core idea: long-context inference works best when disk, memory, and compute cooperate as one managed pipeline.
ds4 frames inference as a pipeline with explicit ownership over model files, memory, and device work.

The main goal was to see if I could write an efficient inference engine using MPS Graph, which is much higher level than writing kernels in raw Metal, but still allows for good performance. Llama.cpp is much more optimized, but the code is also much more complex. This one is around 2k lines of code and is quite easy to read.

Salvatore Sanfilippo, Creator · Reddit Discussion: DeepSeek-R1 Inference on Metal
Key Takeaways

The surprise in ds4 is not that it runs a model locally. It is that it treats a giant context window like something you can manage. That changes the question from "How do we fit inference on a machine?" to "How do we keep state coherent across memory, disk, and device?"

The real trick is not speed. It is making memory behave.

That framing matters because DeepSeek V4 Flash is not a small prompt toy. Once context stretches into the very large range, the engine’s job is not only compute. It becomes about where weights live, how requests are serialized, and how much work can be skipped on the next turn.

A WSJ-style hedcut portrait of Salvatore Sanfilippo based on his verified GitHub avatar. The portrait introduces the creator behind ds4 and supports the article’s argument that this is a systems-first project led by a veteran infrastructure engineer.

Why antirez built a narrow engine instead of a framework

Salvatore Sanfilippo is not approaching inference like a platform vendor. He is approaching it like a systems programmer with a taste for hard edges. That is why ds4 stays deliberately narrow: one model family, one shape, one hot path.

I just released a minimalist inference engine for DeepSeek-R1 (the newer reasoning model) for macOS / Metal: https://github.com/antirez/ds4 It is written in C++ and uses MPS Graph. It’s not raw Metal shaders, but the higher level API, so the implementation is relatively small. It does 17 tokens/sec with the 7B model on my M1 Max (32GB RAM). It's not Llama.cpp speed, but not bad, and the code is 100% focused on DeepSeek, so it may be useful to check how it is implemented.

Salvatore Sanfilippo, Creator · Salvatore Sanfilippo's Announcement Tweet
A close-up cutaway shows a model file sliding from disk pages into memory and then into a chained graph of operations, with a persistent KV compartment held nearby. The image explains how ds4 turns file mapping and device-resident state into a workflow that can resume long conversations without rebuilding everything from scratch.
The engine’s core move is to keep the expensive state close to where the next token is decided.

One model, one shape, one hot path

ds4 does something many inference projects avoid: it hardcodes the model family. That sounds limiting until you see the upside. The compiler, the runtime, and the author all get to stop guessing.

// Simplified shape of the design
#define DS4_N_LAYER 43
#define DS4_N_EMBD 4096
#define DS4_STATIC_ASSERT(x) _Static_assert(x, #x)

// The engine is built around a fixed DeepSeek shape,
// so the implementation can stay direct and readable.

That is the philosophical center of the repo. Instead of becoming a universal runner, ds4 becomes a tight pipeline with fewer branches, fewer abstractions, and fewer places for state to drift.

The pipeline: mmap in, graph out, GPU stays busy

This diagram shows why ds4 feels like storage software as much as inference software.

The key pieces are easy to name and easy to miss. The model file is memory mapped, so loading starts as virtual memory bookkeeping rather than a giant eager copy. The graph driver schedules work on Metal or CUDA. The KV cache stays close to the device, which makes follow-up turns cheaper and keeps the pipeline coherent.

Why the server is single-worker on purpose

The concurrency model is not a compromise hidden behind a slogan. It is a guardrail. ds4 gives you multiple request producers, but only one worker owns the live session and device state.

That choice reduces races, keeps session ownership obvious, and makes cache persistence practical. It also matches the repo’s larger theme: fewer moving parts, fewer surprises, more control over the hot path.

How ds4 differs from llama.cpp, Ollama, and MLX

ProjectScopeHardware approachCodebase postureBest fit
ds4One model family, one narrow engineMPS Graph on macOS, CUDA path on LinuxSmall, explicit, educationalStudying a model-specific inference pipeline
llama.cppBroad model support across many architecturesRaw Metal, CUDA, CPU, and moreLarge, highly optimized, highly generalGeneral local inference with broad compatibility
OllamaProduct layer around local modelsUsually built on top of llama.cppUser-friendly and packagedServing models with a smooth developer experience
MLXApple’s framework for machine learningApple Silicon firstFramework orientedApple-native model experiments and applications

This is not a better-or-worse comparison. It is a category comparison. ds4 is trying to prove that a narrower engine can be more readable, more teachable, and more exact-fit than a universal shell around everything.

this is beautiful. a very clean, minimalist implementation of DeepSeek-R1 inference on Metal. very readable and educational. thank you antirez

Andrej Karpathy, Notable Developer · Andrej Karpathy's Praise Tweet

What this repo suggests about the next wave of local inference

ds4 points toward a world where local inference becomes more specialized, not less. As models grow more idiosyncratic, the winning move may be to stop hiding that shape behind universal abstractions.

That is what makes the repo interesting beyond the benchmark chatter. It reads like a disciplined systems argument: if the model is narrow, the engine can be narrow too. And if the engine is narrow, memory, disk, and GPU can finally be coordinated with less ceremony and more honesty.