We are currently migrating Bugzilla to GitHub issues.
Any changes made to the bug tracker now will be lost, so please do not post new bugs or make changes to them.
When we're done, all bug URLs will redirect to their equivalent location on the new bug tracker.

Bug 93

Summary: detecting lost surfaces with SDL's DirectDraw driver
Product: SDL Reporter: Sam Lantinga <slouken>
Component: videoAssignee: Ryan C. Gordon <icculus>
Status: RESOLVED WONTFIX QA Contact: Sam Lantinga <slouken>
Severity: normal    
Priority: P2    
Version: 2.0.0   
Hardware: x86   
OS: Windows (All)   

Description Sam Lantinga 2006-01-27 02:21:33 UTC
Date: Wed, 19 May 2004 00:43:59 -0400
From: "David Ludwig" <davidl@funkitron.com>
Subject: [SDL] detecting lost surfaces with SDL's DirectDraw driver

I've been running into some problems using SDL and it's DirectDraw driver.
Any assistance would be greatly appreciated...

I have an SDL application that needs to deal with video mode changes made
from Windows' Display control panel.  When the resolution is changed, blits
will work fine (and not report lost surfaces), however the call to SDL_Flip
does not.  The application will continue to run except that the screen,
which was created with SDL_SetVideoMode(640, 480, 0, SDL_SWSURFACE), will
not get redrawn.  A few runs through the debugger indicated that SDL has a
buffer that gets blitted to the actual screen (in
sdl_dx5video.c:DX5_WindowUpdate).  DirectX will indicate that the blit
failed and that it was due to a lost surface.  SDL's response is to restore
the surface (through DirectDraw) and try again.  The 2nd blit will also
fail, however SDL does not report this error to the application.

What I'd like to be able to do is catch the failed call to SDL_UpdateRect
and then do my own restore.  Unfortunately, there does not seem to be a way
to do this, other than modifying the SDL source (which I'd be happy to do,
but would rather avoid if possible) or poking around in data structures
internal to SDL.  Is there a better way to do this?  Catching              
WM_DISPLAYCHANGE messages seems like one possibility, however handling a
DirectDraw error seems like the better way to go.               

--
David Ludwig
davidl@funkitron.com
Comment 1 Ryan C. Gordon 2006-01-27 11:23:28 UTC
Setting Sam as "QA Contact" on all bugs (even resolved ones) so he'll definitely be in the loop to any further discussion here about SDL.

--ryan.

Comment 2 Ryan C. Gordon 2007-02-15 05:35:32 UTC
Ugh, this is a big pain.

If we lose the primary surface, IDirectDrawSurface3_Restore() fails until the resolution is changed back to the original, so it's not just a question of calling it in a loop with some sleep calls thrown in until it passes.

Likely we'd have to tear down the surface and create a new one, and probably take into account the possibility that the pixel format might change. Also, since we want to restore the data from an internal DirectDraw surface, that's probably lost too, anyhow.

I don't really want to add a DirectDraw-specific event to SDL, but the original poster is right...the simplest way to handle this is to tell the app to call SDL_SetVideoMode() again and recreate the contents of the screen surface.

What a mess. I'm flagging this as WONTFIX, since there's really no good solution here in 1.2 and it's less relevant with windib becoming primary (this problem is directx specific)...and it wouldn't hit most people anyhow.

If anyone has a better idea, please reopen the bug and discuss it.

--ryan.