summaryrefslogtreecommitdiffstats
path: root/kernel/gsp_sema_service.c
diff options
context:
space:
mode:
authorArthur Hanson Rasmusson <arthur@vgpu.io>2026-11-07 18:44:21 -0500
committerArthur Hanson Rasmusson <arthur@vgpu.io>2026-11-07 18:44:21 -0500
commit035d033c5a047e395a7b06bceea1dc5b594c3b90 (patch)
treeec772c209376abf0fa65fb1cea5c1527d4ce1fbe /kernel/gsp_sema_service.c
parent22ca5d04f2fdd91500ff82b6e5154a7e5efb50d4 (diff)
downloadopen-iov-035d033c5a047e395a7b06bceea1dc5b594c3b90.tar.gz
open-iov-035d033c5a047e395a7b06bceea1dc5b594c3b90.zip
vgsp-disp: host-side EVO display engine (channels, push buffer, notifier, raster)
The guest nvidia-modeset drives the display through per-channel NV-DMA push buffers kicked via the BAR0 UDISP control windows. Emulate that engine contract host-side, unmodified guest: - channel registration: display-channel RM objects (core 0xc57d, window 0xc57e, cursor 0xc57b, 0xc57a) are noted from the alloc stream, and the internal control NV2080_CTRL_CMD_INTERNAL_DISPLAY_CHANNEL_PUSHBUFFER (0x20800a58) records each push buffer (guest PA, size, class, instance, validity); - PUT polling + GET publication in the channel control pages (core 0x680000, window 0x690000+n*0x1000, cursor 0x6D8000+n*0x1000); - NV-DMA method parser (METHOD/ONE_INC/NONINC/JUMP/SET_SUBDEVICE_MASK) with the wrap-JUMP follow; - completion: SET_CONTEXT_DMA_NOTIFIER / SET_NOTIFIER_CONTROL tracking, exact notifier-surface resolution through the display instance hash table (no heuristic writes), NV_DISP_NOTIFIER FINISHED on UPDATE (0x200), and the channel completion event post; - free-running 1080p60 raster line for NVC57E_GET_LINE. All effects are behind independent knobs (disp_engine, disp_finish, disp_vblank, disp_events, disp_notifier_pa) with verbose diagnostics (disp_dbg, disp_dump), so the previous behaviour stays one load away.
Diffstat (limited to 'kernel/gsp_sema_service.c')
-rw-r--r--kernel/gsp_sema_service.c18
1 files changed, 18 insertions, 0 deletions
diff --git a/kernel/gsp_sema_service.c b/kernel/gsp_sema_service.c
index 6f0103b..fb75f33 100644
--- a/kernel/gsp_sema_service.c
+++ b/kernel/gsp_sema_service.c
@@ -53,6 +53,7 @@
#include "bar_emulation.h"
#include "gsp_sema_service.h"
#include "gsp_rm_emulation.h"
+#include "gsp_display_engine.h"
#include "gsp_phys_booter.h"
#include "gsp_phys_gpu.h"
#include "gsp_cuda_bridge.h"
@@ -44686,6 +44687,16 @@ static int svc_thread(void *arg)
pumped = true;
/*
+ * r1621: display-engine progress. The guest's
+ * nvidia-modeset kicks its EVO channels through the
+ * BAR0 UDISP control windows; consume the push buffers,
+ * publish GET and complete each UPDATE's core notifier.
+ * The boot display-init and every Xorg mode set wait on
+ * that completion.
+ */
+ gsp_disp_engine_pump(vgpu);
+
+ /*
* Host CUDA bridge: marshal one queued launch into a
* daemon job and resolve completions. Inert until a
* launch is seen.
@@ -44876,8 +44887,11 @@ int gsp_sema_service_start(void)
* while gsp_phys_work_forward is enabled; the software path needs no
* workqueue at all.
*/
+ if (gsp_disp_engine_init())
+ pr_warn("sema-svc: display engine init failed\n");
svc.task = kthread_run(svc_thread, NULL, "gsp-sema-svc");
if (IS_ERR(svc.task)) {
+ gsp_disp_engine_fini();
int ret = PTR_ERR(svc.task);
svc.task = NULL;
@@ -44921,6 +44935,7 @@ void gsp_sema_service_stop(void)
svc_fwd_wq = NULL;
}
/* Thread is gone: release the bridge's pending jobs and debugfs files. */
+ gsp_disp_engine_fini();
gsp_cuda_bridge_fini();
svc_setup_demand_debugfs_fini();
/* A fresh session must not inherit shadowed bytes from the last one. */
@@ -44957,6 +44972,9 @@ void gsp_sema_service_vgpu_cleanup(struct nv_vgpu_device *vgpu)
if (!vgpu)
return;
+ /* r1621: drop the guest's display channels with the rest of its state. */
+ gsp_disp_engine_vgpu_cleanup(vgpu);
+
/*
* The forward work item runs on its own kthread and may be using the
* request's vgpu; quiesce waits for it (bounded by the submit's