Kazeia-engine/CLAUDE.md

49 lines
4.5 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

# Kazeia-Engine
Moteur d'inférence LLM Snapdragon 8 Elite **sans conversion `.pte`** : charger
GGUF directement, NPU pour le prefill, CPU pour le decode. Mono-tablette,
local-first, sans root. Bench-driven : aucune décision sans chiffre reproductible.
## Cibles & gabarits
- **Qwen3-4B** (dense, attn pleine) — tourne déjà sous ExecuTorch : decode 14-21 tok/s, TTFT 190 ms. **Réf à approcher.**
- **Qwen3.5-4B** (hybride DDDA×8 : 24 DeltaNet + 8 FullAttn, GDN, conv1d, SSM, head_dim 256, vocab 248k, tied embeds) — ExecuTorch ne sait pas l'exporter proprement. C'est lui qu'il faut bien faire tourner. Empreinte mémoire mini = priorité.
## Verdict R&D (issu de briques + bench, ne PAS refaire l'erreur)
Sur SM8750, Qwen3.5-4B-Q4_0, **decode M=1 = memory-bandwidth bound**, pas compute. Mesures :
| Voie | Decode | Prefill | Statut |
|---|---:|---:|---|
| llama.cpp CPU NEON (`-dev none`) | **16.5 tok/s** | 75 | stable, ~67% BW |
| llama.cpp CPU+Hexagon auto | 16.5 | **159** | stable — prefill HMX |
| llama.cpp Hexagon-only | 3.6 | — | DSP seul = perdant decode |
| briques DSP-first custom | 5.3 | 26 | crash ~12min, abandonné |
**Angle = NPU prefill / CPU decode, exactement ce que fait llama.cpp+chraac.** Tout DSP-first sur decode plafonne (~5 tok/s) ; gros vocab + tied embeds bloque spec-dec. CPU NEON bat le HVX 3.4× sur Q6_K M=1. Bonus DDDA : 75% des couches O(1) → decode stable en long contexte.
## Base = llama.cpp upstream master (ne PAS forker chraac)
Upstream `ggml-org/llama.cpp` a le backend Hexagon officiel Qualcomm : `libggml-hexagon` (CPU) + HTP `libggml-htp-v79.so` (notre V79), sélection auto runtime, actif (avril 2026: Linux NPU, cumsum, argsort, op-batching). chraac = fork perso superseded. Decode CPU NEON mûr déjà là.
- ExecuTorch — référence à dépasser, pas dépendance.
- `briques-archive/` + mémoires `project_briques_qwen35*` — pièces : pièges V79 0x2e, q4x4x2/Q6_K valign, oracle ggml. À ne pas refaire DSP-first.
- HW: i8mm+bf16+dotprod, **PAS de SVE** ; LPDDR5x ~77 GB/s, CPU ~25.
## Le seul vrai trou = prefill GDN Qwen3.5 sur Hexagon
- Qwen3-4B prefill → HTP standard, flag de build, livré (159 tok/s). Qwen3.5 decode → CPU récurrent, livré. Qwen3.5 prefill: 8 FullAttn → HTP, 24 GDN → scan chunkwise, **pas de kernel HTP** (GDN fusionné = CUDA/Vulkan only). Decode toujours CPU pour les deux, verrouillé.
-`to_delete/llama.cpp` a déjà `qwen3next` + `ggml_backend_hexagon_qwen35_compile` : amorce GDN-HTP existante → BENCHER avant d'écrire un kernel.
- Charge Kazeia: prefill 500-2000 tok/tour, CPU ~75 → 7-27s, HTP → 3-13s. Utile, pas vital.
## Identité = faire tourner Qwen3.5-4B bien (tranché Richard, ambition haute)
Pas l'intégration minimale. Cible: Qwen3.5-4B near-ExecuTorch sur Pad3, mémoire mini, sans .pte. Decode=CPU verrouillé (16.5 tok/s, acquis). Bataille = prefill: pousser les 24 GDN sur HTP. Kernel GDN-HTP = sujet R&D, frontière kernel (aide assistant partielle: structure/debug, pas micro-optims bit-exactes).
1. Rebuild upstream master + ggml-hexagon, valider htp-v79 + run 3.5-4B end-to-end CPU.
2. **Bencher `qwen35_compile` HTP existant**: 0%, partiel ou OK? décide écrire-vs-finir kernel.
3. Baseline prefill GDN CPU à battre. Mémoire <4 GB Q4_0/Q6_K-embeds. Itérer kernel si gap.
Source: `/opt/Kazeia/to_delete/llama.cpp` = upstream ggerganov + ggml-hexagon + htp + qwen35_compile, commit f0fe1058b. Backend Hexagon prod: libggml-hexagon (CPU) + libggml-htp-v79 (auto). Session HTP plafond 3.5GB NDEV multi-device si >. NDK r27d, Hexagon SDK 6.5.0.0. Rebuild en cours.
## Limite assistant
R&D LLM frontière (kernels HVX bit-exacts, quant) = aide partielle, je le dis au cas par cas.
GGUF/llama.cpp archivés vers `/opt/Kazeia/to_delete`. Git local: commits réguliers. — Richard & Damien.
## Mesures 24/05 (build f0fe1058b, Pad3, Q4_0)
prefill HTP pp128=44 / decode CPU tg16=13.4 ; HTP decode=4.4, CPU prefill pp32=18.5. → split prefill-HTP/decode-CPU OK, qwen35_compile HTP fonctionne. cli boucle (76min/0tok) — bench OK. Cible: pousser prefill 44→. Staging tablette: /data/local/tmp/kz-engine.
## Verdict 24/05 (mesure honnête, pp égal)
prefill pp32/128/512: CPU 18.5/18.7/18.7 (PLAT), HTP 18.5/44/47. HTP ×2.5 reel a pp512. GDN HTP = decode-only (ggml-hexagon.cpp:2284 "n_tokens!=1 -> CPU fallback"). Prefill GDN sur CPU serie = ancre. Kernel GDN-prefill chunked HTP = le sujet B, gros gain (FA/FFN HTP pourraient ~159). cli boucle = bug runtime aval, PAS compile (bench=meme graphe). Decode tranche, prefill = chantier.