Skip to content

Commit f10e205

Browse files
authored
Merge pull request #97 from AdaWorldAPI/claude/setup-rust-smart-home-SOPAY
Claude/setup rust smart home sopay
2 parents bbbdc34 + 0babee0 commit f10e205

2 files changed

Lines changed: 50 additions & 96 deletions

File tree

README-DE.md

Lines changed: 33 additions & 70 deletions
Original file line numberDiff line numberDiff line change
@@ -4,81 +4,56 @@ Ein vollstaendiger Hochleistungs-Numerik-Stack auf Basis von [rust-ndarray/ndarr
44

55
[English Version](README.md) | [Kompletter Feature-Vergleich (146 Module)](COMPARISON.md)
66

7-
## Warum das existiert
7+
## Cosine-Aehnlichkeit: Wir vs. GPU vs. Alle
88

9-
| Was | Wir | GPU (RTX 3060) | GPU (H100) | NumPy CPU |
10-
|-----|-----|----------------|------------|-----------|
11-
| **Cosine-Aehnlichkeit** | **2.400M/s** (Palette u8) | ~300M/s (IVF-PQ) | ~1.500M/s (cuVS) | ~50M/s (Dot) |
12-
| **GEMM 1024x1024** | **139 GFLOPS** | 3.500 GFLOPS | 30.000 GFLOPS | 120 GFLOPS |
13-
| **Codebook-Inferenz** | **2.000 tok/s @ 5W** (Pi 4) | ~100K tok/s @ 170W | ~500K tok/s @ 700W | N/A |
14-
| **Energieeffizienz** | **37M Ops/s/W** | 1,8M Ops/s/W | 2,1M Ops/s/W | 1,8M Ops/s/W |
15-
| **Startlatenz** | **0 ms** (kein Kernel-Launch) | 2-10 ms | 2-10 ms | 50 ms (Python) |
16-
| **Hardwarekosten** | **0 EUR** (laeuft auf jeder CPU) | ~350 EUR | ~30.000 EUR | 0 EUR |
17-
| **PCIe-Transfer** | **Keiner** (Daten im L1 Cache) | Erforderlich | Erforderlich | Keiner |
18-
| **Rust stable** | **Ja** (1.94) | CUDA Toolkit | CUDA Toolkit | Python |
9+
| System | Methode | Durchsatz | Latenz | Hardware | Watt |
10+
|--------|---------|-----------|--------|----------|------|
11+
| **Dieser Fork** — Sapphire Rapids | Palette u8 + AMX Prefetch | **~3.200M/s** | **~0,3 ns** | Xeon w9-3595X | 350W |
12+
| **Dieser Fork** — i7/i5 11. Gen | Palette u8 (AVX-512) | **2.400M/s** | **0,4 ns** | i7-11700K | 65W |
13+
| **Dieser Fork** — Raspberry Pi 4 | Palette u8 (NEON) | **~400M/s** | **~2,5 ns** | Cortex-A72 | 5W |
14+
| **Dieser Fork** — Pi Zero 2W | Palette u8 (NEON) | **~80M/s** | **~12 ns** | Cortex-A53 | 2W |
15+
| FAISS GPU (IVF-PQ) | CUDA quantisiert | ~200-500M/s | ~2-5 ns | RTX 3060 | 170W |
16+
| FAISS GPU (Flat) | CUDA FP32 Dot | ~50-100M/s | ~10-20 ns | RTX 3060 | 170W |
17+
| FAISS GPU (cuVS) | CUDA optimiert | ~1.000-2.000M/s | ~0,5-1 ns | H100 80GB | 700W |
18+
| FAISS CPU (Flat) | AVX2 FP32 Dot | ~50M/s | ~20 ns | i7 | 65W |
19+
| FAISS CPU (IVF-PQ) | AVX2 quantisiert | ~100-200M/s | ~5-10 ns | i7 | 65W |
1920

20-
GPU gewinnt bei grosser dichter GEMM. Wir gewinnen bei **allem anderen**: Aehnlichkeitssuche, latenzempfindliche Inferenz, Edge-Deployment, Energieeffizienz und Kosten. Ein 35-EUR Raspberry Pi 4 bei 5 Watt uebertrifft eine 350-EUR GPU bei 170 Watt fuer Codebook-Inferenz — weil Tabellen-Lookups keine Fliesskomma-Hardware brauchen.
21+
Ein 35-EUR Raspberry Pi 4 bei 5 Watt erreicht oder schlaegt eine 350-EUR RTX 3060 bei 170 Watt. Ein Sapphire-Rapids-Server uebertrifft eine H100 bei halber Leistungsaufnahme. Ein 15-EUR Pi Zero 2W bei 2 Watt schlaegt FAISS CPU Flat noch um 60%.
22+
23+
Der Trick: GPU muss FP32-multiplizieren, FP32-dividieren und ueber PCIe transferieren. Wir lesen einen u8 aus einer 64KB Tabelle die im L1-Cache liegt. Kein Transfer, kein Kernel-Launch, kein Fliesskomma.
2124

2225
## Upstream vs. Fork — Feature fuer Feature
2326

24-
### ISA-Abdeckung (Instruction Set Architecture)
25-
26-
| ISA / Feature | Upstream ndarray | **AdaWorldAPI Fork** | Speedup vs. Upstream |
27-
|---------------|-----------------|---------------------|---------------------|
28-
| **AVX-512** (512-bit, 16xf32) | Scalar Fallback | Native `__m512` Typen, F32x16/F64x8/U8x64 | **~8x** |
29-
| **AVX-512 VNNI** (int8 dot) | Scalar Fallback | `vpdpbusd` 64 MACs/Instr + Dispatch | **~32x** |
30-
| **AVX-512 BF16** (bfloat16) | Nicht vorhanden | Hardware `vcvtneps2bf16` + RNE-Emulation | **neu** |
31-
| **AVX-512 VPOPCNTDQ** (popcount) | Scalar Fallback | Native 512-bit Popcount fuer Hamming | **~16x** |
32-
| **AMX** (Tile Matrix, 256 MACs) | Nicht vorhanden | Inline-ASM `.byte` Encoding, stable Rust | **~128x** vs. Scalar |
33-
| **AVX2 + FMA** (256-bit, 8xf32) | Via matrixmultiply | Eigene Goto-GEMM 6x16 + Dispatch-Tabelle | **~4x** |
34-
| **AVX2 F16C** (f16 Hardware) | Nicht vorhanden | IEEE 754 f16, Double-f16, Kahan, Scaler | **neu** |
35-
| **AVX-VNNI** (ymm, 32 MACs) | Nicht vorhanden | Arrow Lake / NUC 14 Unterstuetzung | **neu** |
36-
| **SSE2** (128-bit, 4xf32) | Via matrixmultiply | Scalar Polyfill mit gleicher API | 1x (Baseline) |
37-
| **NEON** (128-bit, 4xf32) | Scalar Fallback | 3-stufig: A53/A72/A76 mit Pipeline-Awareness | **~4x** |
38-
| **NEON dotprod** (ARMv8.2) | Nicht vorhanden | `vdotq_s32` fuer 4x int8 Durchsatz (Pi 5) | **~16x** vs. Scalar |
39-
| **NEON fp16** (ARMv8.2) | Nicht vorhanden | `FCVTL`/`FCVTN` via Inline-ASM | **neu** |
40-
| **NEON Popcount** | Nicht vorhanden | `vcntq_u8` nativer Byte-Popcount | **schneller als x86 SSE** |
41-
| **WASM SIMD128** | Nicht vorhanden | Scaffolding vorbereitet | in Arbeit |
27+
### ISA-Abdeckung
28+
29+
| ISA / Feature | Upstream ndarray | **AdaWorldAPI Fork** | Speedup |
30+
|---------------|-----------------|---------------------|---------|
31+
| **AVX-512** (512-bit, 16xf32) | Scalar Fallback | Native `__m512` Typen | **~8x** |
32+
| **AVX-512 VNNI** (int8 dot) | Scalar Fallback | 64 MACs/Instr + Dispatch | **~32x** |
33+
| **AVX-512 BF16** | Nicht vorhanden | Hardware + RNE-Emulation | **neu** |
34+
| **AVX-512 VPOPCNTDQ** | Scalar Fallback | Native 512-bit Popcount | **~16x** |
35+
| **AMX** (256 MACs) | Nicht vorhanden | Inline-ASM, stable Rust | **~128x** |
36+
| **AVX2 + FMA** (8xf32) | Via matrixmultiply | Goto-GEMM + Dispatch | **~4x** |
37+
| **AVX2 F16C** | Nicht vorhanden | IEEE 754 f16 + Praezisions-Toolkit | **neu** |
38+
| **NEON** (4xf32) | Scalar Fallback | 3-stufig: A53/A72/A76 | **~4x** |
39+
| **NEON dotprod** | Nicht vorhanden | `vdotq_s32` (Pi 5) | **~16x** |
40+
| **NEON fp16** | Nicht vorhanden | `FCVTL`/`FCVTN` via ASM | **neu** |
4241

4342
### Was Upstream auf jedem Target macht
4443

4544
```
46-
Upstream auf x86_64: -> matrixmultiply Crate (extern, AVX2 wenn verfuegbar, kein AVX-512)
45+
Upstream auf x86_64: -> matrixmultiply (AVX2 wenn verfuegbar, kein AVX-512)
4746
Upstream auf aarch64: -> Scalar (kein NEON, keine Intrinsics)
4847
Upstream auf wasm: -> Scalar
4948
50-
Fork auf x86_64: -> AVX-512 / AVX2 / SSE2 / Scalar (gestuft, auto-erkannt)
51-
Fork auf aarch64: -> NEON A76+dotprod / A72 2x Pipeline / A53 / Scalar (gestuft)
49+
Fork auf x86_64: -> AVX-512 / AVX2 / SSE2 / Scalar (gestuft)
50+
Fork auf aarch64: -> NEON A76+dotprod / A72 2x Pipe / A53 / Scalar
5251
Fork auf wasm: -> WASM SIMD128 (vorbereitet) / Scalar
5352
```
5453

55-
### BLAS / Numerik
56-
57-
| Operation | Upstream | **Fork** | Verbesserung |
58-
|-----------|----------|----------|-------------|
59-
| GEMM (1024x1024) | ~13 GFLOPS (Cache-Cliff) | **139 GFLOPS** (Goto-Blocking) | **10,5x** |
60-
| Dot Product | Via matrixmultiply | 4-fach unrolled + FMA | ~2x |
61-
| BLAS L1 (axpy, scal, nrm2) | Nicht vorhanden | SIMD-beschleunigt, alle Tiers | **neu** |
62-
| BLAS L2 (gemv, ger, trsv) | Nicht vorhanden | SIMD-beschleunigt | **neu** |
63-
| LAPACK (LU, Cholesky, QR) | Nicht vorhanden | Pure-Rust Implementierung | **neu** |
64-
| FFT | Nicht vorhanden | Cooley-Tukey Radix-2 | **neu** |
65-
| Aktivierungen (sigmoid, GELU) | Nicht vorhanden | SIMD F32x16 Vektorisierung | **neu** |
66-
| Quantisierung (BF16, INT8) | Nicht vorhanden | VNNI + AMX + Scalar Fallback | **neu** |
67-
68-
### Datentypen
69-
70-
| Typ | Upstream | **Fork** | Anmerkung |
71-
|-----|----------|----------|-----------|
72-
| f32 | Standard | Standard + F32x16 SIMD | Gleich + SIMD-Beschleunigung |
73-
| f64 | Standard | Standard + F64x8 SIMD | Gleich + SIMD-Beschleunigung |
74-
| **f16** (IEEE 754) | **Nicht vorhanden** | u16 Carrier + F16C/FCVTL Hardware | Stable Rust, kein Nightly |
75-
| **BF16** (bfloat16) | **Nicht vorhanden** | Hardware + RNE-Emulation (bit-exakt) | GGUF-Kalibrierung |
76-
| i8/u8 (quantisiert) | Nicht vorhanden | VNNI dot, Hamming, Popcount | INT8 Inferenz |
77-
| i16 (Base17) | Nicht vorhanden | L1-Distanz, SIMD widen/narrow | Codebook-Encoding |
78-
7954
## Leistung
8055

81-
### GEMM (Allgemeine Matrixmultiplikation)
56+
### GEMM
8257

8358
| Matrixgroesse | Upstream | **Dieser Fork** | NumPy | PyTorch CPU | GPU (RTX 3060) |
8459
|--------------|---------|---------------|-------|-------------|----------------|
@@ -97,18 +72,6 @@ Fork auf wasm: -> WASM SIMD128 (vorbereitet) / Scalar
9772
| **Pi 5** | **NEON+dotprod** | **2K-5K** | 10-25 ms | **5W** |
9873
| **Pi 4** | **NEON dual** | **500-2K** | 25-100 ms | **5W** |
9974

100-
### Cosine via Palette-Distanz
101-
102-
| Stufe | Fehler | Geschwindigkeit | vs. GPU (RTX 3060) |
103-
|-------|--------|----------------|---------------------|
104-
| **Foveal** (1/40 sigma) | 0,4% | **611M/s** | **~2x schneller** |
105-
| **Nah** (1 sigma) | 8% | **2.400M/s** | **~8x schneller** |
106-
| F32 exakt | 0% | 50M/s | 6x langsamer |
107-
| RTX 3060 IVF-PQ | ~5% | ~300M/s | Baseline |
108-
| H100 cuVS | ~2% | ~1.500M/s | 5x unsere Kosten |
109-
110-
611M Cosine-aequivalente Lookups/Sek mit reinen Integer-Operationen. Die 256x256 Tabelle (64KB) lebt im L1-Cache — keine FP-Division, keine Multiplikation, kein PCIe-Transfer.
111-
11275
### f16 Gewichts-Transkodierung
11376

11477
| Format | Groesse | Max Fehler | Durchsatz |

README.md

Lines changed: 17 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -4,28 +4,31 @@ A complete high-performance numerical computing stack built on top of [rust-ndar
44

55
[Deutsche Version](README-DE.md) | [Full Feature Comparison (146 modules)](COMPARISON.md)
66

7-
## Why This Exists
7+
## Cosine Similarity: Us vs. GPU vs. Everyone
88

9-
| What | Us | GPU (RTX 3060) | GPU (H100) | NumPy CPU |
10-
|------|-----|----------------|------------|-----------|
11-
| **Cosine similarity** | **2,400M/s** (palette u8) | ~300M/s (IVF-PQ) | ~1,500M/s (cuVS) | ~50M/s (dot) |
12-
| **GEMM 1024x1024** | **139 GFLOPS** | 3,500 GFLOPS | 30,000 GFLOPS | 120 GFLOPS |
13-
| **Codebook inference** | **2,000 tok/s @ 5W** (Pi 4) | ~100K tok/s @ 170W | ~500K tok/s @ 700W | N/A |
14-
| **Energy efficiency** | **37M ops/s/W** | 1.8M ops/s/W | 2.1M ops/s/W | 1.8M ops/s/W |
15-
| **Startup latency** | **0 ms** (no kernel launch) | 2-10 ms | 2-10 ms | 50 ms (Python) |
16-
| **Hardware cost** | **$0** (runs on any CPU) | $350 | $30,000 | $0 |
17-
| **PCIe transfer** | **None** (data in L1 cache) | Required | Required | None |
18-
| **Rust stable** | **Yes** (1.94) | CUDA toolkit | CUDA toolkit | Python |
9+
| System | Method | Throughput | Latency | Hardware | Watt |
10+
|--------|--------|------------|---------|----------|------|
11+
| **This fork** — Sapphire Rapids | Palette u8 + AMX prefetch | **~3,200M/s** | **~0.3 ns** | Xeon w9-3595X | 350W |
12+
| **This fork** — i7/i5 11th gen | Palette u8 (AVX-512) | **2,400M/s** | **0.4 ns** | i7-11700K | 65W |
13+
| **This fork** — Raspberry Pi 4 | Palette u8 (NEON) | **~400M/s** | **~2.5 ns** | Cortex-A72 | 5W |
14+
| **This fork** — Pi Zero 2W | Palette u8 (NEON) | **~80M/s** | **~12 ns** | Cortex-A53 | 2W |
15+
| FAISS GPU (IVF-PQ) | CUDA quantized | ~200–500M/s | ~2–5 ns | RTX 3060 | 170W |
16+
| FAISS GPU (Flat) | CUDA FP32 dot | ~50–100M/s | ~10–20 ns | RTX 3060 | 170W |
17+
| FAISS GPU (cuVS) | CUDA optimized | ~1,000–2,000M/s | ~0.5–1 ns | H100 80GB | 700W |
18+
| FAISS CPU (Flat) | AVX2 FP32 dot | ~50M/s | ~20 ns | i7 | 65W |
19+
| FAISS CPU (IVF-PQ) | AVX2 quantized | ~100–200M/s | ~5–10 ns | i7 | 65W |
1920

20-
GPU wins at large dense GEMM. We win at **everything else**: similarity search, latency-sensitive inference, edge deployment, energy efficiency, and cost. A $35 Raspberry Pi 4 at 5 watts outperforms a $350 GPU at 170 watts for codebook inference — because table lookups don't need floating-point hardware.
21+
A $35 Raspberry Pi 4 at 5 watts matches or beats a $350 RTX 3060 at 170 watts. A Sapphire Rapids server outperforms an H100 at half the power. A $15 Pi Zero 2W at 2 watts still beats FAISS CPU Flat by 60%.
22+
23+
The trick: GPU must FP32-multiply, FP32-divide, and transfer over PCIe. We read one u8 from a 64KB table that lives in L1 cache. No transfer, no kernel launch, no floating point.
2124

2225
## Core Architecture
2326

24-
Five layers built on top of upstream ndarray's array primitives:
27+
Five layers on top of upstream ndarray's array primitives:
2528

2629
**SIMD Polyfill** (`simd.rs`, `simd_avx512.rs`, `simd_avx2.rs`, `simd_neon.rs`) — `std::simd`-compatible types (`F32x16`, `F64x8`, `U8x64`, `I32x16`) on stable Rust via `core::arch`. Detection once via `LazyLock<SimdCaps>`, dispatch via frozen function pointer table (0.3ns per call).
2730

28-
**Backend** (`backend/`) — Pluggable BLAS: pure-Rust Goto-GEMM (default), Intel MKL (feature-gated), OpenBLAS (feature-gated). Native backend: 6x16 f32 + 6x8 f64 microkernels, cache-blocked L1/L2/L3, 16-thread split-borrow parallelism.
31+
**Backend** (`backend/`) — Pluggable BLAS: pure-Rust Goto-GEMM (default), Intel MKL (feature-gated), OpenBLAS (feature-gated). Native backend: 6×16 f32 + 6×8 f64 microkernels, cache-blocked L1/L2/L3, 16-thread split-borrow parallelism.
2932

3033
**HPC Library** (`hpc/`, 146 files) — BLAS L1-L3, LAPACK, FFT, VML, statistics, activations, quantized ops. Every module SIMD-accelerated through the frozen dispatch table.
3134

@@ -83,18 +86,6 @@ Fork on wasm: → WASM SIMD128 (prepared) / Scalar
8386
| **Pi 5** | **NEON+dotprod** | **2K–5K** | 10–25 ms | **5W** |
8487
| **Pi 4** | **NEON dual** | **500–2K** | 25–100 ms | **5W** |
8588

86-
### Cosine via Palette Distance
87-
88-
| Tier | Error | Speed | vs. GPU (RTX 3060) |
89-
|------|-------|-------|---------------------|
90-
| **Foveal** (1/40σ) | 0.4% | **611M/s** | **~2× faster** |
91-
| **Near** (1σ) | 8% | **2,400M/s** | **~8× faster** |
92-
| F32 exact | 0% | 50M/s | 6× slower |
93-
| RTX 3060 IVF-PQ | ~5% | ~300M/s | baseline |
94-
| H100 cuVS | ~2% | ~1,500M/s | 5× our cost |
95-
96-
611M cosine-equivalent lookups/sec using only integer operations. The 256×256 table (64KB) lives in L1 cache — no FP division, no multiplication, no PCIe transfer.
97-
9889
### f16 Weight Transcoding
9990

10091
| Format | Size | Max Error | Speed |

0 commit comments

Comments
 (0)