summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorArthur Hanson Rasmusson <arthur@vgpu.io>2026-10-26 16:37:08 -0400
committerArthur Hanson Rasmusson <arthur@vgpu.io>2026-10-26 16:37:08 -0400
commitadd223299e9bab04c66025c18d750feef936ffd1 (patch)
treebb87ca035c6be8be8e542986cfd33a54204fa021
parent140b9463d9a1c09b144ac1512331b25cec86d2a4 (diff)
downloadopen-iov-add223299e9bab04c66025c18d750feef936ffd1.tar.gz
open-iov-add223299e9bab04c66025c18d750feef936ffd1.zip
vgsp-sema: SESSION 139 GR fill: reject float-shaped scan words + scan the deduped word-48 page
Two evidence-based corrections to the launch-data candidate scan: 1. Float-shape filter at all four scan sites (the three page scans and svc_gr_scan_cand): a word whose f32 exponent byte is in ~[0x6c..0x8f] (2^-19..2^16) is a plausible float scalar, not a device VA - device VAs (2^28..2^47) as f32 land in subnormal/tiny exponents. Root evidence (r789): the launch param page carries the kernel's scalar arguments (0.2f, 640.0f, 480.0f at +0x630 - the 640x480 viewport) and 0x43f00000 = 480.0f was the fill's ONLY candidate - an unresolvable "arg base=0x43f00000" that drove the fail-closed diagnostic and the demand-loop noise for days. After the filter: 'fill cand n=0' (r790) - no false candidates, no false demands. 2. The bank-page scan now covers word 48: the QMD pointer-region pair can name a 4K page that also carries the program pair (r788: ptr[0] 0xdff0febc00 word 34 shares its page with prog 0xdff0feb900), and svc_gr_page_note dedupes the first note (the program's, word 48), so the old 32..47-even filter left that page unscanned. The remaining wall is content, not wiring: with the false candidates removed the launch still refuses (n_data=0 vs min 16) because no scanned source holds real device pointers - the param page holds scalars, the QMD window page reads zero (its content would arrive via the driver's i2m/LOAD_INLINE_DATA writes whose payloads are not in the push), and the inline payload is the driver's zero stub. This matches the SESSION 130 zero-buffer finding and leaves the never-queued i2m copies (or the real GPU path) as the only content sources.
-rw-r--r--kernel/gsp_sema_service.c65
1 files changed, 64 insertions, 1 deletions
diff --git a/kernel/gsp_sema_service.c b/kernel/gsp_sema_service.c
index 4c54e0b..cc508dc 100644
--- a/kernel/gsp_sema_service.c
+++ b/kernel/gsp_sema_service.c
@@ -21613,6 +21613,14 @@ static void svc_gr_scan_cand(u64 *wins, u32 *n_cand, const u8 *data, u32 bytes)
if (v < 0x10000000ULL || v >= (1ULL << 47) || (v & 3))
continue;
+ /* SESSION 139: float-shaped words are scalars, not device VAs
+ * (see the scan-site note; r789's 480.0f = 0x43f00000). */
+ {
+ u32 fexp = (u32)(v >> 23) & 0xffu;
+
+ if (fexp >= 0x6cu && fexp <= 0x8fu)
+ continue;
+ }
wv = v & ~(u64)(SEMA_PAGE_SIZE - 1);
for (w = 0; w < *n_cand; w++)
if (wins[w] == wv)
@@ -22137,6 +22145,23 @@ static void svc_gr_data_fill(struct nv_vgpu_device *vgpu,
if (v < 0x10000000ULL || v >= (1ULL << 47) ||
(v & 3))
continue;
+ /*
+ * SESSION 139: reject float-shaped words. The launch
+ * param page carries f32 scalars (r789: 0.2f, 640.0f,
+ * 480.0f at +0x630) whose bit patterns pass the
+ * VA-shape filter (0x43f00000 = 480.0f) and were the
+ * fill's only candidate - an unresolvable "arg base".
+ * A plausible f32 magnitude has an exponent byte in
+ * ~[0x6c..0x8f] (2^-19..2^16); device VAs (2^28..2^47)
+ * as f32 land in subnormal/tiny exponents, so this
+ * does not reject pointers.
+ */
+ {
+ u32 fexp = (u32)(v >> 23) & 0xffu;
+
+ if (fexp >= 0x6cu && fexp <= 0x8fu)
+ continue;
+ }
wv = v & ~(u64)(SEMA_PAGE_SIZE - 1);
for (w = 0; w < n_cand; w++)
if (wins[w] == wv)
@@ -22192,6 +22217,23 @@ static void svc_gr_data_fill(struct nv_vgpu_device *vgpu,
if (v < 0x10000000ULL || v >= (1ULL << 47) ||
(v & 3))
continue;
+ /*
+ * SESSION 139: reject float-shaped words. The launch
+ * param page carries f32 scalars (r789: 0.2f, 640.0f,
+ * 480.0f at +0x630) whose bit patterns pass the
+ * VA-shape filter (0x43f00000 = 480.0f) and were the
+ * fill's only candidate - an unresolvable "arg base".
+ * A plausible f32 magnitude has an exponent byte in
+ * ~[0x6c..0x8f] (2^-19..2^16); device VAs (2^28..2^47)
+ * as f32 land in subnormal/tiny exponents, so this
+ * does not reject pointers.
+ */
+ {
+ u32 fexp = (u32)(v >> 23) & 0xffu;
+
+ if (fexp >= 0x6cu && fexp <= 0x8fu)
+ continue;
+ }
wv = v & ~(u64)(SEMA_PAGE_SIZE - 1);
for (w = 0; w < n_cand; w++)
if (wins[w] == wv)
@@ -22206,7 +22248,11 @@ static void svc_gr_data_fill(struct nv_vgpu_device *vgpu,
const u8 *page;
u32 k;
- if (pp->qmd_word < 32 || pp->qmd_word > 47 ||
+ /* SESSION 139: include word 48 (see the r788 finding: the
+ * word-34 pointer dedupes into the program's 4K page whose
+ * entry carries qmd_word=48; the old 32..47-even filter left
+ * that page unscanned). */
+ if (pp->qmd_word < 32 || pp->qmd_word > 48 ||
(pp->qmd_word & 1) || !pp->pa)
continue;
kind = (pp->ap == SVC_APERTURE_FB) ? SVC_APERTURE_FB :
@@ -22229,6 +22275,23 @@ static void svc_gr_data_fill(struct nv_vgpu_device *vgpu,
if (v < 0x10000000ULL || v >= (1ULL << 47) ||
(v & 3))
continue;
+ /*
+ * SESSION 139: reject float-shaped words. The launch
+ * param page carries f32 scalars (r789: 0.2f, 640.0f,
+ * 480.0f at +0x630) whose bit patterns pass the
+ * VA-shape filter (0x43f00000 = 480.0f) and were the
+ * fill's only candidate - an unresolvable "arg base".
+ * A plausible f32 magnitude has an exponent byte in
+ * ~[0x6c..0x8f] (2^-19..2^16); device VAs (2^28..2^47)
+ * as f32 land in subnormal/tiny exponents, so this
+ * does not reject pointers.
+ */
+ {
+ u32 fexp = (u32)(v >> 23) & 0xffu;
+
+ if (fexp >= 0x6cu && fexp <= 0x8fu)
+ continue;
+ }
wv = v & ~(u64)(SEMA_PAGE_SIZE - 1);
for (w = 0; w < n_cand; w++)
if (wins[w] == wv)