Sign in to follow this  
jafe

EnumSurfaces

Recommended Posts

jafe    122
Hey, Has anybody had any experience getting IDirectDraw::EnumSurfaces to work properly? I'm not usually a directx coder so any help is appreciated. I have my code set up as so:

int index=0;

static HRESULT WINAPI DDEnum(
  LPDIRECTDRAWSURFACE7 lpDDSurface, 
  LPDDSURFACEDESC lpDDSurfaceDesc, 
  LPVOID lpContext)
{
	index++;
	lpDDSurface->Release();
	return DDENUMRET_OK;
}

...WinMain...


LPDIRECTDRAW7 lpDD=NULL;
HRESULT hr=DirectDrawCreateEx(NULL,(void**)&lpDD,IID_IDirectDraw7,NULL);

if(hr==DD_OK){
	hr=lpDD->EnumSurfaces(DDENUMSURFACES_DOESEXIST|DDENUMSURFACES_ALL ,NULL,NULL, (LPDDENUMSURFACESCALLBACK7)DDEnum);
	if(hr!=DD_OK){
		sndPlaySound("Windows XP Information Bar.wav",SND_SYNC);
	}
	lpDD->Release();
}
But the output remains as
index=0
DirectDrawCreateEx==DD_OK
lpDD->EnumSurfaces==DD_OK
And I was expecting for index to be at least 1 or more. Perhaps I am using the function wrongly, I am trying to use it to enumerate all of the active DirectX surfaces.

Share this post


Link to post
Share on other sites
Evil Steve    2017
A couple of things:

Firstly, NEVER cast function pointers like that. It's an ideal way to get weird crashes. If the function pointer won't work without the cast, something is wrong with the function prototype and it needs fixed. Casting it just forces the compile error to turn into runtime error.

Secondly, Why would EnumSurfaces() give you a surface if you haven't created any yet? Creating a DirectDraw interface won't magically create any surfaces. Try creating a surface and then calling EnumSurfaces() and see if that makes any difference.

EDIT: Thirdly, I'm not at all sure you should be Release()ing the surface passed to your callback function. The docs don't seem to mention either way, but when your callback starts getting called, I'd check this out.

Share this post


Link to post
Share on other sites
jafe    122
Quote:
Original post by Evil Steve
A couple of things:

Firstly, NEVER cast function pointers like that. It's an ideal way to get weird crashes. If the function pointer won't work without the cast, something is wrong with the function prototype and it needs fixed. Casting it just forces the compile error to turn into runtime error.

Secondly, Why would EnumSurfaces() give you a surface if you haven't created any yet? Creating a DirectDraw interface won't magically create any surfaces. Try creating a surface and then calling EnumSurfaces() and see if that makes any difference.

EDIT: Thirdly, I'm not at all sure you should be Release()ing the surface passed to your callback function. The docs don't seem to mention either way, but when your callback starts getting called, I'd check this out.


Firstly, since it's pseudocode above, ASSUME I'm smart enough to right procedures to stop this.

Secondly, the SDK mentions that EnumSurfaces returns pointers to all drawable directdraw surfaces.

Thirdly, releasing a COM object used to be standard procedure after it's been intialised to clean up memory when the object is no longer needed.

EDIT: Also, it's not the one surface I want from my process, I'm trying to enumerate all of the directdraw surfaces in use and active on the computer at that time.

Share this post


Link to post
Share on other sites
Hollowtip    122
Quote:
Original post by jafe
EDIT: Also, it's not the one surface I want from my process, I'm trying to enumerate all of the directdraw surfaces in use and active on the computer at that time.


Trying to grab the surfaces created by another application is IMPOSSIBLE (short of hacking apart windows/directx).

If you wanted to grab surfaces from another program you'd have to write a DLL hook that will take note of all surfaces created/destroyed, as well as display/store them somehow, though this can cause major problems with your PC if you don't know what you're doing, so just be careful.

Share this post


Link to post
Share on other sites
Evil Steve    2017
Quote:
Original post by jafe
Firstly, since it's pseudocode above, ASSUME I'm smart enough to right procedures to stop this.

Secondly, the SDK mentions that EnumSurfaces returns pointers to all drawable directdraw surfaces.

Thirdly, releasing a COM object used to be standard procedure after it's been intialised to clean up memory when the object is no longer needed.

EDIT: Also, it's not the one surface I want from my process, I'm trying to enumerate all of the directdraw surfaces in use and active on the computer at that time.

1) write [smile] And if it's psuedocode, that's even less reason to have the cast in there. You'd be surprised how many people just stuff a cast in there for the hell of it.

2) Where exactly does it say that? Exactly what it does depends on the flags you pass it. You're asking it for all the surfaces that already exist, and you haven't create any surfaces yet. So there's none to return, so the callback is never called, so this is correct behaviour. If you have created some surfaces, please show us the code you use to create them.

3) Yes, but you don't initialise the surface, do you? Like I said, I'm not sure what you're supposed to do here, the SDK docs don't actually say. What I mean is that when this starts working, you should check that you're not leaking memory or using invalid memory by incorrectly Release()ing or not Release()ing the suface.
EDIT: Never mind, it does say that - I just missed it.

Share this post


Link to post
Share on other sites
jafe    122
Quote:
Original post by Hollowtip
Quote:
Original post by jafe
EDIT: Also, it's not the one surface I want from my process, I'm trying to enumerate all of the directdraw surfaces in use and active on the computer at that time.


Trying to grab the surfaces created by another application is IMPOSSIBLE (short of hacking apart windows/directx).

If you wanted to grab surfaces from another program you'd have to write a DLL hook that will take note of all surfaces created/destroyed, as well as display/store them somehow, though this can cause major problems with your PC if you don't know what you're doing, so just be careful.



Hacking the other process and getting the surface for it would be no problem - have fair experience in doing so, but I didn't want to use that method on this problem so I came accross that function EnumSurfaces which I hoped would indeed grab the surfaces in use by other processes. Guessing not.


Quote:
Original post by Evil Steve
Quote:
Original post by jafe
Firstly, since it's pseudocode above, ASSUME I'm smart enough to right procedures to stop this.

Secondly, the SDK mentions that EnumSurfaces returns pointers to all drawable directdraw surfaces.

Thirdly, releasing a COM object used to be standard procedure after it's been intialised to clean up memory when the object is no longer needed.

EDIT: Also, it's not the one surface I want from my process, I'm trying to enumerate all of the directdraw surfaces in use and active on the computer at that time.

1) write [smile] And if it's psuedocode, that's even less reason to have the cast in there. You'd be surprised how many people just stuff a cast in there for the hell of it.

2) Where exactly does it say that? Exactly what it does depends on the flags you pass it. You're asking it for all the surfaces that already exist, and you haven't create any surfaces yet. So there's none to return, so the callback is never called, so this is correct behaviour. If you have created some surfaces, please show us the code you use to create them.

3) Yes, but you don't initialise the surface, do you? Like I said, I'm not sure what you're supposed to do here, the SDK docs don't actually say. What I mean is that when this starts working, you should check that you're not leaking memory or using invalid memory by incorrectly Release()ing or not Release()ing the suface.
EDIT: Never mind, it does say that - I just missed it.


1) Yeh, I know my fair share of people who are guilty to this :)

2) As above, wasen't trying to get surfaces my process had made, but surfaces from other processes.

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

Sign in to follow this