Show HN: Getting GLM 5.2 running on my slow computer

814 points - yesterday at 8:05 AM


A few days ago I found myself trying out GLM 5.2 and was really positively impressed. The capabilities and security I was getting from this LLM are similar to those I've gotten from models like Claude or GPT, and this really surprised me.

But then I thought, "I wonder how it would work on a normal computer like mine," and above all, "I wonder if it would work without going into OOM on a computer like mine." So I started working with the help of agents to test this possibility.

I started converting the model to int4, understanding MTP usage, and if possible implementing DSA for long context. How it responds in int4 and whether the quality is maintained or not. Until I got to the point, on my computer with 32GB of RAM, I was able to communicate with GLM 5.2 with times that, of course, aren't high in cold start, but even then, we're talking about 0.1 tok/s, but that wasn't important to me. The important thing was the journey to reach this goal. I just wanted it to work at all costs, even slowly.

So I created Colibrì, which was born from a very simple idea, to be honest, but tested in every way, where a 744B Mixture-of-Experts model activates only ~40B parameters per token—and only ~11 GB of those change from token to token (the routed experts). So:

The dense part (attention, shared experts, embeddings—~17B params) stays resident in RAM at int4 (~9.9 GB); The 21,504 routed experts (75 MoE layers × 256 experts + the MTP head, ~19 MB each at int4) live on disk (~370 GB) and are streamed on demand, with a per-layer LRU cache, an optional pinned hot-store, and the OS page cache as a free L2.

The engine is a single C file (c/glm.c, ~1,300 lines) plus small headers. No BLAS, no Python at runtime, no GPU.No GPU or serious hardware because I don't have that hardware so I can't test it on hardware that is more powerful than my computer.Colibrì is a one-person project, written and tested entirely on a 12-core laptop with 25 GB of RAM — the numbers above are the ceiling of what I can measure at home.

Any feedback is welcome! (and if anyone wanted to participate in the project I would be delighted)

Repo: https://github.com/JustVugg/colibri

Source

Comments

lopatin today at 9:38 AM
After spending way too much time with Fable a few days ago, I noticed a new hallmark of AI generated text is using the word "honest" everywhere, in a somewhat self congratulating way.

Some things that give it away to me:

- "Honest numbers (WSL2, 12 cores, 25 GB RAM, NVMe via VHDX)"

- "an honest peak projection (working set, KV, MTP row, reconstruction buffers) so the kernel OOM-killer never fires."

- "Honest caveat from the same measurement: ..."

It's the new "It's not X, it's Y". I have no issue with this, I just found it amusing.

Cool project btw!

walrus01 yesterday at 9:03 PM
My main question is whether when put into practical use, this can be measured in tokens/second, or more like 1 token per minute... I have seen locally hosted LLM that are as slow as 1 tok/second still be very useful if you give it a project to do something overnight and metaphorically walk away from it, check back with what it has done in 6 or 8 hours.

0.05 to 0.1 tok/s on the other hand, as reported in the URL for the lowest class of hardware, isn't really usable for much.

edit: I think this is a fantastic project in general concept, and look forward to seeing more efforts towards the general idea of being able to run a 350B to 900B size model locally, even if as slow as 1 tok/s, on hardware that ordinary people can afford. Anything along the general concept of "we have fast read NVME SSD storage, we have a big ass model on local disk, we'll read it at 11GB/tok as we need it, not try to load the whole thing".

Archit3ch yesterday at 10:44 PM
Working on something similar targeting macOS on Apple Silicon, Unsloth split GGUF, compressed partial residency in unified memory (would make more sense on 128GB instead of my 64GB...), native Metal kernels, and RAM-only native compressed KV. Happy to put on GitHub when it's ready.
harrouet today at 6:01 AM
This is exactly the kind of technology that I expect Apple to ship anytime soon given the RAM prices and their HW/SW integration skills:

- ship super fast SSD (tbh they are already top notch)

- add a specific cache layer for tokens

- keep the amount of unified memory reasonable

Cieric yesterday at 9:44 PM
I was actually just working on the same thing as this, but I went down the route of mmapping the entire model into memory to avoid the extra ram usage. I also had Claude implement Medusa[1] on the model to try and avoid loading an additional model into memory but still get the benefits of MTP. Currently at a stop light so I can't list everything and I didn't get to read your full post either yet.

To expand since I just got home, I'm making all of my modifications to llama.cpp, the goal was to eventually put this on a SBC of some kind with an nvme to handle the mmapped files. I think the theoretical limit of my current setup is about 1.8 tok/s based on prior testing but that is also with the additional medusa heads not fully trained (I honestly don't know if the counting it's generated tokens or not.)

In the end it seems like the idea we had is similar, I just don't know how to write an llm parser/runner from scratch yet and instead of specifying what needed to stay in memory I just let the linux kernel handle it.

Oh last note, I also capped llama.cpp usage to 16GB of my 32GB, so it might be possible to get it down even lower.

[1] https://arxiv.org/abs/2401.10774

ac29 today at 3:18 AM
llama.cpp supports a wide variety of 4-bit and smaller quants and mmap's models by default, so you dont need to be able to hold the weights in memory (the OS will handle bringing them in from storage as needed)

Its cool to see this implemented in a tiny amount of code without dependencies, but does it actually bring more performance?

kodablah yesterday at 9:46 PM
I've taken a similar strategy w/ image/video gen at https://github.com/cretz/thinfer (see video branch for a ton of work).

Basically I kept needing an inference engine that could stream weights in and out as needed in an LRU manner. So I ended up vibe coding this thing that accepts a `--vram-budget` and stays under it (mostly). It turns out moving mmap'd bytes in and out of VRAM is way cheap compared to compute. Coupled with some pipelining/double-buffering, I almost always end up compute bound not memory bound. Granted I use way smaller models heh.

rullopat today at 9:12 AM
Looking at the progress with DS4 project from Antirez and Colibri, are we probably going in the direction of having a stripe RAID of SSDs instead of RAM to get decent performance without losing a kidney to the RAM mafia? I really hope so.
shrinks99 yesterday at 9:10 PM
Pretty cool! I've also been playing around with GLM 5.2 this week and was equally impressed. At work we're running it locally on some crazy expensive hardware as a test before starting another project so it's great to see people taking this massive FOSS model release and running it on an average machine, even if it's not terribly practical at this point.

Nice work!

tarpitt yesterday at 10:28 PM
I am curious if it's possible to adjust this to use more RAM, as i've got a machine with 64GB RAM and 24GB VRAM. Or perhaps I could run Gemma/Qwen on the GPU and have GLM-5.2 delegate smaller tasks to it. It might take some retraining of GLM-5.2

I'm also curious if you can speed this up by using many disks in parallel to increase bandwidth.

>SSD Wear Warning

> Cold starts are heavy on random reads (~11 GB/token). Reads themselves are safe, but the OS page cache can generate writes. Heavy use may accelerate wear on cheaper SSDs. Use with caution and monitor your drive health.

Hmm, maybe a safe way to do this would be to make a separate partition for the model weights, and set them to read-only? Not sure how the page cache works, if it's like per partition or per disk. If it's per disk, maybe you could have a read-only data.iso formatted as a partition and mount it as a disk?

timedude today at 3:26 PM
Impressive work. Also it must be said that the Apple M5 is incredible.
miohtama yesterday at 8:49 PM
This is the hacker spirit
voidmain0001 yesterday at 10:41 PM
The page has an SSD wear warning [0] I use desktop PCs that I build from components so I can replace the SSD, but what do users with soldered SSD do? Just avoid these applications or forge ahead disregarding the possible early burnout of their storage? They must use external storage as the burner SSD.

[0] https://github.com/JustVugg/colibri#ssd-wear-warning

