| Commit message (Collapse) | Author | Age |
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
New default-off gsp_phys_relay: for a forwarded guest CE copy whose push
ends in a one-word release, the release page is resolved at forward time,
mapped on a fresh scratch line, and the real engine writes the payload
directly into the guest-visible semaphore page; the deferred-release hold
then verifies that page and skips only that record's software apply. Any
failure (unresolvable target, refused kind, pool exhaustion, poll timeout,
data mismatch, channel teardown) falls back to applying every release in
software, so a release is never lost or duplicated.
- new exported gsp_phys_backend_guest_ce_copy_ex() + relay counters;
gsp_phys_backend_guest_ce_copy() behavior unchanged (wrapper)
- new work_relay: counters line in gsp-phys-state
- relay limited to CE channels and one-word absolute releases; counter
and reduction releases stay on the existing paths
Live: param-off regression matched the wave-2 baseline exactly (req=101
ok=101 verify_ok=101, copy_skipped=119, smoke matched=64/64, relay zeros).
With the parameter on: requested=68 ok=67 skipped_sw=67, verify_fail=0,
resolve_fail=0, timeouts=0, smoke 64/64, and the engine-authored guest
semaphore was observed directly (sem=0x00000003 / 0x0000007e at the guest
page). One copy in 68 released its semaphore but failed the host-side data
compare; it fell back to the software apply (fallback accounting
applied+fallback==engaged) with the smoke green - residual to triage, which
is why the parameter stays default-off. A forced-unresolvable run
(requested=103, fallback=105, no relay submissions) kept the smoke green.
Every cycle: 5 power-domain locks held, driver rebound, WPR2 down, no rail
cycles, pstore empty, same boot.
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
Triggers 6 (W2G) and 7 (G2H) previously used page-table slots pre-built once
during the ladder's stage 3. A guest page's host physical address can change
between translations (observed 0x13a591000 -> 0x3b8318000 for the same GPA),
and a runtime PTE rewrite into an already-fetched 128-byte line is invisible
(no invalidate path), so the later write-direction trigger validated against
the wrong page and failed its data check.
Both triggers now translate at trigger time and run through the same
fresh-scratch-line path as forwarding, via a shared internal copy body; the
exported forwarding API is unchanged and still requires
gsp_phys_work_forward. A changed HPA is now an informational once-per-boot
note rather than a failure; the probe-pattern guard still refuses stale pages.
Trigger 8 and the stage-3 pre-built slots are unchanged.
Live (run p6w3): GUEST G2H COPY OK gpa=0x12423d000 hpa=0x56ab3a000;
GUEST W2G COPY OK with verify_ok=1; PTE selftest OK; guest SEEN_W2G; ladder
REAL COPY OK; clean latched release (5 power-domain locks, rebound, WPR2 down,
no rail cycles, pstore empty, same boot). The full smoke run hit the known
guest cuInit/WPR2-already-up wedge at cdt; the trigger path itself is green.
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
copies
- new default-off gsp_phys_work_defer_release: a forwarded guest push's
releases are recorded and its GPFIFO entry is held (no consume, no
GP_GET write, no counter publish/stall) until the work item publishes
completion; the service thread then delivers the releases, with a
fallback on failure/timeout (500 ms cap enforced every pump pass)/
pause/quiesce/channel-delete
- new default-off gsp_phys_work_hw_primary: the software copy is skipped
for forwarded ops, so the physical engine authors the data; a once-only
software copy runs before the releases on any hardware failure or when
the request cannot be queued
- release-apply helpers extracted; exactly-once latches; channel-delete
and teardown handling; counters and a work_guard state line
- live: deferred-release run engaged=75 applied=75 timeouts=0 with the
full smoke green; hardware-primary run req=100 ok=100 verify_ok=100
fallback=0 copy_skipped=119 copy_fail=0, smoke ALL OK 64/64 (guest read
data the engine authored), with 19 fail-closed inline software
fallbacks under single-inflight contention; a range-unregistered run
proved the fallback (121 skipped copies, all recovered, smoke green)
- defaults off; the software path and all existing guards unchanged
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
- the sema service captures the first eligible copy per push from the
software resolver's own operands (the real push shape mixes guest RAM
with emulated-VRAM shadow addresses, including physical destinations)
- HPA resolution: guest RAM through the shared guest-RAM file page cache,
emulated VRAM through the mapping of its kernel shadow
- new scratch page-table pool: 16 zeroed page-table pages with their
page-directory entries built before any engine access, handing out one
whole 128-byte GMMU PTE fetch line per copy pair (16 PTEs, 512 pairs
per boot, never reused; a PTE written into an already-fetched line is
not observed and there is no invalidate path)
- the backend submits the copy on the module-owned channel and verifies
the result host-side; every miss falls back to the ladder shadow copy,
and the software pump remains authoritative
- live (full smoke, both parameters on): req=42 ok=42 verify_ok=42
verify_fail=0 fallback=0, guest payload roundtrip ALL OK 64/64,
clean latched release; defaults stay off
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
- file-backed guest RAM (launcher memory-backend-file share=on) and
in-kernel GPA->HPA translation through the shared file page cache
(read_cache_page + page_to_phys + pfn_valid), opened O_LARGEFILE;
new default-off gsp_phys_guest_mem parameter
- debugfs gsp-phys-guest-ram (path + gpa/off/size ranges) and
gsp-phys-guest-gpa (one pinned GPA per boot); rm-call triggers 6/7 run
host->guest and guest->host 4 KiB CE copies; trigger 8 is a PTE
self-test through a fresh slot
- guest page-table slots are pre-built during ladder stage 3: runtime
PTE writes into an already-walked page-table line are not observed
without a TLB invalidate
- guest RAM layout (q35 4.2, 4 GiB): below-4G GPA == file offset,
above-4G offset = GPA - 0x80000000 (2 GiB PCI hole)
- tests: tools/test/gpage_test.c guest probe; docs + STATE-CURRENT
record the live green (G2H/W2G with semaphore release, guest observed
the write, smoke ALL OK 64/64, clean latched release)
|
| |
|
|
| |
third-party references
|
| | |
|
| |
|
|
| |
P5 wave-1 shadow execution
|
| |
|
|
|
|
|
|
| |
- STATE-CURRENT snapshot moves to the P3 frontier: the host-freeze latch
and readiness gates are validated, the static identity overlay and the
read-only control forwarding are landed and live-verified
- the physical-backend guest-wiring design is now marked P0-P3 implemented
with the P2/P3 acceptance results
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
Host-freeze fix bundle (validated 2/2 supervised cycles):
- power unlock now latches D0/D3cold by default (new gsp_phys_repower,
default 0); releasing the claim can no longer power-gate the board and
hard-freeze the host on resume
- bounded post-rebind readiness gate before dropping the locks; bounded D0
settle/verify before the unbind
- READY means a live GSP-RM session: the async worker and the module-owned
join only expose READY when init-done is seen and no unload was sent;
otherwise the claim is released fail-open
- FWSEC reads DMEM0/IMEM back before STARTCPU and fails fast when the
staging is not visible
- the claim harness leaves the board latched by default and takes
--restore-power to opt back into the old restore
Guest-wiring:
- P2: generation-keyed fn65 static-config snapshot cache plus a default-off
identity overlay (new gsp_phys_static_live) for name/short-name/VBIOS;
the probe cycle runs once per backend generation at READY
- P3: default-off read-only RM_CONTROL forwarding whitelist (new
gsp_phys_ctrl_forward) with emulated-handle translation to the adopted
server handles and full emulation fallback
- P5 wave 1: default-off shadow execution of guest CE pushes on the ladder
channel (new gsp_phys_work_forward) via a dedicated ordered work item;
the ladder stage-4 submission is refactored into a shared bounded helper
and the software release path stays authoritative
Live: module-owned boot to init-done, guest smoke ALL OK 64/64 with P2/P3
enabled, 514 shadow copies observed on the physical CE; all cycles released
cleanly with WPR2 down and no reboot.
|
| |
|
|
| |
identity overlay live (GREEN); LIVE=0 control did not pass
|
| |
|
|
|
|
|
|
|
|
| |
Clarify in the post-1.0 record and the public status page that host-native
acceleration / host display is a stretch goal we are only considering:
do not block on it, pursue it, or design around it. It is never reached
automatically, requires an explicit human decision after all baseline goals
are complete (and only once there is no known risk), and may be scrapped on
architectural grounds. No aspect of the baseline software may be designed
toward it. No baseline design or code changes.
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
The host-VF design is reverted. Independent adversarial, soundness and
VM-support reviews falsified its load-bearing mechanisms: RAM-backed BARs
cannot be ioremapped or claimed by the stock driver on x86_64 or aarch64;
trap-free windows cannot observe edge-triggered writes or read side
effects; multi-client GSP-RM is unproven; the MSI and bridge bring-up
plans were incorrect; and the isolation and performance claims were
overstated for the mechanism.
Replace it with one self-contained post-1.0 document recording the
findings, corrected candidate approaches and trade-offs, a minimal-risk
future architecture, the compile-time + module-load experimental gating
policy, a phased plan with abort gates, and the revisit criteria. No
baseline design or code path is changed; all earlier doc edits are
reverted.
|
| |
|
|
| |
exercised (fail-open); async boot FWSEC failure and a release-path freeze recurrence noted
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
Add the gsp_phys_mdev_owned ownership selector (default 0: unchanged
load-time module-owned claim/boot). With 1, module load claims nothing;
the first mdev create starts a refcounted backend session whose
claim+boot runs asynchronously from a work item, so mdev create and
init_work never block. The last mdev remove releases after the emulation
thread is stopped. Failures are fail-open: the backend stays OFF and the
mdev keeps serving the emulation path.
nv_vgpu_exit now gates the session STOPPING under the session lock,
drains the emulation threads via mdev_unregister_driver(), and only then
releases the claim; the module-owned path keeps its previous release
position. A start while STOPPING is refused and a concurrent second
stopper cannot release twice. No forwarding is added.
|
| | |
|
| |
|
|
| |
API skeleton); PLAN A baseline re-verified 64/64
|
| | |
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
| |
physical-backend guest-wiring design
- STATE-CURRENT snapshot 2026-10-01 21:05: the host RM-client ladder now
allocates VAS+PDB+TSG+channel and executes a real 4 KiB VA-mode CE copy
(semaphore released, dst==src) on the physical engine; next is wiring the
live session into the guest-facing mdev/vfio path.
- docs/03-architecture/11-physical-backend-guest-wiring.md: phased design
(P0-P6) for bridging the physical backend into the guest-facing emulation,
with the seam table, lifecycle changes and static-config flow.
- docs/README.md: reading order updated for the new document; execution
status refreshed.
|
| |
|
|
| |
the mapped VA
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
After a doorbell the GSP-RM status ring accumulated unconsumed records
that nothing drained: the host readPtr stayed behind the writePtr and
the engine's error text was never decoded. Add a bounded drain (max 64
records) using the existing validated ring walk: each record is logged
with its function/status/seqNum, function 0x1006 (OS_ERROR_LOG) is
decoded into exceptType/runlistId/chid/prevXid/errString, and function
0x1020 (GSP_POST_NOCAT_RECORD) into recType/errorCode/subsystem/
bugcheck/faultingEngine plus a bounded printable view of the diagnostic
buffer. The host read pointer advances per consumed record (the normal
consumer side), so the ring keeps free space. Stage 4's poll-timeout
path drains before returning -ETIMEDOUT, and a new read-only debugfs
file gsp-phys-status-drain triggers one bounded drain per read. No
locks are taken and no device register is written.
|
| |
|
|
|
|
|
|
|
|
| |
SET_SEMAPHORE_A/B always take a GPU VA and the channel is USER, so the
release cannot target a raw DMA address and physical-mode src/dst is not
permitted. Map the src/dst/semem pages at VA 0x102000/0x103000/0x104000
(small-PT slots 258/259/260) in the existing channel PDB, push the semaphore
VA, drop the SET_SRC/DST_PHYS_MODE pairs and clear LAUNCH_DMA bits 12/13
(0x18d: Pipelined|Flush|Release-one-word|Pitch). The block is now 13 method
pairs / 26 dwords; GPFIFO/PUT/doorbell/poll/memcmp are unchanged.
|
| |
|
|
|
|
|
|
|
|
|
|
| |
Revert the USERD selection to the client sysmem chunk unconditionally:
the ladder advances GP_PUT by writing that chunk directly, and there is
no BAR1/PRAMIN aperture here to reach an FBMEM page, so an FBMEM USERD
would leave the host write invisible to the hardware USERD the engine
polls. Remove the now-dead FBMEM USERD allocator, handle and state; the
FBMEM error-notifier allocation path is unchanged. The PDB hierarchy,
VA-based gpFifoOffset and ring-entry GET, TSG schedule insurance, logs
and asserts from the PDB change are kept. Logs now say userd=sysmem
(host-writable) so the path in use is unambiguous.
|
| |
|
|
|
|
|
|
|
|
|
|
| |
GPU VAs
Fill the external VAS root's GP10X v2 hierarchy (root/PD2/PD1/PD0-small/PT)
around a 2 MB VA window so the PDBMA/CE can fetch the GPFIFO and pushbuffer
by GPU VA; gpFifoOffset and the GPFIFO ring entry GET now carry those VAs.
Allocate the USERD page in FBMEM (class 0x40, matching the reference default)
with the sysmem chunk as fallback, and add the advisory TSG-level
GPFIFO_SCHEDULE 0xa06c0101 after the channel BIND/schedule. Log the window,
table DMAs and entries, and expose them in the debugfs state snapshot.
|
| |
|
|
| |
physical engine; channel now allocates; engine did not execute the block
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
the notif index advisory
The class-0x40 NV_MEMORY_ALLOCATION_PARAMS reached the server with owner=0,
which the class constructor rejects with NV_ERR_INVALID_OWNER (0x39). Set
owner=HEAP_OWNER_RM_CLIENT_GENERIC (0xDEAF000C) and internalflags=
NVOS32_ALLOC_INTERNAL_FLAGS_SKIP_SCRUB (0x4), matching the reference notifier
allocation. Add static_asserts pinning owner/attr/size/offset/hVASpace/
internalflags to the reference 128-byte ABI so a layout drift breaks the build.
SET_WORK_SUBMIT_TOKEN_NOTIF_INDEX (0xc36f010a, index 3) now logs an advisory
warning on failure (no error-context object exists, so the server returns
NV_ERR_OBJECT_NOT_FOUND 0x57) and the stage continues to GET_WORK_SUBMIT_TOKEN:
the server writes the work-submit token before the notifier update, so the
token is independent of the notifier object.
|
| |
|
|
| |
submission
|
| |
|
|
|
|
|
|
|
| |
The TU104 GMMU root level has 2 index bits (4 PDEs of 2^47 bytes each), so
the server's vaLimitNew = (numEntries << 47) - 1 must stay within its
vaLimitMax = 2^49-1; numEntries=256 computed 2^55-1 and drew
NV_ERR_INVALID_ARGUMENT (0x1f). Send 4 entries (32 bytes of the 4 KB
page-aligned VASPDB chunk) and log the value on failure. The aperture/flags
word is unchanged (0x0a, SYSMEM_NONCOH + ALL_CHANNELS).
|
| |
|
|
| |
GSP-RM; wall moved to the address-space page-directory setup; clean release
|
| |
|
|
| |
channel ladder (V5)
|
| |
|
|
| |
channel allocation blocked; unsafe variant removed after fail-safe reboot
|
| | |
|
| |
|
|
| |
gsp-owned, server-allocated memdescs)
|
| |
|
|
| |
and decode rm-call statuses
|
| |
|
|
| |
static-config-handle ladder path
|
| |
|
|
| |
allocation and a first real copy
|
| |
|
|
| |
milestone (log-ring and identity fixes)
|
| |
|
|
| |
static-config RPC
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
identity, and request the full static-config payload
The RM log-ring init argument carried a malformed libos id (LOGM), so the
server never mapped the ring and its early failure path was invisible.
The pre-boot system-info payload carried unpacked 16-bit identity fields;
the server expects the raw config-space dwords (device<<16|vendor), so its
GPU device-id read back as zero and the static-config device-name lookup
returned NOT_SUPPORTED.
The static-config RPC must be sized to the full reply payload, and the
guest-system-info RPC is sent first, matching the reference order.
Live result: GSP-RM completes initialization (init-done rpc_result=0),
serves the 1656-byte static config (name, FB size, handles, PDE bases),
and shuts down cleanly through the unload RPC.
|
| |
|
|
| |
harness
|
| |
|
|
| |
PMU-provisioned chip identity is the one hard dependency
|
| |
|
|
| |
init wall narrowed to static-config collection
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
Fill the GspSystemInfo chipset fields the production client syncs before
the GSP boot instead of leaving them zero:
- clPdbProperties (bitmask in the client's clSyncWithGsp order): bit 0
(config space accessible, from the OS MCFG/ECAM availability), bit 7
and bit 21 (Intel Skylake-family upstream-port setup: ASPM POR list,
root-port nosnoop WAR), bit 13 (upstream port ASPM L1 capable), bit 27
(LTR supported+enabled up to the root port) and bit 32 (IO coherent).
PDB_PROP_CL_UNSUPPORTED_CHIPSET is never assigned by the client, so the
faithful unmatched-chipset value is 0.
- Chipset = 0 (CS_UNKNOWN) for a host bridge with no chipsetInfo[] entry,
the reference's no-match fallback.
- FHBBusInfo/chipsetIDInfo: 10-byte BUSINFO blobs of the first host
bridge of the GPU's domain (device, vendor, subdevice, subvendor,
revision), with the subsystem-capability fallback on chipsetIDInfo.
acpiMethodData is intentionally sent all-zero (bValid=0): no ACPI/AML
calls are made and every consumer tolerates the no-data encoding. All
device lookups use refcounted pci_get_device()/pci_dev_put().
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
experiment)
The working distribution driver runs with display enabled; the
RmDisableDisplay=1 deviation changes board/display state and may be
implicated in the devid/board validation failure blocking GSP-RM init.
Regenerate the profile without it: the 35 host default parameters plus
RMDevidCheckIgnore=1, 36 entries total, display brought up as a stock
boot would.
Same canonical packing: size 1344, numEntries 36, rpc.length 1376,
record 1392 (8-byte aligned), one 4 KB element. The module is unchanged
apart from comments and the prepared log line, which now reports
'host default profile + RMDevidCheckIgnore=1, display enabled'.
|
| |
|
|
| |
under test
|
| |
|
|
|
|
|
|
|
|
|
|
|
| |
Append RMDevidCheckIgnore=1 (dword) to the pre-boot SET_REGISTRY
profile, after the 35 host default parameters and RmDisableDisplay=1.
The key is the registry escape for the static-config devid/board check
that currently fails GSP-RM init; every existing entry is unchanged.
Regenerated kernel/gsp_phys_registry_img.h with the same canonical
packing (values inline, names-only blob): size 1377, numEntries 37,
rpc.length 1409, one 4 KB element. The module code is unchanged apart
from comments: the submission and the prepared log line read the size
and entry count from the generated blob/macros.
|
| |
|
|
| |
handshake); error journal collapsed 851->4; cycles 4-7 release clean
|
| | |
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
GSP-RM init
The pre-boot SET_REGISTRY (function 73) submitted an empty
PACKED_REGISTRY_TABLE. Replace it with the default registry profile the
host driver sends before boot: the 35 default dword parameters from its
parameter table plus RmDisableDisplay=1. The display key makes the GSP-RM
display-presence check treat display as absent, so the display engine is
removed during pre-init instead of being brought up on a headless boot.
The payload is generated into kernel/gsp_phys_registry_img.h as a
PACKED_REGISTRY_TABLE blob (8-byte header, 36 16-byte dword entries,
NUL-terminated names after the array; values inline; no value bytes in
the name blob, matching the reference packer): size 1342, numEntries 36,
rpc.length 1374, one 4 KB element. fn72 is unchanged.
The payload length is not 8-byte aligned (record 1390 -> 1392); the TX
producer already zero-pads the kvzalloc'd staging record and folds the
XOR checksum over the padded length, exactly like the reference producer
zero-pads before _checkSum32, so no producer change is needed. The blob
is static const data: no heap, no new stack frame, and a submit failure
still aborts the boot. The prepared log line now prints the payload size
and entry count.
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
The real-GSP boot path staged the message queue but never queued the two
fire-and-forget init RPCs the production client places in it before the
booter starts. GSP-RM therefore created its GPU object without any system
information and aborted RM init (live GSP_INIT_DONE rpc_result=0x59), with
the resource-manager's object-database lookups asserting from the first
journal record.
Submit function 72 (GSP_SET_SYSTEM_INFO, 928-byte v17_00 payload carrying
the BAR physical bases, domain/bus/slot, PCI IDs, the BAR0 config-mirror
offset, link/FLR capabilities and upstream-port flags read from the
pci_dev) and function 73 (SET_REGISTRY, header-only empty table, which the
server explicitly accepts) through the existing submit-only queue producer
after all stage-3d preconditions and before the GSP falcon reset/Booter
Load kick. The wire layouts are re-declared in the module with per-field
static asserts against the reference ABI; payloads are heap-allocated, so
no new stack frames are introduced.
|