Skip to content

fix: support A5 i16 pto.vdiv via SoftOps and reject unsupported integer vdiv - #1253

Open
jimmychou0 wants to merge 1 commit into
hw-native-sys:mainfrom
jimmychou0:zjm/issue1241-fix
Open

fix: support A5 i16 pto.vdiv via SoftOps and reject unsupported integer vdiv#1253
jimmychou0 wants to merge 1 commit into
hw-native-sys:mainfrom
jimmychou0:zjm/issue1241-fix

Conversation

@jimmychou0

Copy link
Copy Markdown
Contributor

Summary

Fixes #1241 — A5 signed i16 pto.vdiv on !pto.vreg<128xi16> compiled and linked but the kernel hung at runtime (aclrtSynchronizeStream never returned, NPU pinned at 100%, device Alarm).

Root cause

Only signed i32/b32 vdiv was intercepted by PTOExpandSoftLibPass (the issue #1181 fix, commit 4c52ba8). i16 vdiv fell through to the unsupported integer HiVM VDIV intrinsic (llvm.hivm.vdiv.s.x.v128s16), which the A5 micro-ISA cannot execute — the micro-ISA doc already documented A5 vdiv as f16/f32 + i32 softlib, but the contract was never enforced, so the unsupported intrinsic silently reached the device and hung it.

Changes

Step 1 — compile-time rejection (contract enforcement)

  • lib/PTO/Transforms/PTOExpandSoftLib.cpp: widened the softlib interception window to signed/signless i16 and i32 vdiv (isSoftLibVdivIntegerVReg), validated operand/mask consistency, and emit a hard compile error for any other A5 integer pto.vdiv (e.g. unsigned variants, mismatched masks) instead of lowering it.

Step 2 — i16 vdiv via the Software Library

  • lib/SoftOps/div_int.py: added div_i16_soft mirroring the TileLang-validated u16 soft-division algorithm — b16 interleave + 2:1 vcvt(EVEN) widening into the u32 domain, 65536-scaled f32 reciprocal via f32 pto.vdiv, high-16 narrowing back through vdintlv, two exact remainder-correction passes, and sign restoration with C-style truncation semantics.
  • lib/SoftOps/__init__.py / ptodsl/ptodsl/softlib/_compiler_runtime.py: export and dispatch div_i16_soft for i16 (default 128 lanes / b16 mask).

Tests & docs

  • test/lit/vpto/issue_1241_vdiv_i16_reject.pto — unsigned ui16 vdiv must fail at compile time on A5.
  • test/lit/vpto/issue_1241_vdiv_i16_soft_lowering.pto — i16 vdiv lowers to the f32 soft implementation; no vdiv.s.x.v128s16.
  • test/dsl-st/vdiv_i16.py — 1×128 i16 tile, 16 divisor magnitudes, exact C-style truncation (rtol=atol=0).
  • docs/isa/micro-isa/07-binary-vector-ops.md — A5 vdiv types line now lists i16/i32 softlib materialization and the compile-time rejection of other integer widths.

Validation

Layer Machine Result
Full build (LLVM 19.1.7) 238 (x86_64) / dev-481211 (aarch64) PASS, 0 FAILED
Full lit suite (incl. both new tests) 238 1786/1787 PASS
New lit tests dev-481211 (aarch64) PASS
CANN simulator Ascend950PR_9599 dsl-st 238 (vdiv_i16.py) PASS, all lanes exact
A5 hardware (Ascend950PR, NPU0) dsl-st 238 PASS — kernel terminates, no hang

All 128 lanes matched the exact truncated quotient (verified against a bit-exact numpy mirror of the algorithm; an initial 43-lane "off-by-one" report was traced to a floor-vs-truncation bug in the test's expected-value function, not the implementation).

Note: 144 / a5 hosts were unreachable during validation; the CANN simulator and A5 hardware checks were run on 238 (same LLVM19 toolchain, full A5 simulator set, Ascend950PR cards).

…integer vdiv

Issue 1241: A5 signed i16 pto.vdiv (128xi16) compiled and linked but hung the
device at runtime (aclrtSynchronizeStream never returned, NPU 100%). The i16
form fell through to the unsupported llvm.hivm.vdiv.s.x.v128s16 integer HiVM
intrinsic; only the i32 form was intercepted.

Changes:
- PTOExpandSoftLib: for non-softlib integer vdiv (unsigned ui16/ui32 and
  masks/granularities that do not match) emit a compile-time error instead of
  lowering to the unsupported integer HiVM path.
- lib/SoftOps/div_int.py: add div_i16_soft, computed in the u32 domain via an
  f32 reciprocal with exact remainder correction and sign truncation; the
  active mask is re-interleaved with pintlv_b16 so the vintlv/vcvt half-split
  gates the original lane order for partial masks (VL2, sparse, and
  cross-64-lane-boundary predicates).
- SoftOps/__init__.py and ptodsl/softlib/_compiler_runtime.py dispatch i16
  vdiv to the softlib.
- Docs: vdiv micro-ISA chapter states only signed/signless i16/i32 are
  materialized; unsigned and other-width integer vdiv are rejected at compile
  time on A5.
- Tests: lit T1 rejects ui16 vdiv; lit T2 asserts the softlib lowering
  (f32 vdiv, pintlv.b16, no v128s16 HiVM VDIV); dsl-st vdiv_i16.py (full
  mask, including negative denominators) and vdiv_i16_partial_masks.py
  (VL64/VL2/sparse/cross-boundary).

Validated: check-pto 1786 passed / 1 unsupported; simulator (Ascend950PR_9599)
and A5 hardware (Ascend950PR) full-mask 128/128 lanes exact and all four
partial-mask cases exact; the issue hw-native-sys#1241 original repro
(fatobj + aclrtLaunchKernel/aclrtSynchronizeStream launcher) on A5 prints
"kernel launched"/"stream synchronized" and exits 0 with VERIFY OK.
@jimmychou0
jimmychou0 marked this pull request as ready for review August 14, 2026 07:41
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.

[Bug][阻塞] A5 上 int16 pto.vdiv 编译成功但 kernel 运行挂死

1 participant