summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorArthur Hanson Rasmusson <arthur@vgpu.io>2026-10-31 05:08:26 -0400
committerArthur Hanson Rasmusson <arthur@vgpu.io>2026-10-31 05:08:26 -0400
commitd6302743f43bc1119477bd13ba7565a469f6efc2 (patch)
tree145d76503b958a5b0d41d4b398520246db5cc650
parente3ecd6a3ff20196d6e768590ad5239caee138b60 (diff)
downloadopen-iov-d6302743f43bc1119477bd13ba7565a469f6efc2.tar.gz
open-iov-d6302743f43bc1119477bd13ba7565a469f6efc2.zip
vgsp: demand set 64->512 + ring-overwrite (no silent drop; head/total/evicted in debugfs sema_setup_demand), EBADMSG return authors software release (suppresses synth), ZEROWIN-SKIP (all-zero 3D window software-released, no engine submit) - verified: demand 197 VAs past cap, MISS-ABORT convergence (submit only at miss=0), ZEROWIN-SKIP no-poison; store-bearing window still not achieved (r1106 retire root-caused zero window); r1108 slow-death (Wait for channel idle timed out + red screen on SKIP edge); next: re-arm candidate on MISS-ABORT (not consume) - SESSION 153 r1107-r1108
-rw-r--r--kernel/gsp_phys_booter.c43
-rw-r--r--kernel/gsp_sema_service.c70
2 files changed, 103 insertions, 10 deletions
diff --git a/kernel/gsp_phys_booter.c b/kernel/gsp_phys_booter.c
index 7f41df6..6f3898f 100644
--- a/kernel/gsp_phys_booter.c
+++ b/kernel/gsp_phys_booter.c
@@ -16841,6 +16841,14 @@ static u64 gsp_phys_gr_submitted;
static u64 gsp_phys_gr_ok;
static u64 gsp_phys_gr_refused;
static u64 gsp_phys_gr_timed_out;
+/*
+ * SESSION 153-CONTINUED-60: 3D-stream launches whose window was all-zero
+ * (the client's push page caught mid-rewrite). They are never handed to the
+ * engine: the zero method stream trips the PBDMA (trap 0x1168 -> priv-error
+ * poison, see the ZEROWIN-SKIP site). Counted so a boot's zero-window rate
+ * is visible without dmesg archaeology.
+ */
+static u64 gsp_phys_gr_zerowin_skips;
static u64 gsp_phys_gr_retries; /* fresh-entry launch retries published */
static u64 gsp_phys_gr_pool_exhausted;
/* m156 (E5): zero-write retries where the warm sem push proved the engine
@@ -21139,6 +21147,41 @@ int gsp_phys_backend_guest_gr_submit(const struct gsp_phys_gr_submit *req,
ret = -EIO;
goto out;
}
+ /*
+ * SESSION 153-CONTINUED-60: all-zero 3D-window skip. The client's push
+ * page is cyclically zeroed/rewritten (CONT-45); a capture that lands
+ * on the zero phase still forwards an all-zero method window. Live
+ * r1107: such a window launched (3D raw dump words=252, every word 0),
+ * the engine trapped SET_VERTEX_ATTRIBUTE_A(2) (trap=00001168
+ * data_lo=0x50) and escalated to a priv-error poison (grfifo=
+ * 0xbadf1201, mme_pc=513) that wedged the GR lane for the rest of the
+ * boot; r1031 had already seen the same class fault the PBDMA on the
+ * zero lead (PB-FAULT-DUMP P0). A zero window carries no method to
+ * execute and nothing to store: skip the hardware handoff entirely -
+ * no shadow relocation, no engine contact, no wedge - and return the
+ * distinct rc -EBADMSG so the service authors the software release and
+ * suppresses the synthetic fault (a frame with no content deserves no
+ * client-visible engine error).
+ */
+ if (stream3d) {
+ u32 zwi;
+ bool zerowin = req->stream_n != 0;
+
+ for (zwi = 0; zwi < req->stream_n; zwi++) {
+ if (req->stream[zwi]) {
+ zerowin = false;
+ break;
+ }
+ }
+ if (zerowin) {
+ gsp_phys_gr_zerowin_skips++;
+ pr_warn_ratelimited("vgsp-gr: ZEROWIN-SKIP h=0x%x push=0x%llx window=%u all-zero (no engine submit; software release) n=%llu\n",
+ req->h_object, req->push_va, req->stream_n,
+ gsp_phys_gr_zerowin_skips);
+ ret = -EBADMSG;
+ goto out;
+ }
+ }
gsp_phys_gr_submitted++;
gsp_phys_gr_override_apply_param();
diff --git a/kernel/gsp_sema_service.c b/kernel/gsp_sema_service.c
index 11f4f46..6a4d4ef 100644
--- a/kernel/gsp_sema_service.c
+++ b/kernel/gsp_sema_service.c
@@ -1531,10 +1531,24 @@ struct sema_svc {
* rotate out of the ring before the 3 s harvest reads them, so the
* setup-push pages were lost (r1090 needed a manual demand); the pin
* tool now reads this file directly each pass instead.
- */
-#define SVC_SETUP_DEMAND_MAX 64
+ *
+ * SESSION 153-CONTINUED-60: the set is a RING. At 64 entries the
+ * r1106 MISS wall (push=0xcf3d724 miss=11..17/pass, abort loop
+ * n=2..9) never converged because every later gsp_sema_demand_note
+ * (the MISS pages themselves, the attr-prelude program pages) was
+ * silently dropped once the 64 slots were exhausted -> the pin tool
+ * never demanded them -> never resolved -> perpetual pre-doorbell
+ * abort. Capacity is raised to 512 and a full set overwrites the
+ * oldest slot instead of refusing the note, so the resident set is
+ * the demand-paging working set and a later note is never lost;
+ * total/evicted counters are published for observability.
+ */
+#define SVC_SETUP_DEMAND_MAX 512
u64 setup_demand_vas[SVC_SETUP_DEMAND_MAX];
u32 setup_demand_count;
+ u32 setup_demand_head; /* ring write cursor (valid once full) */
+ u64 setup_demand_total; /* notes accepted (dedup hits excluded) */
+ u64 setup_demand_evicted; /* oldest-slot overwrites */
};
static struct sema_svc svc;
@@ -1573,6 +1587,12 @@ static void svc_log_stalled_va(u64 va)
* thread); the debugfs reader publishes entries with a write barrier on the
* count, so a reader can never observe a torn entry (the count never
* decreases and an entry is stable once its slot is covered by the count).
+ *
+ * SESSION 153-CONTINUED-60: full-set behaviour is ring overwrite (oldest
+ * slot) instead of drop, so the r1106 MISS pages can never be refused a
+ * slot by a stale 64-entry set; see the member comment. Entry stores are
+ * aligned u64 on a 64-bit kernel, so the in-place overwrite cannot tear for
+ * the seq reader (worst case it sees the previous resident VA once more).
*/
static void svc_setup_demand_record(u64 va)
{
@@ -1583,11 +1603,25 @@ static void svc_setup_demand_record(u64 va)
for (i = 0; i < n; i++)
if (svc.setup_demand_vas[i] == va)
return;
- if (n >= SVC_SETUP_DEMAND_MAX)
- return;
- svc.setup_demand_vas[n] = va;
- smp_wmb();
- svc.setup_demand_count = n + 1;
+ if (n < SVC_SETUP_DEMAND_MAX) {
+ svc.setup_demand_vas[n] = va;
+ smp_wmb();
+ svc.setup_demand_count = n + 1;
+ } else {
+ static u32 ring_log;
+ u32 w = svc.setup_demand_head;
+
+ svc.setup_demand_vas[w] = va;
+ svc.setup_demand_head = (w + 1u) % SVC_SETUP_DEMAND_MAX;
+ svc.setup_demand_evicted++;
+ if (ring_log < 4u || !(svc.setup_demand_evicted % 4096u)) {
+ ring_log++;
+ pr_info("sema-svc: demand ring full; evicting oldest slot %u for va=0x%llx (evicted=%llu total=%llu)\n",
+ w, va, svc.setup_demand_evicted,
+ svc.setup_demand_total + 1u);
+ }
+ }
+ svc.setup_demand_total++;
}
/*
@@ -1606,15 +1640,19 @@ void gsp_sema_demand_note(u64 va)
/*
* Read-only view of the setup-hold demand set for the pin tool:
- * # sema setup-hold demand VAs (page-aligned): N
+ * # sema setup-hold demand VAs (page-aligned): N total=T evicted=E
* 0x4021000
* ...
+ * `total` counts every accepted note (dedup hits excluded); `evicted` counts
+ * ring overwrites of the oldest slot (SESSION 153-CONTINUED-60).
*/
static int svc_setup_demand_show(struct seq_file *m, void *v)
{
u32 i, n = READ_ONCE(svc.setup_demand_count);
- seq_printf(m, "# sema setup-hold demand VAs (page-aligned): %u\n", n);
+ seq_printf(m, "# sema setup-hold demand VAs (page-aligned): %u total=%llu evicted=%llu\n",
+ n, (unsigned long long)svc.setup_demand_total,
+ (unsigned long long)svc.setup_demand_evicted);
for (i = 0; i < n && i < SVC_SETUP_DEMAND_MAX; i++)
seq_printf(m, "0x%llx\n",
(unsigned long long)svc.setup_demand_vas[i]);
@@ -27577,7 +27615,19 @@ static void svc_fwd_outcome_check(struct nv_vgpu_device *vgpu)
svc_fwd_req.gr_rel_va,
svc_fwd_req.gr_rel_payload);
svc.fwd_gr_stall_swrel++;
- if (svc_fwd_req.hw_rc != 0) {
+ if (svc_fwd_req.hw_rc == -EBADMSG) {
+ /*
+ * SESSION 153-CONTINUED-60: the backend skipped an all-zero 3D
+ * window (ZEROWIN-SKIP) - nothing was submitted, so there is no
+ * engine error to report. Author the software release and do
+ * NOT raise the synthetic fault: the client sees a clean
+ * completion for a frame whose window had no content, and the
+ * engine is never handed the zero method stream that used to
+ * poison it (trap 0x1168 -> grfifo=0xbadf1201, r1107).
+ */
+ pr_warn("vgsp-gr: GR-STALL-backend va=0x%llx waited_ms=%lu action=proceed (zero window skipped; QMD release authored in software, no synth fault)\n",
+ svc_fwd_req.gr_push_va, waited);
+ } else if (svc_fwd_req.hw_rc != 0) {
pr_warn("vgsp-gr: GR-STALL-backend va=0x%llx waited_ms=%lu action=proceed (failed forwarded launch, rc=%d; QMD release authored in software)\n",
svc_fwd_req.gr_push_va, waited, svc_fwd_req.hw_rc);
/*