VirtualBox

source: vbox/trunk/src/VBox/Additions/WINNT/Graphics/Display/wddm/VBoxCrHgsmi.cpp@ 35127

Last change on this file since 35127 was 35127, checked in by vboxsync, 14 years ago

crOpenGL: fix OpenGL support for win2k guests

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 8.5 KB
Line 
1#include <VBox/VBoxCrHgsmi.h>
2#include <iprt/err.h>
3
4#include "VBoxUhgsmiKmt.h"
5
6static VBOXDISPKMT_CALLBACKS g_VBoxCrHgsmiKmtCallbacks;
7static int g_bVBoxKmtCallbacksInited = 0;
8
9#ifdef VBOX_CRHGSMI_WITH_D3DDEV
10static VBOXCRHGSMI_CALLBACKS g_VBoxCrHgsmiCallbacks;
11static HMODULE g_hVBoxCrHgsmiProvider = NULL;
12static uint32_t g_cVBoxCrHgsmiProvider = 0;
13
14
15typedef VBOXWDDMDISP_DECL(int) FNVBOXDISPCRHGSMI_INIT(PVBOXCRHGSMI_CALLBACKS pCallbacks);
16typedef FNVBOXDISPCRHGSMI_INIT *PFNVBOXDISPCRHGSMI_INIT;
17
18typedef VBOXWDDMDISP_DECL(int) FNVBOXDISPCRHGSMI_TERM();
19typedef FNVBOXDISPCRHGSMI_TERM *PFNVBOXDISPCRHGSMI_TERM;
20
21typedef VBOXWDDMDISP_DECL(HVBOXCRHGSMI_CLIENT) FNVBOXDISPCRHGSMI_QUERY_CLIENT();
22typedef FNVBOXDISPCRHGSMI_QUERY_CLIENT *PFNVBOXDISPCRHGSMI_QUERY_CLIENT;
23
24static PFNVBOXDISPCRHGSMI_INIT g_pfnVBoxDispCrHgsmiInit = NULL;
25static PFNVBOXDISPCRHGSMI_TERM g_pfnVBoxDispCrHgsmiTerm = NULL;
26static PFNVBOXDISPCRHGSMI_QUERY_CLIENT g_pfnVBoxDispCrHgsmiQueryClient = NULL;
27
28VBOXCRHGSMI_DECL(int) VBoxCrHgsmiInit(PVBOXCRHGSMI_CALLBACKS pCallbacks)
29{
30 if (!g_bVBoxKmtCallbacksInited)
31 {
32 HRESULT hr = vboxDispKmtCallbacksInit(&g_VBoxCrHgsmiKmtCallbacks);
33 Assert(hr == S_OK);
34 if (hr == S_OK)
35 g_bVBoxKmtCallbacksInited = 1;
36 else
37 g_bVBoxKmtCallbacksInited = -1;
38 }
39
40 Assert(g_bVBoxKmtCallbacksInited);
41 if (g_bVBoxKmtCallbacksInited < 0)
42 {
43 Assert(0);
44 return VERR_NOT_SUPPORTED;
45 }
46
47 g_VBoxCrHgsmiCallbacks = *pCallbacks;
48 if (!g_hVBoxCrHgsmiProvider)
49 {
50 g_hVBoxCrHgsmiProvider = GetModuleHandle(L"VBoxDispD3D");
51 if (g_hVBoxCrHgsmiProvider)
52 {
53 g_hVBoxCrHgsmiProvider = LoadLibrary(L"VBoxDispD3D");
54 }
55
56 if (g_hVBoxCrHgsmiProvider)
57 {
58 g_pfnVBoxDispCrHgsmiInit = (PFNVBOXDISPCRHGSMI_INIT)GetProcAddress(g_hVBoxCrHgsmiProvider, "VBoxDispCrHgsmiInit");
59 Assert(g_pfnVBoxDispCrHgsmiInit);
60 if (g_pfnVBoxDispCrHgsmiInit)
61 {
62 g_pfnVBoxDispCrHgsmiInit(pCallbacks);
63 }
64
65 g_pfnVBoxDispCrHgsmiTerm = (PFNVBOXDISPCRHGSMI_TERM)GetProcAddress(g_hVBoxCrHgsmiProvider, "VBoxDispCrHgsmiTerm");
66 Assert(g_pfnVBoxDispCrHgsmiTerm);
67
68 g_pfnVBoxDispCrHgsmiQueryClient = (PFNVBOXDISPCRHGSMI_QUERY_CLIENT)GetProcAddress(g_hVBoxCrHgsmiProvider, "VBoxDispCrHgsmiQueryClient");
69 Assert(g_pfnVBoxDispCrHgsmiQueryClient);
70 }
71#ifdef DEBUG_misha
72 else
73 {
74 DWORD winEr = GetLastError();
75 Assert(0);
76 }
77#endif
78 }
79
80 if (g_hVBoxCrHgsmiProvider)
81 {
82 if (g_pfnVBoxDispCrHgsmiInit)
83 {
84 g_pfnVBoxDispCrHgsmiInit(pCallbacks);
85 }
86 ++g_cVBoxCrHgsmiProvider;
87 return VINF_SUCCESS;
88 }
89
90 /* we're called from ogl ICD driver*/
91 Assert(0);
92
93 return VINF_SUCCESS;
94}
95
96static __declspec(thread) PVBOXUHGSMI_PRIVATE_KMT gt_pHgsmiGL = NULL;
97
98VBOXCRHGSMI_DECL(HVBOXCRHGSMI_CLIENT) VBoxCrHgsmiQueryClient()
99{
100
101 HVBOXCRHGSMI_CLIENT hClient;
102 if (g_pfnVBoxDispCrHgsmiQueryClient)
103 {
104 hClient = g_pfnVBoxDispCrHgsmiQueryClient();
105//#ifdef DEBUG_misha
106// Assert(hClient);
107//#endif
108 if (hClient)
109 return hClient;
110 }
111 PVBOXUHGSMI_PRIVATE_KMT pHgsmiGL = gt_pHgsmiGL;
112 if (pHgsmiGL)
113 {
114 Assert(pHgsmiGL->BasePrivate.hClient);
115 return pHgsmiGL->BasePrivate.hClient;
116 }
117 pHgsmiGL = (PVBOXUHGSMI_PRIVATE_KMT)RTMemAllocZ(sizeof (*pHgsmiGL));
118 if (pHgsmiGL)
119 {
120#if 0
121 HRESULT hr = vboxUhgsmiKmtCreate(pHgsmiGL, TRUE /* bD3D tmp for injection thread*/);
122#else
123 HRESULT hr = vboxUhgsmiKmtEscCreate(pHgsmiGL, TRUE /* bD3D tmp for injection thread*/);
124#endif
125 Assert(hr == S_OK);
126 if (hr == S_OK)
127 {
128 hClient = g_VBoxCrHgsmiCallbacks.pfnClientCreate(&pHgsmiGL->BasePrivate.Base);
129 Assert(hClient);
130 if (hClient)
131 {
132 pHgsmiGL->BasePrivate.hClient = hClient;
133 gt_pHgsmiGL = pHgsmiGL;
134 return hClient;
135 }
136 vboxUhgsmiKmtDestroy(pHgsmiGL);
137 }
138 RTMemFree(pHgsmiGL);
139 }
140
141 return NULL;
142}
143#else
144static int vboxCrHgsmiInitPerform(VBOXDISPKMT_CALLBACKS *pCallbacks)
145{
146 HRESULT hr = vboxDispKmtCallbacksInit(pCallbacks);
147 /*Assert(hr == S_OK);*/
148 if (hr == S_OK)
149 {
150 /* check if we can create the hgsmi */
151 PVBOXUHGSMI pHgsmi = VBoxCrHgsmiCreate();
152 if (pHgsmi)
153 {
154 /* yes, we can, so this is wddm mode */
155 VBoxCrHgsmiDestroy(pHgsmi);
156 Log(("CrHgsmi: WDDM mode supported\n"));
157 return 1;
158 }
159 vboxDispKmtCallbacksTerm(pCallbacks);
160 }
161 Log(("CrHgsmi: unsupported\n"));
162 return -1;
163}
164
165VBOXCRHGSMI_DECL(int) VBoxCrHgsmiInit()
166{
167 if (!g_bVBoxKmtCallbacksInited)
168 {
169 g_bVBoxKmtCallbacksInited = vboxCrHgsmiInitPerform(&g_VBoxCrHgsmiKmtCallbacks);
170 Assert(g_bVBoxKmtCallbacksInited);
171 }
172
173 return g_bVBoxKmtCallbacksInited > 0 ? VINF_SUCCESS : VERR_NOT_SUPPORTED;
174}
175
176VBOXCRHGSMI_DECL(PVBOXUHGSMI) VBoxCrHgsmiCreate()
177{
178 PVBOXUHGSMI_PRIVATE_KMT pHgsmiGL = (PVBOXUHGSMI_PRIVATE_KMT)RTMemAllocZ(sizeof (*pHgsmiGL));
179 if (pHgsmiGL)
180 {
181#if 0
182 HRESULT hr = vboxUhgsmiKmtCreate(pHgsmiGL, TRUE /* bD3D tmp for injection thread*/);
183#else
184 HRESULT hr = vboxUhgsmiKmtEscCreate(pHgsmiGL, TRUE /* bD3D tmp for injection thread*/);
185#endif
186 Log(("CrHgsmi: faled to create KmtEsc UHGSMI instance, hr (0x%x)\n", hr));
187 if (hr == S_OK)
188 {
189 return &pHgsmiGL->BasePrivate.Base;
190 }
191 RTMemFree(pHgsmiGL);
192 }
193
194 return NULL;
195}
196
197VBOXCRHGSMI_DECL(void) VBoxCrHgsmiDestroy(PVBOXUHGSMI pHgsmi)
198{
199 PVBOXUHGSMI_PRIVATE_KMT pHgsmiGL = VBOXUHGSMIKMT_GET(pHgsmi);
200 HRESULT hr = vboxUhgsmiKmtDestroy(pHgsmiGL);
201 Assert(hr == S_OK);
202 if (hr == S_OK)
203 {
204 RTMemFree(pHgsmiGL);
205 }
206}
207#endif
208
209VBOXCRHGSMI_DECL(int) VBoxCrHgsmiTerm()
210{
211#if 0
212 PVBOXUHGSMI_PRIVATE_KMT pHgsmiGL = gt_pHgsmiGL;
213 if (pHgsmiGL)
214 {
215 g_VBoxCrHgsmiCallbacks.pfnClientDestroy(pHgsmiGL->BasePrivate.hClient);
216 vboxUhgsmiKmtDestroy(pHgsmiGL);
217 gt_pHgsmiGL = NULL;
218 }
219
220 if (g_pfnVBoxDispCrHgsmiTerm)
221 g_pfnVBoxDispCrHgsmiTerm();
222#endif
223 if (g_bVBoxKmtCallbacksInited > 0)
224 {
225 vboxDispKmtCallbacksTerm(&g_VBoxCrHgsmiKmtCallbacks);
226 }
227 return VINF_SUCCESS;
228}
229
230VBOXCRHGSMI_DECL(void) VBoxCrHgsmiLog(char * szString)
231{
232 VBOXDISPKMT_ADAPTER Adapter;
233 HRESULT hr = vboxDispKmtOpenAdapter(&g_VBoxCrHgsmiKmtCallbacks, &Adapter);
234 Assert(hr == S_OK);
235 if (hr == S_OK)
236 {
237 uint32_t cbString = (uint32_t)strlen(szString) + 1;
238 uint32_t cbCmd = RT_OFFSETOF(VBOXDISPIFESCAPE_DBGPRINT, aStringBuf[cbString]);
239 PVBOXDISPIFESCAPE_DBGPRINT pCmd = (PVBOXDISPIFESCAPE_DBGPRINT)RTMemAllocZ(cbCmd);
240 Assert(pCmd);
241 if (pCmd)
242 {
243 pCmd->EscapeHdr.escapeCode = VBOXESC_DBGPRINT;
244 memcpy(pCmd->aStringBuf, szString, cbString);
245
246 D3DKMT_ESCAPE EscapeData = {0};
247 EscapeData.hAdapter = Adapter.hAdapter;
248 //EscapeData.hDevice = NULL;
249 EscapeData.Type = D3DKMT_ESCAPE_DRIVERPRIVATE;
250 // EscapeData.Flags.HardwareAccess = 1;
251 EscapeData.pPrivateDriverData = pCmd;
252 EscapeData.PrivateDriverDataSize = cbCmd;
253 //EscapeData.hContext = NULL;
254
255 int Status = g_VBoxCrHgsmiKmtCallbacks.pfnD3DKMTEscape(&EscapeData);
256 Assert(!Status);
257
258 RTMemFree(pCmd);
259 }
260 hr = vboxDispKmtCloseAdapter(&Adapter);
261 Assert(hr == S_OK);
262 }
263}
264
265///* to be used by injection thread and by ogl ICD driver for hgsmi initialization*/
266//VBOXCRHGSMI_DECL(int) VBoxCrHgsmiCustomCreate(PVBOXUHGSMI *ppHgsmi)
267//{
268// PVBOXUHGSMI_PRIVATE_KMT pHgsmi = RTMemAllocZ(sizeof (*pHgsmi));
269// if (pHgsmi)
270// {
271// HRESULT hr = vboxUhgsmiKmtCreate(pHgsmi, FALSE);
272// Assert(hr == S_OK);
273// if (hr == S_OK)
274// {
275// *ppHgsmi = &pHgsmi->BasePrivate.Base;
276// return VINF_SUCCESS;
277// }
278// RTMemFree(pHgsmi);
279// return VERR_GENERAL_FAILURE;
280// }
281// return VERR_NO_MEMORY;
282//}
283//
284//VBOXCRHGSMI_DECL(int) VBoxCrHgsmiCustomDestroy(PVBOXUHGSMI pHgsmi)
285//{
286// PVBOXUHGSMI_PRIVATE_KMT pHgsmiKmt = VBOXUHGSMIKMT_GET(pHgsmi);
287// HRESULT hr = vboxUhgsmiKmtDestroy(pHgsmiKmt, FALSE);
288// Assert(hr == S_OK);
289// if (hr == S_OK)
290// {
291// RTMemFree(pHgsmiKmt);
292// return VINF_SUCCESS;
293// }
294// return VERR_GENERAL_FAILURE;
295//}
296
Note: See TracBrowser for help on using the repository browser.

© 2024 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette