diff options
| author | Arthur Hanson Rasmusson <arthur@vgpu.io> | 2026-10-31 13:57:07 -0400 |
|---|---|---|
| committer | Arthur Hanson Rasmusson <arthur@vgpu.io> | 2026-10-31 13:57:07 -0400 |
| commit | 54584ef147e24691932c5356397d4063263e86fb (patch) | |
| tree | 1ec4b63d3003cec779109f3a8007a109f19bdb43 | |
| parent | 8528df77141cb6f6ee6b2f4af1cc8f6bfa91a2c3 (diff) | |
| download | open-iov-54584ef147e24691932c5356397d4063263e86fb.tar.gz open-iov-54584ef147e24691932c5356397d4063263e86fb.zip | |
vgsp: sema_gl_mme_keep_mask (u64, slots never stubbed/dropped), MME-PRE-DUMP one-shot (raw words+sa_mask+IR coverage), SA data-port capture (0x120 runs), gsp_sema_mme_code_words_get - offline MME64 sim proves macro(0) loads CB offsets (0x238c<-0x320 etc) and macro(2) binds vertex streams with observed args, no poison; live A/B keep_mask works (dropped 115 vs 181 words); r1146 boot beef did NOT retire (timeout 2500ms, elapsed 8842ms, 0/902 pages) vs r1144 94us retire - re-establish r1144 state (prelude 901 vs 773 words, pages 7 shadow 6 vs 8/5, warm-sem wedged) then rerun keep 0x4/0x1 - SESSION 153 r1145-r1146
| -rw-r--r-- | kernel/gsp_phys_booter.c | 84 | ||||
| -rw-r--r-- | kernel/gsp_sema_service.c | 51 | ||||
| -rw-r--r-- | kernel/gsp_sema_service.h | 6 |
3 files changed, 140 insertions, 1 deletions
diff --git a/kernel/gsp_phys_booter.c b/kernel/gsp_phys_booter.c index 07c63ee..47e5168 100644 --- a/kernel/gsp_phys_booter.c +++ b/kernel/gsp_phys_booter.c @@ -17503,15 +17503,38 @@ MODULE_PARM_DESC(sema_gl_mme_call_drop, "Drop CALL_MME_MACRO/DATA runs of stubbed slots from emitted 3D windows (prevents the noop-stub parameter-port stall; default 1)"); /* + * SESSION 153-CONTINUED-70: per-slot macro re-enable mask, one slot at a + * time. The r1142-r1144 state drops EVERY stubbed-slot CALL run: the window + * retires on real HW (~94 us) but the macros that expand the driver's + * per-draw state (vertex stream binds, constant binds, ...) never execute, + * so no state the draw needs exists and every launch still stores 0 pages. + * A slot named in this mask is never treated as stubbed: its + * CALL_MME_MACRO/DATA words stay in the emitted window and the engine + * executes the macro against the replayed context (SA RAM + IR program as + * the client's own uploads left them; a slot the client never uploaded + * reads SA=0 exactly like silicon and lands in macro 0). A/B one bit per + * cycle; keep the proven-good set empty until the offline MME64 sim has + * shown the slot's macro emits sane methods for its caller args. + */ +static u64 gsp_phys_rmcall_gr_keep_mask; +module_param_named(sema_gl_mme_keep_mask, gsp_phys_rmcall_gr_keep_mask, + ullong, 0644); +MODULE_PARM_DESC(sema_gl_mme_keep_mask, + "Slots whose CALL_MME_MACRO/DATA runs are never dropped/stubbed (u64 bitmask; one slot at a time for macro re-enable)"); + +/* * The same stubbed-slot predicate the launch builder applies (see the * sa_stub emit decision): a slot is stubbed when stubbing is on and either * the all-slots knob is set, the capture holds no SA entry, or the IR - * instruction the entry names never entered the replay. + * instruction the entry names never entered the replay. A kept slot + * (sema_gl_mme_keep_mask) is never stubbed. */ static bool gsp_phys_gr_slot_stubbed(u32 j, u64 sa_mask, const u32 *sa_ent) { if (j >= 64u || !gsp_sema_gr_sa_stub_value()) return false; + if (READ_ONCE(gsp_phys_rmcall_gr_keep_mask) & (1ull << j)) + return false; if (READ_ONCE(gsp_phys_rmcall_gr_sa_stub_all)) return true; if (!(sa_mask & (1ull << j))) @@ -17599,6 +17622,7 @@ static u32 gsp_phys_gr_mme_drop_calls(u32 *win, u32 n, u64 sa_mask, */ static u32 gsp_phys_gr_mme_prelude_gen; static u32 gsp_phys_gr_mme_prelude_h; +static u32 gsp_phys_gr_mme_pre_full_dump; /* * SESSION 153-CONTINUED-57: attr/pipeline state prelude. The r1091 @@ -17818,6 +17842,28 @@ static u32 gsp_phys_rmcall_build_gr_launch(u32 *pb, if (j >= 64u) continue; /* + * SESSION 153-CONTINUED-70: a kept slot + * (sema_gl_mme_keep_mask) is never + * stubbed - its real macro must run + * against the context exactly as the + * client's own SA/IR uploads left it. + * Logged in the covered list for the + * census; no stub pair is emitted. + */ + if (READ_ONCE(gsp_phys_rmcall_gr_keep_mask) & + (1ull << j)) { + for (t = 0; t < sa_ncov; t++) + if (sa_cov[t] == j) + have = true; + if (!have && sa_ncov < 40u) { + sa_cov[sa_ncov] = j; + sa_cov_ent[sa_ncov] = + sa_ent[j]; + sa_ncov++; + } + continue; + } + /* * SESSION 153-CONTINUED-68: a slot is only * usable when the capture holds its SA entry * AND the IR instruction that entry names @@ -17980,6 +18026,42 @@ static u32 gsp_phys_rmcall_build_gr_launch(u32 *pb, pr_info("vgsp-gr: MME-PRELUDE emitted gen=%u words=%u window=%u h=0x%x push=0x%llx sdm_drop=%u\n", g0, pwords, win3d_n, req->h_object, req->push_va, sdrop); + /* + * SESSION 153-CONTINUED-70: one full dump of the + * replayed MME context-setup program per boot + * (the offline MME64 sim needs the same words the + * engine will execute). Also list the SA table + * with per-entry IR coverage so the slot-by-slot + * macro re-enable has its proof in one place. + */ + if (!gsp_phys_gr_mme_pre_full_dump) { + u32 k, sj; + u32 sa_ent[64]; + u64 sa_mask; + u32 cov_n = 0; + + gsp_phys_gr_mme_pre_full_dump = 1; + sa_mask = gsp_sema_mme_sa_get(sa_ent, 64); + for (sj = 0; sj < 64u; sj++) + if ((sa_mask & (1ull << sj)) && + gsp_sema_mme_ir_covered(sa_ent[sj])) + cov_n++; + pr_info("vgsp-gr: MME-PRE-DUMP words=%u gen=%u h=0x%x ir_end=0x%x sa_mask=0x%llx covered=%u code_words=%u keep_mask=0x%llx\n", + pl_n, g0, req->h_object, + gsp_sema_mme_ir_end_get(), + (unsigned long long)sa_mask, + cov_n, gsp_sema_mme_code_words_get(), + (unsigned long long)READ_ONCE(gsp_phys_rmcall_gr_keep_mask)); + for (k = 0; k + 4u <= pl_n; k += 4u) + pr_info("vgsp-gr: MME-PRE[%03u] %08x %08x %08x %08x\n", + k, pl[k], pl[k + 1], + pl[k + 2], pl[k + 3]); + for (sj = 0; sj < 64u; sj++) + if (sa_mask & (1ull << sj)) + pr_info("vgsp-gr: MME-PRE-SA[%u] entry=0x%x cov=%u\n", + sj, sa_ent[sj], + gsp_sema_mme_ir_covered(sa_ent[sj])); + } } else { pr_info("vgsp-gr: MME-PRELUDE copy raced an append (gen %u->%u); emitted words=%u, will re-emit next launch\n", g0, g1, pl_n); diff --git a/kernel/gsp_sema_service.c b/kernel/gsp_sema_service.c index 2b8b422..d79bfc5 100644 --- a/kernel/gsp_sema_service.c +++ b/kernel/gsp_sema_service.c @@ -14264,6 +14264,12 @@ MODULE_PARM_DESC(sema_mme_prelude_cap, static u64 svc_mme_sa_present; static u32 svc_mme_sa_entry[64]; static u32 svc_mme_sa_log; +/* + * SESSION 153-CONTINUED-70: last LOAD_MME_START_ADDRESS_RAM_POINTER (0x11c) + * value; the data port (0x120) writes entries for consecutive slots from + * here (see the 0x120 case in svc_mme_prelude_capture). + */ +static u32 svc_mme_sa_ptr; /* * SESSION 153-CONTINUED-68: furthest IR instruction any CAPTURED 0x114 @@ -14283,6 +14289,15 @@ u32 gsp_sema_mme_ir_end_get(void) } /* + * SESSION 153-CONTINUED-70: IR code words captured so far (the maturity + * gate's measure; the MME-PRE-DUMP prints it for the offline sim). + */ +u32 gsp_sema_mme_code_words_get(void) +{ + return READ_ONCE(svc_mme_prelude_code_words); +} + +/* * SESSION 153-CONTINUED-68: instruction-granular coverage of the IR the * REPLAY buffer actually holds (marked for every 0x114 run that entered * svc_mme_prelude_buf). Values >= SVC_MME_IR_BITS are treated as covered @@ -14392,7 +14407,43 @@ static void svc_mme_prelude_capture(const u8 *buf, u32 len, u64 push_va, memcpy(&sv, buf + off + 4u + 4u * k, 4); memcpy(&ev, buf + off + 8u + 4u * k, 4); svc_mme_sa_record(sv, ev); + /* the pointer follows the pair (see the + * 0x120 data-port case below). */ + svc_mme_sa_ptr = sv + 1u; + } + } else if (addr == 0x11cu && cnt == 1u && span > 1u) { + /* pointer-only write (LOAD_MME_START_ADDRESS_RAM_ + * POINTER <- slot) */ + u32 sv; + + memcpy(&sv, buf + off + 4u, 4); + svc_mme_sa_ptr = sv; + } + /* + * SESSION 153-CONTINUED-70: SA data-port form. The pair form + * above only catches [slot,entry] runs AT 0x11c; a client that + * seeds the pointer once and then streams entries through + * LOAD_MME_START_ADDRESS_RAM (0x120) left every slot beyond + * the seeded range unrecorded, so the builder stubbed macros + * the client had really uploaded (r1143/r1144: only slots + * 0..12 known while the window calls 34/39/40/48/51/57). The + * data port takes consecutive slots from the last 0x11c + * pointer value; whether the hardware auto-increments is not + * externally documented, so the host-side table is treated as + * a hint - the builder's keep/stub decision still A/Bs one + * slot at a time and the engine only ever sees the client's + * own runs. + */ + if (addr == 0x120u && cnt && span > 1u) { + u32 k; + + for (k = 0; k < cnt; k++) { + u32 ev; + + memcpy(&ev, buf + off + 4u + 4u * k, 4); + svc_mme_sa_record(svc_mme_sa_ptr + k, ev); } + svc_mme_sa_ptr += cnt; } if (!svc_mme_setup_run_addr(addr)) { off += span * 4u; diff --git a/kernel/gsp_sema_service.h b/kernel/gsp_sema_service.h index d2db39f..257a0ef 100644 --- a/kernel/gsp_sema_service.h +++ b/kernel/gsp_sema_service.h @@ -544,6 +544,12 @@ u64 gsp_sema_mme_sa_get(u32 *entries, u32 n); u32 gsp_sema_mme_ir_end_get(void); /* + * SESSION 153-CONTINUED-70: IR code words captured so far (the maturity + * gate's measure; printed by the MME-PRE-DUMP for the offline sim). + */ +u32 gsp_sema_mme_code_words_get(void); + +/* * SESSION 153-CONTINUED-68: is the IR instruction at address `pc` present * in the replay buffer (i.e. was it uploaded by a captured run that was * NOT dropped as a duplicate/over-cap)? The launch builder stubs every |
