227b73f2eb23815d5a9926ab144d2c35aaa811cc
[reactos.git] / reactos / dll / win32 / gdi32 / misc / gdientry.c
1 /*
2 * COPYRIGHT: See COPYING in the top level directory
3 * PROJECT: ReactOS GDI32
4 * PURPOSE: GDI DirectX inteface
5 * FILE: lib/gdi32/misc/gdientry.c
6 * PROGRAMERS: Alex Ionescu (alex@relsoft.net)
7 * Magnus Olsen (magnus@greatlord.com)
8 */
9
10 /* INCLUDES ******************************************************************/
11
12 #include "precomp.h"
13 #include <ddraw.h>
14 #include <ddrawi.h>
15 #include <ddrawint.h>
16 #include <ddrawgdi.h>
17 #include <ntgdi.h>
18
19 /* DATA **********************************************************************/
20
21 HANDLE ghDirectDraw;
22 ULONG gcDirectDraw;
23
24 #define GetDdHandle(Handle) ((HANDLE)Handle ? (HANDLE)Handle : ghDirectDraw)
25
26
27 /* CALLBACKS *****************************************************************/
28
29 /*
30 * Dd Surface Callbacks
31 */
32 DWORD
33 WINAPI
34 DdAddAttachedSurface(LPDDHAL_ADDATTACHEDSURFACEDATA Attach)
35 {
36 /* Call win32k */
37 return NtGdiDdAddAttachedSurface((HANDLE)Attach->lpDDSurface->hDDSurface,
38 (HANDLE)Attach->lpSurfAttached->hDDSurface,
39 (PDD_ADDATTACHEDSURFACEDATA)Attach);
40 }
41
42 DWORD
43 WINAPI
44 DdBlt(LPDDHAL_BLTDATA Blt)
45 {
46 HANDLE Surface = 0;
47
48 /* Use the right surface */
49 if (Blt->lpDDSrcSurface) Surface = (HANDLE)Blt->lpDDSrcSurface->hDDSurface;
50
51 /* Call win32k */
52 return NtGdiDdBlt((HANDLE)Blt->lpDDDestSurface->hDDSurface, Surface, (PDD_BLTDATA)Blt);
53 }
54
55 DWORD
56 APIENTRY
57 DdDestroySurface(LPDDHAL_DESTROYSURFACEDATA pDestroySurface)
58 {
59 DWORD Return = DDHAL_DRIVER_NOTHANDLED;
60 BOOL RealDestroy = TRUE;
61 LPDDRAWI_DDRAWSURFACE_LCL pSurfaceLocal;
62
63 /* Get the local surface */
64 pSurfaceLocal = pDestroySurface->lpDDSurface;
65
66 /* Make sure there's a surface */
67 if (pSurfaceLocal->hDDSurface)
68 {
69 /* Check if we shoudl really destroy it */
70 if ((pSurfaceLocal->dwFlags & DDRAWISURF_DRIVERMANAGED) &&
71 (pSurfaceLocal->dwFlags & DDRAWISURF_INVALID))
72 {
73 RealDestroy = FALSE;
74 }
75
76 /* Call win32k */
77 Return = NtGdiDdDestroySurface((HANDLE)pSurfaceLocal->hDDSurface,
78 RealDestroy);
79 }
80
81 return Return;
82 }
83
84 DWORD
85 WINAPI
86 DdFlip(LPDDHAL_FLIPDATA Flip)
87 {
88 /* Call win32k */
89
90 return NtGdiDdFlip( (HANDLE)Flip->lpSurfCurr->hDDSurface,
91 (HANDLE)Flip->lpSurfTarg->hDDSurface,
92 /* FIXME the two last should be current left handler */
93 (HANDLE)Flip->lpSurfCurr->hDDSurface,
94 (HANDLE)Flip->lpSurfTarg->hDDSurface,
95 (PDD_FLIPDATA)Flip);
96 }
97
98 DWORD
99 WINAPI
100 DdLock(LPDDHAL_LOCKDATA Lock)
101 {
102 /* Call win32k */
103 return NtGdiDdLock((HANDLE)Lock->lpDDSurface->hDDSurface,
104 (PDD_LOCKDATA)Lock,
105 (HANDLE)Lock->lpDDSurface->hDC);
106 }
107
108 DWORD
109 WINAPI
110 DdUnlock(LPDDHAL_UNLOCKDATA Unlock)
111 {
112 /* Call win32k */
113 return NtGdiDdUnlock((HANDLE)Unlock->lpDDSurface->hDDSurface,
114 (PDD_UNLOCKDATA)Unlock);
115 }
116
117 DWORD
118 WINAPI
119 DdGetBltStatus(LPDDHAL_GETBLTSTATUSDATA GetBltStatus)
120 {
121 /* Call win32k */
122 return NtGdiDdGetBltStatus((HANDLE)GetBltStatus->lpDDSurface->hDDSurface,
123 (PDD_GETBLTSTATUSDATA)GetBltStatus);
124 }
125
126 DWORD
127 WINAPI
128 DdGetFlipStatus(LPDDHAL_GETFLIPSTATUSDATA GetFlipStatus)
129 {
130 /* Call win32k */
131 return NtGdiDdGetFlipStatus((HANDLE)GetFlipStatus->lpDDSurface->hDDSurface,
132 (PDD_GETFLIPSTATUSDATA)GetFlipStatus);
133 }
134
135 DWORD
136 APIENTRY
137 DdUpdateOverlay(LPDDHAL_UPDATEOVERLAYDATA UpdateOverlay)
138 {
139 /* We have to handle this manually here */
140 if (UpdateOverlay->dwFlags & DDOVER_KEYDEST)
141 {
142 /* Use the override */
143 UpdateOverlay->dwFlags &= ~DDOVER_KEYDEST;
144 UpdateOverlay->dwFlags |= DDOVER_KEYDESTOVERRIDE;
145
146 /* Set the overlay */
147 UpdateOverlay->overlayFX.dckDestColorkey =
148 UpdateOverlay->lpDDDestSurface->ddckCKDestOverlay;
149 }
150 if (UpdateOverlay->dwFlags & DDOVER_KEYSRC)
151 {
152 /* Use the override */
153 UpdateOverlay->dwFlags &= ~DDOVER_KEYSRC;
154 UpdateOverlay->dwFlags |= DDOVER_KEYSRCOVERRIDE;
155
156 /* Set the overlay */
157 UpdateOverlay->overlayFX.dckSrcColorkey =
158 UpdateOverlay->lpDDSrcSurface->ddckCKSrcOverlay;
159 }
160
161 /* Call win32k */
162 return NtGdiDdUpdateOverlay((HANDLE)UpdateOverlay->lpDDDestSurface->hDDSurface,
163 (HANDLE)UpdateOverlay->lpDDSrcSurface->hDDSurface,
164 (PDD_UPDATEOVERLAYDATA)UpdateOverlay);
165 }
166
167 DWORD
168 APIENTRY
169 DdSetOverlayPosition(LPDDHAL_SETOVERLAYPOSITIONDATA SetOverlayPosition)
170 {
171 /* Call win32k */
172 return NtGdiDdSetOverlayPosition((HANDLE)SetOverlayPosition->
173 lpDDSrcSurface->hDDSurface,
174 (HANDLE)SetOverlayPosition->
175 lpDDDestSurface->hDDSurface,
176 (PDD_SETOVERLAYPOSITIONDATA)
177 SetOverlayPosition);
178 }
179
180 /*
181 * Dd Callbacks
182 */
183 DWORD
184 WINAPI
185 DdWaitForVerticalBlank(LPDDHAL_WAITFORVERTICALBLANKDATA WaitForVerticalBlank)
186 {
187 /* Call win32k */
188 return NtGdiDdWaitForVerticalBlank(GetDdHandle(
189 WaitForVerticalBlank->lpDD->hDD),
190 (PDD_WAITFORVERTICALBLANKDATA)
191 WaitForVerticalBlank);
192 }
193
194 DWORD
195 WINAPI
196 DdCanCreateSurface(LPDDHAL_CANCREATESURFACEDATA CanCreateSurface)
197 {
198 /* Call win32k */
199 return NtGdiDdCanCreateSurface(GetDdHandle(CanCreateSurface->lpDD->hDD),
200 (PDD_CANCREATESURFACEDATA)CanCreateSurface);
201 }
202
203 DWORD
204 APIENTRY
205 DdCreateSurface(LPDDHAL_CREATESURFACEDATA pCreateSurface)
206 {
207 DWORD Return = DDHAL_DRIVER_NOTHANDLED;
208 ULONG SurfaceCount = pCreateSurface->dwSCnt;
209 DD_SURFACE_LOCAL DdSurfaceLocal;
210 DD_SURFACE_MORE DdSurfaceMore;
211 DD_SURFACE_GLOBAL DdSurfaceGlobal;
212
213 HANDLE hPrevSurface, hSurface;
214
215
216 PDD_SURFACE_LOCAL pDdSurfaceLocal = NULL;
217 PDD_SURFACE_MORE pDdSurfaceMore = NULL;
218 PDD_SURFACE_GLOBAL pDdSurfaceGlobal = NULL;
219
220 PDD_SURFACE_LOCAL ptmpDdSurfaceLocal = NULL;
221 PDD_SURFACE_MORE ptmpDdSurfaceMore = NULL;
222 PDD_SURFACE_GLOBAL ptmpDdSurfaceGlobal = NULL;
223 PHANDLE phSurface = NULL, puhSurface = NULL;
224 ULONG i;
225 LPDDSURFACEDESC pSurfaceDesc = NULL;
226
227 /* Check how many surfaces there are */
228 if (SurfaceCount != 1)
229 {
230 /* We'll have to allocate more data, our stack isn't big enough */
231
232 }
233 else
234 {
235 /* We'll use what we have on the stack */
236 pDdSurfaceLocal = &DdSurfaceLocal;
237 pDdSurfaceMore = &DdSurfaceMore;
238 pDdSurfaceGlobal = &DdSurfaceGlobal;
239 phSurface = &hPrevSurface;
240 puhSurface = &hSurface;
241
242 /* Clear the structures */
243 RtlZeroMemory(&DdSurfaceLocal, sizeof(DdSurfaceLocal));
244 RtlZeroMemory(&DdSurfaceGlobal, sizeof(DdSurfaceGlobal));
245 RtlZeroMemory(&DdSurfaceMore, sizeof(DdSurfaceMore));
246 }
247
248 /* check if we got a surface or not */
249 if (SurfaceCount!=0)
250 {
251 /* Loop for each surface */
252 ptmpDdSurfaceGlobal = pDdSurfaceGlobal;
253 ptmpDdSurfaceLocal = pDdSurfaceLocal;
254 ptmpDdSurfaceMore = pDdSurfaceMore;
255 pSurfaceDesc = pCreateSurface->lpDDSurfaceDesc;
256
257 for (i = 0; i < SurfaceCount; i++)
258 {
259 LPDDRAWI_DDRAWSURFACE_LCL lcl = pCreateSurface->lplpSList[i];
260 LPDDRAWI_DDRAWSURFACE_GBL gpl = pCreateSurface->lplpSList[i]->lpGbl;
261
262 phSurface[i] = (HANDLE)lcl->hDDSurface;
263 ptmpDdSurfaceLocal->ddsCaps.dwCaps = lcl->ddsCaps.dwCaps;
264
265 ptmpDdSurfaceLocal->dwFlags = (ptmpDdSurfaceLocal->dwFlags &
266 (0xB0000000 | DDRAWISURF_INMASTERSPRITELIST |
267 DDRAWISURF_HELCB | DDRAWISURF_FRONTBUFFER |
268 DDRAWISURF_BACKBUFFER | DDRAWISURF_INVALID |
269 DDRAWISURF_DCIBUSY | DDRAWISURF_DCILOCK)) |
270 (lcl->dwFlags & DDRAWISURF_DRIVERMANAGED);
271
272 ptmpDdSurfaceGlobal->wWidth = gpl->wWidth;
273 ptmpDdSurfaceGlobal->wHeight = gpl->wHeight;
274 ptmpDdSurfaceGlobal->lPitch = gpl->lPitch;
275 ptmpDdSurfaceGlobal->fpVidMem = gpl->fpVidMem;
276 ptmpDdSurfaceGlobal->dwBlockSizeX = gpl->dwBlockSizeX;
277 ptmpDdSurfaceGlobal->dwBlockSizeY = gpl->dwBlockSizeY;
278
279 if (lcl->dwFlags & DDRAWISURF_HASPIXELFORMAT)
280 {
281 RtlCopyMemory( &ptmpDdSurfaceGlobal->ddpfSurface ,
282 &gpl->ddpfSurface,
283 sizeof(DDPIXELFORMAT));
284
285 ptmpDdSurfaceGlobal->ddpfSurface.dwSize = sizeof(DDPIXELFORMAT);
286 }
287 else
288 {
289 RtlCopyMemory( &ptmpDdSurfaceGlobal->ddpfSurface ,
290 &gpl->lpDD->vmiData.ddpfDisplay,
291 sizeof(DDPIXELFORMAT));
292 }
293
294 if (lcl->lpSurfMore)
295 {
296 ptmpDdSurfaceMore->ddsCapsEx.dwCaps2 = lcl->lpSurfMore->ddsCapsEx.dwCaps2;
297 ptmpDdSurfaceMore->ddsCapsEx.dwCaps3 = lcl->lpSurfMore->ddsCapsEx.dwCaps3;
298 ptmpDdSurfaceMore->ddsCapsEx.dwCaps4 = lcl->lpSurfMore->ddsCapsEx.dwCaps4;
299 ptmpDdSurfaceMore->dwSurfaceHandle = (DWORD) pCreateSurface->lplpSList[i]->dbnOverlayNode.object_int;
300 }
301
302 /* FIXME count to next SurfaceCount for
303 ptmpDdSurfaceGlobal = pDdSurfaceGlobal;
304 ptmpDdSurfaceLocal = pDdSurfaceLocal;
305 ptmpDdSurfaceMore = pDdSurfaceMore;
306
307 we only support one surface create at moment
308 */
309 }
310 }
311
312 /* Call win32k now */
313 pCreateSurface->ddRVal = DDERR_GENERIC;
314
315 Return = NtGdiDdCreateSurface(GetDdHandle(pCreateSurface->lpDD->hDD),
316 (HANDLE *)phSurface,
317 pSurfaceDesc,
318 pDdSurfaceGlobal,
319 pDdSurfaceLocal,
320 pDdSurfaceMore,
321 (PDD_CREATESURFACEDATA)pCreateSurface,
322 puhSurface);
323
324 if (SurfaceCount == 0)
325 {
326 pCreateSurface->ddRVal = DDERR_GENERIC;
327 }
328 else
329 {
330 ptmpDdSurfaceMore = pDdSurfaceMore;
331 ptmpDdSurfaceGlobal = pDdSurfaceGlobal;
332 ptmpDdSurfaceLocal = pDdSurfaceLocal;
333
334 for (i=0;i<SurfaceCount;i++)
335 {
336 LPDDRAWI_DDRAWSURFACE_LCL lcl = pCreateSurface->lplpSList[i];
337 LPDDRAWI_DDRAWSURFACE_GBL gpl = pCreateSurface->lplpSList[i]->lpGbl;
338
339 gpl->lPitch = ptmpDdSurfaceGlobal->lPitch;
340 gpl->fpVidMem = ptmpDdSurfaceGlobal->fpVidMem;
341 gpl->dwBlockSizeX = ptmpDdSurfaceGlobal->dwBlockSizeX;
342 gpl->dwBlockSizeY = ptmpDdSurfaceGlobal->dwBlockSizeY;
343
344 if (lcl->dwFlags & DDRAWISURF_HASPIXELFORMAT)
345 {
346 RtlCopyMemory( &gpl->ddpfSurface, &ptmpDdSurfaceGlobal->ddpfSurface , sizeof(DDPIXELFORMAT));
347 }
348
349 if (pCreateSurface->ddRVal != DD_OK)
350 {
351 gpl->fpVidMem = 0;
352 if (lcl->hDDSurface)
353 {
354 NtGdiDdDeleteSurfaceObject( (HANDLE)lcl->hDDSurface);
355 }
356 lcl->hDDSurface = 0;
357 }
358 else
359 {
360
361 lcl->hDDSurface = (ULONG_PTR) puhSurface[i];
362 }
363
364 lcl->ddsCaps.dwCaps = ptmpDdSurfaceLocal->ddsCaps.dwCaps;
365 if (lcl->lpSurfMore)
366 {
367 lcl->lpSurfMore->ddsCapsEx.dwCaps2 = ptmpDdSurfaceMore->ddsCapsEx.dwCaps2;
368 lcl->lpSurfMore->ddsCapsEx.dwCaps3 = ptmpDdSurfaceMore->ddsCapsEx.dwCaps3;
369 lcl->lpSurfMore->ddsCapsEx.dwCaps4 = ptmpDdSurfaceMore->ddsCapsEx.dwCaps4;
370 }
371 /* FIXME count to next SurfaceCount for
372 ptmpDdSurfaceGlobal = pDdSurfaceGlobal;
373 ptmpDdSurfaceLocal = pDdSurfaceLocal;
374 ptmpDdSurfaceMore = pDdSurfaceMore;
375 we only support one surface create at moment
376 */
377 }
378 }
379
380 /* Check if we have to free all our local allocations */
381 if (SurfaceCount > 1)
382 {
383 /* FIXME: */
384 }
385
386 /* Return */
387 return Return;
388 }
389
390 DWORD
391 APIENTRY
392 DdSetColorKey(LPDDHAL_SETCOLORKEYDATA pSetColorKey)
393 {
394 /* Call win32k */
395 return NtGdiDdSetColorKey((HANDLE)pSetColorKey->lpDDSurface->hDDSurface,
396 (PDD_SETCOLORKEYDATA)pSetColorKey);
397 }
398
399 DWORD
400 APIENTRY
401 DdGetScanLine(LPDDHAL_GETSCANLINEDATA pGetScanLine)
402 {
403 /* Call win32k */
404 return NtGdiDdGetScanLine(GetDdHandle(pGetScanLine->lpDD->hDD),
405 (PDD_GETSCANLINEDATA)pGetScanLine);
406 }
407
408 /* PRIVATE FUNCTIONS *********************************************************/
409
410 BOOL
411 WINAPI
412 bDDCreateSurface(LPDDRAWI_DDRAWSURFACE_LCL pSurface,
413 BOOL bComplete)
414 {
415 DD_SURFACE_LOCAL SurfaceLocal;
416 DD_SURFACE_GLOBAL SurfaceGlobal;
417 DD_SURFACE_MORE SurfaceMore;
418
419 /* Zero struct */
420 RtlZeroMemory(&SurfaceLocal, sizeof(DD_SURFACE_LOCAL));
421 RtlZeroMemory(&SurfaceGlobal, sizeof(DD_SURFACE_GLOBAL));
422 RtlZeroMemory(&SurfaceMore, sizeof(DD_SURFACE_MORE));
423
424 /* Set up SurfaceLocal struct */
425 SurfaceLocal.ddsCaps.dwCaps = pSurface->ddsCaps.dwCaps;
426 SurfaceLocal.dwFlags = pSurface->dwFlags;
427
428 /* Set up SurfaceMore struct */
429 RtlMoveMemory(&SurfaceMore.ddsCapsEx,
430 &pSurface->ddckCKDestBlt,
431 sizeof(DDSCAPSEX));
432 SurfaceMore.dwSurfaceHandle = (DWORD)pSurface->dbnOverlayNode.object_int->lpVtbl;
433
434 /* Set up SurfaceGlobal struct */
435 SurfaceGlobal.fpVidMem = pSurface->lpGbl->fpVidMem;
436 SurfaceGlobal.dwLinearSize = pSurface->lpGbl->dwLinearSize;
437 SurfaceGlobal.wHeight = pSurface->lpGbl->wHeight;
438 SurfaceGlobal.wWidth = pSurface->lpGbl->wWidth;
439
440 /* Check if we have a pixel format */
441 if (pSurface->dwFlags & DDSD_PIXELFORMAT)
442 {
443 /* Use global one */
444 SurfaceGlobal.ddpfSurface = pSurface->lpGbl->lpDD->vmiData.ddpfDisplay;
445 SurfaceGlobal.ddpfSurface.dwSize = sizeof(DDPIXELFORMAT);
446 }
447 else
448 {
449 /* Use local one */
450 SurfaceGlobal.ddpfSurface = pSurface->lpGbl->lpDD->vmiData.ddpfDisplay;
451 }
452
453 /* Create the object */
454 pSurface->hDDSurface = (DWORD)NtGdiDdCreateSurfaceObject(GetDdHandle(pSurface->lpGbl->lpDD->hDD),
455 (HANDLE)pSurface->hDDSurface,
456 &SurfaceLocal,
457 &SurfaceMore,
458 &SurfaceGlobal,
459 bComplete);
460
461 /* Return status */
462 if (pSurface->hDDSurface) return TRUE;
463 return FALSE;
464 }
465
466 /* PUBLIC FUNCTIONS **********************************************************/
467
468 /*
469 * @implemented
470 *
471 * GDIEntry 1
472 */
473 BOOL
474 WINAPI
475 DdCreateDirectDrawObject(LPDDRAWI_DIRECTDRAW_GBL pDirectDrawGlobal,
476 HDC hdc)
477 {
478 BOOL Return = FALSE;
479
480 /* Check if the global hDC (hdc == 0) is being used */
481 if (!hdc)
482 {
483 /* We'll only allow this if the global object doesn't exist yet */
484 if (!ghDirectDraw)
485 {
486 /* Create the DC */
487 if ((hdc = CreateDCW(L"Display", NULL, NULL, NULL)))
488 {
489 /* Create the DDraw Object */
490 ghDirectDraw = NtGdiDdCreateDirectDrawObject(hdc);
491
492 /* Delete our DC */
493 NtGdiDeleteObjectApp(hdc);
494 }
495 }
496
497 /* If we created the object, or had one ...*/
498 if (ghDirectDraw)
499 {
500 /* Increase count and set success */
501 gcDirectDraw++;
502 Return = TRUE;
503 }
504
505 /* Zero the handle */
506 pDirectDrawGlobal->hDD = 0;
507 }
508 else
509 {
510 /* Using the per-process object, so create it */
511 pDirectDrawGlobal->hDD = (ULONG_PTR)NtGdiDdCreateDirectDrawObject(hdc);
512
513 /* Set the return value */
514 Return = pDirectDrawGlobal->hDD ? TRUE : FALSE;
515 }
516
517 /* Return to caller */
518 return Return;
519 }
520
521 /*
522 * @implemented
523 *
524 * GDIEntry 2
525 */
526 BOOL
527 WINAPI
528 DdQueryDirectDrawObject(LPDDRAWI_DIRECTDRAW_GBL pDirectDrawGlobal,
529 LPDDHALINFO pHalInfo,
530 LPDDHAL_DDCALLBACKS pDDCallbacks,
531 LPDDHAL_DDSURFACECALLBACKS pDDSurfaceCallbacks,
532 LPDDHAL_DDPALETTECALLBACKS pDDPaletteCallbacks,
533 LPD3DHAL_CALLBACKS pD3dCallbacks,
534 LPD3DHAL_GLOBALDRIVERDATA pD3dDriverData,
535 LPDDHAL_DDEXEBUFCALLBACKS pD3dBufferCallbacks,
536 LPDDSURFACEDESC pD3dTextureFormats,
537 LPDWORD pdwFourCC,
538 LPVIDMEM pvmList)
539 {
540 PVIDEOMEMORY VidMemList = NULL;
541 DD_HALINFO HalInfo;
542 D3DNTHAL_CALLBACKS D3dCallbacks;
543 D3DNTHAL_GLOBALDRIVERDATA D3dDriverData;
544 DD_D3DBUFCALLBACKS D3dBufferCallbacks;
545 DWORD CallbackFlags[3];
546 DWORD dwNumHeaps=0, FourCCs=0;
547 DWORD Flags;
548
549 /* Clear the structures */
550 RtlZeroMemory(&HalInfo, sizeof(DD_HALINFO));
551 RtlZeroMemory(&D3dCallbacks, sizeof(D3DNTHAL_CALLBACKS));
552 RtlZeroMemory(&D3dDriverData, sizeof(D3DNTHAL_GLOBALDRIVERDATA));
553 RtlZeroMemory(&D3dBufferCallbacks, sizeof(DD_D3DBUFCALLBACKS));
554 RtlZeroMemory(CallbackFlags, sizeof(DWORD)*3);
555
556 pvmList = NULL;
557
558 /* Do the query */
559 if (!NtGdiDdQueryDirectDrawObject(GetDdHandle(pDirectDrawGlobal->hDD),
560 &HalInfo,
561 CallbackFlags,
562 &D3dCallbacks,
563 &D3dDriverData,
564 &D3dBufferCallbacks,
565 pD3dTextureFormats,
566 &dwNumHeaps,
567 VidMemList,
568 &FourCCs,
569 pdwFourCC))
570 {
571 /* We failed, free the memory and return */
572 return FALSE;
573 }
574
575 /* Clear the incoming pointer */
576 RtlZeroMemory(pHalInfo, sizeof(DDHALINFO));
577
578 /* Convert all the data */
579 pHalInfo->dwSize = sizeof(DDHALINFO);
580 pHalInfo->lpDDCallbacks = pDDCallbacks;
581 pHalInfo->lpDDSurfaceCallbacks = pDDSurfaceCallbacks;
582 pHalInfo->lpDDPaletteCallbacks = pDDPaletteCallbacks;
583
584 /* Check for NT5+ D3D Data */
585 if (D3dCallbacks.dwSize && D3dDriverData.dwSize)
586 {
587 /* Write these down */
588 pHalInfo->lpD3DGlobalDriverData = (ULONG_PTR)pD3dDriverData;
589 pHalInfo->lpD3DHALCallbacks = (ULONG_PTR)pD3dCallbacks;
590
591 /* Check for Buffer Callbacks */
592 if (D3dBufferCallbacks.dwSize)
593 {
594 /* Write this one too */
595 pHalInfo->lpDDExeBufCallbacks = pD3dBufferCallbacks;
596 }
597 }
598
599 /* Continue converting the rest */
600 pHalInfo->vmiData.dwFlags = HalInfo.vmiData.dwFlags;
601 pHalInfo->vmiData.dwDisplayWidth = HalInfo.vmiData.dwDisplayWidth;
602 pHalInfo->vmiData.dwDisplayHeight = HalInfo.vmiData.dwDisplayHeight;
603 pHalInfo->vmiData.lDisplayPitch = HalInfo.vmiData.lDisplayPitch;
604 pHalInfo->vmiData.fpPrimary = 0;
605
606 RtlCopyMemory( &pHalInfo->vmiData.ddpfDisplay,
607 &HalInfo.vmiData.ddpfDisplay,
608 sizeof(DDPIXELFORMAT));
609
610 pHalInfo->vmiData.dwOffscreenAlign = HalInfo.vmiData.dwOffscreenAlign;
611 pHalInfo->vmiData.dwOverlayAlign = HalInfo.vmiData.dwOverlayAlign;
612 pHalInfo->vmiData.dwTextureAlign = HalInfo.vmiData.dwTextureAlign;
613 pHalInfo->vmiData.dwZBufferAlign = HalInfo.vmiData.dwZBufferAlign;
614 pHalInfo->vmiData.dwAlphaAlign = HalInfo.vmiData.dwAlphaAlign;
615 pHalInfo->vmiData.dwNumHeaps = 0;
616 pHalInfo->vmiData.pvmList = pvmList;
617
618 RtlCopyMemory( &pHalInfo->ddCaps, &HalInfo.ddCaps,sizeof(DDCORECAPS ));
619
620 pHalInfo->ddCaps.dwNumFourCCCodes = FourCCs;
621 pHalInfo->lpdwFourCC = pdwFourCC;
622 pHalInfo->ddCaps.dwRops[6] = 0x1000;
623
624 /* FIXME implement DdGetDriverInfo */
625 // pHalInfo->dwFlags = HalInfo.dwFlags | DDHALINFO_GETDRIVERINFOSET;
626 // pHalInfo->GetDriverInfo = DdGetDriverInfo;
627
628 /* Now check if we got any DD callbacks */
629 if (pDDCallbacks)
630 {
631 /* Zero the structure */
632 RtlZeroMemory(pDDCallbacks, sizeof(DDHAL_DDCALLBACKS));
633
634 /* Set the flags for this structure */
635 Flags = CallbackFlags[0];
636
637 /* Write the header */
638 pDDCallbacks->dwSize = sizeof(DDHAL_DDCALLBACKS);
639 pDDCallbacks->dwFlags = Flags;
640
641 /* Now write the pointers, if applicable */
642 if (Flags & DDHAL_CB32_CREATESURFACE)
643 {
644 pDDCallbacks->CreateSurface = DdCreateSurface;
645 }
646 if (Flags & DDHAL_CB32_WAITFORVERTICALBLANK)
647 {
648 pDDCallbacks->WaitForVerticalBlank = DdWaitForVerticalBlank;
649 }
650 if (Flags & DDHAL_CB32_CANCREATESURFACE)
651 {
652 pDDCallbacks->CanCreateSurface = DdCanCreateSurface;
653 }
654 if (Flags & DDHAL_CB32_GETSCANLINE)
655 {
656 pDDCallbacks->GetScanLine = DdGetScanLine;
657 }
658 }
659
660 /* Check for DD Surface Callbacks */
661 if (pDDSurfaceCallbacks)
662 {
663 /* Zero the structures */
664 RtlZeroMemory(pDDSurfaceCallbacks, sizeof(DDHAL_DDSURFACECALLBACKS));
665
666 /* Set the flags for this one */
667 Flags = CallbackFlags[1];
668
669 /* Write the header, note that some functions are always exposed */
670 pDDSurfaceCallbacks->dwSize = sizeof(DDHAL_DDSURFACECALLBACKS);
671
672 pDDSurfaceCallbacks->dwFlags = Flags;
673 /*
674 pDDSurfaceCallBacks->dwFlags = (DDHAL_SURFCB32_LOCK |
675 DDHAL_SURFCB32_UNLOCK |
676 DDHAL_SURFCB32_SETCOLORKEY |
677 DDHAL_SURFCB32_DESTROYSURFACE) | Flags;
678 */
679
680 /* Write the always-on functions */
681 pDDSurfaceCallbacks->Lock = DdLock;
682 pDDSurfaceCallbacks->Unlock = DdUnlock;
683 pDDSurfaceCallbacks->SetColorKey = DdSetColorKey;
684 pDDSurfaceCallbacks->DestroySurface = DdDestroySurface;
685
686 /* Write the optional ones */
687 if (Flags & DDHAL_SURFCB32_FLIP)
688 {
689 pDDSurfaceCallbacks->Flip = DdFlip;
690 }
691 if (Flags & DDHAL_SURFCB32_BLT)
692 {
693 pDDSurfaceCallbacks->Blt = DdBlt;
694 }
695 if (Flags & DDHAL_SURFCB32_GETBLTSTATUS)
696 {
697 pDDSurfaceCallbacks->GetBltStatus = DdGetBltStatus;
698 }
699 if (Flags & DDHAL_SURFCB32_GETFLIPSTATUS)
700 {
701 pDDSurfaceCallbacks->GetFlipStatus = DdGetFlipStatus;
702 }
703 if (Flags & DDHAL_SURFCB32_UPDATEOVERLAY)
704 {
705 pDDSurfaceCallbacks->UpdateOverlay = DdUpdateOverlay;
706 }
707 if (Flags & DDHAL_SURFCB32_SETOVERLAYPOSITION)
708 {
709 pDDSurfaceCallbacks->SetOverlayPosition = DdSetOverlayPosition;
710 }
711 if (Flags & DDHAL_SURFCB32_ADDATTACHEDSURFACE)
712 {
713 pDDSurfaceCallbacks->AddAttachedSurface = DdAddAttachedSurface;
714 }
715 }
716
717 /* Check for DD Palette Callbacks */
718 if (pDDPaletteCallbacks)
719 {
720 /* Zero the struct */
721 RtlZeroMemory(pDDPaletteCallbacks, sizeof(DDHAL_DDPALETTECALLBACKS));
722
723 /* Get the flags for this one */
724 Flags = CallbackFlags[2];
725
726 /* Write the header */
727 pDDPaletteCallbacks->dwSize = sizeof(DDHAL_DDPALETTECALLBACKS);
728 pDDPaletteCallbacks->dwFlags = Flags;
729 }
730
731 /* Check for D3D Callbacks */
732 if (pD3dCallbacks)
733 {
734 /* Zero the struct */
735 RtlZeroMemory(pD3dCallbacks, sizeof(D3DHAL_CALLBACKS));
736
737 /* Check if we have one */
738 if (D3dCallbacks.dwSize)
739 {
740 /* Write the header */
741 pD3dCallbacks->dwSize = sizeof(D3DHAL_CALLBACKS);
742
743 /* Now check for each callback */
744 if (D3dCallbacks.ContextCreate)
745 {
746 /* FIXME
747 pD3dCallbacks->ContextCreate = D3dContextCreate;
748 */
749 }
750 if (D3dCallbacks.ContextDestroy)
751 {
752 pD3dCallbacks->ContextDestroy = (LPD3DHAL_CONTEXTDESTROYCB) NtGdiD3dContextDestroy;
753 }
754 if (D3dCallbacks.ContextDestroyAll)
755 {
756 /* FIXME
757 pD3dCallbacks->ContextDestroyAll = (LPD3DHAL_CONTEXTDESTROYALLCB) NtGdiD3dContextDestroyAll;
758 */
759 }
760 }
761 }
762
763 /* Check for D3D Driver Data */
764 if (pD3dDriverData)
765 {
766 /* Copy the struct */
767 RtlMoveMemory(pD3dDriverData,
768 &D3dDriverData,
769 sizeof(D3DHAL_GLOBALDRIVERDATA));
770
771 /* Write the pointer to the texture formats */
772 pD3dDriverData->lpTextureFormats = pD3dTextureFormats;
773 }
774
775 /* FIXME: Check for D3D Buffer Callbacks */
776
777 return TRUE;
778 }
779
780 /*
781 * @implemented
782 *
783 * GDIEntry 3
784 */
785 BOOL
786 WINAPI
787 DdDeleteDirectDrawObject(LPDDRAWI_DIRECTDRAW_GBL pDirectDrawGlobal)
788 {
789 BOOL Return = FALSE;
790
791 /* If this is the global object */
792 if(pDirectDrawGlobal->hDD)
793 {
794 /* Free it */
795 Return = NtGdiDdDeleteDirectDrawObject((HANDLE)pDirectDrawGlobal->hDD);
796 if (Return == TRUE)
797 {
798 pDirectDrawGlobal->hDD = 0;
799 }
800 }
801 else if (ghDirectDraw)
802 {
803 /* Always success here */
804 Return = TRUE;
805
806 /* Make sure this is the last instance */
807 if (!(--gcDirectDraw))
808 {
809 /* Delete the object */
810 Return = NtGdiDdDeleteDirectDrawObject(ghDirectDraw);
811 if (Return == TRUE)
812 {
813 ghDirectDraw = 0;
814 }
815 }
816 }
817
818 /* Return */
819 return Return;
820 }
821
822 /*
823 * @implemented
824 *
825 * GDIEntry 4
826 */
827 BOOL
828 WINAPI
829 DdCreateSurfaceObject( LPDDRAWI_DDRAWSURFACE_LCL pSurfaceLocal,
830 BOOL bPrimarySurface)
831 {
832 return bDDCreateSurface(pSurfaceLocal, TRUE);
833 }
834
835
836 /*
837 * @implemented
838 *
839 * GDIEntry 5
840 */
841 BOOL
842 WINAPI
843 DdDeleteSurfaceObject(LPDDRAWI_DDRAWSURFACE_LCL pSurfaceLocal)
844 {
845 BOOL Return = FALSE;
846
847 /* Make sure there is one */
848 if (pSurfaceLocal->hDDSurface)
849 {
850 /* Delete it */
851 Return = NtGdiDdDeleteSurfaceObject((HANDLE)pSurfaceLocal->hDDSurface);
852 pSurfaceLocal->hDDSurface = 0;
853 }
854
855 return Return;
856 }
857
858 /*
859 * @implemented
860 *
861 * GDIEntry 6
862 */
863 BOOL
864 WINAPI
865 DdResetVisrgn(LPDDRAWI_DDRAWSURFACE_LCL pSurfaceLocal,
866 HWND hWnd)
867 {
868 /* Call win32k directly */
869 return NtGdiDdResetVisrgn((HANDLE) pSurfaceLocal->hDDSurface, hWnd);
870 }
871
872 /*
873 * @implemented
874 *
875 * GDIEntry 7
876 */
877 HDC
878 WINAPI
879 DdGetDC(LPDDRAWI_DDRAWSURFACE_LCL pSurfaceLocal,
880 LPPALETTEENTRY pColorTable)
881 {
882 /* Call win32k directly */
883 return NtGdiDdGetDC(pColorTable, (HANDLE) pSurfaceLocal->hDDSurface);
884 }
885
886 /*
887 * @implemented
888 *
889 * GDIEntry 8
890 */
891 BOOL
892 WINAPI
893 DdReleaseDC(LPDDRAWI_DDRAWSURFACE_LCL pSurfaceLocal)
894 {
895 /* Call win32k directly */
896 return NtGdiDdReleaseDC((HANDLE) pSurfaceLocal->hDDSurface);
897 }
898
899 /*
900 * @unimplemented
901 * GDIEntry 9
902 */
903 HBITMAP
904 STDCALL
905 DdCreateDIBSection(HDC hdc,
906 CONST BITMAPINFO *pbmi,
907 UINT iUsage,
908 VOID **ppvBits,
909 HANDLE hSectionApp,
910 DWORD dwOffset)
911 {
912 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
913 return 0;
914 }
915
916 /*
917 * @implemented
918 *
919 * GDIEntry 10
920 */
921 BOOL
922 WINAPI
923 DdReenableDirectDrawObject(LPDDRAWI_DIRECTDRAW_GBL pDirectDrawGlobal,
924 BOOL *pbNewMode)
925 {
926 /* Call win32k directly */
927 return NtGdiDdReenableDirectDrawObject(GetDdHandle(pDirectDrawGlobal->hDD),
928 pbNewMode);
929 }
930
931
932 /*
933 * @implemented
934 *
935 * GDIEntry 11
936 */
937 BOOL
938 STDCALL
939 DdAttachSurface( LPDDRAWI_DDRAWSURFACE_LCL pSurfaceFrom,
940 LPDDRAWI_DDRAWSURFACE_LCL pSurfaceTo)
941 {
942 /* Create Surface if it does not exits one */
943 if (!pSurfaceFrom->hDDSurface)
944 {
945 if (!bDDCreateSurface(pSurfaceFrom, FALSE))
946 {
947 return FALSE;
948 }
949 }
950
951 /* Create Surface if it does not exits one */
952 if (!pSurfaceTo->hDDSurface)
953 {
954 if (!bDDCreateSurface(pSurfaceTo, FALSE))
955 {
956 return FALSE;
957 }
958 }
959
960 /* Call win32k */
961 return NtGdiDdAttachSurface((HANDLE)pSurfaceFrom->hDDSurface,
962 (HANDLE)pSurfaceTo->hDDSurface);
963 }
964
965 /*
966 * @implemented
967 *
968 * GDIEntry 12
969 */
970 VOID
971 STDCALL
972 DdUnattachSurface(LPDDRAWI_DDRAWSURFACE_LCL pSurface,
973 LPDDRAWI_DDRAWSURFACE_LCL pSurfaceAttached)
974 {
975 /* Call win32k */
976 NtGdiDdUnattachSurface((HANDLE)pSurface->hDDSurface,
977 (HANDLE)pSurfaceAttached->hDDSurface);
978 }
979
980 /*
981 * @implemented
982 *
983 * GDIEntry 13
984 */
985 ULONG
986 STDCALL
987 DdQueryDisplaySettingsUniqueness()
988 {
989 return GdiSharedHandleTable->flDeviceUniq;
990 }
991
992 /*
993 * @implemented
994 *
995 * GDIEntry 14
996 */
997 HANDLE
998 WINAPI
999 DdGetDxHandle(LPDDRAWI_DIRECTDRAW_LCL pDDraw,
1000 LPDDRAWI_DDRAWSURFACE_LCL pSurface,
1001 BOOL bRelease)
1002 {
1003 HANDLE hDD = NULL;
1004 HANDLE hSurface = (HANDLE)pSurface->hDDSurface;
1005
1006 /* Check if we already have a surface */
1007 if (!pSurface)
1008 {
1009 /* We don't have one, use the DirectDraw Object handle instead */
1010 hSurface = NULL;
1011 hDD = GetDdHandle(pDDraw->lpGbl->hDD);
1012 }
1013
1014 /* Call the API */
1015 return (HANDLE)NtGdiDdGetDxHandle(hDD, hSurface, bRelease);
1016 }
1017
1018 /*
1019 * @implemented
1020 *
1021 * GDIEntry 15
1022 */
1023 BOOL
1024 WINAPI
1025 DdSetGammaRamp(LPDDRAWI_DIRECTDRAW_LCL pDDraw,
1026 HDC hdc,
1027 LPVOID lpGammaRamp)
1028 {
1029 /* Call win32k directly */
1030 return NtGdiDdSetGammaRamp(GetDdHandle(pDDraw->lpGbl->hDD),
1031 hdc,
1032 lpGammaRamp);
1033 }
1034
1035
1036
1037
1038