1 /* $Id: driver.c,v 1.21 2002/09/07 15:13:11 chorns Exp $
3 * GDI Driver support routines
4 * (mostly swiped from Wine)
8 #undef WIN32_LEAN_AND_MEAN
11 #define NTOS_KERNEL_MODE
14 #include <ddk/winddi.h>
15 #include <ddk/ntddvdeo.h>
16 #include <win32k/driver.h>
22 typedef struct _GRAPHICS_DRIVER
25 PGD_ENABLEDRIVER EnableDriver
;
27 struct _GRAPHICS_DRIVER
*Next
;
28 } GRAPHICS_DRIVER
, *PGRAPHICS_DRIVER
;
30 static PGRAPHICS_DRIVER DriverList
;
31 static PGRAPHICS_DRIVER GenericDriver
= 0;
33 BOOL
DRIVER_RegisterDriver(LPCWSTR Name
, PGD_ENABLEDRIVER EnableDriver
)
35 PGRAPHICS_DRIVER Driver
= ExAllocatePool(NonPagedPool
, sizeof(*Driver
));
36 DPRINT( "DRIVER_RegisterDriver( Name: %S )\n", Name
);
37 if (!Driver
) return FALSE
;
38 Driver
->ReferenceCount
= 0;
39 Driver
->EnableDriver
= EnableDriver
;
42 Driver
->Name
= ExAllocatePool(PagedPool
, (wcslen(Name
) + 1) * sizeof(WCHAR
));
43 wcscpy(Driver
->Name
, Name
);
44 Driver
->Next
= DriverList
;
49 if (GenericDriver
!= NULL
)
55 GenericDriver
= Driver
;
59 PGD_ENABLEDRIVER
DRIVER_FindDDIDriver(LPCWSTR Name
)
61 SYSTEM_LOAD_IMAGE GdiDriverInfo
;
62 GRAPHICS_DRIVER
*Driver
= DriverList
;
65 /* First see if the driver hasn't already been loaded */
66 while (Driver
&& Name
)
68 if (!_wcsicmp( Driver
->Name
, Name
))
70 return Driver
->EnableDriver
;
72 Driver
= Driver
->Next
;
75 /* If not, then load it */
76 RtlInitUnicodeString (&GdiDriverInfo
.ModuleName
, (LPWSTR
)Name
);
77 Status
= ZwSetSystemInformation (SystemLoadImage
, &GdiDriverInfo
, sizeof(SYSTEM_LOAD_IMAGE
));
78 if (!NT_SUCCESS(Status
)) return NULL
;
80 DRIVER_RegisterDriver( L
"DISPLAY", GdiDriverInfo
.EntryPoint
);
81 return (PGD_ENABLEDRIVER
)GdiDriverInfo
.EntryPoint
;
84 BOOL
DRIVER_BuildDDIFunctions(PDRVENABLEDATA DED
,
89 for (i
=0; i
<DED
->c
; i
++)
91 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvEnablePDEV
) DF
->EnablePDev
= (PGD_ENABLEPDEV
)DED
->pdrvfn
[i
].pfn
;
92 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvCompletePDEV
) DF
->CompletePDev
= (PGD_COMPLETEPDEV
)DED
->pdrvfn
[i
].pfn
;
93 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvDisablePDEV
) DF
->DisablePDev
= (PGD_DISABLEPDEV
)DED
->pdrvfn
[i
].pfn
;
94 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvEnableSurface
) DF
->EnableSurface
= (PGD_ENABLESURFACE
)DED
->pdrvfn
[i
].pfn
;
95 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvDisableSurface
) DF
->DisableSurface
= (PGD_DISABLESURFACE
)DED
->pdrvfn
[i
].pfn
;
96 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvAssertMode
) DF
->AssertMode
= (PGD_ASSERTMODE
)DED
->pdrvfn
[i
].pfn
;
97 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvResetPDEV
) DF
->ResetPDev
= (PGD_RESETPDEV
)DED
->pdrvfn
[i
].pfn
;
98 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvCreateDeviceBitmap
)
99 DF
->CreateDeviceBitmap
= (PGD_CREATEDEVICEBITMAP
)DED
->pdrvfn
[i
].pfn
;
100 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvDeleteDeviceBitmap
)
101 DF
->DeleteDeviceBitmap
= (PGD_DELETEDEVICEBITMAP
)DED
->pdrvfn
[i
].pfn
;
102 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvRealizeBrush
) DF
->RealizeBrush
= (PGD_REALIZEBRUSH
)DED
->pdrvfn
[i
].pfn
;
103 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvDitherColor
) DF
->DitherColor
= (PGD_DITHERCOLOR
)DED
->pdrvfn
[i
].pfn
;
104 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvStrokePath
) DF
->StrokePath
= (PGD_STROKEPATH
)DED
->pdrvfn
[i
].pfn
;
105 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvFillPath
) DF
->FillPath
= (PGD_FILLPATH
)DED
->pdrvfn
[i
].pfn
;
106 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvStrokeAndFillPath
)
107 DF
->StrokeAndFillPath
= (PGD_STROKEANDFILLPATH
)DED
->pdrvfn
[i
].pfn
;
108 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvPaint
) DF
->Paint
= (PGD_PAINT
)DED
->pdrvfn
[i
].pfn
;
109 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvBitBlt
) DF
->BitBlt
= (PGD_BITBLT
)DED
->pdrvfn
[i
].pfn
;
110 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvTransparentBlt
) DF
->TransparentBlt
= (PGD_TRANSPARENTBLT
)DED
->pdrvfn
[i
].pfn
;
111 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvCopyBits
) DF
->CopyBits
= (PGD_COPYBITS
)DED
->pdrvfn
[i
].pfn
;
112 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvStretchBlt
) DF
->StretchBlt
= (PGD_STRETCHBLT
)DED
->pdrvfn
[i
].pfn
;
113 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvSetPalette
) DF
->SetPalette
= (PGD_SETPALETTE
)DED
->pdrvfn
[i
].pfn
;
114 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvTextOut
) DF
->TextOut
= (PGD_TEXTOUT
)DED
->pdrvfn
[i
].pfn
;
115 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvEscape
) DF
->Escape
= (PGD_ESCAPE
)DED
->pdrvfn
[i
].pfn
;
116 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvDrawEscape
) DF
->DrawEscape
= (PGD_DRAWESCAPE
)DED
->pdrvfn
[i
].pfn
;
117 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvQueryFont
) DF
->QueryFont
= (PGD_QUERYFONT
)DED
->pdrvfn
[i
].pfn
;
118 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvQueryFontTree
) DF
->QueryFontTree
= (PGD_QUERYFONTTREE
)DED
->pdrvfn
[i
].pfn
;
119 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvQueryFontData
) DF
->QueryFontData
= (PGD_QUERYFONTDATA
)DED
->pdrvfn
[i
].pfn
;
120 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvSetPointerShape
) DF
->SetPointerShape
= (PGD_SETPOINTERSHAPE
)DED
->pdrvfn
[i
].pfn
;
121 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvMovePointer
) DF
->MovePointer
= (PGD_MOVEPOINTER
)DED
->pdrvfn
[i
].pfn
;
122 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvLineTo
) DF
->LineTo
= (PGD_LINETO
)DED
->pdrvfn
[i
].pfn
;
123 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvSendPage
) DF
->SendPage
= (PGD_SENDPAGE
)DED
->pdrvfn
[i
].pfn
;
124 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvStartPage
) DF
->StartPage
= (PGD_STARTPAGE
)DED
->pdrvfn
[i
].pfn
;
125 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvEndDoc
) DF
->EndDoc
= (PGD_ENDDOC
)DED
->pdrvfn
[i
].pfn
;
126 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvStartDoc
) DF
->StartDoc
= (PGD_STARTDOC
)DED
->pdrvfn
[i
].pfn
;
127 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvGetGlyphMode
) DF
->GetGlyphMode
= (PGD_GETGLYPHMODE
)DED
->pdrvfn
[i
].pfn
;
128 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvSynchronize
) DF
->Synchronize
= (PGD_SYNCHRONIZE
)DED
->pdrvfn
[i
].pfn
;
129 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvSaveScreenBits
) DF
->SaveScreenBits
= (PGD_SAVESCREENBITS
)DED
->pdrvfn
[i
].pfn
;
130 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvGetModes
) DF
->GetModes
= (PGD_GETMODES
)DED
->pdrvfn
[i
].pfn
;
131 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvFree
) DF
->Free
= (PGD_FREE
)DED
->pdrvfn
[i
].pfn
;
132 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvDestroyFont
) DF
->DestroyFont
= (PGD_DESTROYFONT
)DED
->pdrvfn
[i
].pfn
;
133 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvQueryFontCaps
) DF
->QueryFontCaps
= (PGD_QUERYFONTCAPS
)DED
->pdrvfn
[i
].pfn
;
134 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvLoadFontFile
) DF
->LoadFontFile
= (PGD_LOADFONTFILE
)DED
->pdrvfn
[i
].pfn
;
135 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvUnloadFontFile
) DF
->UnloadFontFile
= (PGD_UNLOADFONTFILE
)DED
->pdrvfn
[i
].pfn
;
136 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvFontManagement
) DF
->FontManagement
= (PGD_FONTMANAGEMENT
)DED
->pdrvfn
[i
].pfn
;
137 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvQueryTrueTypeTable
)
138 DF
->QueryTrueTypeTable
= (PGD_QUERYTRUETYPETABLE
)DED
->pdrvfn
[i
].pfn
;
139 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvQueryTrueTypeOutline
)
140 DF
->QueryTrueTypeOutline
= (PGD_QUERYTRUETYPEOUTLINE
)DED
->pdrvfn
[i
].pfn
;
141 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvGetTrueTypeFile
) DF
->GetTrueTypeFile
= (PGD_GETTRUETYPEFILE
)DED
->pdrvfn
[i
].pfn
;
142 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvQueryFontFile
) DF
->QueryFontFile
= (PGD_QUERYFONTFILE
)DED
->pdrvfn
[i
].pfn
;
143 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvQueryAdvanceWidths
)
144 DF
->QueryAdvanceWidths
= (PGD_QUERYADVANCEWIDTHS
)DED
->pdrvfn
[i
].pfn
;
145 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvSetPixelFormat
) DF
->SetPixelFormat
= (PGD_SETPIXELFORMAT
)DED
->pdrvfn
[i
].pfn
;
146 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvDescribePixelFormat
)
147 DF
->DescribePixelFormat
= (PGD_DESCRIBEPIXELFORMAT
)DED
->pdrvfn
[i
].pfn
;
148 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvSwapBuffers
) DF
->SwapBuffers
= (PGD_SWAPBUFFERS
)DED
->pdrvfn
[i
].pfn
;
149 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvStartBanding
) DF
->StartBanding
= (PGD_STARTBANDING
)DED
->pdrvfn
[i
].pfn
;
150 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvNextBand
) DF
->NextBand
= (PGD_NEXTBAND
)DED
->pdrvfn
[i
].pfn
;
152 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvGetDirectDrawInfo
) DF
->GETDIRECTDRAWINFO
= (PGD_
)DED
->pdrvfn
[i
].pfn
;
153 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvEnableDirectDraw
) DF
->ENABLEDIRECTDRAW
= (PGD_
)DED
->pdrvfn
[i
].pfn
;
154 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvDisableDirectDraw
) DF
->DISABLEDIRECTDRAW
= (PGD_
)DED
->pdrvfn
[i
].pfn
;
156 if(DED
->pdrvfn
[i
].iFunc
== INDEX_DrvQuerySpoolType
) DF
->QuerySpoolType
= (PGD_QUERYSPOOLTYPE
)DED
->pdrvfn
[i
].pfn
;
162 typedef NTSTATUS (*PMP_DRIVERENTRY
)(PVOID
, PVOID
);
164 HANDLE
DRIVER_FindMPDriver(LPCWSTR Name
)
166 OBJECT_ATTRIBUTES ObjectAttributes
;
167 UNICODE_STRING DeviceName
;
168 IO_STATUS_BLOCK Iosb
;
169 HANDLE DisplayHandle
;
172 RtlInitUnicodeStringFromLiteral(&DeviceName
, L
"\\??\\DISPLAY1");
173 InitializeObjectAttributes(&ObjectAttributes
,
178 Status
= ZwOpenFile(&DisplayHandle
,
183 FILE_SYNCHRONOUS_IO_ALERT
);
184 if (!NT_SUCCESS(Status
))
186 DPRINT("ZwOpenFile() failed (Status %lx)\n", Status
);
190 return(DisplayHandle
);
194 BOOL
DRIVER_UnregisterDriver(LPCWSTR Name
)
196 PGRAPHICS_DRIVER Driver
= NULL
;
200 if (DriverList
!= NULL
)
202 if (!_wcsicmp(DriverList
->Name
, Name
))
205 DriverList
= DriverList
->Next
;
210 while (Driver
->Next
&& _wcsicmp(Driver
->Name
, Name
))
212 Driver
= Driver
->Next
;
219 if (GenericDriver
!= NULL
)
221 Driver
= GenericDriver
;
222 GenericDriver
= NULL
;
228 ExFreePool(Driver
->Name
);
239 INT
DRIVER_ReferenceDriver (LPCWSTR Name
)
241 GRAPHICS_DRIVER
*Driver
= DriverList
;
243 while (Driver
&& Name
)
245 DPRINT( "Comparing %S to %S\n", Driver
->Name
, Name
);
246 if (!_wcsicmp( Driver
->Name
, Name
))
248 return ++Driver
->ReferenceCount
;
250 Driver
= Driver
->Next
;
252 DPRINT( "Driver %S not found to reference, generic count: %d\n", Name
, GenericDriver
->ReferenceCount
);
253 assert( GenericDriver
!= 0 );
254 return ++GenericDriver
->ReferenceCount
;
257 INT
DRIVER_UnreferenceDriver (LPCWSTR Name
)
259 GRAPHICS_DRIVER
*Driver
= DriverList
;
261 while (Driver
&& Name
)
263 DPRINT( "Comparing %S to %S\n", Driver
->Name
, Name
);
264 if (!_wcsicmp( Driver
->Name
, Name
))
266 return --Driver
->ReferenceCount
;
268 Driver
= Driver
->Next
;
270 DPRINT( "Driver '%S' not found to dereference, generic count: %d\n", Name
, GenericDriver
->ReferenceCount
);
271 assert( GenericDriver
!= 0 );
272 return --GenericDriver
->ReferenceCount
;