Qwen3.8-27B의 가중치가 아침에 도착했고, 같은 날 나는 Kimi K3를 고사고 모드에서 실행하며 모험을 시작했다. 나는 단일 질문으로 전체를 시작했다: 이 새로운 밀집 27B — 그 크기 클래스에서 가장 강력한 공개 모델일 수 있는 — 가 Mac Studio에서 M1 Ultra, 20 CPU 코어, 128 GB 통합 메모리, 그리고 800 GB/s 메모? 일반적인 지식은 조밀한 모델이 Apple 실리콘에서 느리게 디코딩된다고 말하지만, 이만큼의 RAM과 대역폭이 패턴을 깨뜨릴 수 있는지 알아보고 싶었습니다. 4-비트 MLX 가중치는 15 GB였고, 프레임워크는 최신이었으며, 박스에서 다른 것은 실행되지 않았고, 첫 번째 숫자는 12.1 토큰/초였습니다. 잘못된 것처럼 느껴졌습니다.
나는 이 종류의 실험을 한동안 돌려왔습니다. 3월에, 자율 정제 실험실에서 다른 AI와 함께 작업하면서, 우리는 M4 Max에서 30B 모델의 20 토크/초 이하 벽을 OS 수준 페이징으로 인한 대역폭 부족으로 추적했고, 그 조사 결과는 플레이북을 남겼습니다: powermetrics 먼저, 클러스터별 샘플링, 책임을 묻기 전에 메모리 고정. 이번 실행은 순수한 호기심에서 시작되었습니다: 나는 Qwen3.8의 최적화에 대해 들었고, 이 기계에서 이만큼의 RAM으로 바로 빠르게 실행될지 알고 싶었습니다. 실험 중반에 대역폭 제한 현실이 스스로를 느끼게 했습니다. 그 뒤에는 우리가 함께 설계한 통제된 실험의 스프린트가 이어졌습니다 — Kimi가 가설을 작성하고 내 옆에서 하드웨어 카운터를 읽었으며, 나는 금속에 손을 얹었습니다. 각 실험은 스택의 한 층을 무죄 또는 유죄로 판결하도록 설계되었습니다. 승리는 2 장소에서 온 것이었습니다. 로컬 추론 전설이 과소평가하는 곳: CPU 스케줄러 힌트와 투기적 디코딩. 2 유행하는 대안 — llama.cpp에서 제공되는 GGUF 빌드와 종이에서 무적처럼 보이는 전문가 혼합 모델 — 두 가지 모두 측정에서 실패했습니다. 이 기사에는 우리가 함께 구축한 전체 증거 트레일이 있습니다. 방법이 어떤 단일 숫자보다 더 가치가 있다는 것이 밝혀졌기 때문입니다.

네트워크 릴레이와 서버가 첫 번째 용의자였고, 둘 다 무죄였다

서빙 경로는 3개의 홉이 있었다: 내 워크스테이션, SSH 기반 실행 릴레이, 그리고 Studio의 루프백에 있는 모델 서버. 릴레이를 비난하는 것은 쉬웠겠지만, 우리는 먼저 그것을 측정했다. 서버 자체의 타이밍은 12.1 토크/초 디코드를 보여 주었고, 서버와 릴레이 없이 순수 인-프로세스 생성 벤치마크는 11.5 토크/초를 생성했다. 전송은 연결당 오버헤드로 약 25%를 비용으로 들었고, 모델 자체가 느린 계층이었다.
한 가지 전송 버그는 어쨌든 고쳐야 할 가치가 있었고, 그것은 한 번도 본 적이 없는 경우 몇 시간을 비용으로 드는 세부 사항의 종류이다: 버퍼링된 read(65536)를 사용하는 Python TCP 릴레이는 채팅이 많은 로컬 프로토콜에 대해 교착 상태가 된다, 왜냐하면 버퍼링된 리더가 전체 버퍼 또는 EOF를 기다렸다가 반환하기 때문이다. 단일 기본 읽기 후 반환하는 read1()으로 전환하면 릴레이가 동작했다. 증상은 네트워크 정지처럼 보였고, 원인은 stdio 의미론이었다.
전송이 정정되었으므로 우리는 일반적인 sysctl 계층을 통해 작업했다. GPU 배선 메모리 한계(iogpu.wired_limit_mb)를 올려도 128 GB의 RAM이 남아 있었으므로 아무것도 바뀌지 않았고, 우리는 그것을 되돌렸다. Python 프로세스는 네이티브 arm64였고, MLX는 GPU를 기본 장치로 보고, powermetrics은 디코드 중에 20-23 W를 소비하며 54-62% 활성 점유율을 보이는 GPU를 보여 주었다. 이 라운드의 모든 용의자는 자유롭게 걸어 나갔다 — 이는 자체적으로 유용한 결과였다, 왜냐하면 그것이 조사 대상이 CPU임을 가리켰기 때문이다

스케줄러는 효율성 코어에 추론을 주차했다

기계당이 아니라 CPU 클러스터당 powermetrics를 읽음으로써 첫 번째 실제 발견이 드러났다. 디코드 중에 효율성 클러스터는 75-93% 가득 차 있었고, 성능 클러스터는 1-12%에서 유휴 상태였다. SSH 이상으로 실행되는 모든 것은 macOS가 낮은 우선순위 작업으로 읽는 서비스 품질 클래스를 상속하며, 스케줄러는 그 힌트를 존중해 지연 민감한 워크로드를 느린 코어에 유지했다.
수정은 모델 가중치를 로드하기 전에 실행되는 1 줄의 ctypes였다:
python
import ctypes
ctypes.CDLL("libSystem.B.dylib").pthread_set_qos_class_self_np(0x21, 0) # QOS_CLASS_USER_INTERACTIVE
그 핀과 mlx-lm를 통해 모델의 텍스트 타워를 전체 비전 스택 대신 로드함으로써 원시 디코드는 11.5에서 15.1 토크/초로 이동했다 — 스케줄러 배치와 가벼운 로더로 인한 31% 향상이며 모델에는 전혀 변형이 없었다. 나중에 우리는 핀의 범위에 한계가 있다는 것을 알았다: 그것은 호출 스레드를 이동시키고, MLX의 워커 스레드는 자체 스케줄링 클래스를 유지한다. 이 모델에서는 메인 스레드가 충분한 작업을 수행해 의미가 있었다.

가정적 디코딩은 sysctl이 할 수 없는 점프를 제공했습니다

가장 큰 단일 승리는 기본 모델이 이미 보유하고 있던 기능에서 나왔습니다. Qwen3.8는 다중 토큰 예측 헤드를 제공하며 — 앞서 몇 개의 토큰을 초안하는 작은 보조 모듈 — MLX 변환기는 변환 중에 그 15 텐서를 조용히 버립니다. 커뮤니티 패키지는 헤드를 독립 실행형 253 MB 초안기로 다시 호스팅하며, 이는 제가 모델과 함께 훈련된 것과 다시 연결할 수 있게 했습니다.
서비스 패턴은 초안-후-검증이며, 초안기는 몇 개의 토큰을 제안하고 전체 모델은 1 패스에서 이를 확인하며, 수락된 토큰은 모두 계산됩니다. 서버에서 --draft-model 및 --draft-kind mtp를 사용하면 초안 수락률이 현실적인 코딩 및 채팅 프롬프트에서 94%를 기록했고, 디코드는 15.1에서 20.3 토크/초로 서버 측에서 향상되었으며, 릴레이를 통해 13.4 토크/초가 되었고, 이는 9.0에서 상승한 수치입니다. GPU는 확인된 이야기를 전했습니다: 77% 활성 점유율, 전부가 전체 1296 MHz에서, 48 W를 소비하며, 성능 클러스터 97%가 가득 차 있었습니다. 프리필은 같은 업그레이드에서 개선되었으며, 14.7 토크/초에서 18-55로 프롬프트 모양에 따라 달라집니다.
Decode speed by configuration (tok/s, M1 Ultra, 27B-4bit)
Chart data
tokens per second
MLX stackllama.cpp Q4_K_M
raw stack11.59.2
+ text tower13.6
+ QoS pin15.1
+ MTP drafter20.312.2

