ProprietaryLegal's picture
PLI Labs public snapshot 2026-10-28 (history squashed)
0693474
Raw History Blame Contribute Delete
6.83 kB
"""The native GPU ops against formats.py / reference.py on the real official tensors.
GPU: CUDA_VISIBLE_DEVICES=GPU-7744b44b-... python -m pytest -q offload/dspark/native/tests/test_ops.py
CPU: TRITON_INTERPRET=1 python -m pytest -q offload/dspark/native/tests/test_ops.py (Triton interpreter; slow)
"""
from __future__ import annotations
import os
import pytest
import torch
from offload.dspark.native import formats as F
from offload.dspark.native import ops as NO
from offload.dspark.native import reference as R
from offload.dspark.native.loader import LoadStats, load_dense, load_expert_banks
from offload.dspark.native.official import OfficialShards
ROOT = os.environ.get("NATIVE_1017_ROOT", "/opt/dsv41/x86host-data/native-1017")
HAVE = os.path.exists(os.path.join(ROOT, "model-00044-of-00048.safetensors"))
INTERP = os.environ.get("TRITON_INTERPRET") == "1"
DEV = torch.device("cpu") if INTERP or not torch.cuda.is_available() else torch.device("cuda")
pytestmark = pytest.mark.skipif(not INTERP and not torch.cuda.is_available(), reason="needs a GPU or the interpreter")
def test_act_qdq_bit_identical():
g = torch.Generator().manual_seed(0)
x = (torch.randn(9, 640, generator=g) * torch.logspace(-7, 4, 640)).to(torch.bfloat16)
x[0, :32] = 0
x[1, 32:64] = 448.0
x[2, 64:96] = -448.0 * 2 ** -5
x[3] = x[3] * 1e-30
want = F.act_qdq(x)
got = NO.act_qdq(x.to(DEV)).cpu()
assert torch.equal(got.view(torch.int16), want.view(torch.int16))
@pytest.mark.skipif(not HAVE, reason="official shards not present")
@pytest.mark.parametrize("kind", ["fp8", "bf16"])
def test_dense_matches_reference(kind):
sh = OfficialShards(ROOT)
st = LoadStats()
d = load_dense(sh, "mtp.1.attn.wkv", DEV, kind, st)
w, s = sh.get("mtp.1.attn.wkv.weight"), sh.get("mtp.1.attn.wkv.scale")
g = torch.Generator().manual_seed(3)
x = torch.randn(5, 5120, generator=g).to(torch.bfloat16)
want = R.linear_fp8(x, w, s, "f64").float()
xq = NO.act_qdq(x.to(DEV))
got = d(xq).cpu().float()
tol = torch.finfo(torch.bfloat16).eps * want.abs().amax()
assert (got - want).abs().max() <= tol
assert (got == want).float().mean() > 0.97
got32 = d(xq, out_f32=True).cpu()
ref32 = (F.act_qdq(x).double() @ F.decode_fp8_block(w, s).double().t()).float()
assert ((got32 - ref32).abs() <= 1e-5 * ref32.abs().amax()).all()
if kind == "bf16" and DEV.type == "cuda": # the Triton kernel on bf16 weights agrees too
dt = NO.NativeDense("wkv-triton", "bf16", d.w, None, backend="triton")
assert (dt(xq).cpu().float() - want).abs().max() <= tol
assert ((dt(xq, out_f32=True).cpu() - ref32).abs() <= 1e-5 * ref32.abs().amax()).all()
# a row shard keeps the full tensor's scale blocks
d2 = load_dense(sh, "mtp.1.attn.wkv", DEV, kind, st, rows=(256, 512))
assert torch.equal(d2(xq).cpu(), d(xq).cpu()[:, 256:512]) or kind == "bf16"
@pytest.mark.skipif(not HAVE, reason="official shards not present")
@pytest.mark.parametrize("kind", ["packed", "expanded"])
def test_expert_slots_match_reference(kind):
sh = OfficialShards(ROOT)
E = 6
banks = load_expert_banks(sh, 2, [(0, DEV), (1, DEV)], 2, kind, LoadStats(), verify_sample=2, n_experts=E)
g = torch.Generator().manual_seed(4)
T = 2
x = (torch.randn(T, 5120, generator=g) * 0.7).to(torch.bfloat16)
ids = torch.tensor([[0, 5, 3], [2, 0, 4]], dtype=torch.int64)
rw = torch.rand(T, 3, generator=g)
xq = F.act_qdq(x)
full = torch.zeros(T, 3, 5120, dtype=torch.float32)
hs = {}
for r in (0, 1):
h = torch.empty(T * 3, 1152, dtype=torch.bfloat16, device=DEV)
full += banks[r].forward_slots(xq.to(DEV), ids.to(DEV), rw.to(DEV), h=h).cpu()
hs[r] = h.cpu()
for t in range(T):
for j in range(3):
e = int(ids[t, j])
p = f"mtp.2.ffn.experts.{e}."
w1, s1, w3, s3, w2, s2 = (sh.get(p + n) for n in ("w1.weight", "w1.scale", "w3.weight", "w3.scale",
"w2.weight", "w2.scale"))
gg = R.linear_fp4(x[t:t + 1], w1, s1)
uu = R.linear_fp4(x[t:t + 1], w3, s3)
hq = F.act_qdq(R.swiglu(gg, uu, rw[t:t + 1, j:j + 1]))
got_h = torch.cat([hs[0][t * 3 + j], hs[1][t * 3 + j]])
frac = (got_h == hq[0]).float().mean().item()
assert frac > 0.995, frac # bf16 g/u ties may flip by fp32 order: a few elements
y = (hq.double() @ F.decode_fp4(w2, s2).double().t()).float()[0]
rel = ((full[t, j] - y).norm() / y.norm()).item()
assert rel < 5e-3, rel
def test_official_combine_order():
parts = torch.randn(2, 3, 8) * 100
ids = torch.tensor([[7, 1, 4], [0, 9, 2]])
sh = torch.randn(2, 8)
got = NO.moe_combine_official(parts, sh, ids)
want = torch.zeros(2, 8)
for t in range(2):
for j in ids[t].argsort().tolist():
want[t] += parts[t, j].to(torch.bfloat16).float()
want = (want + sh.to(torch.bfloat16).float()).to(torch.bfloat16)
assert torch.equal(got, want)
def test_markov_logits_fp32_exact_bias():
g = torch.Generator().manual_seed(6)
V, Vr, Rk = 1000, 300, 256
w1 = (torch.randn(V, Rk, generator=g) * 0.05).to(torch.bfloat16)
w2 = (torch.randn(Vr, Rk, generator=g) * 0.05).to(torch.bfloat16)
base = torch.randn(3, Vr, generator=g) * 4
prev = torch.tensor([5, 999, 0])
got = NO.markov_logits_fp32(base.to(DEV), prev.to(DEV), w1.to(DEV), w2.to(DEV)).cpu()
want = (base.double() + w1[prev].double() @ w2.double().t()).float()
assert ((got - want).abs() <= 1e-5 * want.abs().amax()).all()
def test_markov_hot_rows_bit_identical_to_computed():
g = torch.Generator().manual_seed(7)
V, Vr = 700, 260
w1 = (torch.randn(V, 256, generator=g) * 0.05).to(torch.bfloat16).to(DEV)
w2 = (torch.randn(Vr, 256, generator=g) * 0.05).to(torch.bfloat16).to(DEV)
base = (torch.randn(3, Vr, generator=g) * 4).to(DEV)
prev = torch.tensor([5, 699, 17]).to(DEV)
rows = NO.MarkovRowsFP32(w1, w2, [17, 5, 3], rows=2) # 5 and 17 cached, 699 computed
assert rows.rows == 2
a = NO.markov_logits_fp32(base, prev, w1, w2, rows).cpu()
b = NO.markov_logits_fp32(base, prev, w1, w2, None).cpu()
assert torch.equal(a, b)
def test_swiglu_qdq_matches_reference():
g_ = torch.Generator().manual_seed(8)
T, I = 4, 1152
g = torch.randn(T, 3, I, generator=g_) * 6
u = torch.randn(T, 3, I, generator=g_) * 6
rw = torch.rand(T, 3, generator=g_)
got = NO.swiglu_qdq(g.to(DEV), u.to(DEV), rw.to(DEV)).cpu()
want = F.act_qdq(R.swiglu(g.to(torch.bfloat16), u.to(torch.bfloat16), rw.reshape(T, 3, 1))).view(T * 3, I)
assert (got == want).float().mean() > 0.999