- Auf einem ESP32-S3 läuft ein Sprachmodell mit 28,9 Millionen Parametern ohne Serververbindung und gibt Text mit etwa 9 Token pro Sekunde auf einem kleinen Bildschirm aus
- Verwendet wird eine Per-Layer-Embeddings-Architektur, bei der 25 Millionen der Gesamtparameter im langsamen Flash liegen und pro Token nur etwa 6 benötigte Zeilen bzw. 450 Byte gelesen werden
- Das Modell ist in 4-Bit 14,9 MB groß; im 512KB-SRAM liegt der pro Token verwendete Rechenkern, im 8MB-PSRAM der Output-Head und der Arbeitsspeicher, im 16MB-Flash die große Embedding-Tabelle
- Mit TinyStories trainiert, erzeugt es meist konsistente kurze und einfache Geschichten, eignet sich aber nicht für Frage-Antwort, Befehlsausführung, Code-Erstellung oder Faktenwissen
- Es enthält etwa 100-mal mehr Parameter als ein zuvor auf einem ähnlichen Chip ausgeführtes Modell mit 260.000 Parametern; der Kern liegt weniger in der Generierungsqualität als in der Speicherarchitektur, die ein großes Modell auf einem kleinen Chip unterbringt
Hardware und Laufzeit
- Ein einzelner ESP32-S3 für etwa 8 Dollar übernimmt die gesamte Verarbeitung, ohne Daten an einen Server zu senden
- Verwendet werden 512KB SRAM, 8MB PSRAM und 16MB Flash
- Die Gesamtgeschwindigkeit liegt bei etwa 9,5 tok/s, die reine Rechengeschwindigkeit bei etwa 9,7 tok/s
- Die 4-Bit-Modellgröße beträgt 14,9MB
- Von insgesamt 28,9 Millionen Parametern werden 25 Millionen in einer Flash-Lookup-Tabelle gespeichert
Wie das Modell in kleinen Speicher passt
- Normalerweise muss das gesamte Modell aus schnellem Speicher zugänglich sein, doch der SRAM des ESP32-S3 umfasst nur 512KB und kann daher nur sehr kleine Modelle aufnehmen
- Genutzt wird, dass die meisten Parameter in einer Embedding-Tabelle liegen und nicht direkt berechnet werden, weshalb die Tabelle im Flash verbleibt
- Pro Token werden nur etwa 6 benötigte Zeilen bzw. rund 450 Byte gelesen
- Nur der kleine Teil, der die eigentliche Berechnung übernimmt, bleibt im schnellen Speicher
- Der Großteil des Modells wird während der Ausführung nicht geladen, sondern bei Bedarf selektiv aus dem Flash geholt
- Die Speicherrollen sind wie folgt aufgeteilt
- SRAM: Rechenkern, der bei allen Token verwendet wird
- PSRAM: Output-Head und Arbeitsspeicher
- Flash: Tabelle mit 25 Millionen Parametern
Einsatz von Per-Layer Embeddings
- Per-Layer Embeddings, wie sie in Googles Gemma 3n und Gemma 4 verwendet werden, wurden hier nicht auf Smartphones oder GPUs, sondern auf die Speicherarchitektur eines Mikrocontrollers angewendet
- Soweit der Projektautor prüfen konnte, gibt es keinen bekannten Präzedenzfall für diesen Ansatz auf einem derart kleinen Chip
Was das Modell kann und wo seine Grenzen liegen
- Trainiert auf den kurzen synthetischen Geschichten von TinyStories, erzeugt es einfache Geschichten und bleibt dabei meist konsistent
- Frage-Antwort, Befehlsausführung, Code-Erstellung und faktisches Wissen beherrscht es nicht
- Diese Grenze ergibt sich aus dem kleinen Kern, der das Schlussfolgern übernimmt; die Technik der Speicherplatzierung erhöht die Inferenzfähigkeit selbst nicht
Code und Experimentmaterial
- In
firmware/esp32_llm/README.mdfinden sich Firmware, Verkabelung und Flashing-Ablauf src/undexperiments/enthalten Code für Training, Ablationsexperimente und Quantisierung- In
RESULTS.mdsind die vollständige Methode, Ablationsexperimente und On-Chip-Messwerte zusammengefasst
Basisprojekte und Verlauf
- TinyStories ist ein Datensatz aus kurzen synthetischen Geschichten, der kleinen Modellen konsistentes Schreiben beibringen soll
- Per-Layer Embeddings aus Google Gemma bilden die Grundlage dafür, große Modelle auf kleinen Chips unterzubringen
- Andrej Karpathys llama2.c prägte den Ansatz, kleine Sprachmodelle zu trainieren und in reinem C auszuführen
- Im Repository ist auch der Rechenfehler dokumentiert, der die ursprüngliche Parameterzahl aufgebläht hatte, ebenso wie dessen Korrektur
- In der Commit-Historie und in
RESULTS.mdlässt sich nachvollziehen, an welchen Stellen und aus welchen Gründen die Werte geändert wurden
- In der Commit-Historie und in
1 Kommentare
Hacker-News-Kommentare
Es ist erstaunlich, was heutzutage mit einem 5-Dollar-Mikrocontroller möglich ist. Vom Milk-V-Board habe ich das Duo gekauft; es hat bis zu 256 MB Speicher, eine 1TOPS@INT8-TPU und läuft sogar mit Linux, deshalb habe ich gleich fünf gekauft
GCC und Clang unterstützen xTHeadVector vollständig, und bei Verwendung von C-Intrinsics ist es allein über Kommandozeilenoptionen mit RVV 1.0 kompatibel. Viel Code für 8-Bit-Elemente wie
memcpy(),memset(),memcmp(),strlen(),strcpy()undstrcmp()ist binärkompatibelAls ich das 64MB-Duo gekauft habe, kostete es 3 Dollar, danach lagen die 64MB-, 256MB- und 512MB-Modelle bei 5, 7 und 10 Dollar, aber dieses Jahr sind die Preise deutlich gestiegen: https://arace.tech/products/milk-v-duo, https://arace.tech/products/milkv-duo-s
Es gibt zwar weiterhin Einsatzfälle, in denen ein 4KB-PIC das Beste ist, aber man sollte in den meisten Situationen nicht so handeln, als gäbe es keine besseren Optionen
Auch Speech-to-Text- und Text-to-Speech-Modelle nähern sich dieser Größe an, daher frage ich mich, wie nah wir an kleinen Geräten sind, die sich mit uns unterhalten können. Vielleicht kommt eine Welt, in der die Zahnbürste Tipps zur Mundhygiene gibt oder sogar Zahnpasta-Werbung macht
Aber ich möchte nicht in einer Welt leben, in der man sogar einen Adblocker für Zahnbürsten-KI braucht
Die schichtweise Embedding-Technik wurde sehr clever eingesetzt. Es gibt auch praktische TTS-Modelle mit etwa 20 bis 30 Millionen Parametern, daher könnte ein nicht vernetzter ESP32 Texte fast in Echtzeit vorlesen
PSRAM, Flash und SD-Karten haben jeweils keine hohe Einzelbandbreite, aber wenn viele gleichzeitig laufen, kann man einen beachtlichen Durchsatz erreichen. Große spezialisierte Hardware wäre bei Performance pro Watt überlegen, aber wegen der niedrigen Anfangskosten und schrittweisen Skalierbarkeit ist so eine Konfiguration trotzdem attraktiv
Mich würde interessieren, welche realistische Alternative es zum lokalen LLM auf dem Raspberry Pi 4 gibt, damit Antworten nicht jeweils 30 Sekunden brauchen
Es ist zwar cool, ein LLM auf einem winzigen Gerät laufen zu lassen, aber noch beeindruckender ist die Trainingsmethode, die diese Gewichte hervorgebracht hat
Wenn man Flash mit guten Zugriffsmustern nutzt, frage ich mich, ob sich das nicht auf deutlich größere Modelle auf der CPU ausweiten ließe
Der ESP32-S3 ist ziemlich leistungsfähig, so sehr, dass ich ihn aktuell für Entwicklungsarbeit für den Raspberry Pi 4 nutze. Einer der beiden USB-Ports unterstützt OTG, sodass sich Funktionen umsetzen lassen, die sonst über 100 Dollar kosten würden
Derzeit läuft das mit tinyusb und pico-pio-usb, und ich experimentiere auch mit einer Portierung nach Rust in der Hoffnung auf höhere Leistung
Ich frage mich, wie gut die Genauigkeit dieses quantisierten Modells ist
Die Leistung bei dieser Größe ist erstaunlich, und ich bin gespannt, was auf den etwas leistungsfähigeren Single-Board-Computern aus dem Thread alles möglich sein wird