VirtualBox

source: vbox/trunk/src/VBox/HostDrivers/VBoxUSB/win/testcase/USBTest.cpp@ 31896

最後變更 在這個檔案從31896是 31896,由 vboxsync 提交於 15 年 前

export the VBoxUSB host driver to OSE

  • 屬性 svn:eol-style 設為 native
  • 屬性 svn:keywords 設為 Author Date Id Revision
檔案大小: 11.3 KB
 
1/** @file
2 *
3 * VBox host drivers - USB drivers - Filter & driver installation
4 *
5 * Installation code
6 *
7 * Copyright (C) 2006-2007 Oracle Corporation
8 *
9 * Oracle Corporation confidential
10 * All rights reserved
11 */
12
13
14/*******************************************************************************
15* Header Files *
16*******************************************************************************/
17#include <windows.h>
18#include <setupapi.h>
19#include <newdev.h>
20#include <iprt/assert.h>
21#include <iprt/err.h>
22#include <iprt/param.h>
23#include <iprt/path.h>
24#include <iprt/string.h>
25#include <VBox/err.h>
26#include <stdio.h>
27#include <VBox/usblib.h>
28
29/** Handle to the open device. */
30static HANDLE g_hUSBMonitor = INVALID_HANDLE_VALUE;
31/** Flags whether or not we started the service. */
32static bool g_fStartedService = false;
33
34/**
35 * Attempts to start the service, creating it if necessary.
36 *
37 * @returns 0 on success.
38 * @returns -1 on failure.
39 * @param fRetry Indicates retry call.
40 */
41int usbMonStartService(void)
42{
43 /*
44 * Check if the driver service is there.
45 */
46 SC_HANDLE hSMgr = OpenSCManager(NULL, NULL, SERVICE_QUERY_STATUS | SERVICE_START);
47 if (hSMgr == NULL)
48 {
49 AssertMsgFailed(("couldn't open service manager in SERVICE_QUERY_CONFIG | SERVICE_QUERY_STATUS mode!\n"));
50 return -1;
51 }
52
53 /*
54 * Try open our service to check it's status.
55 */
56 SC_HANDLE hService = OpenService(hSMgr, USBMON_SERVICE_NAME, SERVICE_QUERY_STATUS | SERVICE_START);
57 if (!hService)
58 return -1;
59
60 /*
61 * Check if open and on demand create succeeded.
62 */
63 int rc = -1;
64 if (hService)
65 {
66
67 /*
68 * Query service status to see if we need to start it or not.
69 */
70 SERVICE_STATUS Status;
71 BOOL fRc = QueryServiceStatus(hService, &Status);
72 Assert(fRc);
73 if ( Status.dwCurrentState != SERVICE_RUNNING
74 && Status.dwCurrentState != SERVICE_START_PENDING)
75 {
76 /*
77 * Start it.
78 */
79 printf("usbMonStartService -> start it\n");
80
81 fRc = StartService(hService, 0, NULL);
82 DWORD LastError = GetLastError(); NOREF(LastError);
83 AssertMsg(fRc, ("StartService failed with LastError=%Rwa\n", LastError));
84 if (fRc)
85 g_fStartedService = true;
86 }
87
88 /*
89 * Wait for the service to finish starting.
90 * We'll wait for 10 seconds then we'll give up.
91 */
92 QueryServiceStatus(hService, &Status);
93 if (Status.dwCurrentState == SERVICE_START_PENDING)
94 {
95 int iWait;
96 for (iWait = 100; iWait > 0 && Status.dwCurrentState == SERVICE_START_PENDING; iWait--)
97 {
98 Sleep(100);
99 QueryServiceStatus(hService, &Status);
100 }
101 DWORD LastError = GetLastError(); NOREF(LastError);
102 AssertMsg(Status.dwCurrentState != SERVICE_RUNNING,
103 ("Failed to start. LastError=%Rwa iWait=%d status=%d\n",
104 LastError, iWait, Status.dwCurrentState));
105 }
106
107 if (Status.dwCurrentState == SERVICE_RUNNING)
108 rc = 0;
109
110 /*
111 * Close open handles.
112 */
113 CloseServiceHandle(hService);
114 }
115 else
116 {
117 DWORD LastError = GetLastError(); NOREF(LastError);
118 AssertMsgFailed(("OpenService failed! LastError=%Rwa\n", LastError));
119 }
120 if (!CloseServiceHandle(hSMgr))
121 AssertFailed();
122
123 return rc;
124}
125
126/**
127 * Stops a possibly running service.
128 *
129 * @returns 0 on success.
130 * @returns -1 on failure.
131 */
132int usbMonStopService(void)
133{
134 printf("usbMonStopService\n");
135 /*
136 * Assume it didn't exist, so we'll create the service.
137 */
138 int rc = -1;
139 SC_HANDLE hSMgr = OpenSCManager(NULL, NULL, SERVICE_STOP | SERVICE_QUERY_STATUS);
140 DWORD LastError = GetLastError(); NOREF(LastError);
141 AssertMsg(hSMgr, ("OpenSCManager(,,delete) failed rc=%d\n", LastError));
142 if (hSMgr)
143 {
144 SC_HANDLE hService = OpenService(hSMgr, USBMON_SERVICE_NAME, SERVICE_STOP | SERVICE_QUERY_STATUS);
145 if (hService)
146 {
147 /*
148 * Stop the service.
149 */
150 SERVICE_STATUS Status;
151 QueryServiceStatus(hService, &Status);
152 if (Status.dwCurrentState == SERVICE_STOPPED)
153 rc = 0;
154 else if (ControlService(hService, SERVICE_CONTROL_STOP, &Status))
155 {
156 int iWait = 100;
157 while (Status.dwCurrentState == SERVICE_STOP_PENDING && iWait-- > 0)
158 {
159 Sleep(100);
160 QueryServiceStatus(hService, &Status);
161 }
162 if (Status.dwCurrentState == SERVICE_STOPPED)
163 rc = 0;
164 else
165 AssertMsgFailed(("Failed to stop service. status=%d\n", Status.dwCurrentState));
166 }
167 else
168 {
169 DWORD LastError = GetLastError(); NOREF(LastError);
170 AssertMsgFailed(("ControlService failed with LastError=%Rwa. status=%d\n", LastError, Status.dwCurrentState));
171 }
172 CloseServiceHandle(hService);
173 }
174 else if (GetLastError() == ERROR_SERVICE_DOES_NOT_EXIST)
175 rc = 0;
176 else
177 {
178 DWORD LastError = GetLastError(); NOREF(LastError);
179 AssertMsgFailed(("OpenService failed LastError=%Rwa\n", LastError));
180 }
181 CloseServiceHandle(hSMgr);
182 }
183 return rc;
184}
185/**
186 * Release specified USB device to the host.
187 *
188 * @returns VBox status code
189 * @param usVendorId Vendor id
190 * @param usProductId Product id
191 * @param usRevision Revision
192 */
193int usbMonReleaseDevice(USHORT usVendorId, USHORT usProductId, USHORT usRevision)
194{
195 USBSUP_RELEASE release;
196 DWORD cbReturned = 0;
197
198 printf("usbLibReleaseDevice %x %x %x\n", usVendorId, usProductId, usRevision);
199
200 release.usVendorId = usVendorId;
201 release.usProductId = usProductId;
202 release.usRevision = usRevision;
203
204 if (!DeviceIoControl(g_hUSBMonitor, SUPUSBFLT_IOCTL_RELEASE_DEVICE, &release, sizeof(release), NULL, 0, &cbReturned, NULL))
205 {
206 AssertMsgFailed(("DeviceIoControl failed with %d\n", GetLastError()));
207 return RTErrConvertFromWin32(GetLastError());
208 }
209
210 return VINF_SUCCESS;
211}
212
213
214/**
215 * Add USB device filter
216 *
217 * @returns VBox status code.
218 * @param pszVendor Vendor filter string
219 * @param pszProduct Product filter string
220 * @param pszRevision Revision filter string
221 * @param ppID Pointer to filter id
222 */
223int usbMonInsertFilter(const char *pszVendor, const char *pszProduct, const char *pszRevision, void **ppID)
224{
225 USBFILTER filter;
226 USBSUP_FLTADDOUT flt_add;
227 DWORD cbReturned = 0;
228
229 Assert(g_hUSBMonitor);
230
231 printf("usblibInsertFilter %s %s %s\n", pszVendor, pszProduct, pszRevision);
232
233// strncpy(filter.szVendor, pszVendor, sizeof(filter.szVendor));
234// strncpy(filter.szProduct, pszProduct, sizeof(filter.szProduct));
235// strncpy(filter.szRevision, pszRevision, sizeof(filter.szRevision));
236
237 if (!DeviceIoControl(g_hUSBMonitor, SUPUSBFLT_IOCTL_ADD_FILTER, &filter, sizeof(filter), &flt_add, sizeof(flt_add), &cbReturned, NULL))
238 {
239 AssertMsgFailed(("DeviceIoControl failed with %d\n", GetLastError()));
240 return RTErrConvertFromWin32(GetLastError());
241 }
242 *ppID = (void *)flt_add.uId;
243 return VINF_SUCCESS;
244}
245
246/**
247 * Remove USB device filter
248 *
249 * @returns VBox status code.
250 * @param aID Filter id
251 */
252int usbMonRemoveFilter (void *aID)
253{
254 uintptr_t uId;
255 DWORD cbReturned = 0;
256
257 Assert(g_hUSBMonitor);
258
259 printf("usblibRemoveFilter %x\n", aID);
260
261 uId = (uintptr_t)aID;
262 if (!DeviceIoControl(g_hUSBMonitor, SUPUSBFLT_IOCTL_REMOVE_FILTER, &uId, sizeof(uId), NULL, 0,&cbReturned, NULL))
263 {
264 AssertMsgFailed(("DeviceIoControl failed with %d\n", GetLastError()));
265 return RTErrConvertFromWin32(GetLastError());
266 }
267 return VINF_SUCCESS;
268}
269
270/**
271 * Initialize the USB monitor
272 *
273 * @returns VBox status code.
274 */
275int usbMonitorInit()
276{
277 int rc;
278 USBSUP_VERSION version = {0};
279 DWORD cbReturned;
280
281 printf("usbproxy: usbLibInit\n");
282
283 g_hUSBMonitor = CreateFile (USBMON_DEVICE_NAME,
284 GENERIC_READ | GENERIC_WRITE,
285 FILE_SHARE_READ | FILE_SHARE_WRITE,
286 NULL, // no SECURITY_ATTRIBUTES structure
287 OPEN_EXISTING, // No special create flags
288 FILE_ATTRIBUTE_SYSTEM,
289 NULL); // No template file
290
291 if (g_hUSBMonitor == INVALID_HANDLE_VALUE)
292 {
293 usbMonStartService();
294
295 g_hUSBMonitor = CreateFile (USBMON_DEVICE_NAME,
296 GENERIC_READ | GENERIC_WRITE,
297 FILE_SHARE_READ | FILE_SHARE_WRITE,
298 NULL, // no SECURITY_ATTRIBUTES structure
299 OPEN_EXISTING, // No special create flags
300 FILE_ATTRIBUTE_SYSTEM,
301 NULL); // No template file
302
303 if (g_hUSBMonitor == INVALID_HANDLE_VALUE)
304 {
305 /* AssertFailed(); */
306 printf("usbproxy: Unable to open filter driver!! (rc=%d)\n", GetLastError());
307 rc = VERR_FILE_NOT_FOUND;
308 goto failure;
309 }
310 }
311
312 /*
313 * Check the version
314 */
315 cbReturned = 0;
316 if (!DeviceIoControl(g_hUSBMonitor, SUPUSBFLT_IOCTL_GET_VERSION, NULL, 0,&version, sizeof(version), &cbReturned, NULL))
317 {
318 printf("usbproxy: Unable to query filter version!! (rc=%d)\n", GetLastError());
319 rc = VERR_VERSION_MISMATCH;
320 goto failure;
321 }
322
323 if (version.u32Major != USBMON_MAJOR_VERSION ||
324 version.u32Minor < USBMON_MINOR_VERSION)
325 {
326 printf("usbproxy: Filter driver version mismatch!!\n");
327 rc = VERR_VERSION_MISMATCH;
328 goto failure;
329 }
330
331 return VINF_SUCCESS;
332
333failure:
334 if (g_hUSBMonitor != INVALID_HANDLE_VALUE)
335 {
336 CloseHandle(g_hUSBMonitor);
337 g_hUSBMonitor = INVALID_HANDLE_VALUE;
338 }
339 return rc;
340}
341
342
343
344/**
345 * Terminate the USB monitor
346 *
347 * @returns VBox status code.
348 */
349int usbMonitorTerm()
350{
351 if (g_hUSBMonitor != INVALID_HANDLE_VALUE)
352 {
353 CloseHandle(g_hUSBMonitor);
354 g_hUSBMonitor = INVALID_HANDLE_VALUE;
355 }
356 /*
357 * If we started the service we might consider stopping it too.
358 *
359 * Since this won't work unless the process starting it is the
360 * last user we might wanna skip this...
361 */
362 if (g_fStartedService)
363 {
364 usbMonStopService();
365 g_fStartedService = false;
366 }
367
368 return VINF_SUCCESS;
369}
370
371
372int __cdecl main(int argc, char **argv)
373{
374 int rc;
375
376 printf("USB test\n");
377
378 rc = usbMonitorInit();
379 AssertRC(rc);
380
381 void *pId1, *pId2;
382
383 usbMonInsertFilter("0529", "0514", "0100", &pId1);
384 usbMonInsertFilter("0A16", "2499", "0100", &pId2);
385
386 printf("Waiting to capture device\n");
387 getchar();
388
389 printf("Releasing device\n");
390 usbMonReleaseDevice(0xA16, 0x2499, 0x100);
391
392 usbMonRemoveFilter(pId1);
393 usbMonRemoveFilter(pId2);
394
395 rc = usbMonitorTerm();
396
397 return 0;
398}
注意: 瀏覽 TracBrowser 來幫助您使用儲存庫瀏覽器

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