GGUF 도전자는 40%에 의해 패배했습니다

커뮤니티 게시물은 llama.cpp가 이 모델 클래스에서 M1 Ultra에서 25-32 토크/초의 추측 초안을 제공한다고 했으며, 이는 우리의 MLX 숫자보다 편안하게 앞서 있습니다. 그래서 우리는 도전자에게 공정한 기회를 주었습니다: 공식 Q4_K_M GGUF, 일치하는 MTP 전용 초안 모델, 그리고 Metal 가속이 활성화된 현재 llama.cpp 빌드를 확인했습니다. GGUF 레인은 9.2 토크/초 기준선과 초안이 있는 12.2를 측정했으며 — 약 40% MLX 스택 뒤에 있었던 것처럼, 그것이 전복하려는 대상이었습니다.
llama.cpp는 여전히 훌륭한 엔지니어링입니다; 차이는 각 런타임의 Metal 커널이 이 체크포인트를 이 칩에서 어떻게 처리하는지에 있을 가능성이 큽니다. 지속 가능한 교훈은 더 간단합니다: 다른 사람이 자신의 기계, 빌드 및 체크포인트에서 측정한 숫자는 당신의 것에 대한 가설일 뿐입니다. 18 GB의 도전자 가중치는 같은 오후에 기계를 떠났고, 50 MB llama.cpp 바이너리는 향후 재전투를 위해 남아 있었습니다. 나는 이전에 이 규칙에 대해 benchmark-driven development — 그것은 SEOReport from heuristics to a product — 에 대해 썼으며, 여기서 그것은 마이그레이션을 구했습니다.

3B-활성 MoE는 승리해야 했으며, GPU 미터는 손실을 설명했다

마지막 도전자는 가장 강력한 이론을 가지고 있었다 — 우리가 시작할 때 테스트하려고 했던 동일한 일반 지식. 밀집 모델은 Apple 실리콘에서 느리게 디코드된다. 생성된 모든 토큰이 거의 모든 가중치를 읽는 데 비용을 지불하기 때문이다; 35B 총 매개변수를 가진 전문가 혼합 모델은 토큰당 약 3B만 활성화하므로 대역폭이 제한된 기계에서는 밀집 27B보다 몇 배 빠르게 디코드해야 한다 — 각 토큰은 가중치의 약 11%를 읽는다. 우리는 4비트 MoE와 일치하는 MTP 초안을 다운로드하고 서버를 예열한 뒤 14.7 토크/초를 측정했다: 이는 그가 모욕해야 할 밀집 모델과 동일한 속도였다. 추측 디코딩으로 실제 프롬프트에서 19 토크/초, 매우 예측 가능한 텍스트에서 26.3를 달성했다 — 밀집 모델의 20.3와의 무승부이며, 품질 논쟁이 없어서 결점을 깨뜨릴 수 없었다.
powermetrics은 1개의 샘플에서 체제를 식별했다. MoE 디코딩 중 GPU는 0-3% 활성 점유율을 유지했고, 효율성 클러스터는 60-90%로 떨어졌다. 모델은 토큰당 예산을 CPU 측 작업에 사용하며, 운영 수준 타이밍은 이유를 보여 주었다: 각 배포된 작업은 50-100 마이크로초의 오버헤드를 비용으로 하며, 이 하이브리드 아키텍처 — GatedDeltaNet 선형 주의와 작은 2048-폭 숨겨진 상태 뒤에 256 전문가 —는 40 레이어에 걸쳐 레이어당 약 78개의 작업을 발행한다. 배치 크기 1에서 GPU는 CPU가 다음을 대기열에 넣기 전에 각 작은 커널을 완료한다. 기계는 배포에 제한되었으며, 배포에 제한된 워크로드는 토큰당 가중치가 적게 읽히는 것에서 이득을 얻지 못한다.
Diagram source
graph TB
    A[느린 디코딩  
배치 1] --> B{GPU 사용 중  
디코딩 중?}
    B -->|예| C[대역폭 제한  
바이트가 적을수록 승리]
    B -->|아니오| D[배포 제한  
작은 작업이 승리]
    C --> E[MoE는  
작은 양자화가 도움이 된다]
    D --> F[추측 디코딩  
가장 큰 도움이 된다]

    style E fill:transparent,stroke:#10B981,stroke-width:2px
    style F fill:transparent,stroke:#3B82F6,stroke-width:2px
