Skip to content

[GEN][ZH] Exclusive fullscreen remains device-lost for ~45 seconds after startup #3049

Description

@sailro

Summary

On Windows 11 with an NVIDIA GPU, the clean latest main build can enter a prolonged Direct3D 8 lost-device state shortly after startup while the game is foreground and not minimized.

During the fault, render FPS drops to roughly 5-8 FPS, DX8Wrapper::IsDeviceLost remains true, and DX8Wrapper::FrameCount stays at zero. The process is responsive and game logic is not the bottleneck. The behavior disappears completely in windowed/windowed-fullscreen presentation.

This appears related to the lost-device recovery discussed in #28 / #846, but is not a crash: the game can remain in the recovery loop for approximately 45-50 seconds before recovering by itself.

Tested build

  • Repository: clean TheSuperHackers/GeneralsGameCode main
  • Commit: bb5168c8d0685f0fc0628f6b1b74e49a91258e41
  • Release executable SHA-256: C1069626F2B354C5B0505C9EC314D1D21D5E7C6D705CAB2611C96254856FE785
  • Steam Zero Hour 1.04 data

System

  • Windows 11 Pro 10.0.26200 (build 26200)
  • Intel Core i9-13900KF
  • NVIDIA GeForce RTX 4090
  • NVIDIA drivers reproduced: 610.74 and 610.88 (32.0.16.1088)
  • Desktop/game resolution: 2560x1440 at 239 Hz

Reproduction

  1. Build current main in Release.
  2. Launch generalszh.exe in the default exclusive-fullscreen mode at the desktop resolution.
  3. Keep the window foreground and not minimized.
  4. Within roughly 10-20 seconds, observe repeated device resets followed by a sustained lost-device state and ~5-8 render FPS.

Representative clean-upstream monitor output after activating the game window:

16:51:07 fps=10.2 cap=30 frame=1 lost=0 resets=11 foreground=true
16:51:10 fps=30.0 cap=30 frame=0 lost=1 resets=13 foreground=true
16:51:20 fps=6.4  cap=30 frame=0 lost=1 resets=16 foreground=true
16:51:28 fps=5.9  cap=30 frame=0 lost=1 resets=16 foreground=true
16:51:44 fps=5.5  cap=30 frame=0 lost=1 resets=16 foreground=true

On the GeneralsOnline fork (which contains the same upstream rendering code), monitoring from process creation shows the full recovery cycle:

16:19:39 fps=9.3 cap=60 frame=0 lost=1 foreground=true
16:19:47 fps=6.0 cap=60 frame=0 lost=1 foreground=true
...
16:20:26 fps=4.6 cap=60 frame=0 lost=1 foreground=true
16:20:27 fps=60.0 cap=60 frame=46 lost=0 foreground=true

A/B results

Configuration Result
Clean upstream main, exclusive fullscreen Reproduces
Clean upstream main, -win -nologo -noshellmap Stable 30 FPS, lost=0, no resets
GeneralsOnline latest main, normal launcher Reproduces
GeneralsOnline executable launched directly Reproduces
GeneralsOnline with -nologo Reproduces
GeneralsOnline with -nologo -noshellmap Reproduces
GeneralsOnline with GENERALS_ONLINE_WINDOWED_FULLSCREEN Stable 60 FPS, lost=0, no resets

This rules out the launcher, startup movie, shell map, terrain rendering changes, FPS limiter, CPU/GPU load, and a single NVIDIA driver version.

Source observation

DX8Wrapper::End_Scene() does this after Present() returns D3DERR_DEVICELOST:

hr = _Get_D3D_Device8()->TestCooperativeLevel();
if (hr == D3DERR_DEVICENOTRESET)
    Reset_Device();
else
    ThreadClass::Sleep_Ms(200);

The measured ~5 FPS cadence exactly matches the 200 ms sleep path. During the fault, IsDeviceLost stays true and FrameCount remains zero until recovery.

PR #846 removed the old Reset_D3D_Device(bool active) activation hack and relies on the cooperative-level recovery path. Its discussion already contains a closely related observation:

This is even happening if I launch the game and never leave the game window.

#846 (comment)

Related work:

Expected behavior

Exclusive-fullscreen startup should not remain device-lost for tens of seconds while foreground. Alternatively, fullscreen-at-desktop-resolution could use a supported windowed/borderless presentation path, which avoids the failure in all measurements above.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions