xref: /reactos/win32ss/gdi/gdi32/include/gdi32p.h (revision 84ccccab)
1 /*
2  * COPYRIGHT:       See COPYING in the top level directory
3  * PROJECT:         ReactOS System Libraries
4  * FILE:            win32ss/gdi/gdi32/include/gdi32p.h
5  * PURPOSE:         User-Mode Win32 GDI Library Private Header
6  * PROGRAMMER:      Alex Ionescu (alex@relsoft.net)
7  */
8 
9 #pragma once
10 
11 /* DATA **********************************************************************/
12 
13 extern PGDI_TABLE_ENTRY GdiHandleTable;
14 extern PGDI_SHARED_HANDLE_TABLE GdiSharedHandleTable;
15 extern HANDLE hProcessHeap;
16 extern HANDLE CurrentProcessId;
17 extern DWORD GDI_BatchLimit;
18 extern PDEVCAPS GdiDevCaps;
19 extern BOOL gbLpk;          // Global bool LanguagePack
20 extern HANDLE ghSpooler;
21 extern RTL_CRITICAL_SECTION semLocal;
22 
23 typedef INT
24 (CALLBACK* EMFPLAYPROC)(
25     HDC hdc,
26     INT iFunction,
27     HANDLE hPageQuery
28 );
29 
30 /* DEFINES *******************************************************************/
31 
32 #define HANDLE_LIST_INC 20
33 
34 #define METAFILE_MEMORY 1
35 #define METAFILE_DISK   2
36 
37 #define SAPCALLBACKDELAY 244
38 
39 /* MACRO ********************************************************************/
40 
41 #define ROP_USES_SOURCE(Rop)   (((Rop) << 2 ^ Rop) & 0xCC0000)
42 #define RCAST(_Type, _Value)   (*((_Type*)&_Value))
43 
44 
45 /* TYPES *********************************************************************/
46 
47 // Based on wmfapi.h and Wine.
48 typedef struct tagMETAFILEDC
49 {
50     PVOID       pvMetaBuffer;
51     HANDLE      hFile;
52     DWORD       Size;
53     DWORD       dwWritten;
54     METAHEADER  mh;
55     WORD        reserved;
56     HLOCAL      MFObjList;
57     HPEN        hPen;
58     HBRUSH      hBrush;
59     HDC         hDc;
60     HGDIOBJ     hMetaDc;
61     HPALETTE    hPalette;
62     HFONT       hFont;
63     HBITMAP     hBitmap;
64     HRGN        hRegion;
65     HGDIOBJ     hMetafile;
66     HGDIOBJ     hMemDc;
67     HPEN        hExtPen;
68     HGDIOBJ     hEnhMetaDc;
69     HGDIOBJ     hEnhMetaFile;
70     HCOLORSPACE hColorSpace;
71     WCHAR       Filename[MAX_PATH+2];
72 } METAFILEDC,*PMETAFILEDC;
73 
74 // Metafile Entry handle
75 typedef struct tagMF_ENTRY
76 {
77     LIST_ENTRY   List;
78     HGDIOBJ      hmDC;             // Handle return from NtGdiCreateClientObj.
79     PMETAFILEDC pmfDC;
80 } MF_ENTRY, *PMF_ENTRY;
81 
82 typedef struct tagENHMETAFILE
83 {
84     PVOID      pvMetaBuffer;
85     HANDLE     hFile;      /* Handle for disk based MetaFile */
86     DWORD      Size;
87     INT        iType;
88     PENHMETAHEADER emf;
89     UINT       handles_size, cur_handles;
90     HGDIOBJ   *handles;
91     INT        horzres, vertres;
92     INT        horzsize, vertsize;
93     INT        logpixelsx, logpixelsy;
94     INT        bitspixel;
95     INT        textcaps;
96     INT        rastercaps;
97     INT        technology;
98     INT        planes;
99 } ENHMETAFILE,*PENHMETAFILE;
100 
101 
102 #define PDEV_UMPD_ID  0xFEDCBA98
103 // UMPDEV flags
104 #define UMPDEV_NO_ESCAPE      0x0002
105 #define UMPDEV_SUPPORT_ESCAPE 0x0004
106 typedef struct _UMPDEV
107 {
108     DWORD           Sig;            // Init with PDEV_UMPD_ID
109     struct _UMPDEV *pumpdNext;
110     PDRIVER_INFO_5W pdi5Info;
111     HMODULE         hModule;
112     DWORD           dwFlags;
113     DWORD           dwDriverAttributes;
114     DWORD           dwConfigVersion; // Number of times the configuration
115     // file for this driver has been upgraded
116     // or downgraded since the last spooler restart.
117     DWORD           dwDriverCount;   // After init should be 2
118     DWORD           WOW64_UMPDev;
119     DWORD           WOW64_hMod;
120     DWORD           Unknown;
121     PVOID           apfn[INDEX_LAST]; // Print Driver pfn
122 } UMPDEV, *PUMPDEV;
123 
124 #define LOCALFONT_COUNT 10
125 typedef struct _LOCALFONT
126 {
127     FONT_ATTR  lfa[LOCALFONT_COUNT];
128 } LOCALFONT, *PLOCALFONT;
129 
130 // sdk/winspool.h
131 typedef BOOL (WINAPI *ABORTPRINTER) (HANDLE);
132 typedef BOOL (WINAPI *CLOSEPRINTER) (HANDLE);
133 typedef BOOL (WINAPI *CLOSESPOOLFILEHANDLE) (HANDLE, HANDLE); // W2k8
134 typedef HANDLE (WINAPI *COMMITSPOOLDATA) (HANDLE,HANDLE,DWORD); // W2k8
135 typedef LONG (WINAPI *DOCUMENTPROPERTIESW) (HWND,HANDLE,LPWSTR,PDEVMODEW,PDEVMODEW,DWORD);
136 typedef BOOL (WINAPI *ENDDOCPRINTER) (HANDLE);
137 typedef BOOL (WINAPI *ENDPAGEPRINTER) (HANDLE);
138 typedef BOOL (WINAPI *GETPRINTERW) (HANDLE,DWORD,LPBYTE,DWORD,LPDWORD);
139 typedef BOOL (WINAPI *GETPRINTERDRIVERW) (HANDLE,LPWSTR,DWORD,LPBYTE,DWORD,LPDWORD);
140 typedef HANDLE (WINAPI *GETSPOOLFILEHANDLE) (HANDLE); // W2k8
141 typedef BOOL (WINAPI *ISVALIDDEVMODEW) (PDEVMODEW,size_t);
142 typedef BOOL (WINAPI *OPENPRINTERW) (LPWSTR,PHANDLE,LPPRINTER_DEFAULTSW);
143 typedef BOOL (WINAPI *READPRINTER) (HANDLE,PVOID,DWORD,PDWORD);
144 typedef BOOL (WINAPI *RESETPRINTERW) (HANDLE,LPPRINTER_DEFAULTSW);
145 typedef LPWSTR (WINAPI *STARTDOCDLGW) (HANDLE,DOCINFOW *);
146 typedef DWORD (WINAPI *STARTDOCPRINTERW) (HANDLE,DWORD,PBYTE);
147 typedef BOOL (WINAPI *STARTPAGEPRINTER) (HANDLE);
148 // ddk/winsplp.h
149 typedef BOOL (WINAPI *SEEKPRINTER) (HANDLE,LARGE_INTEGER,PLARGE_INTEGER,DWORD,BOOL);
150 typedef BOOL (WINAPI *SPLREADPRINTER) (HANDLE,LPBYTE *,DWORD);
151 // Same as ddk/winsplp.h DriverUnloadComplete?
152 typedef BOOL (WINAPI *SPLDRIVERUNLOADCOMPLETE) (LPWSTR);
153 // Driver support:
154 // DrvDocumentEvent api/winddiui.h not W2k8 DocumentEventAW
155 typedef INT (WINAPI *DOCUMENTEVENT) (HANDLE,HDC,INT,ULONG,PVOID,ULONG,PVOID);
156 // DrvQueryColorProfile
157 typedef BOOL (WINAPI *QUERYCOLORPROFILE) (HANDLE,PDEVMODEW,ULONG,VOID*,ULONG,FLONG);
158 // Unknown:
159 typedef DWORD (WINAPI *QUERYSPOOLMODE) (HANDLE,DWORD,DWORD);
160 typedef DWORD (WINAPI *QUERYREMOTEFONTS) (DWORD,DWORD,DWORD);
161 
162 extern CLOSEPRINTER fpClosePrinter;
163 extern OPENPRINTERW fpOpenPrinterW;
164 
165 /* FUNCTIONS *****************************************************************/
166 
167 PVOID
168 HEAP_alloc(DWORD len);
169 
170 NTSTATUS
171 HEAP_strdupA2W(
172     LPWSTR* ppszW,
173     LPCSTR lpszA
174 );
175 
176 VOID
177 HEAP_free(LPVOID memory);
178 
179 VOID
180 FASTCALL
181 FONT_TextMetricWToA(
182     const TEXTMETRICW *ptmW,
183     LPTEXTMETRICA ptmA
184 );
185 
186 VOID
187 FASTCALL
188 NewTextMetricW2A(
189     NEWTEXTMETRICA *tma,
190     NEWTEXTMETRICW *tmw
191 );
192 
193 VOID
194 FASTCALL
195 NewTextMetricExW2A(
196     NEWTEXTMETRICEXA *tma,
197     NEWTEXTMETRICEXW *tmw
198 );
199 
200 BOOL
201 FASTCALL
202 DeleteRegion( HRGN );
203 
204 BOOL
205 WINAPI
206 GdiValidateHandle(HGDIOBJ);
207 
208 BOOL
209 GdiGetHandleUserData(
210     HGDIOBJ hGdiObj,
211     DWORD ObjectType,
212     PVOID *UserData
213 );
214 
215 PLDC
216 FASTCALL
217 GdiGetLDC(HDC hDC);
218 
219 BOOL
220 FASTCALL
221 GdiSetLDC(HDC hdc, PVOID pvLDC);
222 
223 HGDIOBJ
224 WINAPI
225 GdiFixUpHandle(HGDIOBJ hGO);
226 
227 BOOL
228 WINAPI
229 CalculateColorTableSize(
230     CONST BITMAPINFOHEADER *BitmapInfoHeader,
231     UINT *ColorSpec,
232     UINT *ColorTableSize
233 );
234 
235 LPBITMAPINFO
236 WINAPI
237 ConvertBitmapInfo(
238     CONST BITMAPINFO *BitmapInfo,
239     UINT ColorSpec,
240     UINT *BitmapInfoSize,
241     BOOL FollowedByData
242 );
243 
244 DWORD
245 WINAPI
246 GetAndSetDCDWord(
247     _In_ HDC hdc,
248     _In_ UINT u,
249     _In_ DWORD dwIn,
250     _In_ ULONG ulMFId,
251     _In_ USHORT usMF16Id,
252     _In_ DWORD dwError);
253 
254 DWORD
255 WINAPI
256 GetDCDWord(
257     _In_ HDC hdc,
258     _In_ UINT u,
259     _In_ DWORD dwError);
260 
261 HGDIOBJ
262 WINAPI
263 GetDCObject( HDC, INT);
264 
265 VOID
266 NTAPI
267 LogFontA2W(
268     LPLOGFONTW pW,
269     CONST LOGFONTA *pA
270 );
271 
272 VOID
273 NTAPI
274 LogFontW2A(
275     LPLOGFONTA pA,
276     CONST LOGFONTW *pW
277 );
278 
279 VOID
280 WINAPI
281 EnumLogFontExW2A(
282     LPENUMLOGFONTEXA fontA,
283     CONST ENUMLOGFONTEXW *fontW );
284 
285 BOOL
286 WINAPI
287 GetETM(HDC hdc,
288        EXTTEXTMETRIC *petm);
289 
290 /* FIXME: Put in some public header */
291 UINT
292 WINAPI
293 UserRealizePalette(HDC hDC);
294 
295 int
296 WINAPI
297 GdiAddFontResourceW(LPCWSTR lpszFilename,FLONG fl,DESIGNVECTOR *pdv);
298 
299 VOID
300 WINAPI
301 GdiSetLastError( DWORD dwErrCode );
302 
303 DWORD WINAPI GdiGetCodePage(HDC);
304 
305 int
306 WINAPI
307 GdiGetBitmapBitsSize(BITMAPINFO *lpbmi);
308 
309 VOID GdiSAPCallback(PLDC pldc);
310 HGDIOBJ FASTCALL hGetPEBHandle(HANDLECACHETYPE,COLORREF);
311 
312 int FASTCALL DocumentEventEx(PVOID,HANDLE,HDC,int,ULONG,PVOID,ULONG,PVOID);
313 BOOL FASTCALL EndPagePrinterEx(PVOID,HANDLE);
314 BOOL FASTCALL LoadTheSpoolerDrv(VOID);
315 
316 FORCEINLINE
317 PVOID
318 GdiAllocBatchCommand(
319     HDC hdc,
320     USHORT Cmd)
321 {
322     PTEB pTeb;
323     USHORT cjSize;
324     PGDIBATCHHDR pHdr;
325 
326     /* Get a pointer to the TEB */
327     pTeb = NtCurrentTeb();
328 
329     /* Check if we have a valid environment */
330     if (!pTeb || !pTeb->Win32ThreadInfo) return NULL;
331 
332     /* Do we use a DC? */
333     if (hdc)
334     {
335         /* If the batch DC is NULL, we set this one as the new one */
336         if (!pTeb->GdiTebBatch.HDC) pTeb->GdiTebBatch.HDC = hdc;
337 
338         /* If not, check if the batch DC equal to our DC */
339         else if (pTeb->GdiTebBatch.HDC != hdc) return NULL;
340     }
341 
342     /* Get the size of the entry */
343     if      (Cmd == GdiBCPatBlt) cjSize = 0;
344     else if (Cmd == GdiBCPolyPatBlt) cjSize = 0;
345     else if (Cmd == GdiBCTextOut) cjSize = 0;
346     else if (Cmd == GdiBCExtTextOut) cjSize = 0;
347     else if (Cmd == GdiBCSetBrushOrg) cjSize = sizeof(GDIBSSETBRHORG);
348     else if (Cmd == GdiBCExtSelClipRgn) cjSize = 0;
349     else if (Cmd == GdiBCSelObj) cjSize = sizeof(GDIBSOBJECT);
350     else if (Cmd == GdiBCDelRgn) cjSize = sizeof(GDIBSOBJECT);
351     else if (Cmd == GdiBCDelObj) cjSize = sizeof(GDIBSOBJECT);
352     else cjSize = 0;
353 
354     /* Unsupported operation */
355     if (cjSize == 0) return NULL;
356 
357     /* Check if the buffer is full */
358     if ((pTeb->GdiBatchCount >= GDI_BatchLimit) ||
359         ((pTeb->GdiTebBatch.Offset + cjSize) > GDIBATCHBUFSIZE))
360     {
361         /* Call win32k, the kernel will call NtGdiFlushUserBatch to flush
362            the current batch */
363         NtGdiFlush();
364     }
365 
366     /* Get the head of the entry */
367     pHdr = (PVOID)((PUCHAR)pTeb->GdiTebBatch.Buffer + pTeb->GdiTebBatch.Offset);
368 
369     /* Update Offset and batch count */
370     pTeb->GdiTebBatch.Offset += cjSize;
371     pTeb->GdiBatchCount++;
372 
373     /* Fill in the core fields */
374     pHdr->Cmd = Cmd;
375     pHdr->Size = cjSize;
376 
377     return pHdr;
378 }
379 
380 FORCEINLINE
381 PDC_ATTR
382 GdiGetDcAttr(HDC hdc)
383 {
384     GDILOOBJTYPE eDcObjType;
385     PDC_ATTR pdcattr;
386 
387     /* Check DC object type */
388     eDcObjType = GDI_HANDLE_GET_TYPE(hdc);
389     if ((eDcObjType != GDILoObjType_LO_DC_TYPE) &&
390         (eDcObjType != GDILoObjType_LO_ALTDC_TYPE))
391     {
392         return NULL;
393     }
394 
395     /* Get the DC attribute */
396     if (!GdiGetHandleUserData((HGDIOBJ)hdc, eDcObjType, (PVOID*)&pdcattr))
397     {
398         return NULL;
399     }
400 
401     return pdcattr;
402 }
403 
404 FORCEINLINE
405 PRGN_ATTR
406 GdiGetRgnAttr(HRGN hrgn)
407 {
408     PRGN_ATTR prgnattr;
409 
410     /* Get the region attribute */
411     if (!GdiGetHandleUserData(hrgn, GDILoObjType_LO_REGION_TYPE, (PVOID*)&prgnattr))
412     {
413         return NULL;
414     }
415 
416     return prgnattr;
417 }
418 
419 #ifdef _M_IX86
420 FLOATL FASTCALL EFtoF(EFLOAT_S * efp);
421 #define FOtoF(pfo) EFtoF((EFLOAT_S*)pfo)
422 #else
423 #define FOtoF(pfo) (*(pfo))
424 #endif
425 
426 /* This is an inlined version of lrintf. */
427 FORCEINLINE
428 int
429 _lrintf(float f)
430 {
431 #if defined(_M_IX86) && defined(__GNUC__)
432     int result;
433     __asm__ __volatile__ ("fistpl %0" : "=m" (result) : "t" (f) : "st");
434     return result;
435 #elif defined(_M_IX86) && defined(_MSC_VER)
436     int result;
437     __asm
438     {
439         fld f;
440         fistp result;
441     }
442 #else
443     /* slow, but portable */
444     return (int)(f >= 0 ? f+0.5 : f-0.5);
445 #endif
446 }
447 
448 HBRUSH
449 WINAPI
450 GdiSelectBrush(
451     _In_ HDC hdc,
452     _In_ HBRUSH hbr);
453 
454 HPEN
455 WINAPI
456 GdiSelectPen(
457     _In_ HDC hdc,
458     _In_ HPEN hpen);
459 
460 HFONT
461 WINAPI
462 GdiSelectFont(
463     _In_ HDC hdc,
464     _In_ HFONT hfont);
465 
466 HGDIOBJ
467 WINAPI
468 GdiCreateClientObj(
469     _In_ PVOID pvObject,
470     _In_ GDILOOBJTYPE eObjType);
471 
472 PVOID
473 WINAPI
474 GdiDeleteClientObj(
475     _In_ HGDIOBJ hobj);
476 
477 BOOL
478 WINAPI
479 GdiCreateClientObjLink(
480     _In_ HGDIOBJ hobj,
481     _In_ PVOID pvObject);
482 
483 PVOID
484 WINAPI
485 GdiGetClientObjLink(
486     _In_ HGDIOBJ hobj);
487 
488 PVOID
489 WINAPI
490 GdiRemoveClientObjLink(
491     _In_ HGDIOBJ hobj);
492 
493 extern ULONG gcClientObj;
494 
495 VOID
496 WINAPI
497 METADC_DeleteObject(HGDIOBJ hobj);
498 
499 BOOL
500 WINAPI
501 METADC_DeleteDC(
502     _In_ HDC hdc);
503 
504 INT
505 WINAPI
506 METADC16_Escape(
507     _In_ HDC hdc,
508     _In_ INT nEscape,
509     _In_ INT cbInput,
510     _In_ LPCSTR lpvInData,
511     _Out_ LPVOID lpvOutData);
512 
513 BOOL
514 WINAPI
515 METADC_ExtTextOutW(
516     HDC hdc,
517     INT x,
518     INT y,
519     UINT fuOptions,
520     const RECT *lprc,
521     LPCWSTR lpString,
522     UINT cchString,
523     const INT *lpDx);
524 
525 BOOL
526 WINAPI
527 METADC_PatBlt(
528     _In_ HDC hdc,
529     _In_ INT xLeft,
530     _In_ INT yTop,
531     _In_ INT nWidth,
532     _In_ INT nHeight,
533     _In_ DWORD dwRop);
534 
535 
536 /* The following METADC_* functions follow this pattern: */
537 #define HANDLE_METADC0P(_RetType, _Func, dwError, hdc, ...) \
538     if (GDI_HANDLE_GET_TYPE(hdc) != GDILoObjType_LO_DC_TYPE) \
539     { \
540         DWORD_PTR dwResult; \
541         if (METADC_Dispatch(DCFUNC_##_Func, &dwResult, (DWORD_PTR)dwError, hdc)) \
542         { \
543             return (_RetType)dwResult; \
544         } \
545     }
546 
547 #define HANDLE_METADC(_RetType, _Func, dwError, hdc, ...) \
548     if (GDI_HANDLE_GET_TYPE(hdc) != GDILoObjType_LO_DC_TYPE) \
549     { \
550         DWORD_PTR dwResult = 1; \
551         if (METADC_Dispatch(DCFUNC_##_Func, &dwResult, (DWORD_PTR)dwError, hdc, __VA_ARGS__)) \
552         { \
553             return (_RetType)dwResult; \
554         } \
555     }
556 
557 
558 typedef enum _DCFUNC
559 {
560     //DCFUNC_AbortDoc,
561     DCFUNC_AbortPath,
562     DCFUNC_AlphaBlend, // UNIMPLEMENTED
563     DCFUNC_AngleArc, // UNIMPLEMENTED
564     DCFUNC_Arc,
565     DCFUNC_ArcTo, // UNIMPLEMENTED
566     DCFUNC_BeginPath,
567     //DCFUNC_BitBlt,
568     DCFUNC_Chord,
569     DCFUNC_CloseFigure,
570     DCFUNC_Ellipse,
571     DCFUNC_EndPath,
572     DCFUNC_ExcludeClipRect,
573     DCFUNC_ExtEscape,
574     DCFUNC_ExtFloodFill,
575     DCFUNC_ExtSelectClipRgn,
576     DCFUNC_ExtTextOut,
577     DCFUNC_FillPath,
578     DCFUNC_FillRgn,
579     DCFUNC_FlattenPath,
580     DCFUNC_FrameRgn,
581     DCFUNC_GetDeviceCaps,
582     DCFUNC_GdiComment,
583     DCFUNC_GradientFill, // UNIMPLEMENTED
584     DCFUNC_IntersectClipRect,
585     DCFUNC_InvertRgn,
586     DCFUNC_LineTo,
587     DCFUNC_MaskBlt, // UNIMPLEMENTED
588     DCFUNC_ModifyWorldTransform,
589     DCFUNC_MoveTo,
590     DCFUNC_OffsetClipRgn,
591     DCFUNC_OffsetViewportOrgEx,
592     DCFUNC_OffsetWindowOrgEx,
593     DCFUNC_PathToRegion, // UNIMPLEMENTED
594     DCFUNC_PatBlt,
595     DCFUNC_Pie,
596     DCFUNC_PlgBlt, // UNIMPLEMENTED
597     DCFUNC_PolyBezier,
598     DCFUNC_PolyBezierTo,
599     DCFUNC_PolyDraw,
600     DCFUNC_Polygon,
601     DCFUNC_Polyline,
602     DCFUNC_PolylineTo,
603     DCFUNC_PolyPolygon,
604     DCFUNC_PolyPolyline,
605     DCFUNC_RealizePalette,
606     DCFUNC_Rectangle,
607     DCFUNC_RestoreDC,
608     DCFUNC_RoundRect,
609     DCFUNC_SaveDC,
610     DCFUNC_ScaleViewportExtEx,
611     DCFUNC_ScaleWindowExtEx,
612     DCFUNC_SelectBrush,
613     DCFUNC_SelectClipPath,
614     DCFUNC_SelectFont,
615     DCFUNC_SelectPalette,
616     DCFUNC_SelectPen,
617     DCFUNC_SetDCBrushColor,
618     DCFUNC_SetDCPenColor,
619     DCFUNC_SetDIBitsToDevice,
620     DCFUNC_SetBkColor,
621     DCFUNC_SetBkMode,
622     DCFUNC_SetLayout,
623     //DCFUNC_SetMapMode,
624     DCFUNC_SetPixel,
625     DCFUNC_SetPolyFillMode,
626     DCFUNC_SetROP2,
627     DCFUNC_SetStretchBltMode,
628     DCFUNC_SetTextAlign,
629     DCFUNC_SetTextCharacterExtra,
630     DCFUNC_SetTextColor,
631     DCFUNC_SetTextJustification,
632     DCFUNC_SetViewportExtEx,
633     DCFUNC_SetViewportOrgEx,
634     DCFUNC_SetWindowExtEx,
635     DCFUNC_SetWindowOrgEx,
636     DCFUNC_StretchBlt,
637     DCFUNC_StrokeAndFillPath,
638     DCFUNC_StrokePath,
639     DCFUNC_TransparentBlt, // UNIMPLEMENTED
640     DCFUNC_WidenPath,
641 
642 } DCFUNC;
643 
644 BOOL
645 METADC_Dispatch(
646     _In_ DCFUNC eFunction,
647     _Out_ PDWORD_PTR pdwResult,
648     _In_ DWORD_PTR dwError,
649     _In_ HDC hdc,
650     ...);
651 
652 #define HANDLE_METADC2(_RetType, _Func, hdc, ...) \
653     if (GDI_HANDLE_GET_TYPE(hdc) != GDILoObjType_LO_DC_TYPE) \
654     { \
655         _RetType result; \
656         if (METADC_##_Func(&result, hdc, __VA_ARGS__)) \
657         { \
658             return result; \
659         } \
660     }
661 
662 BOOL
663 WINAPI
664 METADC_GetAndSetDCDWord(
665     _Out_ PDWORD pdwResult,
666     _In_ HDC hdc,
667     _In_ UINT u,
668     _In_ DWORD dwIn,
669     _In_ ULONG ulMFId,
670     _In_ USHORT usMF16Id,
671     _In_ DWORD dwError);
672 
673 /* EOF */
674