Skip to content

feat(laya): engine 0.61.0 and the packed Q8_0 lane (SKEEP-007 consumer) - #498

Merged
michalharakal merged 1 commit into
SKaiNET-developers:developfrom
michalharakal:feature/engine-0.61.0-laya-consumer
Oct 17, 2026
Merged

michalharakal merged 1 commit into
SKaiNET-developers:developfrom
michalharakal:feature/engine-0.61.0-laya-consumer

Conversation

@michalharakal

Copy link
Copy Markdown
Contributor

Engine 0.61.0 and the Laya consumer of SKEEP-007 (quantize-at-load, the browser lane).

Engine bump

skainet = "0.61.0": SKEEP-007 Tiers 0–2 (packed-weight dispatch order, the skainet-backend-wasm-simd sidecar, quantize-at-load for the SafeTensors and GGUF loaders) and the scheduled removal of the SKEEP-006 compatibility aliases — nothing in this repository referenced them.

Laya on the packed Q8_0 lane

  • LayaModelLoader.load is common code (commonMain): the four side files as text (LayaCheckpointFiles) plus a RandomAccessSource for model.safetensors, suspend, with weightForm / weightFormFor passed through to the engine's SafeTensors loader. The JVM load(directory: Path, ctx, exactGelu, weightFormFor) is now an extension over it — source-compatible for Kotlin callers (same call), a different owner class for Java callers (API dump updated). The Android replica of the six steps in the examples repository can collapse onto this function.
  • LayaWeightForms.q8_0For: Q8_0 for the encoder and head projections (Wqkv, Wo, Wi, mlp.Wo, in_proj_weight, out_proj.weight, linear1/2.weight) and the 256k × 768 token table; norms, biases, the type embedding and the scorer stay dense. About a quarter of the FP32 bytes, served by the packed kernels on every tier (FFM on the JVM, JNI on Android, the SIMD128 sidecar in a browser after WasmSimd.install()).
  • LayaWeightPreparation splits the fused Wqkv / Wi / in_proj matrices in their packed form (in row-major block storage a row block is a contiguous byte range, so no FP32 transient) and wraps the token table as PackedRowDequantTensorData, which the embedding layer reads row by row.
  • Decision-quality gate: LayaQuantizedParityTest (model-gated like the other fixture tests) loads the FP32 and the Q8_0 agent, runs the predict.json single cases through both, and requires every choice to agree and no probability, score, noul value or confidence to shift by more than 0.05 (LAYA_Q8_TOL; measured 0.035). FP32 parity (1.5e-4) stays the contract of the reference lane. The fixture question parser moved to LayaFixtures.questionOf so both tests share it.
  • Docs: typed-decisions.adoc gains a Quantized lane section and its Current limits no longer lists "JVM only"; CHANGELOG Unreleased.

Verification (local, 12-core laptop, engine 0.61.0 from Maven Central)

  • compileKotlinJvm and compileTestKotlinJvm across the repository against 0.61.0: clean (nothing referenced the removed engine aliases).
  • :llm-inference:laya:jvmTest with LAYA_MULTILINGUAL_PATH: 33 tests, the FP32 fixtures and batching tests unchanged.
  • LayaQuantizedParityTest: 5/5 choices agree, 45 values compared, max shift 0.035 against the 0.05 gate; packed weights 325 MB; FP32 load 11.4 s, Q8_0 load 12.1 s. On the eager JVM path the Q8_0 lane runs the six fixture cases in 171 s against 69 s for FP32 — the row-major packed kernels take one activation row at a time — so on the JVM this lane is a memory measure; the speed is the browser sidecar's.
  • apiDump for the laya module regenerated (the JVM load(Path, …) is now in LayaModelLoaderKt).

Engine 0.61.0 brings quantize-at-load and the browser kernel pack. The Laya
loader becomes common code over a RandomAccessSource (the JVM Path overload
is an extension over it); LayaWeightForms.q8_0For quantizes the encoder and
head projections and the token table to Q8_0 at load, LayaWeightPreparation
splits the fused matrices in their packed form and wraps the token table for
row-wise reads, and LayaQuantizedParityTest gates the lane on decision
quality: every predict.json choice agrees with FP32, no value shifts by more
than 0.05 (measured 0.035, 5/5 choices).
@michalharakal
michalharakal merged commit a92d65e into SKaiNET-developers:develop Oct 17, 2026
3 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant