Edge Zero to otwarty silnik inferencyjny, który uruchamia model o trzydziestu pięciu miliardach parametrów na Mac mini i raportuje dwa i dziewięć dziesiątych gigabajta pamięci. Wagi nie zmalały. Cały checkpoint to dziewiętnaście i pół gigabajta, z czego osiemnaście to wagi ekspertów, które przez cały czas rozmowy leżą na S S D. Odczyt jest uczciwy, tylko mierzy co innego, niż się wydaje: to szczyt tego, co przydzielił alokator M L X, a nie to, co wydała maszyna. Cloud Codes prześwietlił nagłówki safetensors, kod źródłowy i zgłoszenia na GitHubie, żeby odpowiedzieć na dwa pytania. Dlaczego strumieniowanie wag z dysku nie zabija prędkości, i czego ta liczba nie liczy.
Projekt wyszedł ósmego września na licencji Apache dwa zero, ma dziś około tysiąca sześciuset gwiazdek. Pod spodem siedzi Quen trzy i sześć — większość omówień wciąż pisze o trzy i pięć, maintainer poprawił to dopiero rano.
Co naprawdę leży na dysku
Model typu mixture of experts tnie blok feedforward każdej warstwy na wiele małych. Ten checkpoint ma dwieście pięćdziesiąt sześć ekspertów na warstwę, czterdzieści warstw, a na token odpalają dokładnie cztery. Reszta nie robi nic i dalej trzeba ją gdzieś trzymać. Jeden wspólny ekspert na warstwę zostaje w pamięci i jest mały — czterdzieści siedem megabajtów łącznie.
Pliki safetensors publikują nagłówki osobno od wag, więc można je przeczytać po HTTP bez pobierania jednego parametru. Z nagłówków wychodzi, że blok ekspertów jednej warstwy waży czterysta pięćdziesiąt trzy megabajty. Dokumentacja strumieniowania mówi o około trzystu dziesięciu. Plik, który faktycznie pobierzesz, nie zgadza się z dokumentacją.
Rachunek za jeden token
Jeden ekspert to jeden i siedemdziesiąt siedem setnych megabajta. Cztery na warstwę, czterdzieści warstw, i pojedynczy token potrzebuje dwustu osiemdziesięciu trzech megabajtów wag, których nie ma jeszcze w pamięci. Przy piętnastu do osiemnastu tokenach na sekundę to cztery do pięciu gigabajtów na sekundę w trybie ciągłym. I nie jako jeden długi strumień, tylko jako sto sześćdziesiąt osobnych drobnych odczytów na słowo.
Dysk chętnie czyta jeden długi plik. Setki rozrzuconych odczytów, każdy z mnożeniem macierzy zawieszonym za nim, to zupełnie inne obciążenie. Sekwencyjna liczba z pudełka nie ma tu zastosowania.
Naiwna wersja tego pomysłu jest znana. W lipcu Kimi K trzy strumieniowany z dysku na M jeden Max dawał jeden token na czternaście sekund. Checkpoint był dużo większy, ale kształt problemu ten sam.
Pre-router, czyli zgadywanie o token wcześniej
Routing zależy od wyjścia poprzedniej warstwy, więc wiesz, których czterech ekspertów potrzebujesz, dokładnie w chwili, w której są potrzebne. Przy wagach w pamięci to nie problem. Przy wagach na dysku każda warstwa każdego tokenu zaczynałaby się od czekania.
Odpowiedzią jest mała wytrenowana sieć na warstwę, nazwana pre-routerem. Trzydzieści trzy takie głowice siedzą na większości stosu, każda z warstwą ukrytą o szerokości pięciuset dwunastu. Ich wagi jadą w osobnym pliku obok modelu.
Cały trik jest w kształcie zgadywania. Głowica na warstwie n nie przewiduje własnych ekspertów — przewiduje, czego będzie chciała warstwa n plus jeden. A ta warstwa korzysta z przewidywania zrobionego o cały token wcześniej. Gdy model kończy jeszcze poprzednie słowo, głowica warstwy dziewiętnastej wskazuje cztery z dwustu pięćdziesięciu sześciu ekspertów. Te cztery pakiety są wczytywane, podczas gdy arytmetyka wciąż trwa. Kiedy dochodzi do warstwy dwudziestej, eksperci już czekają.
Nic nie jest wyrzucane, a odczyt, którego się baliśmy, skończył się token temu. Autorzy wyceniają ten narzut na do pięćdziesięciu dziewięciu procent większej przepustowości dekodowania, i uczciwie zaznaczają, kiedy zysk jest większy: wolniejszy nośnik, większy model, więcej ekspertów na token.
Zgadywanie, które jest decyzją
Większość omówień nazywa to prefetchem. Pliki projektu mówią coś mocniejszego w dwóch miejscach. Dokumentacja tieru stwierdza, że routing dostarczają wytrenowane głowice pre-routera i że blok mixture of experts routuje na logitach pre-routera. Komentarz w źródłach powtarza to niemal słowo w słowo. W czasie dekodowania zgadywanie nigdy nie jest konfrontowane z prawdziwym routerem.
Co przewidziała głowica, to się wykonuje. Nazywają to zero drop by construction — zbiór, który został wczytany, jest zbiorem, który liczy. Zła predykcja nie kosztuje cię więc przestoju. Zmienia to, którzy eksperci policzyli twój token.
Dlatego ta sieć jest trenowana, a nie heurystyczna, dlatego jest flaga do jej wyłączenia, i dlatego promień rażenia widać w zgłoszeniach. Jedenastego ktoś zgłosił, że wyjścia zapadają się w ciąg wykrzykników, a każde kolejne żądanie w tym procesie kończy się tak samo. Przy wyłączonym pre-routerze problem znikał. Warstwa przepełniała się w arytmetyce szesnastobitowej, logity szły na not a number, a argmax lądował na tokenie zero. Poprawka następnego dnia.
Dwa szczegóły, których nie ma w opisie
Pierwszy leży w pliku konfiguracyjnym. Konfiguracja Quena dla modelu bazowego mówi o ośmiu ekspertach na token. Edge Zero przypina cztery. Połowa szerokości routingu, zdecydowana przez runtime, nie przez checkpoint. To właśnie ta zmiana ścina rachunek z pięciuset sześćdziesięciu sześciu megabajtów na token do dwustu osiemdziesięciu trzech. Różnica między potrzebą dziesięciu gigabajtów na sekundę a czterema. Znaczy też, że spadek jakości nie jest wyłącznie efektem kwantyzacji.
Drugi to cache. Jest jeden wspólny cache zdekodowanych ekspertów i mieści sześćdziesiąt cztery sztuki dla całego modelu, nie na warstwę. Pojedynczy krok dekodowania dotyka stu sześćdziesięciu ekspertów. Wychodzi poniżej trzech slotów na warstwę. Komentarz w ich własnym źródle mówi wprost: przy wydanej liczbie slotów zmierzono dokładnie zero trafień, przebudowując sto osiemdziesiąt cztery pakiety w każdym kroku.
Zero trafień. Cokolwiek daje tu prędkość, nie jest to cache ekspertów, który dostajesz w paczce. Nie są nim też przypięte rezydentne wagi, bo ten tier je wyłącza.
Prawdziwy silnik siedzi w systemie
Eksperci czytani są przez mapowane w pamięć zakresy bajtów, więc tym, co ich naprawdę trzyma, jest page cache systemu. Readme wprost definiuje ciepły przebieg jako sytuację, w której strony są rezydentne. To jest pamięć, której nagłówkowa liczba nie liczy. Dwa i dziewięć dziesiątych gigabajta to tyle, ile poprosił alokator, a nie tyle, ile oddaje maszyna. Ich własny kod stawia próg akceptacji na trzy i cztery dziesiąte gigabajta oraz trzynaście tokenów na sekundę.
Widać to w opublikowanym rozbiciu na zimny i ciepły start. Pierwsze żądanie po uruchomieniu procesu: sto trzynaście tokenów na sekundę na prompcie. Każde następne: sto czterdzieści. Jedna piąta wolniej raz, potem różnica znika. Mac z dwudziestoma czterema gigabajtami ma gdzie trzymać dziewiętnastogigabajtowy checkpoint w cache’u plików, więc po jednym przebiegu dysk prawie nie jest ruszany.
Teraz zabierz tę przestrzeń. Dwunastego ktoś zgłosił uruchomienie mniejszego tieru na ośmiogigabajtowym M jeden, który był już głęboko w swapie. Zmierzył około siedmiu dziesiątych tokena na sekundę. Karta modelu obiecuje dla tego tieru dwadzieścia cztery, czyli mniej więcej trzydzieści razy wolniej. Zajętość pamięci wyszła około jednego gigabajta, czyli samo offloadowanie działało dokładnie jak zaprojektowano. Zgłaszający puścił też próbę kontrolną i to ona czyni raport wiarygodnym: gęsty model o czterech miliardach parametrów przez zwykły M L X, ta sama maszyna, ta sama sesja, jedenaście i cztery dziesiąte tokena na sekundę. Z laptopem nic nie było nie tak.
Maintainer potwierdził przyczynę w wątku. Na maszynie z ciasną pamięcią dekodowanie jest ograniczone błędami stron, nie obliczeniami. Pierwsza sugestia to zmienna środowiskowa, która przed startem rozgrzewa page cache na checkpointcie. Inny wątek dokłada kolejny punkt: szesnastogigabajtowy MacBook Air strumieniujący z zewnętrznego dysku U S B, około pięciu tokenów na sekundę.
Wymaganiem nigdy nie były trzy gigabajty pamięci. To trzy gigabajty alokatora plus szybki nośnik plus tyle wolnego RAM-u, żeby zbuforować dwudziestogigabajtowy plik.
Ile kosztuje jakość
Baza czterobitowa jest zamrożona, a na wierzchu siedzi adapter LoRA wytrenowany destylacją z nauczyciela w pełnej precyzji, odzyskujący to, co zabrała kwantyzacja. Adaptery nigdy nie są wtapiane w bazę, więc jedna baza tylko do odczytu może obsłużyć kilka z nich.
Autorzy przepuścili zestaw benchmarków przeciwko modelowi bazowemu w pełnej precyzji, z identycznymi ustawieniami po obu stronach. Siedemdziesiąt dziewięć i dwie dziesiąte przeciwko osiemdziesięciu trzem i dwóm dziesiątym średnio, czyli cztery punkty. Najostrzejszy pojedynczy spadek jest na zestawie matematycznym A I M E: osiemdziesiąt sześć i sześć dziesiątych przeciwko dziewięćdziesięciu dwóm i siedmiu dziesiątym.
Jeśli opierasz się na tym modelu przy rozumowaniu, poczujesz to. Jeśli piszesz kod, w większości nie. W tę jedną cytowaną liczbę zapakowane są czterobitowe wagi, połowa szerokości routingu i przewidywany router, z adapterem odciągającym tyle, ile zdoła. Czytanie tego jako straty na kwantyzacji zaniża to, co faktycznie zmieniono.
Zastrzeżenia i werdykt
Obie strony tej tabeli policzyli sami autorzy, a przepustowości nie powtórzył dotąd nikt z zewnątrz. Działa tylko na mac O S i Apple Silicon. Obsługuje jedno żądanie naraz, a K V cache rośnie ponad nagłówkową liczbę wraz z długością kontekstu.
Głowica predykcyjna to prawdziwa inżynieria, robiąca więcej, niż sugerują omówienia — bo nie podpowiada routingu, tylko go decyduje. Dwa i dziewięć dziesiątych gigabajta to z kolei prawdziwy odczyt niewłaściwej rzeczy.
Liczba, którą trzeba sprawdzić, to nie dwa i dziewięć dziesiątych. To ile pamięci zostaje ci wolnej po wszystkim innym, bo ten wolny RAM jest cache’em wykonującym całą robotę. Na Macu z dwudziestoma czterema gigabajtami i szybkim dyskiem to używalny model o trzydziestu pięciu miliardach parametrów. Na ośmiu — nie.
Koniec artykułu.