β¬’ DragonFlyBSD Kernel Audit
← triage Β· dashboard
DF-4071

Kernel STACK overflow in vegam_program_memory_timing_parameters: unclamped sclk x mclk counts fill a 640B stack SMU75_Discrete_MCArbDramTimingTable (entries[8][4])

Summary

The nested walk fills arb_regs.entries[i][j] with i < sclk count and j < mclk count, both unclamped VBIOS u8 counts. sclk=9 alone writes at byte 820 (180B past the object); sclk=255 => byte 20,400 (~20KB past a stack object, return-address-smashing shape with MMIO-derived 20B records). Distinct from DF-1368 (which enumerated only cac/clock-stretcher/avfs sites). Hit on init and every OD sclk/mclk update. Clamp fix.

Discussion (0)

No comments yet.

PoC verification

Evidence pack

findings/poc/DF-4071 Β· 8 files
FileTypeDescriptionSize
probe.c β€” 2.5 KB view raw
build.log β€” 28 B view raw
run.log β€” 792 B view raw
verdict.json β€” 2.4 KB view raw
README.md β€” 508 B ↓ raw
VERDICT.md β€” 1.7 KB ↓ raw
fix.diff β€” 481 B view raw
manifest.json β€” 858 B view raw

DF-4071 β€” vegam MC-arb timing table KERNEL STACK overflow (pass 2)

File: sys/dev/drm/amd/powerplay/smumgr/vegam_smumgr.c:1287-1315 (walk at 1297-1306)

Build (guest probe): cd /tmp && cc -I/usr/src/sys/dev/drm/amd/powerplay/inc -o probe probe.c Run: ./probe Expected: SMU75_Discrete_MCArbDramTimingTable = 640B (entries[8][4] of 20B); sclk count=9 -> writes at byte 820 (already 180B past); sclk count=255 -> byte 20,400. Full trigger needs VegaM GPU + crafted VBIOS pptable (absent). Hardware-gated.

VERDICT.md
↓ download raw

DF-4071 VERDICT β€” source-level certain, hardware-gated

Root cause

  • vegam_program_memory_timing_parameters() puts struct SMU75_Discrete_MCArbDramTimingTable arb_regs ON THE STACK (vegam_smumgr.c:1291; 640B total = entries[SMU__NUM_SCLK_DPM_STATE=8][SMU__NUM_MCLK_DPM_LEVELS=4] of 20B records β€” smu75_discrete.h:191-192) and fills arb_regs.entries[i][j] with i < sclk_table.count and j < mclk_table.count (:1297-1302) β€” both unclamped VBIOS u8 counts (same provenance as DF-4069/4070).
  • sclk count = 9 alone writes 20B at byte 820 of the 640B object (180B past its end); sclk count = 255 β‡’ byte 20,400 β‡’ ~20 KB past a 640-byte KERNEL STACK object, in the frame of vegam_program_memory_timing_parameters called from vegam_init_smc_table (:1991) and on every OD sclk/mclk table update (:2204-2212 β‡’ vegam_update_sclk_threshold).
  • Written content: 5 x 32-bit MC-arb register values read from MMIO (attacker-influenced via the crafted clocks fed to atomctrl) β€” a stack-smashing shape (return address / adjacent frames).

Distinct from knowns

DF-1368 enumerated ONLY cac_table (:515), clock_stretcher (:1515), avfs (:1636) β€” the MC-arb walk at :1287-1315 is none of those three functions (pass-1's broad 515-1642 line range notwithstanding, its summary names the covered walks).

Why not reproduced

No VegaM GPU on the audit guest; probe (run.log) proves the struct sizes.

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.

Fix verification

not_testable
baseline no→ patch + rebuild →patched clean

Hardware-gated finding (no AMD VegaM GPU / no LSI mps controller on the audit guest): fix authored at source level (fix.diff) but not build/boot-validated.

fix.diff in this pack; authored post-analysis, not hardware-validated.
↓ fix.diffper-fix-DF-4071

Confirmed kernel references

Detail

Evidence (decisive lines)

run.log: sizeof(SMU75_Discrete_MCArbDramTimingTable)=640; sclk=9 -> offset 820; sclk=255 -> 20400; smu75_discrete.h:191-192 (entries[SMU__NUM_SCLK_DPM_STATE=8][SMU__NUM_MCLK_DPM_LEVELS=4])

PoC changes

n/a (source-level; sizes from guest probe run.log)

Verified recommended fix

Clamp i-loop to SMU__NUM_SCLK_DPM_STATE and j-loop to SMU__NUM_MCLK_DPM_LEVELS.

Verdict

Source-level certain, hardware-gated. vegam_program_memory_timing_parameters() declares 'struct SMU75_Discrete_MCArbDramTimingTable arb_regs' ON THE KERNEL STACK (640B: entries[8][4] of 20B) and fills arb_regs.entries[i][j] with i < sclk count, j < mclk count -- both straight unclamped VBIOS u8 counts. sclk count=9 alone writes at byte offset 820 of the 640B object (180B past it); sclk count=255 walks 20,400B past -- a kernel STACK overflow with MMIO-register-derived (semi-controlled) 20B records, adjacent to the caller frame in vegam_init_smc_table -> return-address smashing shape. Distinct from DF-1368 (which enumerated cac_table :515, clock_stretcher :1515, avfs :1636 only).