gqa(adr-0064/0065): flat-ops CompositeCmd (P1) + structural dispatch cost (ADR-0064 Rev2); promote ADR-0064
ADR-0065 P1: CompositeCmd -> flat ordered ops list (drop legacy op/a/b/out_addr fields); OpSpec.operands dict + out handle. Meaning-preserving (op_log byte-equal); pe_scheduler + op_log read the head op. ADR-0064 Rev2: replace Rev1 per-op cost table with structural FIXED + logical_bytes*R formula. logical_bytes on every PeCommand; new common/pe_cost_model.py; cost centralized in TLContext._emit (load/recv_async charge explicitly); pe_cpu/kernel_runner wire the per-PE model + clock. D7: cap exceeded -> ValueError (no auto-segmentation). Remove Rev1 cpu_issue_cost.py + its tests. No goldens churn. Promote ADR-0064 Rev2 Proposed->Accepted (docs/adr/ + docs/adr-ko/); amend D7 (error not segmentation) + record P1-before-P0 ordering in ADR-0064/0065 Migration notes (EN+KO). Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -156,19 +156,21 @@ class PeSchedulerComponent(ComponentBase):
|
||||
pp = self._pe_prefix
|
||||
bpe = 2 # default bytes per element (f16)
|
||||
|
||||
if cmd.op == "gemm" and cmd.b is not None:
|
||||
a = cmd.a
|
||||
b = cmd.b
|
||||
# Flat-ops (ADR-0065 D1): ops[0] is the head, ops[1:] are epilogue
|
||||
# specs placed by scope. The head's kind selects the engine path.
|
||||
head = cmd.ops[0]
|
||||
epi_specs = tuple(cmd.ops[1:])
|
||||
|
||||
if head.kind == "gemm" and "b" in head.operands:
|
||||
a = head.operands["a"]
|
||||
b = head.operands["b"]
|
||||
M, K = a.shape[-2], a.shape[-1]
|
||||
N = b.shape[-1]
|
||||
# When CompositeCmd.ops is populated, ops[0] is the head and
|
||||
# ops[1:] is the epilogue spec list. Empty ops → legacy path.
|
||||
epi_specs = tuple(cmd.ops[1:]) if cmd.ops else ()
|
||||
return generate_gemm_plan(
|
||||
M=M, K=K, N=N,
|
||||
tile_m=self.TILE_M, tile_k=self.TILE_K, tile_n=self.TILE_N,
|
||||
bytes_per_element=bpe,
|
||||
A_addr=a.addr, B_addr=b.addr, C_addr=cmd.out_addr,
|
||||
A_addr=a.addr, B_addr=b.addr, C_addr=head.out.addr,
|
||||
pe_prefix=pp,
|
||||
a_pinned=getattr(a, "pinned", False),
|
||||
b_pinned=getattr(b, "pinned", False),
|
||||
@@ -176,14 +178,14 @@ class PeSchedulerComponent(ComponentBase):
|
||||
)
|
||||
else:
|
||||
# Math composite
|
||||
a = cmd.a
|
||||
a = head.operands["a"]
|
||||
M = a.shape[-2] if len(a.shape) >= 2 else a.shape[0]
|
||||
N = a.shape[-1] if len(a.shape) >= 2 else 1
|
||||
return generate_math_plan(
|
||||
M=M, N=N,
|
||||
tile_m=self.TILE_M, tile_n=self.TILE_N,
|
||||
bytes_per_element=bpe,
|
||||
math_op=cmd.math_op or "identity",
|
||||
src_addr=a.addr, dst_addr=cmd.out_addr,
|
||||
math_op=head.extra.get("math_op") or "identity",
|
||||
src_addr=a.addr, dst_addr=head.out.addr,
|
||||
pe_prefix=pp,
|
||||
)
|
||||
|
||||
Reference in New Issue
Block a user