# DF-3655 — VERDICT

**Status: inconclusive (kernel path hardware-gated on the virtio-only guest);
the evaluation-order defect is source-certain and the NULL deref is modeled
on-guest at the exact struct offset.**

## Root cause

`amdgpu_dm_atomic_commit_tail()` connector-scaling loop
(sys/dev/drm/amd/display/amdgpu_dm/amdgpu_dm.c):

```c
4888   status = dc_stream_get_status(dm_new_crtc_state->stream);
4889   WARN_ON(!status);
4890   WARN_ON(!status->plane_count);
```

`WARN_ON(x)` expands to a report + `unlikely(x)`; it does **not** terminate
the control flow. When `dc_stream_get_status()` returns NULL, line 4889
prints the warning and line 4890 immediately loads
`*(int *)((char *)NULL + offsetof(struct dc_stream_status, plane_count))`.
`struct dc_stream_status` begins with `int primary_otg_inst; int
stream_enc_inst; int plane_count;` (sys/dev/drm/amd/display/dc/dc_stream.h)
→ offset **8** → unmapped page-0 VA → page fault → panic.

Note the adjacent line 4837: `WARN_ON(!dc_commit_state(dm->dc, dc_state));` —
a failed DC commit is explicitly tolerated (warned, execution continues with
`dc_state` not applied), which is precisely the condition that leaves a
stream absent from the current context so that `dc_stream_get_status()`
returns NULL on the next underscan-path visit of this loop.

## Reachability

Requires the loop to be entered (connector attached to a CRTC, no modeset,
scaling state changed — same entry conditions as DF-3653's block, but with a
**non-NULL** stream) *and* `dc_stream_get_status(stream)` returning NULL.
The first condition is fully userspace-chosen (DRM-master atomic commit);
the second depends on DC internal state (failed commit / teardown race),
hence Low severity / certain code defect, likely trigger.

## Verification (Phase V)

* Guest virtio-only (env.txt): no AMD GPU, driver cannot attach — kernel path
  not executable.
* Harness models the exact evaluation order with a verbatim-field-order
  `dc_stream_status`; on-guest it prints `WARN_ON(!status) = 1` (the kernel
  WARN fires) and then SIGSEGVs at offset 8 (run.log, EXIT=139).

## Fix

Treat a NULL status as an error and skip (consistent with the intent of the
WARN) — see fix.diff: replaces the two WARN_ONs with a `DC_ERR` + `continue`.
`git apply --check` clean. `fix_status: not_testable` (hardware-gated).

## Fix status (batch validation)
Applied with the 36 sibling fix.diffs of this batch in findings/poc/_batch41/all_fixes.patch; single in-guest `make -j6 nativekernel KERNCONF=X86_64_GENERIC` completed RC=0 with zero errors under -Werror (full log: findings/poc/_batch41/fix_build8.log). Behavior A/B intentionally skipped for this Info-tier item.
