1 /* $Id: main.c 21434 2006-04-01 19:12:56Z greatlrd $
3 * COPYRIGHT: See COPYING in the top level directory
4 * PROJECT: ReactOS kernel
5 * FILE: lib/ddraw/ddraw.c
6 * PURPOSE: DirectDraw Library
7 * PROGRAMMER: Magnus Olsen (greatlrd)
16 DDRAWI_DIRECTDRAW_GBL ddgbl
;
17 DDRAWI_DDRAWSURFACE_GBL ddSurfGbl
;
24 Create_DirectDraw (LPGUID pGUID
, LPDIRECTDRAW
* pIface
,
27 LPDDRAWI_DIRECTDRAW_INT This
;
31 if ((IsBadReadPtr(pIface
,sizeof(LPDIRECTDRAW
))) ||
32 (IsBadWritePtr(pIface
,sizeof(LPDIRECTDRAW
))))
34 return DDERR_INVALIDPARAMS
;
37 This
= (LPDDRAWI_DIRECTDRAW_INT
)*pIface
;
39 if (IsBadReadPtr(This
,sizeof(LPDIRECTDRAW
)))
41 DX_STUB_str("1. no linking\n");
42 /* We do not have a DirectDraw interface, we need alloc it*/
43 LPDDRAWI_DIRECTDRAW_INT memThis
;
45 memThis
= DxHeapMemAlloc(sizeof(DDRAWI_DIRECTDRAW_INT
));
50 DxHeapMemFree(memThis
);
52 DX_STUB_str("DDERR_OUTOFMEMORY");
53 return DDERR_OUTOFMEMORY
;
58 DX_STUB_str("2.linking\n");
59 /* We got the DirectDraw interface alloc and we need create the link */
60 LPDDRAWI_DIRECTDRAW_INT newThis
;
61 newThis
= DxHeapMemAlloc(sizeof(DDRAWI_DIRECTDRAW_INT
));
64 DX_STUB_str("DDERR_OUTOFMEMORY");
65 return DDERR_OUTOFMEMORY
;
68 /* we need check the GUID lpGUID what type it is */
69 if (pGUID
!= (LPGUID
)DDCREATE_HARDWAREONLY
)
74 DX_STUB_str("DDERR_INVALIDDIRECTDRAWGUID");
75 return DDERR_INVALIDDIRECTDRAWGUID
;
78 newThis
->lpLink
= This
;
82 /* Fixme release memory alloc if we fail */
83 This
->lpLcl
= DxHeapMemAlloc(sizeof(DDRAWI_DIRECTDRAW_INT
));
84 if (This
->lpLcl
== NULL
)
86 DX_STUB_str("DDERR_OUTOFMEMORY");
87 return DDERR_OUTOFMEMORY
;
89 This
->lpLcl
->lpGbl
= &ddgbl
;
91 *pIface
= (LPDIRECTDRAW
)This
;
93 /* Get right interface we whant */
94 if (Main_DirectDraw_QueryInterface((LPDIRECTDRAW7
)This
, id
, (void**)&pIface
) == DD_OK
)
96 DX_STUB_str("Got iface");
98 if (StartDirectDraw((LPDIRECTDRAW
)This
, pGUID
, FALSE
) == DD_OK
);
103 RtlZeroMemory(&wnd_class, sizeof(wnd_class));
104 wnd_class.style = CS_HREDRAW | CS_VREDRAW;
105 wnd_class.lpfnWndProc = DefWindowProcW;
106 wnd_class.cbClsExtra = 0;
107 wnd_class.cbWndExtra = 0;
108 wnd_class.hInstance = GetModuleHandleW(0);
110 wnd_class.hCursor = 0;
111 wnd_class.hbrBackground = (HBRUSH) GetStockObject(BLACK_BRUSH);
112 wnd_class.lpszMenuName = NULL;
113 wnd_class.lpszClassName = classname;
114 if(!RegisterClassW(&wnd_class))
116 DX_STUB_str("DDERR_GENERIC");
117 return DDERR_GENERIC;
121 DX_STUB_str("DD_OK");
126 DX_STUB_str("DDERR_INVALIDPARAMS");
127 return DDERR_INVALIDPARAMS
;
132 StartDirectDraw(LPDIRECTDRAW iface
, LPGUID lpGuid
, BOOL reenable
)
134 LPDDRAWI_DIRECTDRAW_INT This
= (LPDDRAWI_DIRECTDRAW_INT
)iface
;
135 DWORD hal_ret
= DD_FALSE
;
136 DWORD hel_ret
= DD_FALSE
;
137 DWORD devicetypes
= 0;
143 * ddgbl.dwPDevice is not longer in use in windows 2000 and higher
144 * I am using it for device type
145 * devicetypes = 1 : both hal and hel are enable
146 * devicetypes = 2 : both hal are enable
147 * devicetypes = 3 : both hel are enable
148 * devicetypes = 4 :loading a guid drv from the register
151 if (reenable
== FALSE
)
153 if (This
->lpLink
== NULL
)
155 RtlZeroMemory(&ddgbl
, sizeof(DDRAWI_DIRECTDRAW_GBL
));
156 This
->lpLcl
->lpGbl
->dwRefCnt
++;
157 if (ddgbl
.lpDDCBtmp
== NULL
)
159 ddgbl
.lpDDCBtmp
= (LPDDHAL_CALLBACKS
) DxHeapMemAlloc(sizeof(DDHAL_CALLBACKS
));
160 if (ddgbl
.lpDDCBtmp
== NULL
)
162 DX_STUB_str("Out of memmory");
171 if (reenable
== FALSE
)
177 /* Create HDC for default, hal and hel driver */
178 This
->lpLcl
->hWnd
= (ULONG_PTR
) GetActiveWindow();
179 This
->lpLcl
->hDC
= (ULONG_PTR
) GetDC((HWND
)This
->lpLcl
->hWnd
);
181 /* cObsolete is undoc in msdn it being use in CreateDCA */
182 RtlCopyMemory(&ddgbl
.cObsolete
,&"DISPLAY",7);
183 RtlCopyMemory(&ddgbl
.cDriverName
,&"DISPLAY",7);
184 dwFlags
|= DDRAWI_DISPLAYDRV
| DDRAWI_GDIDRV
;
186 else if (lpGuid
== (LPGUID
) DDCREATE_HARDWAREONLY
)
189 /* Create HDC for default, hal driver */
190 This
->lpLcl
->hWnd
=(ULONG_PTR
) GetActiveWindow();
191 This
->lpLcl
->hDC
= (ULONG_PTR
) GetDC((HWND
)This
->lpLcl
->hWnd
);
193 /* cObsolete is undoc in msdn it being use in CreateDCA */
194 RtlCopyMemory(&ddgbl
.cObsolete
,&"DISPLAY",7);
195 RtlCopyMemory(&ddgbl
.cDriverName
,&"DISPLAY",7);
196 dwFlags
|= DDRAWI_DISPLAYDRV
| DDRAWI_GDIDRV
;
198 else if (lpGuid
== (LPGUID
) DDCREATE_EMULATIONONLY
)
202 /* Create HDC for default, hal and hel driver */
203 This
->lpLcl
->hWnd
= (ULONG_PTR
) GetActiveWindow();
204 This
->lpLcl
->hDC
= (ULONG_PTR
) GetDC((HWND
)This
->lpLcl
->hWnd
);
206 /* cObsolete is undoc in msdn it being use in CreateDCA */
207 RtlCopyMemory(&ddgbl
.cObsolete
,&"DISPLAY",7);
208 RtlCopyMemory(&ddgbl
.cDriverName
,&"DISPLAY",7);
210 dwFlags
|= DDRAWI_DISPLAYDRV
| DDRAWI_GDIDRV
;
214 /* FIXME : need getting driver from the GUID that have been pass in from
215 * the register. we do not support that yet
218 This
->lpLcl
->hDC
= (ULONG_PTR
) NULL
;
219 This
->lpLcl
->hWnd
= (ULONG_PTR
) GetActiveWindow();
222 if ( (HDC
)This
->lpLcl
->hDC
== NULL
)
224 DX_STUB_str("DDERR_OUTOFMEMORY");
225 return DDERR_OUTOFMEMORY
;
229 This
->lpLcl
->lpDDCB
= ddgbl
.lpDDCBtmp
;
231 /* Startup HEL and HAL */
232 This
->lpLcl
->lpDDCB
= This
->lpLcl
->lpGbl
->lpDDCBtmp
;
233 This
->lpLcl
->dwProcessId
= GetCurrentProcessId();
238 hal_ret
= StartDirectDrawHal(iface
, reenable
);
239 This
->lpLcl
->lpDDCB
->HELDD
.dwFlags
= 0;
243 hel_ret
= StartDirectDrawHel(iface
, reenable
);
244 This
->lpLcl
->lpDDCB
->HALDD
.dwFlags
= 0;
248 hal_ret
= StartDirectDrawHal(iface
, reenable
);
249 hel_ret
= StartDirectDrawHel(iface
, reenable
);
256 DX_STUB_str("DDERR_NODIRECTDRAWSUPPORT");
257 return DDERR_NODIRECTDRAWSUPPORT
;
259 dwFlags
|= DDRAWI_NOHARDWARE
;
264 dwFlags
|= DDRAWI_NOEMULATION
;
269 dwFlags
|= DDRAWI_EMULATIONINITIALIZED
;
272 /* Fill some basic info for Surface */
273 This
->lpLcl
->lpGbl
->dwFlags
= dwFlags
| DDRAWI_ATTACHEDTODESKTOP
;
274 This
->lpLcl
->lpDDCB
= This
->lpLcl
->lpGbl
->lpDDCBtmp
;
275 This
->lpLcl
->hDD
= This
->lpLcl
->lpGbl
->hDD
;
276 ddgbl
.hDD
= This
->lpLcl
->lpGbl
->hDD
;
278 DX_STUB_str("DD_OK\n");
283 StartDirectDrawHel(LPDIRECTDRAW iface
, BOOL reenable
)
285 LPDDRAWI_DIRECTDRAW_INT This
= (LPDDRAWI_DIRECTDRAW_INT
)iface
;
287 This
->lpLcl
->lpGbl
->lpDDCBtmp
->HELDD
.CanCreateSurface
= HelDdCanCreateSurface
;
288 This
->lpLcl
->lpGbl
->lpDDCBtmp
->HELDD
.CreateSurface
= HelDdCreateSurface
;
289 This
->lpLcl
->lpGbl
->lpDDCBtmp
->HELDD
.CreatePalette
= HelDdCreatePalette
;
290 This
->lpLcl
->lpGbl
->lpDDCBtmp
->HELDD
.DestroyDriver
= HelDdDestroyDriver
;
291 This
->lpLcl
->lpGbl
->lpDDCBtmp
->HELDD
.FlipToGDISurface
= HelDdFlipToGDISurface
;
292 This
->lpLcl
->lpGbl
->lpDDCBtmp
->HELDD
.GetScanLine
= HelDdGetScanLine
;
293 This
->lpLcl
->lpGbl
->lpDDCBtmp
->HELDD
.SetColorKey
= HelDdSetColorKey
;
294 This
->lpLcl
->lpGbl
->lpDDCBtmp
->HELDD
.SetExclusiveMode
= HelDdSetExclusiveMode
;
295 This
->lpLcl
->lpGbl
->lpDDCBtmp
->HELDD
.SetMode
= HelDdSetMode
;
296 This
->lpLcl
->lpGbl
->lpDDCBtmp
->HELDD
.WaitForVerticalBlank
= HelDdWaitForVerticalBlank
;
298 This
->lpLcl
->lpGbl
->lpDDCBtmp
->HELDD
.dwFlags
= DDHAL_CB32_CANCREATESURFACE
|
299 DDHAL_CB32_CREATESURFACE
|
300 DDHAL_CB32_CREATEPALETTE
|
301 DDHAL_CB32_DESTROYDRIVER
|
302 DDHAL_CB32_FLIPTOGDISURFACE
|
303 DDHAL_CB32_GETSCANLINE
|
304 DDHAL_CB32_SETCOLORKEY
|
305 DDHAL_CB32_SETEXCLUSIVEMODE
|
307 DDHAL_CB32_WAITFORVERTICALBLANK
;
309 This
->lpLcl
->lpGbl
->lpDDCBtmp
->HELDD
.dwSize
= sizeof(This
->lpLcl
->lpDDCB
->HELDD
);
311 This
->lpLcl
->lpGbl
->lpDDCBtmp
->HELDDSurface
.AddAttachedSurface
= HelDdSurfAddAttachedSurface
;
312 This
->lpLcl
->lpGbl
->lpDDCBtmp
->HELDDSurface
.Blt
= HelDdSurfBlt
;
313 This
->lpLcl
->lpGbl
->lpDDCBtmp
->HELDDSurface
.DestroySurface
= HelDdSurfDestroySurface
;
314 This
->lpLcl
->lpGbl
->lpDDCBtmp
->HELDDSurface
.Flip
= HelDdSurfFlip
;
315 This
->lpLcl
->lpGbl
->lpDDCBtmp
->HELDDSurface
.GetBltStatus
= HelDdSurfGetBltStatus
;
316 This
->lpLcl
->lpGbl
->lpDDCBtmp
->HELDDSurface
.GetFlipStatus
= HelDdSurfGetFlipStatus
;
317 This
->lpLcl
->lpGbl
->lpDDCBtmp
->HELDDSurface
.Lock
= HelDdSurfLock
;
318 This
->lpLcl
->lpGbl
->lpDDCBtmp
->HELDDSurface
.reserved4
= HelDdSurfreserved4
;
319 This
->lpLcl
->lpGbl
->lpDDCBtmp
->HELDDSurface
.SetClipList
= HelDdSurfSetClipList
;
320 This
->lpLcl
->lpGbl
->lpDDCBtmp
->HELDDSurface
.SetColorKey
= HelDdSurfSetColorKey
;
321 This
->lpLcl
->lpGbl
->lpDDCBtmp
->HELDDSurface
.SetOverlayPosition
= HelDdSurfSetOverlayPosition
;
322 This
->lpLcl
->lpGbl
->lpDDCBtmp
->HELDDSurface
.SetPalette
= HelDdSurfSetPalette
;
323 This
->lpLcl
->lpGbl
->lpDDCBtmp
->HELDDSurface
.Unlock
= HelDdSurfUnlock
;
324 This
->lpLcl
->lpGbl
->lpDDCBtmp
->HELDDSurface
.UpdateOverlay
= HelDdSurfUpdateOverlay
;
325 This
->lpLcl
->lpGbl
->lpDDCBtmp
->HELDDSurface
.dwFlags
= DDHAL_SURFCB32_ADDATTACHEDSURFACE
|
327 DDHAL_SURFCB32_DESTROYSURFACE
|
328 DDHAL_SURFCB32_FLIP
|
329 DDHAL_SURFCB32_GETBLTSTATUS
|
330 DDHAL_SURFCB32_GETFLIPSTATUS
|
331 DDHAL_SURFCB32_LOCK
|
332 DDHAL_SURFCB32_RESERVED4
|
333 DDHAL_SURFCB32_SETCLIPLIST
|
334 DDHAL_SURFCB32_SETCOLORKEY
|
335 DDHAL_SURFCB32_SETOVERLAYPOSITION
|
336 DDHAL_SURFCB32_SETPALETTE
|
337 DDHAL_SURFCB32_UNLOCK
|
338 DDHAL_SURFCB32_UPDATEOVERLAY
;
340 This
->lpLcl
->lpGbl
->lpDDCBtmp
->HELDDSurface
.dwSize
= sizeof(This
->lpLcl
->lpDDCB
->HELDDSurface
);
343 This->lpLcl->lpDDCB->HELDDPalette.DestroyPalette = HelDdPalDestroyPalette;
344 This->lpLcl->lpDDCB->HELDDPalette.SetEntries = HelDdPalSetEntries;
345 This->lpLcl->lpDDCB->HELDDPalette.dwSize = sizeof(This->lpLcl->lpDDCB->HELDDPalette);
349 This->lpLcl->lpDDCB->HELDDExeBuf.CanCreateExecuteBuffer = HelDdExeCanCreateExecuteBuffer;
350 This->lpLcl->lpDDCB->HELDDExeBuf.CreateExecuteBuffer = HelDdExeCreateExecuteBuffer;
351 This->lpLcl->lpDDCB->HELDDExeBuf.DestroyExecuteBuffer = HelDdExeDestroyExecuteBuffer;
352 This->lpLcl->lpDDCB->HELDDExeBuf.LockExecuteBuffer = HelDdExeLockExecuteBuffer;
353 This->lpLcl->lpDDCB->HELDDExeBuf.UnlockExecuteBuffer = HelDdExeUnlockExecuteBuffer;
361 StartDirectDrawHal(LPDIRECTDRAW iface
, BOOL reenable
)
365 BOOL newmode
= FALSE
;
366 LPDDSURFACEDESC mpTextures
;
367 D3DHAL_CALLBACKS mD3dCallbacks
;
368 D3DHAL_GLOBALDRIVERDATA mD3dDriverData
;
369 DDHAL_DDEXEBUFCALLBACKS mD3dBufferCallbacks
;
370 LPDDRAWI_DIRECTDRAW_INT This
= (LPDDRAWI_DIRECTDRAW_INT
)iface
;
374 RtlZeroMemory(&mHALInfo
, sizeof(DDHALINFO
));
375 RtlZeroMemory(&mD3dCallbacks
, sizeof(D3DHAL_CALLBACKS
));
376 RtlZeroMemory(&mD3dDriverData
, sizeof(D3DHAL_GLOBALDRIVERDATA
));
377 RtlZeroMemory(&mD3dBufferCallbacks
, sizeof(DDHAL_DDEXEBUFCALLBACKS
));
379 if (reenable
== FALSE
)
381 if (ddgbl
.lpDDCBtmp
== NULL
)
383 ddgbl
.lpDDCBtmp
= DxHeapMemAlloc(sizeof(DDHAL_CALLBACKS
));
384 if ( ddgbl
.lpDDCBtmp
== NULL
)
392 RtlZeroMemory(ddgbl
.lpDDCBtmp
,sizeof(DDHAL_CALLBACKS
));
396 * Startup DX HAL step one of three
398 if (!DdCreateDirectDrawObject(This
->lpLcl
->lpGbl
, (HDC
)This
->lpLcl
->hDC
))
400 DxHeapMemFree(ddgbl
.lpDDCBtmp
);
404 /* Some card disable the dx after it have been created so
405 * we are force reanble it
407 if (!DdReenableDirectDrawObject(This
->lpLcl
->lpGbl
, &newmode
))
409 DxHeapMemFree(ddgbl
.lpDDCBtmp
);
413 if (!DdQueryDirectDrawObject(This
->lpLcl
->lpGbl
,
415 &ddgbl
.lpDDCBtmp
->HALDD
,
416 &ddgbl
.lpDDCBtmp
->HALDDSurface
,
417 &ddgbl
.lpDDCBtmp
->HALDDPalette
,
420 &mD3dBufferCallbacks
,
425 DxHeapMemFree(This
->lpLcl
->lpGbl
->lpModeInfo
);
426 DxHeapMemFree(ddgbl
.lpDDCBtmp
);
427 // FIXME Close DX fristcall and second call
433 if (mHALInfo
.ddCaps
.dwNumFourCCCodes
> 0 )
435 mpFourCC
= (DWORD
*) DxHeapMemAlloc(sizeof(DWORD
) * mHALInfo
.ddCaps
.dwNumFourCCCodes
);
436 if (mpFourCC
== NULL
)
438 DxHeapMemFree(ddgbl
.lpDDCBtmp
);
439 // FIXME Close DX fristcall and second call
444 /* Alloc mpTextures */
446 if (mD3dDriverData
.dwNumTextureFormats
> 0)
448 mpTextures
= (DDSURFACEDESC
*) DxHeapMemAlloc(sizeof(DDSURFACEDESC
) * mD3dDriverData
.dwNumTextureFormats
);
449 if (mpTextures
== NULL
)
451 DxHeapMemFree(mpFourCC
);
452 DxHeapMemFree(ddgbl
.lpDDCBtmp
);
453 // FIXME Close DX fristcall and second call
458 /* Get all basic data from the driver */
459 if (!DdQueryDirectDrawObject(This
->lpLcl
->lpGbl
,
461 &ddgbl
.lpDDCBtmp
->HALDD
,
462 &ddgbl
.lpDDCBtmp
->HALDDSurface
,
463 &ddgbl
.lpDDCBtmp
->HALDDPalette
,
466 &ddgbl
.lpDDCBtmp
->HALDDExeBuf
,
467 (DDSURFACEDESC
*)mpTextures
,
471 DxHeapMemFree(mpFourCC
);
472 DxHeapMemFree(mpTextures
);
473 DxHeapMemFree(ddgbl
.lpDDCBtmp
);
474 // FIXME Close DX fristcall and second call
478 memcpy(&ddgbl
.vmiData
, &mHALInfo
.vmiData
,sizeof(VIDMEMINFO
));
479 memcpy(&ddgbl
.ddCaps
, &mHALInfo
.ddCaps
,sizeof(DDCORECAPS
));
481 This
->lpLcl
->lpGbl
->dwNumFourCC
= mHALInfo
.ddCaps
.dwNumFourCCCodes
;
482 This
->lpLcl
->lpGbl
->lpdwFourCC
= mpFourCC
;
484 This
->lpLcl
->lpGbl
->dwMonitorFrequency
= mHALInfo
.dwMonitorFrequency
;
485 This
->lpLcl
->lpGbl
->dwModeIndex
= mHALInfo
.dwModeIndex
;
486 This
->lpLcl
->lpGbl
->dwNumModes
= mHALInfo
.dwNumModes
;
487 This
->lpLcl
->lpGbl
->lpModeInfo
= mHALInfo
.lpModeInfo
;
488 This
->lpLcl
->lpGbl
->hInstance
= mHALInfo
.hInstance
;
489 This
->lpLcl
->lpGbl
->lp16DD
= This
->lpLcl
->lpGbl
;
491 /* FIXME convert mpTextures to DDHALMODEINFO */
492 DxHeapMemFree(mpTextures
);
494 /* FIXME D3D setup mD3dCallbacks and mD3dDriverData */
495 DDHAL_GETDRIVERINFODATA DdGetDriverInfo
= { 0 };
496 DdGetDriverInfo
.dwSize
= sizeof (DDHAL_GETDRIVERINFODATA
);
497 DdGetDriverInfo
.guidInfo
= GUID_MiscellaneousCallbacks
;
498 DdGetDriverInfo
.lpvData
= (PVOID
)&ddgbl
.lpDDCBtmp
->cbDDMiscellaneousCallbacks
;
499 DdGetDriverInfo
.dwExpectedSize
= sizeof (DDHAL_DDMISCELLANEOUSCALLBACKS
);
500 if(mHALInfo
.GetDriverInfo (&DdGetDriverInfo
) == DDHAL_DRIVER_NOTHANDLED
|| DdGetDriverInfo
.ddRVal
!= DD_OK
)
502 DxHeapMemFree(mpFourCC
);
503 DxHeapMemFree(mpTextures
);
504 DxHeapMemFree(ddgbl
.lpDDCBtmp
);
505 // FIXME Close DX fristcall and second call