AymanB today at 9:24 AM
I believe you could use some sort of GPU-direct (or BAM-like approach, see https://dl.acm.org/doi/10.1145/3575693.3575748) to stream weights on-demand from the GPU.
Roxxik today at 8:06 AM
I have prototyped something similar with ollama some months ago.

Do you mmap or issue reads on demand? Also do you use io_uring to interleave compute with io or do you spawn extra threads?

I also tried predicting which experts get reused and I managed to beat a simple LRU very slightly.

EDIT: That was on Kimi 2.5 but even worse quant than 4bit. IIRC it was 2.6 or so

maxignol today at 9:21 AM
I’m truly impressed by your work ! I don’t know if this is planned for near future, but how about adding energy efficiency benchmarks ? Because running locally is a great feeling, but the electricity bill should not be forgotten
xtracto yesterday at 11:26 PM
This is something that would benefit from Intel Optane memory. Too bad it was killed at the time.
AussieWog93 today at 8:29 AM
Well under 1tps, but the fact it runs at all on a 16gb system is incredibly impressive!
barent today at 1:06 AM
The best ideas are the ones that seem obvious. This is one of those ideas.
ballislife30 today at 3:39 PM
What's the cost
qiqitori yesterday at 11:54 PM
How much time is spent interfacing between userland and the kernel? Can you try to get it to run as a kernel module? :)

Also in case your CPU is old enough, did you try disabling CPU bug mitigations?

pianopatrick today at 3:57 AM
I'm curious but don't know much about the internals of LLMs - could you use a similar architecture with other models that have "layers"? I mean, could you have one layer do its work, then remove that layer from RAM, load the next layer from disk, and have that layer activate on the result of the first layer?
webprofusion today at 9:28 AM
This is great stuff, I feel like fast disk (SSD) is a somewhat solvable problem, if you have many disks with the same content and a fast controller (?).
mmastrac yesterday at 11:31 PM
This sort of thing is a lot of fun.

I've been going smaller.. I have a custom-quantized Rust port of DiffusionGemma (26B) that seems to perform better (in responses) than benchmarks seemed to indicate and reasonably fast for its model size. Works really well on a 36GB mac as well for both prefill and generation.

It's been interesting learning about the balance of factors for performant metal kernels on unified memory.

Should have a repo up on github in the next few weeks.

bobim yesterday at 9:27 PM
I'm not fully understanding this business of MoE so please forgive me if this is a dumb question, but would it be possible to use MPI with a small cluster to distribute the load?
SubiculumCode today at 1:14 AM
Excuse my ignorance. Could one just say, "One expert is all I can handle" and strip the others from the model?
_joel today at 10:10 AM
I've got a 48GB M5 - What's the best I can run on that atm (with a bit of headroom).
valentynkit today at 11:46 AM
You've basically build an LRU page cache with readahead for streaming 21, 504 experts off disk. Some problem OS people have solved for mmap'd databases for decades, just with parameters instead of rows.
sakesun yesterday at 11:34 PM
I just learned about Gemma4.pas at the beginning of this week. Now this. This make me wonder how can inference engines could be built that easy. I'm not knowledgeable in this, but I thought it would take very deep Mathematic and system level knowledge, ... and a lot of patience.
tannertech yesterday at 11:05 PM
I love it but where do you find that NVMe SSD for less than the price of an h100 fan let alone the memory
mariopt yesterday at 9:02 PM
I wonder if you could replicate this in a Colourful GeForce RTX 50-series GPU, they ship it with 2 NVMe drive slots.
tw1984 today at 6:03 AM
“answering correctly on a machine that costs less than one H100 fan”

really love such comparison.

khalic yesterday at 9:13 PM
I love seeing that kind of tinkering
deleted yesterday at 9:27 PM
nogajun today at 12:13 AM
Is this similar to fastllm?

https://github.com/ztxz16/fastllm

jhalloran today at 3:17 AM
Nice, looks good. This would mesh really well with the unified system memory on apple silicon
jnaina today at 1:12 AM
was lucky enough to snag the Olares One from Kickstarter just before this whole AI induced memory chip price gouging started.

specs are Intel Core Ultra 9 275HX (24 Cores, 5.4GHz),96GB of DDR5 5600MHz RAM, NVIDIA GeForce RTX 5090 Mobile GPU with 24GB of GDDR7 VRAM, 2TB NVMe PCIe 4.0 SSD.

going to see if I can wring at least 5 tok/s.

flockonus today at 12:07 AM
Curious for what an MTP only result would look like, both in terms of output quality & tk/s ?!
barent today at 1:01 AM
Yeah this idea makes instant sense. Very well done, this deserves a github star on concept alone.
classified today at 2:03 PM
So when I clone that repo, am I downloading > 370 GiB, or when and how is that being pulled in?

And can I leave out the web part? I cannot in good conscience run npm on my machine (it's not even installed).

3abiton today at 4:37 AM
This is technically impressive, but is it usable in practice?
xtracto yesterday at 11:28 PM
I wonder how would a RAID0 array of either disks or even nvme improve the performance of this.
vehbiemiroglu today at 6:57 AM
So, could larger models work this way too?
xfalcox yesterday at 9:08 PM
Question to the OP, have you tested this on a machine where the entire model and context fit in RAM ?
nerder92 yesterday at 8:55 PM
Is this inspired by antirez work on ds4?

Amazing job!

Datagenerator yesterday at 10:19 PM
Great job, it's unique!
kzrdude yesterday at 9:05 PM
Your coding style is halfway to IOCCC. I'm just jealous though :)
efficax today at 11:18 AM
Tried this out on my ThreadRipper:

AMD Ryzen Threadripper PRO 5975WX — 32 cores / 64 threads, Zen3 (znver3), AVX2+FMA (no AVX-512/VNNI), 128GB RAM, Kingston SKC3000D 4TB NVMe (PCIe4). Disk gets around 7GB/s. It took a little tuning (for example pinning to 32 physical cores instead of the 64 threads), but with that and --topp 0.7, got 0.44 tok/s on a cold start. That's way below the estimates in the README, which I assume are pure AI slop (LLMs love to estimate incorrectly. They're far worse than even naive humans at it), but it's pretty cool for a model this size. I sent Fable off to wrap this in an OpenAI API to see how it works when driven by an agent harness.

EDIT: it finally finished the first non test prompt i gave it, which with local LLMs is usually "what is the meaning of life?" (who knows, maybe one of them will finally answer). It got stuck in a loop, which is not encouraging, so there's a lot of work to do to make this a viable local coding tool:

