summaryrefslogtreecommitdiffstats
path: root/kernel
diff options
context:
space:
mode:
authorArthur Hanson Rasmusson <arthur@vgpu.io>2026-10-05 20:23:44 -0400
committerArthur Hanson Rasmusson <arthur@vgpu.io>2026-10-05 20:23:44 -0400
commitac3ecc3857efdf5da9dcafeb433dc9af65ae738f (patch)
tree3cafefc3859b266e1d64d13f445a6b2e68fc556c /kernel
parent52266aa4c59b1b551862cf26d66134300997fd40 (diff)
downloadopen-iov-golden-replay.tar.gz
open-iov-golden-replay.zip
vgsp: golden9k - size every promoted GR ctx buffer from GET_ENGINE_CONTEXT_PROPERTIES (REAL GR SEM OK)golden-replay
The golden replay promoted 0x1000 placeholders for FECS_EVENT/PRIV/UNR and 1-page VA-only mappings for the four 3D globals; the server's own geometry reports FECS_EVENT 0x10000, PRIV/UNR 0x80000 each, PAGEPOOL 0x20000, ATTRIBUTE_CB 0x7d7400 and RTV_CB_GLOBAL 0x80000 on this TU104. The girmap sizes are wrong for the engine's ctx-init access-map copies and the ctxsw bundle, producing INJECTED_BUNDLE_ERROR + FECS ctxsw TDR on every VAS shape. fwclient-mask bit 10 (0x400) sizes every promoted buffer from the server's GET_ENGINE_CONTEXT_PROPERTIES (0x801707), re-spaces the VAs to per-buffer caps, extends the ctx small-PT pages to six 2 MB windows and promotes the real sizes. Result (golden9k2): golden promote status 0, FWCLIENT MAIN promote status 0, stage 3 complete, REAL GR SEM OK sem=0xc0ffee01 GPGet=1 GPPut=1, clean teardown, no wedge.
Diffstat (limited to 'kernel')
-rw-r--r--kernel/gsp_phys_booter.c448
1 files changed, 329 insertions, 119 deletions
diff --git a/kernel/gsp_phys_booter.c b/kernel/gsp_phys_booter.c
index 6a9542b..764e261 100644
--- a/kernel/gsp_phys_booter.c
+++ b/kernel/gsp_phys_booter.c
@@ -398,12 +398,37 @@ bool gsp_phys_boot_requested(void)
* VAs, which can fault the engine context load).
*/
#define GSP_PHYS_RMCALL_VA_GOLDEN9_FECS (GSP_PHYS_RMCALL_VA_GR_CTX + 0x150000ULL)
-#define GSP_PHYS_RMCALL_VA_GOLDEN9_PRIV (GSP_PHYS_RMCALL_VA_GR_CTX + 0x151000ULL)
-#define GSP_PHYS_RMCALL_VA_GOLDEN9_UNR (GSP_PHYS_RMCALL_VA_GR_CTX + 0x152000ULL)
-#define GSP_PHYS_RMCALL_VA_GOLDEN9_BUNDLE_CB (GSP_PHYS_RMCALL_VA_GR_CTX + 0x160000ULL)
-#define GSP_PHYS_RMCALL_VA_GOLDEN9_PAGEPOOL (GSP_PHYS_RMCALL_VA_GR_CTX + 0x170000ULL)
-#define GSP_PHYS_RMCALL_VA_GOLDEN9_ATTRIBUTE_CB (GSP_PHYS_RMCALL_VA_GR_CTX + 0x180000ULL)
-#define GSP_PHYS_RMCALL_VA_GOLDEN9_RTV_CB_GLOBAL (GSP_PHYS_RMCALL_VA_GR_CTX + 0x190000ULL)
+#define GSP_PHYS_RMCALL_VA_GOLDEN9_PRIV (GSP_PHYS_RMCALL_VA_GR_CTX + 0x160000ULL)
+#define GSP_PHYS_RMCALL_VA_GOLDEN9_UNR (GSP_PHYS_RMCALL_VA_GR_CTX + 0x1e0000ULL)
+#define GSP_PHYS_RMCALL_VA_GOLDEN9_BUNDLE_CB (GSP_PHYS_RMCALL_VA_GR_CTX + 0x260000ULL)
+#define GSP_PHYS_RMCALL_VA_GOLDEN9_PAGEPOOL (GSP_PHYS_RMCALL_VA_GR_CTX + 0x270000ULL)
+#define GSP_PHYS_RMCALL_VA_GOLDEN9_ATTRIBUTE_CB (GSP_PHYS_RMCALL_VA_GR_CTX + 0x2b0000ULL)
+#define GSP_PHYS_RMCALL_VA_GOLDEN9_RTV_CB_GLOBAL (GSP_PHYS_RMCALL_VA_GR_CTX + 0xab0000ULL)
+/*
+ * Golden9k: every promoted context buffer is allocated with the size
+ * GET_ENGINE_CONTEXT_PROPERTIES reports for its engine (the client's own
+ * source for those sizes is the GSP static info; the same control returns
+ * them on this server). Live TU104 sizes (golden9k cycle, 2026-10-05):
+ * FECS_EVENT 0x10000, PRIV/UNR 0x80000 each, BUNDLE_CB 0x3000, PAGEPOOL
+ * 0x20000, ATTRIBUTE_CB 0x7d7400, RTV_CB_GLOBAL 0x80000. The golden9j
+ * hardcoded 0x1000/1-page shapes cannot hold these (the engine's ctx-init
+ * copy of the register access maps is 512 KB per map; the attribute CB is
+ * ~8 MB), which is the leading explanation for the invariant
+ * INJECTED_BUNDLE_ERROR + FECS ctxsw TDR. The VAs below are spaced by the
+ * per-buffer caps; a reported size above its cap aborts before any promote.
+ */
+#define GSP_PHYS_RMCALL_GR_FECS_EVENT_MAX 0x10000u
+#define GSP_PHYS_RMCALL_GR_PRIV_ACCESS_MAP_MAX 0x80000u
+#define GSP_PHYS_RMCALL_GR_BUNDLE_CB_MAX 0x10000u
+#define GSP_PHYS_RMCALL_GR_PAGEPOOL_GLOBAL_MAX 0x40000u
+#define GSP_PHYS_RMCALL_GR_ATTRIBUTE_CB_MAX 0x800000u
+#define GSP_PHYS_RMCALL_GR_RTV_CB_GLOBAL_MAX 0x80000u
+#define GSP_PHYS_RMCALL_GR_FECS_EVENT_ENGINE_ID 0x17u
+#define GSP_PHYS_RMCALL_GR_PRIV_ACCESS_MAP_ENGINE_ID 0x18u
+#define GSP_PHYS_RMCALL_GR_BUNDLE_CB_ENGINE_ID 0x11u
+#define GSP_PHYS_RMCALL_GR_PAGEPOOL_GLOBAL_ENGINE_ID 0x12u
+#define GSP_PHYS_RMCALL_GR_ATTRIBUTE_CB_ENGINE_ID 0x13u
+#define GSP_PHYS_RMCALL_GR_RTV_CB_GLOBAL_ENGINE_ID 0x14u
/*
* Golden9e server FBMEM allocations for the small promoted buffers (PATCH is
* sized by the PATCH engine geometry query; FECS/PRIV/UNR are one 4 KB page
@@ -588,6 +613,16 @@ bool gsp_phys_boot_requested(void)
* invalid (the golden VAS controls are skipped when bit 9 is set).
*/
#define GSP_PHYS_RMCALL_GOLDEN9_MASK_LADDER_VAS (1u << 9)
+/*
+ * Golden9k: allocate and promote the golden context buffers at the sizes
+ * GET_ENGINE_CONTEXT_PROPERTIES reports (FECS_EVENT/PRIV_ACCESS_MAP/
+ * UNRESTRICTED_PRIV_ACCESS_MAP/BUNDLE_CB/PAGEPOOL/ATTRIBUTE_CB/RTV_CB_GLOBAL)
+ * instead of the golden9j/j one-page placeholder sizes, and back every
+ * promoted VA with PTEs covering the full size across as many 2 MB windows
+ * as needed. Bit 10 selects this path; the golden9i/j shapes stay available
+ * for comparison.
+ */
+#define GSP_PHYS_RMCALL_GOLDEN9_MASK_SIZED_BUFFERS (1u << 10)
#define GSP_PHYS_RMCALL_GR_PROMOTE_MAX \
(GSP_PHYS_RMCALL_GR_PROMOTE_GOLDEN9)
@@ -1605,6 +1640,10 @@ static struct gsp_phys_boot_stage {
u32 rmcall_pagepool_size;
u32 rmcall_attr_size;
u32 rmcall_rtv_size;
+ /* golden9k: sizes queried from GET_ENGINE_CONTEXT_PROPERTIES */
+ u32 rmcall_fecs_size;
+ u32 rmcall_priv_size;
+ u32 rmcall_unr_size;
/*
* GR context-promote bisection snapshot (stage 3, GR0 only): the 0..3
* gsp_phys_rmcall_gr_promote value, the number of accepted promote
@@ -2237,6 +2276,13 @@ static void gsp_phys_rmcall_reset(void)
boot_stage.rmcall_ctx_valid = false;
boot_stage.rmcall_ctx_fbmem = false;
boot_stage.rmcall_golden_fb_aux = false;
+ boot_stage.rmcall_fecs_size = 0;
+ boot_stage.rmcall_priv_size = 0;
+ boot_stage.rmcall_unr_size = 0;
+ boot_stage.rmcall_bundle_size = 0;
+ boot_stage.rmcall_pagepool_size = 0;
+ boot_stage.rmcall_attr_size = 0;
+ boot_stage.rmcall_rtv_size = 0;
boot_stage.rmcall_ctx_pa = 0;
boot_stage.rmcall_ctx_va = 0;
boot_stage.rmcall_ctx_size = 0;
@@ -8276,6 +8322,36 @@ static u64 gsp_phys_rmcall_pte_vid(u64 fb_offset)
}
/*
+ * Golden9k: map [va, va+size) with VIDMEM PTEs into the ctx small-PT pages.
+ * One rmcall_ctx_pt page covers one 2 MB window (windows start at
+ * GSP_PHYS_RMCALL_VA_GR_CTX >> 21); a range may span windows, and the PT
+ * pages for every window it touches must already exist (gr_ctx_prepare plus
+ * the golden9k extension in golden9_fb_aux_prepare). Every slot written is
+ * distinct from MAIN's and from the other aux buffers (the caller places
+ * them on 1 MB slots).
+ */
+static void gsp_phys_rmcall_golden9_map_range(u64 va, u64 pa, u32 size)
+{
+ u32 first_win = (u32)(GSP_PHYS_RMCALL_VA_GR_CTX >> 21);
+ u32 pages = DIV_ROUND_UP(size, GSP_PHYS_PAGE_SIZE);
+ u32 i;
+
+ for (i = 0; i < pages; i++) {
+ u64 v = va + (u64)i * GSP_PHYS_PAGE_SIZE;
+ u32 win = (u32)(v >> 21) - first_win;
+ u32 slot = (u32)((v >> 12) & 0x1ffu);
+ u8 *ptv;
+
+ if (win >= boot_stage.rmcall_ctx_pt_pages)
+ break;
+ ptv = gsp_phys_chunk_page_va(&boot_stage.rmcall_ctx_pt[win], 0);
+ put_unaligned_le64(gsp_phys_rmcall_pte_vid(pa +
+ (u64)i * GSP_PHYS_PAGE_SIZE),
+ ptv + (size_t)slot * 8);
+ }
+}
+
+/*
* Build the channel's page-directory hierarchy around the 2 MB VA window
* GSP_PHYS_RMCALL_VA_BASE that maps the GPFIFO, pushbuffer and the CE copy's
* src/dst/semaphore sysmem pages:
@@ -8475,114 +8551,70 @@ static void gsp_phys_rmcall_pdb_build(void)
0) + (size_t)pt_slot * 8);
}
/*
- * Golden9e: map the FBMEM PATCH/FECS/PRIV/UNR buffers at their
- * promoted VAs in the same 2 MB window as MAIN (window 17) with
- * VIDMEM PTEs. Every slot used here is above MAIN's tail
- * (0x2200000 + 0x133000 = slot 0x133) and distinct.
+ * Golden9e/j/k: map the FBMEM PATCH/FECS/PRIV/UNR and the four
+ * 3D global buffers at their promoted VAs with VIDMEM PTEs.
+ * Every buffer sits on its own 1 MB slot, so the ranges never
+ * overlap and can span 2 MB windows (the helper picks the PT
+ * page per page).
*/
if (boot_stage.rmcall_golden_fb_aux) {
- u8 *ptv = gsp_phys_chunk_page_va(
- &boot_stage.rmcall_ctx_pt[0], 0);
- u32 slot, npages;
-
- npages = DIV_ROUND_UP(boot_stage.rmcall_patch_size,
- GSP_PHYS_PAGE_SIZE);
- slot = (u32)((GSP_PHYS_RMCALL_VA_GR_PATCH >> 12) &
- 0x1ffu);
- for (i = 0; i < npages; i++)
- put_unaligned_le64(
- gsp_phys_rmcall_pte_vid(
- boot_stage.rmcall_patch_pa +
- (u64)i * GSP_PHYS_PAGE_SIZE),
- ptv + (size_t)(slot + i) * 8);
- slot = (u32)((GSP_PHYS_RMCALL_VA_GOLDEN9_FECS >> 12) &
- 0x1ffu);
- put_unaligned_le64(
- gsp_phys_rmcall_pte_vid(
- boot_stage.rmcall_fecs_pa),
- ptv + (size_t)slot * 8);
- slot = (u32)((GSP_PHYS_RMCALL_VA_GOLDEN9_PRIV >> 12) &
- 0x1ffu);
- put_unaligned_le64(
- gsp_phys_rmcall_pte_vid(
- boot_stage.rmcall_priv_pa),
- ptv + (size_t)slot * 8);
- slot = (u32)((GSP_PHYS_RMCALL_VA_GOLDEN9_UNR >> 12) &
- 0x1ffu);
- put_unaligned_le64(
- gsp_phys_rmcall_pte_vid(
- boot_stage.rmcall_unrestricted_pa),
- ptv + (size_t)slot * 8);
- /*
- * Golden9j: back and map the four 3D globals at their
- * promoted VAs (the promote entries stay VA-only, as
- * captured). Each VA slot holds up to 16 pages.
- */
- slot = (u32)((GSP_PHYS_RMCALL_VA_GOLDEN9_BUNDLE_CB >>
- 12) & 0x1ffu);
- npages = min_t(u32,
- DIV_ROUND_UP(boot_stage.rmcall_bundle_size,
- GSP_PHYS_PAGE_SIZE),
- GSP_PHYS_RMCALL_GR_GLOBAL_MAX_PAGES);
- for (i = 0; i < npages; i++)
- put_unaligned_le64(
- gsp_phys_rmcall_pte_vid(
- boot_stage.rmcall_bundle_pa +
- (u64)i * GSP_PHYS_PAGE_SIZE),
- ptv + (size_t)(slot + i) * 8);
- slot = (u32)((GSP_PHYS_RMCALL_VA_GOLDEN9_PAGEPOOL >>
- 12) & 0x1ffu);
- npages = min_t(u32,
- DIV_ROUND_UP(boot_stage.rmcall_pagepool_size,
- GSP_PHYS_PAGE_SIZE),
- GSP_PHYS_RMCALL_GR_GLOBAL_MAX_PAGES);
- for (i = 0; i < npages; i++)
- put_unaligned_le64(
- gsp_phys_rmcall_pte_vid(
- boot_stage.rmcall_pagepool_pa +
- (u64)i * GSP_PHYS_PAGE_SIZE),
- ptv + (size_t)(slot + i) * 8);
- slot = (u32)((GSP_PHYS_RMCALL_VA_GOLDEN9_ATTRIBUTE_CB >>
- 12) & 0x1ffu);
- npages = min_t(u32,
- DIV_ROUND_UP(boot_stage.rmcall_attr_size,
- GSP_PHYS_PAGE_SIZE),
- GSP_PHYS_RMCALL_GR_GLOBAL_MAX_PAGES);
- for (i = 0; i < npages; i++)
- put_unaligned_le64(
- gsp_phys_rmcall_pte_vid(
- boot_stage.rmcall_attr_pa +
- (u64)i * GSP_PHYS_PAGE_SIZE),
- ptv + (size_t)(slot + i) * 8);
- slot = (u32)((GSP_PHYS_RMCALL_VA_GOLDEN9_RTV_CB_GLOBAL >>
- 12) & 0x1ffu);
- npages = min_t(u32,
- DIV_ROUND_UP(boot_stage.rmcall_rtv_size,
- GSP_PHYS_PAGE_SIZE),
- GSP_PHYS_RMCALL_GR_GLOBAL_MAX_PAGES);
- for (i = 0; i < npages; i++)
- put_unaligned_le64(
- gsp_phys_rmcall_pte_vid(
- boot_stage.rmcall_rtv_pa +
- (u64)i * GSP_PHYS_PAGE_SIZE),
- ptv + (size_t)(slot + i) * 8);
- pr_info("vgsp-boot: rm-call: GOLDEN9E PDB aux mapped: patch va=0x%llx pages=%u (pa=0x%llx) fecs va=0x%llx (pa=0x%llx) priv va=0x%llx (pa=0x%llx) unr va=0x%llx (pa=0x%llx) (VIDMEM PTEs)\n",
- GSP_PHYS_RMCALL_VA_GR_PATCH, npages,
+ gsp_phys_rmcall_golden9_map_range(
+ GSP_PHYS_RMCALL_VA_GR_PATCH,
+ boot_stage.rmcall_patch_pa,
+ boot_stage.rmcall_patch_size);
+ gsp_phys_rmcall_golden9_map_range(
+ GSP_PHYS_RMCALL_VA_GOLDEN9_FECS,
+ boot_stage.rmcall_fecs_pa,
+ boot_stage.rmcall_fecs_size);
+ gsp_phys_rmcall_golden9_map_range(
+ GSP_PHYS_RMCALL_VA_GOLDEN9_PRIV,
+ boot_stage.rmcall_priv_pa,
+ boot_stage.rmcall_priv_size);
+ gsp_phys_rmcall_golden9_map_range(
+ GSP_PHYS_RMCALL_VA_GOLDEN9_UNR,
+ boot_stage.rmcall_unrestricted_pa,
+ boot_stage.rmcall_unr_size);
+ gsp_phys_rmcall_golden9_map_range(
+ GSP_PHYS_RMCALL_VA_GOLDEN9_BUNDLE_CB,
+ boot_stage.rmcall_bundle_pa,
+ boot_stage.rmcall_bundle_size);
+ gsp_phys_rmcall_golden9_map_range(
+ GSP_PHYS_RMCALL_VA_GOLDEN9_PAGEPOOL,
+ boot_stage.rmcall_pagepool_pa,
+ boot_stage.rmcall_pagepool_size);
+ gsp_phys_rmcall_golden9_map_range(
+ GSP_PHYS_RMCALL_VA_GOLDEN9_ATTRIBUTE_CB,
+ boot_stage.rmcall_attr_pa,
+ boot_stage.rmcall_attr_size);
+ gsp_phys_rmcall_golden9_map_range(
+ GSP_PHYS_RMCALL_VA_GOLDEN9_RTV_CB_GLOBAL,
+ boot_stage.rmcall_rtv_pa,
+ boot_stage.rmcall_rtv_size);
+ pr_info("vgsp-boot: rm-call: GOLDEN9E PDB aux mapped: patch va=0x%llx size=0x%x (pa=0x%llx) fecs va=0x%llx size=0x%x (pa=0x%llx) priv va=0x%llx size=0x%x (pa=0x%llx) unr va=0x%llx size=0x%x (pa=0x%llx) (VIDMEM PTEs)\n",
+ GSP_PHYS_RMCALL_VA_GR_PATCH,
+ boot_stage.rmcall_patch_size,
boot_stage.rmcall_patch_pa,
GSP_PHYS_RMCALL_VA_GOLDEN9_FECS,
+ boot_stage.rmcall_fecs_size,
boot_stage.rmcall_fecs_pa,
GSP_PHYS_RMCALL_VA_GOLDEN9_PRIV,
+ boot_stage.rmcall_priv_size,
boot_stage.rmcall_priv_pa,
GSP_PHYS_RMCALL_VA_GOLDEN9_UNR,
+ boot_stage.rmcall_unr_size,
boot_stage.rmcall_unrestricted_pa);
- pr_info("vgsp-boot: rm-call: GOLDEN9J globals mapped: bundle va=0x%llx (pa=0x%llx) pagepool va=0x%llx (pa=0x%llx) attr va=0x%llx (pa=0x%llx) rtv va=0x%llx (pa=0x%llx) (VIDMEM PTEs, one page each)\n",
+ pr_info("vgsp-boot: rm-call: GOLDEN9J globals mapped: bundle va=0x%llx size=0x%x (pa=0x%llx) pagepool va=0x%llx size=0x%x (pa=0x%llx) attr va=0x%llx size=0x%x (pa=0x%llx) rtv va=0x%llx size=0x%x (pa=0x%llx) (VIDMEM PTEs, full-size coverage)\n",
GSP_PHYS_RMCALL_VA_GOLDEN9_BUNDLE_CB,
+ boot_stage.rmcall_bundle_size,
boot_stage.rmcall_bundle_pa,
GSP_PHYS_RMCALL_VA_GOLDEN9_PAGEPOOL,
+ boot_stage.rmcall_pagepool_size,
boot_stage.rmcall_pagepool_pa,
GSP_PHYS_RMCALL_VA_GOLDEN9_ATTRIBUTE_CB,
+ boot_stage.rmcall_attr_size,
boot_stage.rmcall_attr_pa,
GSP_PHYS_RMCALL_VA_GOLDEN9_RTV_CB_GLOBAL,
+ boot_stage.rmcall_rtv_size,
boot_stage.rmcall_rtv_pa);
}
pr_info("vgsp-boot: rm-call: GR ctx PDB mapped: va=0x%llx size=0x%x pages=%u ptPages=%u pd0Entries=%u..%u (%s; fresh slots above the scratch pool; no fetched line rewritten)\n",
@@ -8643,6 +8675,42 @@ static void gsp_phys_rmcall_pdb_build(void)
}
/*
+ * Golden9k: query the size/alignment GET_ENGINE_CONTEXT_PROPERTIES reports
+ * for one engine context buffer (the same control the MAIN/PATCH geometry
+ * uses; the server derives the values from the static info the stock client
+ * caches at GSP boot). Returns 0 with size/align set, the RPC error on
+ * failure, -EINVAL on a zero size (buffer unsupported on this engine).
+ */
+static int gsp_phys_rmcall_engine_ctx_size(void __iomem *bar0, u32 engine_id,
+ const char *name, u32 *size,
+ u32 *align)
+{
+ struct gsp_phys_rmcall_engine_ctx_props props;
+ u32 rpc_result = 0, status = 0;
+ int ret;
+
+ memset(&props, 0, sizeof(props));
+ props.engine_id = cpu_to_le32(engine_id);
+ ret = gsp_phys_rmcall_control(bar0, boot_stage.rmcall_device,
+ GSP_PHYS_RMCALL_CTRL_FIFO_GET_ENGINE_CONTEXT_PROPERTIES,
+ &props, sizeof(props), 24 + sizeof(props),
+ &props, sizeof(props), &rpc_result, &status,
+ "GR_GET_ENGINE_CONTEXT_PROPERTIES (golden9k)");
+ *size = le32_to_cpu(props.size);
+ *align = le32_to_cpu(props.alignment);
+ pr_info("vgsp-boot: rm-call: GOLDEN9K %s geometry: engineId=0x%x rawSize=0x%x alignment=0x%x status=0x%x rpc_result=0x%x\n",
+ name, engine_id, *size, *align, status, rpc_result);
+ if (ret)
+ return ret;
+ if (!*size) {
+ pr_err("vgsp-boot: rm-call: GOLDEN9K %s reports size 0 (unsupported); aborting with no promote and no retry\n",
+ name);
+ return -EINVAL;
+ }
+ return 0;
+}
+
+/*
* Mode-25 golden9e: allocate the promoted PATCH/FECS/PRIV/UNR context
* buffers in server FBMEM (the real golden wire carried FBMEM for every
* context buffer; the earlier host-sysmem substitution is a documented
@@ -8656,6 +8724,7 @@ static int gsp_phys_rmcall_golden9_fb_aux_prepare(void __iomem *bar0)
{
struct gsp_phys_rmcall_engine_ctx_props props;
u32 raw, rpc_result = 0, status = 0;
+ u32 i;
u64 fb = 0;
int ret;
@@ -8689,22 +8758,121 @@ static int gsp_phys_rmcall_golden9_fb_aux_prepare(void __iomem *bar0)
boot_stage.rmcall_patch_size = raw;
boot_stage.rmcall_patch_prepared = true;
+ /*
+ * Golden9k (fwclient-mask bit 10): size every promoted buffer from the
+ * engine-context-properties query. The bInitialize=1 entries (FECS_EVENT/
+ * PRIV/UNR) are written by the server's init copy, and the VA-only
+ * globals are written by the ctxsw bundle through the page tables; the
+ * golden9j one-page shapes cannot hold either (the Turing private and
+ * unrestricted register access maps are 512 KB each). The stock client's
+ * sizes come from the GSP static info; this control reports the same
+ * values. A size above its per-buffer VA cap aborts before any promote.
+ */
+ if (gsp_phys_rmcall_fwclient_mask_value() &
+ GSP_PHYS_RMCALL_GOLDEN9_MASK_SIZED_BUFFERS) {
+ u32 align;
+
+ ret = gsp_phys_rmcall_engine_ctx_size(bar0,
+ GSP_PHYS_RMCALL_GR_FECS_EVENT_ENGINE_ID,
+ "FECS_EVENT", &raw, &align);
+ if (ret)
+ return ret;
+ boot_stage.rmcall_fecs_size = raw;
+ ret = gsp_phys_rmcall_engine_ctx_size(bar0,
+ GSP_PHYS_RMCALL_GR_PRIV_ACCESS_MAP_ENGINE_ID,
+ "PRIV_ACCESS_MAP", &raw, &align);
+ if (ret)
+ return ret;
+ boot_stage.rmcall_priv_size = raw;
+ boot_stage.rmcall_unr_size = raw;
+ ret = gsp_phys_rmcall_engine_ctx_size(bar0,
+ GSP_PHYS_RMCALL_GR_BUNDLE_CB_ENGINE_ID,
+ "BUNDLE_CB", &raw, &align);
+ if (ret)
+ return ret;
+ boot_stage.rmcall_bundle_size = raw;
+ ret = gsp_phys_rmcall_engine_ctx_size(bar0,
+ GSP_PHYS_RMCALL_GR_PAGEPOOL_GLOBAL_ENGINE_ID,
+ "PAGEPOOL", &raw, &align);
+ if (ret)
+ return ret;
+ boot_stage.rmcall_pagepool_size = raw;
+ ret = gsp_phys_rmcall_engine_ctx_size(bar0,
+ GSP_PHYS_RMCALL_GR_ATTRIBUTE_CB_ENGINE_ID,
+ "ATTRIBUTE_CB", &raw, &align);
+ if (ret)
+ return ret;
+ boot_stage.rmcall_attr_size = raw;
+ ret = gsp_phys_rmcall_engine_ctx_size(bar0,
+ GSP_PHYS_RMCALL_GR_RTV_CB_GLOBAL_ENGINE_ID,
+ "RTV_CB_GLOBAL", &raw, &align);
+ if (ret)
+ return ret;
+ boot_stage.rmcall_rtv_size = raw;
+ if (boot_stage.rmcall_fecs_size >
+ GSP_PHYS_RMCALL_GR_FECS_EVENT_MAX ||
+ boot_stage.rmcall_priv_size >
+ GSP_PHYS_RMCALL_GR_PRIV_ACCESS_MAP_MAX ||
+ boot_stage.rmcall_bundle_size >
+ GSP_PHYS_RMCALL_GR_BUNDLE_CB_MAX ||
+ boot_stage.rmcall_pagepool_size >
+ GSP_PHYS_RMCALL_GR_PAGEPOOL_GLOBAL_MAX ||
+ boot_stage.rmcall_attr_size >
+ GSP_PHYS_RMCALL_GR_ATTRIBUTE_CB_MAX ||
+ boot_stage.rmcall_rtv_size >
+ GSP_PHYS_RMCALL_GR_RTV_CB_GLOBAL_MAX) {
+ pr_err("vgsp-boot: rm-call: GOLDEN9K a promoted buffer exceeds its per-buffer VA cap (fecs=0x%x/0x%x priv=0x%x/0x%x bundle=0x%x/0x%x pagepool=0x%x/0x%x attr=0x%x/0x%x rtv=0x%x/0x%x); aborting with no promote and no retry\n",
+ boot_stage.rmcall_fecs_size,
+ GSP_PHYS_RMCALL_GR_FECS_EVENT_MAX,
+ boot_stage.rmcall_priv_size,
+ GSP_PHYS_RMCALL_GR_PRIV_ACCESS_MAP_MAX,
+ boot_stage.rmcall_bundle_size,
+ GSP_PHYS_RMCALL_GR_BUNDLE_CB_MAX,
+ boot_stage.rmcall_pagepool_size,
+ GSP_PHYS_RMCALL_GR_PAGEPOOL_GLOBAL_MAX,
+ boot_stage.rmcall_attr_size,
+ GSP_PHYS_RMCALL_GR_ATTRIBUTE_CB_MAX,
+ boot_stage.rmcall_rtv_size,
+ GSP_PHYS_RMCALL_GR_RTV_CB_GLOBAL_MAX);
+ return -E2BIG;
+ }
+ pr_info("vgsp-boot: rm-call: GOLDEN9K sized buffers: fecs=0x%x priv=0x%x unr=0x%x bundle=0x%x pagepool=0x%x attr=0x%x rtv=0x%x (all queried)\n",
+ boot_stage.rmcall_fecs_size,
+ boot_stage.rmcall_priv_size,
+ boot_stage.rmcall_unr_size,
+ boot_stage.rmcall_bundle_size,
+ boot_stage.rmcall_pagepool_size,
+ boot_stage.rmcall_attr_size,
+ boot_stage.rmcall_rtv_size);
+ } else {
+ boot_stage.rmcall_fecs_size = 0x1000;
+ boot_stage.rmcall_priv_size = 0x1000;
+ boot_stage.rmcall_unr_size = 0x1000;
+ boot_stage.rmcall_bundle_size = 0x1000;
+ boot_stage.rmcall_pagepool_size = 0x1000;
+ boot_stage.rmcall_attr_size = 0x1000;
+ boot_stage.rmcall_rtv_size = 0x1000;
+ }
+
ret = gsp_phys_rmcall_alloc_fb_mem(bar0,
- GSP_PHYS_RMCALL_HANDLE_GOLDEN_FB_FECS, 0x1000, &fb,
+ GSP_PHYS_RMCALL_HANDLE_GOLDEN_FB_FECS,
+ boot_stage.rmcall_fecs_size, &fb,
"GOLDEN9E FECS_EVENT");
if (ret)
return ret;
boot_stage.rmcall_fecs_pa = fb;
ret = gsp_phys_rmcall_alloc_fb_mem(bar0,
- GSP_PHYS_RMCALL_HANDLE_GOLDEN_FB_PRIV, 0x1000, &fb,
+ GSP_PHYS_RMCALL_HANDLE_GOLDEN_FB_PRIV,
+ boot_stage.rmcall_priv_size, &fb,
"GOLDEN9E PRIV_ACCESS_MAP");
if (ret)
return ret;
boot_stage.rmcall_priv_pa = fb;
ret = gsp_phys_rmcall_alloc_fb_mem(bar0,
- GSP_PHYS_RMCALL_HANDLE_GOLDEN_FB_UNR, 0x1000, &fb,
+ GSP_PHYS_RMCALL_HANDLE_GOLDEN_FB_UNR,
+ boot_stage.rmcall_unr_size, &fb,
"GOLDEN9E UNR_PRIV_ACCESS_MAP");
if (ret)
return ret;
@@ -8715,48 +8883,90 @@ static int gsp_phys_rmcall_golden9_fb_aux_prepare(void __iomem *bar0)
* with the size its own geometry query returned and mapped it in the
* channel VAS; the promote carries the VAs (bInitialize=0, no PA), so
* the ctx-init bundle reads and writes them through the page tables.
- * Sizes are clamped to one 16-page slot per VA constant.
+ * Golden9k sizes them from the same query as the rest; golden9j kept
+ * them at one page each.
*/
ret = gsp_phys_rmcall_alloc_fb_mem(bar0,
- GSP_PHYS_RMCALL_HANDLE_GOLDEN_FB_BUNDLE, 0x1000, &fb,
+ GSP_PHYS_RMCALL_HANDLE_GOLDEN_FB_BUNDLE,
+ boot_stage.rmcall_bundle_size, &fb,
"GOLDEN9J BUNDLE_CB");
if (ret)
return ret;
boot_stage.rmcall_bundle_pa = fb;
- boot_stage.rmcall_bundle_size = 0x1000;
ret = gsp_phys_rmcall_alloc_fb_mem(bar0,
- GSP_PHYS_RMCALL_HANDLE_GOLDEN_FB_PAGEPOOL, 0x1000, &fb,
+ GSP_PHYS_RMCALL_HANDLE_GOLDEN_FB_PAGEPOOL,
+ boot_stage.rmcall_pagepool_size, &fb,
"GOLDEN9J PAGEPOOL");
if (ret)
return ret;
boot_stage.rmcall_pagepool_pa = fb;
- boot_stage.rmcall_pagepool_size = 0x1000;
ret = gsp_phys_rmcall_alloc_fb_mem(bar0,
- GSP_PHYS_RMCALL_HANDLE_GOLDEN_FB_ATTR, 0x1000, &fb,
+ GSP_PHYS_RMCALL_HANDLE_GOLDEN_FB_ATTR,
+ boot_stage.rmcall_attr_size, &fb,
"GOLDEN9J ATTRIBUTE_CB");
if (ret)
return ret;
boot_stage.rmcall_attr_pa = fb;
- boot_stage.rmcall_attr_size = 0x1000;
ret = gsp_phys_rmcall_alloc_fb_mem(bar0,
- GSP_PHYS_RMCALL_HANDLE_GOLDEN_FB_RTV, 0x1000, &fb,
+ GSP_PHYS_RMCALL_HANDLE_GOLDEN_FB_RTV,
+ boot_stage.rmcall_rtv_size, &fb,
"GOLDEN9J RTV_CB_GLOBAL");
if (ret)
return ret;
boot_stage.rmcall_rtv_pa = fb;
- boot_stage.rmcall_rtv_size = 0x1000;
+
+ /*
+ * Golden9k: the sized layout spans as many 2 MB windows as the highest
+ * promoted VA needs; allocate the extra small-PT pages now, before the
+ * PDB build and the DMA_UPDATE_PDE_2 window installs consume
+ * rmcall_ctx_pt_pages. MAIN's pages were already sized/allocated.
+ */
+ {
+ u32 first_win = (u32)(GSP_PHYS_RMCALL_VA_GR_CTX >> 21);
+ u32 last_win = (u32)((GSP_PHYS_RMCALL_VA_GOLDEN9_RTV_CB_GLOBAL +
+ boot_stage.rmcall_rtv_size - 1) >> 21);
+ u32 need = last_win - first_win + 1;
+
+ if (need > GSP_PHYS_RMCALL_GR_CTX_PT_MAX) {
+ pr_err("vgsp-boot: rm-call: GOLDEN9K sized layout needs %u PT pages > max %u; aborting with no promote and no retry\n",
+ need, GSP_PHYS_RMCALL_GR_CTX_PT_MAX);
+ return -E2BIG;
+ }
+ for (i = boot_stage.rmcall_ctx_pt_pages; i < need; i++) {
+ ret = gsp_phys_chunk_alloc(boot_stage.pdev,
+ &boot_stage.rmcall_ctx_pt[i],
+ 1u);
+ if (ret) {
+ pr_err("vgsp-boot: rm-call: GOLDEN9K ctx PT page %u/%u allocation failed: %d; aborting the ladder with no retry\n",
+ i, need, ret);
+ return ret;
+ }
+ gsp_phys_chunk_zero(&boot_stage.rmcall_ctx_pt[i]);
+ }
+ if (need > boot_stage.rmcall_ctx_pt_pages) {
+ pr_info("vgsp-boot: rm-call: GOLDEN9K ctx PT pages extended %u -> %u for the sized layout (last VA 0x%llx + 0x%x)\n",
+ boot_stage.rmcall_ctx_pt_pages, need,
+ GSP_PHYS_RMCALL_VA_GOLDEN9_RTV_CB_GLOBAL,
+ boot_stage.rmcall_rtv_size);
+ boot_stage.rmcall_ctx_pt_pages = need;
+ }
+ }
boot_stage.rmcall_golden_fb_aux = true;
- pr_info("vgsp-boot: rm-call: GOLDEN9E FBMEM aux buffers ready: patch pa=0x%llx size=0x%x fecs=0x%llx priv=0x%llx unr=0x%llx (server FBMEM, all mapped in the ctx PDB window)\n",
+ pr_info("vgsp-boot: rm-call: GOLDEN9E FBMEM aux buffers ready: patch pa=0x%llx size=0x%x fecs=0x%llx size=0x%x priv=0x%llx size=0x%x unr=0x%llx size=0x%x (server FBMEM, all mapped in the ctx PDB windows)\n",
boot_stage.rmcall_patch_pa, boot_stage.rmcall_patch_size,
- boot_stage.rmcall_fecs_pa, boot_stage.rmcall_priv_pa,
- boot_stage.rmcall_unrestricted_pa);
- pr_info("vgsp-boot: rm-call: GOLDEN9J global buffers ready: bundle=0x%llx pagepool=0x%llx attr=0x%llx rtv=0x%llx (server FBMEM, one page each, mapped at the promoted VAs)\n",
- boot_stage.rmcall_bundle_pa, boot_stage.rmcall_pagepool_pa,
- boot_stage.rmcall_attr_pa, boot_stage.rmcall_rtv_pa);
+ boot_stage.rmcall_fecs_pa, boot_stage.rmcall_fecs_size,
+ boot_stage.rmcall_priv_pa, boot_stage.rmcall_priv_size,
+ boot_stage.rmcall_unrestricted_pa,
+ boot_stage.rmcall_unr_size);
+ pr_info("vgsp-boot: rm-call: GOLDEN9J global buffers ready: bundle=0x%llx size=0x%x pagepool=0x%llx size=0x%x attr=0x%llx size=0x%x rtv=0x%llx size=0x%x (server FBMEM, PTEs cover the full size)\n",
+ boot_stage.rmcall_bundle_pa, boot_stage.rmcall_bundle_size,
+ boot_stage.rmcall_pagepool_pa, boot_stage.rmcall_pagepool_size,
+ boot_stage.rmcall_attr_pa, boot_stage.rmcall_attr_size,
+ boot_stage.rmcall_rtv_pa, boot_stage.rmcall_rtv_size);
return 0;
}
@@ -9291,15 +9501,15 @@ static int gsp_phys_rmcall_golden9_promote(void __iomem *bar0)
gsp_phys_rmcall_promote_entry_fill(p, 6,
GSP_PHYS_RMCALL_GR_CTX_BUFFER_ID_FECS_EVENT,
boot_stage.rmcall_fecs_pa, GSP_PHYS_RMCALL_VA_GOLDEN9_FECS,
- 0x1000u, fattr, 1, 0);
+ boot_stage.rmcall_fecs_size, fattr, 1, 0);
gsp_phys_rmcall_promote_entry_fill(p, 7,
GSP_PHYS_RMCALL_GR_CTX_BUFFER_ID_PRIV_MAP,
boot_stage.rmcall_priv_pa, GSP_PHYS_RMCALL_VA_GOLDEN9_PRIV,
- 0x1000u, fattr, 1, 0);
+ boot_stage.rmcall_priv_size, fattr, 1, 0);
gsp_phys_rmcall_promote_entry_fill(p, 8,
GSP_PHYS_RMCALL_GR_CTX_BUFFER_ID_UNR_PRIV_MAP,
boot_stage.rmcall_unrestricted_pa, GSP_PHYS_RMCALL_VA_GOLDEN9_UNR,
- 0x1000u, fattr, 1, 0);
+ boot_stage.rmcall_unr_size, fattr, 1, 0);
for (i = 0; i < 9; i++)
pr_info("vgsp-boot: rm-call: PROMOTE_CTX golden9 entry[%u]: bufferId=%u pa=0x%llx va=0x%llx size=0x%llx physAttr=0x%x bInitialize=%u bNonmapped=%u%s\n",