루프를 닫기 위해 우리는 GPU 경로 자체가 건강했음을 합성 하그로 증명했다: 8192³ 행렬 곱셈 루프가 bfloat16에서 10.8 TFLOPS를 기록했고 GPU는 97-100% 점유율과 68W를 보였다. 외부 증거는 현지 진단과 일치했다 — 독립 추정치는 이 MoE 클래스를 M2 Ultra에서 약 21.7 토크/초에 놓았으며, OpenVINO 문제 문서는 동일한 모델이 약한 배포 경로를 가진 백엔드에서 밀집 8B에 패배한 것을 기록했다. 밀집된 27B와 그 MTP 드래프터는 생산 슬롯을 유지했고, 같은 저녁에 38.5 GB의 MoE 가중치가 삭제되었습니다.
GPU active residency during decode (powermetrics, %)
Chart data
GPU active residency (%)
dense 27B + MTP77
MoE 35B-A3B2
matmul hog test100

5가 통제한 실험이 남긴 것

머신은 이제 Qwen 3.8-27B를 20.3 토크/초 서버 측에서 제공하며, 이는 하루가 시작됐을 때보다 68% 향상된 것이며, 더 지속 가능한 수익은 우리가 앞으로 모든 박스에서 재사용할 체크리스트다:
  • 배치 크기 1로 디코드하면 2개의 체제, 대역폭 제한과 디스패치 제한이 있으며, 2초 powermetrics 샘플이 잘못된 수정을 다운로드하기 전에 당신의 것을 식별한다.
  • 추측 디코딩은 단일 사용자 박스에 대한 가장 높은 레버리지 제공 노브다. 여기에서 34%를 추가했고, 모든 다른 최적화와 결합된다. 검증 배치는 GPU를 작동시키고, 드래프터는 유휴 간격을 흡수한다.
  • 스케줄러 QoS는 macOS에서 실제 추론 매개변수다. SSH 이상으로 시작된 모든 것은 스레드를 의도적으로 고정해야 하며, 고정 효과는 분위기 대신 클러스터별로 검증 가능하다.
  • 커뮤니티 처리량 주장은 체크포인트, 빌드, 칩 전반에 걸쳐 잘 전달되지 않는다. 로컬 벤치마크는 마이그레이션보다 저렴하다.
  • 삭제는 워크플로의 일부다. 패배한 모든 도전자는 하루 안에 디스크를 떠났으며, 이는 다음 실험을 정직하게 유지하고 머신을 가볍게 만든다.
이 모험의 만족스러운 부분은 모든 답이 하드웨어 카운터에 있었고, 누군가가 정확한 질문을 할 때까지 기다리고 있었다는 것이며 — 이번에는 함께 물었다. 측정한 로컬 모델은 추측한 더 큰 모델보다 가치가 있다 — 로컬 AI 이득을 인프라로 취급하는 것과 같은 복리 수익을 얻는다. 나는 무게가 도착한 아침에 전체를 시작했고, Kimi K3는 모든 실험, 모든 카운터 읽기, 그리고 같은 저녁의 실험실 노트에서 이 글을 위해 싸움에 남아 있었다. 다음 실험은 이미 대기열에 있다: 컴파일된 디코드 그래프는 MoE 판결을 결정한 per-op 디스패치 비용을 축소할 것을 약속하며, MLX 릴리스가 출시되면, 재전투는 오후와 1개의 다운로드를 걸린다.