> The meaning of life is one of the oldest and greatest questions in human history, yet strangely, there is no single, universally agreed-upon answer. Because "meaning" is a human concept, it doesn't exist out there in the universe; it is something we create for ourselves. The answer depends entirely on the framework through which you view the question. Here are the most common ways to answer it. The meaning of life is the meaning you give to it. We are all in the same position: humanity's search for it never ends in "to be determined" or "to be announced" (TBA, the answer is unknown, and it is a great mystery, or perhaps even the answer "forty-two" (42) is the "Answer to the Ultimate Question of Life, the Universe, and Everything" in The Hitchhiker's Guide to the Galaxy by Douglas Adams (where the number 42 is the "Answer" in Python's language, but we don't know the "Ultimate Question"). Here is a joke that works under the frame of "A..." (any answer): "A clean desk is a..." (42 is a "portmanteau" of words and just a great big "Ad..." (Ad-100) and "A&d" (100)). Life is a deep and strange and we search for meaning in it. "I think, therefore,..." (Cogito, ergo, sum) is the only valid idea in philosophy [3] (cf., "I think, therefore, I am," is a valid translation of "I think, therefore, am" (in the original Latin, "Cogito, ergo, sum" is "I think, therefore, I am")). So, the meaning of life is a bit like "a riddle, wrapped in a mystery, inside a [riddle]..." (G. K. Chesterton) and inside a [block of] "42" (or the number of dimensions, which is the "Answer to Life, the Universe, and Everything" in the "H2G2" (H2G2 is the "Ultimate Question of Life, the universe, and everything")). The "H2G2" is a "puzzle, wrapped in a mystery, inside an enigma" (cf. [3]). We are all in the same position, but we all have to give it a meaning. our own meaning. The meaning of life is what you make of it. The meaning of life is to live for the greater good. The meaning of life is to live in a way that is good and noble and right, and to do so well that with every breath, I think of you, I think of life, and I think of you, and I think of life, and I think of you. (cf. [3]) If life in the universe is a "great question," the answer is 42. The meaning of life is the meaning you make it. The meaning of life is to give life a meaning, and I think of you, and I think of you. So, the answer to the ultimate question of life, the universe, and everything is: 42. The meaning of life is 42. The meaning of life is the meaning of life. This is the Answer to the Ultimate Question of Life, the Universe, and Everything (or "The Answer" for short). It is the Answer to "the" Ultimate Question of Life, the Universe, and Everything. (See, for example, the Ultimate Question of Life, the Universe, and Everything.) This is the answer to the Ultimate Question. This is the Answer. (And, this is the Answer to the Ultimate question of life, universe, and everything.) The meaning of life is the meaning you give to it. The meaning of life is to give it a meaning. The meaning of life is the meaning you give it. The meaning of life is the meaning of life. The meaning of life is the meaning of life. The meaning of life is the meaning of life. (This is a list of the possible meanings of the universe of life. It's a list of the most common and accepted answers. "What is the meaning of life?" The answer is 42. The meaning of life is the meaning of life. The answer is 42.) (See also: [3] for a list of possible meanings.) The meaning of life is to give it a meaning, and the meaning of life is the meaning you give it. The meaning of life is the meaning of life. The meaning of life is the meaning of life. The meaning of life is the meaning of life. (This is the answer to the Ultimate Question of life, the universe, and everything.) (This is the answer to the Ultimate Question.) The meaning of life is 42. The meaning of life is 42. The meaning of life is 42. (See also: [3]) (The answer to the Ultimat

doodlesarefun today at 11:11 AM
is this bad for my SSD?
zftnb666 today at 12:45 PM
"Slow computer" + running a 200B model = "I'll just wait a week."
bobkb today at 12:02 PM
Would love to collaborate
Pragmata yesterday at 9:00 PM
Would this cause issues with SSD lifespan?
bahmboo yesterday at 10:42 PM
Another recent project that runs a huge model on a 48gb Mac is https://github.com/danveloper/flash-moe - it gets over 5 tokens/sec on an M3 Max compared to this projects very impressive 1 token/sec on an M5 Max. So for anyone wanting to tackle a Mac only version that targets lower spec machines this looks like a good candidate with plenty of room for speedups [edit: because it doesn't use the gpu].

Not hijacking anything as this project is amazing.

RahulRajelli today at 9:43 AM
Glm 5.2 on lobehub , i was able to finish a complete the project very quickly
stavros yesterday at 9:58 PM
This is great, well done! I love seeing people run things where they weren't meant to be run.
jdw64 today at 8:23 AM
Coool!!!
khimaros yesterday at 10:42 PM
related and possibly more general purpose https://github.com/t8/hypura
smetannik today at 12:42 AM
> slow computer > 25 GB of RAM

What?

nicogentile today at 11:38 AM
[flagged]
deleted today at 9:33 AM
abhiram304 today at 5:01 AM
[flagged]
cyberelf77 today at 10:34 AM
[flagged]
joka88xj today at 4:19 AM
[flagged]
VaporJournalAPP yesterday at 11:07 PM
[flagged]
kownse today at 6:54 AM
[flagged]
gokulrajaram today at 12:55 AM
[flagged]
redfather yesterday at 11:42 PM
[flagged]
rahulb0802 today at 1:28 AM
[dead]
cereblab today at 9:14 AM
[flagged]
threerouter today at 4:42 AM
[dead]
Purposefather today at 8:54 AM
[dead]
ankit100 today at 4:43 AM
[flagged]
ankit100 today at 4:44 AM
[dead]
deleted today at 8:41 AM