win-pvdrivers

view xenusb/xenusb_hub.c @ 979:8f483a2b2991

Fix up PREfast warnings
author James Harper <james.harper@bendigoit.com.au>
date Sun Apr 15 19:47:10 2012 +1000 (2012-04-15)
parents 1306945ecc59
children ea3c61839ff5
line source
1 /*
2 PV Drivers for Windows Xen HVM Domains
3 Copyright (C) 2007 James Harper
5 This program is free software; you can redistribute it and/or
6 modify it under the terms of the GNU General Public License
7 as published by the Free Software Foundation; either version 2
8 of the License, or (at your option) any later version.
10 This program is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 GNU General Public License for more details.
15 You should have received a copy of the GNU General Public License
16 along with this program; if not, write to the Free Software
17 Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
18 */
20 #include "xenusb.h"
21 #include <stdlib.h>
22 #include <usbioctl.h>
24 typedef struct _USB_START_FAILDATA {
25 ULONG LengthInBytes;
26 NTSTATUS NtStatus;
27 USBD_STATUS UsbdStatus;
28 ULONG ConnectStatus;
29 UCHAR DriverData[4];
30 } USB_START_FAILDATA, *PUSB_START_FAILDATA;
32 #pragma warning(disable: 4127) // conditional expression is constant
34 static EVT_WDF_DEVICE_D0_ENTRY XenUsbHub_EvtDeviceD0Entry;
35 static EVT_WDF_DEVICE_D0_EXIT XenUsbHub_EvtDeviceD0Exit;
36 static EVT_WDF_DEVICE_PREPARE_HARDWARE XenUsbHub_EvtDevicePrepareHardware;
37 static EVT_WDF_DEVICE_RELEASE_HARDWARE XenUsbHub_EvtDeviceReleaseHardware;
38 static EVT_WDF_DEVICE_USAGE_NOTIFICATION XenUsbHub_EvtDeviceUsageNotification;
39 static EVT_WDF_TIMER XenUsbHub_HubInterruptTimer;
40 static EVT_WDF_IO_QUEUE_IO_INTERNAL_DEVICE_CONTROL XenUsbHub_EvtIoInternalDeviceControl;
41 static EVT_WDF_IO_QUEUE_IO_DEVICE_CONTROL XenUsbHub_EvtIoDeviceControl;
42 static EVT_WDF_IO_QUEUE_IO_DEFAULT XenUsbHub_EvtIoDefault;
43 static EVT_WDFDEVICE_WDM_IRP_PREPROCESS XenUsbHub_EvtDeviceWdmIrpPreprocessQUERY_INTERFACE;
45 static USB_BUSIFFN_CREATE_USB_DEVICE XenUsbHub_UBIH_CreateUsbDevice;
46 static USB_BUSIFFN_CREATE_USB_DEVICE_EX XenUsbHub_UBIH_CreateUsbDeviceEx;
47 static USB_BUSIFFN_CREATE_USB_DEVICE_V7 XenUsbHub_UBIH_CreateUsbDeviceV7;
48 static USB_BUSIFFN_INITIALIZE_USB_DEVICE XenUsbHub_UBIH_InitializeUsbDevice;
49 static USB_BUSIFFN_GET_USB_DESCRIPTORS XenUsbHub_UBIH_GetUsbDescriptors;
50 static USB_BUSIFFN_REMOVE_USB_DEVICE XenUsbHub_UBIH_RemoveUsbDevice;
51 static USB_BUSIFFN_RESTORE_DEVICE XenUsbHub_UBIH_RestoreUsbDevice;
52 static USB_BUSIFFN_GET_POTRTHACK_FLAGS XenUsbHub_UBIH_GetPortHackFlags;
53 static USB_BUSIFFN_GET_DEVICE_INFORMATION XenUsbHub_UBIH_QueryDeviceInformation;
54 static USB_BUSIFFN_GET_CONTROLLER_INFORMATION XenUsbHub_UBIH_GetControllerInformation;
55 static USB_BUSIFFN_CONTROLLER_SELECTIVE_SUSPEND XenUsbHub_UBIH_ControllerSelectiveSuspend;
56 static USB_BUSIFFN_GET_EXTENDED_HUB_INFO XenUsbHub_UBIH_GetExtendedHubInformation;
57 static USB_BUSIFFN_GET_ROOTHUB_SYM_NAME XenUsbHub_UBIH_GetRootHubSymbolicName;
58 static USB_BUSIFFN_GET_DEVICE_BUSCONTEXT XenUsbHub_UBIH_GetDeviceBusContext;
59 static USB_BUSIFFN_INITIALIZE_20HUB XenUsbHub_UBIH_Initialize20Hub;
60 static USB_BUSIFFN_ROOTHUB_INIT_NOTIFY XenUsbHub_UBIH_RootHubInitNotification;
61 static USB_BUSIFFN_FLUSH_TRANSFERS XenUsbHub_UBIH_FlushTransfers;
62 static USB_BUSIFFN_SET_DEVHANDLE_DATA XenUsbHub_UBIH_SetDeviceHandleData;
63 static USB_BUSIFFN_INITIALIZE_USB_DEVICE_EX XenUsbHub_UBIH_InitializeUsbDeviceEx;
64 static USB_BUSIFFN_IS_ROOT XenUsbHub_UBIH_HubIsRoot;
65 static USB_BUSIFFN_TEST_POINT XenUsbHub_UBIH_HubTestPoint;
66 static USB_BUSIFFN_GET_DEVICE_PERFORMANCE_INFO XenUsbHub_UBIH_GetDevicePerformanceInfo;
67 static USB_BUSIFFN_WAIT_ASYNC_POWERUP XenUsbHub_UBIH_WaitAsyncPowerUp;
68 static USB_BUSIFFN_GET_DEVICE_ADDRESS XenUsbHub_UBIH_GetDeviceAddress;
69 static USB_BUSIFFN_REF_DEVICE_HANDLE XenUsbHub_UBIH_RefDeviceHandle;
70 static USB_BUSIFFN_DEREF_DEVICE_HANDLE XenUsbHub_UBIH_DerefDeviceHandle;
71 static USB_BUSIFFN_SET_DEVICE_HANDLE_IDLE_READY_STATE XenUsbHub_UBIH_SetDeviceHandleIdleReadyState;
72 static USB_BUSIFFN_GET_CONTAINER_ID_FOR_PORT XenUsbHub_UBIH_GetContainerIdForPort;
73 static USB_BUSIFFN_SET_CONTAINER_ID_FOR_PORT XenUsbHub_UBIH_SetContainerIdForPort;
74 static USB_BUSIFFN_ABORT_ALL_DEVICE_PIPES XenUsbHub_UBIH_AbortAllDevicePipes;
75 static USB_BUSIFFN_SET_DEVICE_ERRATA_FLAG XenUsbHub_UBIH_SetDeviceErrataFlag;
76 static USB_BUSIFFN_ACQUIRE_SEMAPHORE XenUsbHub_UBIH_AcquireBusSemaphore;
77 static USB_BUSIFFN_RELEASE_SEMAPHORE XenUsbHub_UBIH_ReleaseBusSemaphore;
78 static USB_BUSIFFN_CALC_PIPE_BANDWIDTH XenUsbHub_UBIH_CaculatePipeBandwidth;
79 static USB_BUSIFFN_SET_BUS_WAKE_MODE XenUsbHub_UBIH_SetBusSystemWakeMode;
80 static USB_BUSIFFN_SET_DEVICE_FLAG XenUsbHub_UBIH_SetDeviceFlag;
86 static VOID
87 XenUsbHub_EvtIoDefault(
88 WDFQUEUE queue,
89 WDFREQUEST request)
90 {
91 NTSTATUS status;
92 WDF_REQUEST_PARAMETERS parameters;
94 FUNCTION_ENTER();
96 UNREFERENCED_PARAMETER(queue);
98 status = STATUS_UNSUCCESSFUL;
100 WDF_REQUEST_PARAMETERS_INIT(&parameters);
101 WdfRequestGetParameters(request, &parameters);
103 switch (parameters.Type)
104 {
105 case WdfRequestTypeCreate:
106 KdPrint((__DRIVER_NAME " WdfRequestTypeCreate\n"));
107 break;
108 case WdfRequestTypeClose:
109 KdPrint((__DRIVER_NAME " WdfRequestTypeClose\n"));
110 break;
111 case WdfRequestTypeRead:
112 KdPrint((__DRIVER_NAME " WdfRequestTypeRead\n"));
113 break;
114 case WdfRequestTypeWrite:
115 KdPrint((__DRIVER_NAME " WdfRequestTypeWrite\n"));
116 break;
117 case WdfRequestTypeDeviceControl:
118 KdPrint((__DRIVER_NAME " WdfRequestTypeDeviceControl\n"));
120 break;
121 case WdfRequestTypeDeviceControlInternal:
122 KdPrint((__DRIVER_NAME " WdfRequestTypeDeviceControlInternal\n"));
123 break;
124 default:
125 KdPrint((__DRIVER_NAME " Unknown type %x\n", parameters.Type));
126 break;
127 }
128 FUNCTION_MSG("Calling WdfRequestComplete with status = %08x\n");
129 WdfRequestComplete(request, status);
131 FUNCTION_EXIT();
132 }
134 static NTSTATUS
135 XenUsbHub_BusIrpCompletionRoutine(
136 PDEVICE_OBJECT device_object,
137 PIRP irp,
138 PVOID context)
139 {
140 WDFREQUEST request = context;
142 UNREFERENCED_PARAMETER(device_object);
144 FUNCTION_ENTER();
146 FUNCTION_MSG("Calling WdfRequestComplete with status = %08x\n");
147 WdfRequestCompleteWithInformation(request, irp->IoStatus.Status, irp->IoStatus.Information);
148 IoFreeIrp(irp);
150 FUNCTION_EXIT();
152 return STATUS_MORE_PROCESSING_REQUIRED;
153 }
155 static VOID
156 XenUsbHub_EvtIoDeviceControl(
157 WDFQUEUE queue,
158 WDFREQUEST request,
159 size_t output_buffer_length,
160 size_t input_buffer_length,
161 ULONG io_control_code)
162 {
163 NTSTATUS status;
164 //WDFDEVICE device = WdfIoQueueGetDevice(queue);
165 //PXENUSB_PDO_DEVICE_DATA xupdd = GetXupdd(device);
166 //WDF_REQUEST_PARAMETERS wrp;
167 //PURB urb;
168 //xenusb_device_t *usb_device;
170 UNREFERENCED_PARAMETER(queue);
171 UNREFERENCED_PARAMETER(input_buffer_length);
172 UNREFERENCED_PARAMETER(output_buffer_length);
174 FUNCTION_ENTER();
176 status = STATUS_UNSUCCESSFUL;
178 //WDF_REQUEST_PARAMETERS_INIT(&wrp);
179 //WdfRequestGetParameters(request, &wrp);
181 // these are in api\usbioctl.h
182 switch(io_control_code)
183 {
184 case IOCTL_USB_GET_NODE_INFORMATION:
185 KdPrint((__DRIVER_NAME " IOCTL_USB_GET_NODE_INFORMATION\n"));
186 break;
187 case IOCTL_USB_GET_NODE_CONNECTION_INFORMATION:
188 KdPrint((__DRIVER_NAME " IOCTL_USB_GET_NODE_CONNECTION_INFORMATION\n"));
189 break;
190 case IOCTL_USB_GET_DESCRIPTOR_FROM_NODE_CONNECTION:
191 KdPrint((__DRIVER_NAME " IOCTL_USB_GET_DESCRIPTOR_FROM_NODE_CONNECTION\n"));
192 break;
193 case IOCTL_USB_GET_NODE_CONNECTION_NAME:
194 KdPrint((__DRIVER_NAME " IOCTL_USB_GET_NODE_CONNECTION_NAME\n"));
195 break;
196 case IOCTL_USB_DIAG_IGNORE_HUBS_ON:
197 KdPrint((__DRIVER_NAME " IOCTL_USB_DIAG_IGNORE_HUBS_ON\n"));
198 break;
199 case IOCTL_USB_DIAG_IGNORE_HUBS_OFF:
200 KdPrint((__DRIVER_NAME " IOCTL_USB_DIAG_IGNORE_HUBS_OFF\n"));
201 break;
202 case IOCTL_USB_GET_NODE_CONNECTION_DRIVERKEY_NAME:
203 KdPrint((__DRIVER_NAME " IOCTL_USB_GET_NODE_CONNECTION_DRIVERKEY_NAME\n"));
204 break;
205 case IOCTL_USB_GET_HUB_CAPABILITIES:
206 KdPrint((__DRIVER_NAME " IOCTL_USB_GET_HUB_CAPABILITIES\n"));
207 break;
208 case IOCTL_USB_HUB_CYCLE_PORT:
209 KdPrint((__DRIVER_NAME " IOCTL_USB_HUB_CYCLE_PORT\n"));
210 break;
211 case IOCTL_USB_GET_NODE_CONNECTION_ATTRIBUTES:
212 KdPrint((__DRIVER_NAME " IOCTL_USB_GET_NODE_CONNECTION_ATTRIBUTES\n"));
213 break;
214 case IOCTL_USB_GET_NODE_CONNECTION_INFORMATION_EX:
215 KdPrint((__DRIVER_NAME " IOCTL_USB_GET_NODE_CONNECTION_INFORMATION_EX\n"));
216 break;
217 case IOCTL_GET_HCD_DRIVERKEY_NAME:
218 KdPrint((__DRIVER_NAME " IOCTL_GET_HCD_DRIVERKEY_NAME (***)\n"));
219 break;
220 default:
221 KdPrint((__DRIVER_NAME " Unknown IOCTL %08x\n", io_control_code));
222 break;
223 }
224 FUNCTION_MSG("Calling WdfRequestComplete with status = %08x\n");
225 WdfRequestComplete(request, status);
227 FUNCTION_EXIT();
228 }
230 static VOID
231 XenUsbHub_EvtIoInternalDeviceControl(
232 WDFQUEUE queue,
233 WDFREQUEST request,
234 size_t output_buffer_length,
235 size_t input_buffer_length,
236 ULONG io_control_code)
237 {
238 NTSTATUS status;
239 WDFDEVICE device = WdfIoQueueGetDevice(queue);
240 PXENUSB_PDO_DEVICE_DATA xupdd = GetXupdd(device);
241 WDF_REQUEST_PARAMETERS wrp;
242 PURB urb;
243 #if (NTDDI_VERSION >= NTDDI_VISTA)
244 PUSB_START_FAILDATA usfd;
245 PHUB_DEVICE_CONFIG_INFO hdci;
246 PUSB_TOPOLOGY_ADDRESS uta;
247 PUSB_HUB_NAME uhn;
248 size_t length;
249 #endif
250 xenusb_device_t *usb_device;
252 UNREFERENCED_PARAMETER(input_buffer_length);
253 UNREFERENCED_PARAMETER(output_buffer_length);
255 //FUNCTION_ENTER();
257 status = STATUS_UNSUCCESSFUL;
259 WDF_REQUEST_PARAMETERS_INIT(&wrp);
260 WdfRequestGetParameters(request, &wrp);
262 // these are in api\usbioctl.h
263 switch(io_control_code)
264 {
265 case IOCTL_INTERNAL_USB_CYCLE_PORT:
266 KdPrint((__DRIVER_NAME " IOCTL_INTERNAL_USB_CYCLE_PORT\n"));
267 break;
268 case IOCTL_INTERNAL_USB_ENABLE_PORT:
269 KdPrint((__DRIVER_NAME " IOCTL_INTERNAL_USB_ENABLE_PORT\n"));
270 break;
271 case IOCTL_INTERNAL_USB_GET_BUS_INFO:
272 KdPrint((__DRIVER_NAME " IOCTL_INTERNAL_USB_GET_BUS_INFO\n"));
273 break;
274 case IOCTL_INTERNAL_USB_GET_CONTROLLER_NAME:
275 KdPrint((__DRIVER_NAME " IOCTL_INTERNAL_USB_GET_CONTROLLER_NAME\n"));
276 break;
277 case IOCTL_INTERNAL_USB_GET_HUB_COUNT:
278 KdPrint((__DRIVER_NAME " IOCTL_INTERNAL_USB_GET_HUB_COUNT\n"));
279 KdPrint((__DRIVER_NAME " Count before increment = %p\n", *(PULONG)wrp.Parameters.Others.Arg1));
280 (*(PULONG)wrp.Parameters.Others.Arg1)++;
281 status = STATUS_SUCCESS;
282 break;
283 #if (NTDDI_VERSION >= NTDDI_VISTA)
284 case IOCTL_INTERNAL_USB_GET_HUB_NAME:
285 KdPrint((__DRIVER_NAME " IOCTL_INTERNAL_USB_GET_HUB_NAME (hub)\n"));
286 status = WdfRequestRetrieveOutputBuffer(request, FIELD_OFFSET(USB_HUB_NAME, HubName) + 18, (PVOID *)&uhn, &length);
287 if (NT_SUCCESS(status))
288 {
289 /* not sure this is correct... it's not the full symbolic name */
290 uhn->ActualLength = sizeof(USB_HUB_NAME);
291 RtlStringCbCopyW(uhn->HubName, length - FIELD_OFFSET(USB_HUB_NAME, HubName), L"ROOT_HUB");
292 status = STATUS_SUCCESS;
293 }
294 break;
295 #endif
296 case IOCTL_INTERNAL_USB_GET_PORT_STATUS:
297 //FUNCTION_MSG("IOCTL_INTERNAL_USB_GET_PORT_STATUS\n");
298 *(PULONG)wrp.Parameters.Others.Arg1 = USBD_PORT_ENABLED | USBD_PORT_CONNECTED; /* enabled and connected */
299 status = STATUS_SUCCESS;
300 break;
301 case IOCTL_INTERNAL_USB_GET_ROOTHUB_PDO:
302 KdPrint((__DRIVER_NAME " IOCTL_INTERNAL_USB_GET_ROOTHUB_PDO\n"));
303 KdPrint((__DRIVER_NAME " WdfDeviceWdmGetPhysicalDevice(device) = %p\n", WdfDeviceWdmGetPhysicalDevice(device)));
304 //KdPrint((__DRIVER_NAME " IoGetAttachedDevice(WdfDeviceWdmGetDeviceObject(device)) = %p\n", IoGetAttachedDevice(WdfDeviceWdmGetDeviceObject(device))));
305 *(PVOID *)wrp.Parameters.Others.Arg1 = WdfDeviceWdmGetPhysicalDevice(device);
306 //*(PVOID *)wrp.Parameters.Others.Arg2 = IoGetAttachedDevice(WdfDeviceWdmGetDeviceObject(device));
307 *(PVOID *)wrp.Parameters.Others.Arg2 = IoGetAttachedDevice(WdfDeviceWdmGetDeviceObject(xupdd->wdf_device_bus_fdo));
308 status = STATUS_SUCCESS;
309 break;
310 case IOCTL_INTERNAL_USB_RESET_PORT:
311 KdPrint((__DRIVER_NAME " IOCTL_INTERNAL_USB_RESET_PORT\n"));
312 break;
313 case IOCTL_INTERNAL_USB_SUBMIT_IDLE_NOTIFICATION:
314 KdPrint((__DRIVER_NAME " IOCTL_INTERNAL_USB_SUBMIT_IDLE_NOTIFICATION\n"));
315 break;
316 case IOCTL_INTERNAL_USB_SUBMIT_URB:
317 //KdPrint((__DRIVER_NAME " IOCTL_INTERNAL_USB_SUBMIT_URB\n"));
318 urb = (PURB)wrp.Parameters.Others.Arg1;
319 ASSERT(urb);
320 usb_device = urb->UrbHeader.UsbdDeviceHandle;
321 if (!usb_device)
322 usb_device = xupdd->usb_device;
323 WdfRequestForwardToIoQueue(request, usb_device->urb_queue);
324 return;
325 case IOCTL_INTERNAL_USB_GET_DEVICE_HANDLE:
326 FUNCTION_MSG("IOCTL_INTERNAL_USB_GET_DEVICE_HANDLE (returning %p)\n", xupdd->usb_device);
327 *(PVOID *)wrp.Parameters.Others.Arg1 = xupdd->usb_device;
328 status = STATUS_SUCCESS;
329 break;
330 #if (NTDDI_VERSION >= NTDDI_VISTA)
331 case IOCTL_INTERNAL_USB_GET_DEVICE_HANDLE_EX: /* incomplete probably */
332 FUNCTION_MSG("IOCTL_INTERNAL_USB_GET_DEVICE_HANDLE_EX (returning %p)\n", xupdd->usb_device);
333 *(PVOID *)wrp.Parameters.Others.Arg1 = xupdd->usb_device;
334 *(ULONG_PTR *)wrp.Parameters.Others.Arg2 = (ULONG_PTR)0x12345678;
335 status = STATUS_SUCCESS;
336 break;
337 case IOCTL_INTERNAL_USB_GET_TOPOLOGY_ADDRESS:
338 FUNCTION_MSG("IOCTL_INTERNAL_USB_GET_TOPOLOGY_ADDRESS\n");
339 uta = (PUSB_TOPOLOGY_ADDRESS)wrp.Parameters.Others.Arg1;
340 uta->PciBusNumber = 0;
341 uta->PciDeviceNumber = 0;
342 uta->PciFunctionNumber = 0;
343 uta->RootHubPortNumber = 0;
344 uta->HubPortNumber[1] = 0;
345 uta->HubPortNumber[2] = 0;
346 uta->HubPortNumber[3] = 0;
347 uta->HubPortNumber[4] = 0;
348 status = STATUS_SUCCESS;
349 break;
350 case IOCTL_INTERNAL_USB_GET_DEVICE_CONFIG_INFO:
351 FUNCTION_MSG("IOCTL_INTERNAL_USB_GET_DEVICE_CONFIG_INFO\n");
352 hdci = (PHUB_DEVICE_CONFIG_INFO)wrp.Parameters.Others.Arg1;
353 hdci->Version = 1;
354 hdci->Length = 192;
355 hdci->HubFlags.ul = 0;
356 hdci->HubFlags.HubIsHighSpeedCapable = 1;
357 hdci->HubFlags.HubIsHighSpeed = 1;
358 hdci->HubFlags.HubIsMultiTtCapable = 0;
359 hdci->HubFlags.HubIsMultiTt = 0;
360 hdci->HubFlags.HubIsRoot = 1;
361 hdci->HubFlags.HubIsArmedWakeOnConnect = 1;
362 hdci->HubFlags.HubIsBusPowered = 1;
363 //hdci->HardwareIds = ?;
364 //hdci->CompatibleIds = ?;
365 //hdci->DeviceDescription = ?;
366 status = STATUS_SUCCESS;
367 break;
368 case IOCTL_INTERNAL_USB_RECORD_FAILURE:
369 FUNCTION_MSG("IOCTL_INTERNAL_USB_RECORD_FAILURE\n");
370 usfd = (PUSB_START_FAILDATA)wrp.Parameters.Others.Arg1;
371 FUNCTION_MSG(" LengthInBytes = %d\n", usfd->LengthInBytes);
372 FUNCTION_MSG(" NtStatus = %08x\n", usfd->NtStatus);
373 FUNCTION_MSG(" UsbdStatus = %08x\n", usfd->UsbdStatus);
374 FUNCTION_MSG(" ConnectStatus = %08x\n", usfd->ConnectStatus);
375 status = STATUS_SUCCESS;
376 break;
377 #endif
378 default:
379 FUNCTION_MSG("Unknown IOCTL %08x\n", io_control_code);
380 break;
381 }
383 if (status != STATUS_SUCCESS)
384 FUNCTION_MSG("Calling WdfRequestComplete with status = %08x\n", status);
385 WdfRequestComplete(request, status);
387 //FUNCTION_EXIT();
388 }
390 static NTSTATUS
391 XenUsbHub_EvtDeviceD0Entry(WDFDEVICE device, WDF_POWER_DEVICE_STATE previous_state)
392 {
393 NTSTATUS status = STATUS_SUCCESS;
394 DECLARE_CONST_UNICODE_STRING(symbolicname_name, L"SymbolicName");
395 WDFSTRING symbolicname_value_wdfstring;
396 WDFKEY device_key;
397 UNICODE_STRING symbolicname_value;
399 UNREFERENCED_PARAMETER(device);
401 FUNCTION_ENTER();
403 switch (previous_state)
404 {
405 case WdfPowerDeviceD0:
406 KdPrint((__DRIVER_NAME " WdfPowerDeviceD1\n"));
407 break;
408 case WdfPowerDeviceD1:
409 KdPrint((__DRIVER_NAME " WdfPowerDeviceD1\n"));
410 break;
411 case WdfPowerDeviceD2:
412 KdPrint((__DRIVER_NAME " WdfPowerDeviceD2\n"));
413 break;
414 case WdfPowerDeviceD3:
415 KdPrint((__DRIVER_NAME " WdfPowerDeviceD3\n"));
416 break;
417 case WdfPowerDeviceD3Final:
418 KdPrint((__DRIVER_NAME " WdfPowerDeviceD3Final\n"));
419 break;
420 case WdfPowerDevicePrepareForHibernation:
421 KdPrint((__DRIVER_NAME " WdfPowerDevicePrepareForHibernation\n"));
422 break;
423 default:
424 KdPrint((__DRIVER_NAME " Unknown WdfPowerDevice state %d\n", previous_state));
425 break;
426 }
428 /* USB likes to have a registry key with the symbolic link name in it. Have to wait until D0Entry as this is the PDO */
429 status = WdfStringCreate(NULL, WDF_NO_OBJECT_ATTRIBUTES, &symbolicname_value_wdfstring);
430 if (!NT_SUCCESS(status)) {
431 FUNCTION_MSG("WdfStringCreate = %08x\n", status);
432 return status;
433 }
434 status = WdfDeviceRetrieveDeviceInterfaceString(device, &GUID_DEVINTERFACE_USB_HUB, NULL, symbolicname_value_wdfstring);
435 if (!NT_SUCCESS(status)) {
436 FUNCTION_MSG("WdfDeviceREtrieveDeviceInterfaceString = %08x\n", status);
437 return status;
438 }
439 WdfStringGetUnicodeString(symbolicname_value_wdfstring, &symbolicname_value);
440 FUNCTION_MSG("ROOT_HUB SymbolicName = %S\n", symbolicname_value.Buffer);
441 status = WdfDeviceOpenRegistryKey(device, PLUGPLAY_REGKEY_DEVICE, KEY_SET_VALUE, WDF_NO_OBJECT_ATTRIBUTES, &device_key);
442 if (!NT_SUCCESS(status)) {
443 FUNCTION_MSG("WdfDeviceOpenRegistryKey = %08x\n", status);
444 return status;
445 }
446 status = WdfRegistryAssignUnicodeString(device_key, &symbolicname_name, &symbolicname_value);
447 if (!NT_SUCCESS(status)) {
448 FUNCTION_MSG("WdfDeviceOpenRegistryKey = %08x\n", status);
449 return status;
450 }
451 WdfRegistryClose(device_key);
452 FUNCTION_EXIT();
454 return status;
455 }
457 static NTSTATUS
458 XenUsbHub_EvtDeviceD0Exit(WDFDEVICE device, WDF_POWER_DEVICE_STATE target_state)
459 {
460 NTSTATUS status = STATUS_SUCCESS;
461 //PXENUSB_PDO_DEVICE_DATA xupdd = GetXupdd(device);
462 //PXENUSB_DEVICE_DATA xudd = GetXudd(xupdd->wdf_device_bus_fdo);
464 UNREFERENCED_PARAMETER(device);
466 FUNCTION_ENTER();
468 switch (target_state)
469 {
470 case WdfPowerDeviceD0:
471 KdPrint((__DRIVER_NAME " WdfPowerDeviceD1\n"));
472 break;
473 case WdfPowerDeviceD1:
474 KdPrint((__DRIVER_NAME " WdfPowerDeviceD1\n"));
475 break;
476 case WdfPowerDeviceD2:
477 KdPrint((__DRIVER_NAME " WdfPowerDeviceD2\n"));
478 break;
479 case WdfPowerDeviceD3:
480 KdPrint((__DRIVER_NAME " WdfPowerDeviceD3\n"));
481 break;
482 case WdfPowerDeviceD3Final:
483 KdPrint((__DRIVER_NAME " WdfPowerDeviceD3Final\n"));
484 break;
485 case WdfPowerDevicePrepareForHibernation:
486 KdPrint((__DRIVER_NAME " WdfPowerDevicePrepareForHibernation\n"));
487 break;
488 default:
489 KdPrint((__DRIVER_NAME " Unknown WdfPowerDevice state %d\n", target_state));
490 break;
491 }
493 FUNCTION_EXIT();
495 return status;
496 }
498 static NTSTATUS
499 XenUsbHub_EvtDevicePrepareHardware(WDFDEVICE device, WDFCMRESLIST resources_raw, WDFCMRESLIST resources_translated)
500 {
501 NTSTATUS status = STATUS_SUCCESS;
503 UNREFERENCED_PARAMETER(device);
504 UNREFERENCED_PARAMETER(resources_raw);
505 UNREFERENCED_PARAMETER(resources_translated);
507 FUNCTION_ENTER();
508 FUNCTION_EXIT();
510 return status;
511 }
513 static NTSTATUS
514 XenUsbHub_EvtDeviceReleaseHardware(WDFDEVICE device, WDFCMRESLIST resources_translated)
515 {
516 NTSTATUS status = STATUS_SUCCESS;
518 UNREFERENCED_PARAMETER(device);
519 UNREFERENCED_PARAMETER(resources_translated);
521 FUNCTION_ENTER();
522 FUNCTION_EXIT();
524 return status;
525 }
527 static VOID
528 XenUsbHub_EvtDeviceUsageNotification(WDFDEVICE device, WDF_SPECIAL_FILE_TYPE notification_type, BOOLEAN is_in_notification_path)
529 {
530 PXENUSB_PDO_DEVICE_DATA xupdd = GetXupdd(device);
532 UNREFERENCED_PARAMETER(xupdd);
533 UNREFERENCED_PARAMETER(is_in_notification_path);
535 FUNCTION_ENTER();
537 switch (notification_type)
538 {
539 case WdfSpecialFilePaging:
540 KdPrint((__DRIVER_NAME " notification_type = Paging, flag = %d\n", is_in_notification_path));
541 break;
542 case WdfSpecialFileHibernation:
543 KdPrint((__DRIVER_NAME " notification_type = Hibernation, flag = %d\n", is_in_notification_path));
544 break;
545 case WdfSpecialFileDump:
546 KdPrint((__DRIVER_NAME " notification_type = Dump, flag = %d\n", is_in_notification_path));
547 break;
548 default:
549 KdPrint((__DRIVER_NAME " notification_type = %d, flag = %d\n", notification_type, is_in_notification_path));
550 break;
551 }
553 FUNCTION_EXIT();
554 }
556 static NTSTATUS
557 XenUsb_SubmitCompletionRoutine(
558 PDEVICE_OBJECT device_object,
559 PIRP irp,
560 PVOID context)
561 {
562 UNREFERENCED_PARAMETER(device_object);
564 FUNCTION_ENTER();
566 if (irp->PendingReturned)
567 {
568 KeSetEvent ((PKEVENT)context, IO_NO_INCREMENT, FALSE);
569 }
571 FUNCTION_EXIT();
573 return STATUS_MORE_PROCESSING_REQUIRED;
574 }
576 static NTSTATUS
577 XenUsbHub_UBIH_CreateUsbDevice(
578 PVOID BusContext,
579 PUSB_DEVICE_HANDLE *DeviceHandle,
580 PUSB_DEVICE_HANDLE HubDeviceHandle,
581 USHORT PortStatus,
582 USHORT PortNumber)
583 {
584 NTSTATUS status = STATUS_SUCCESS;
585 xenusb_device_t *usb_device;
587 UNREFERENCED_PARAMETER(BusContext);
588 UNREFERENCED_PARAMETER(HubDeviceHandle);
589 UNREFERENCED_PARAMETER(PortStatus);
591 FUNCTION_ENTER();
593 FUNCTION_MSG("BusContext = %p\n", BusContext);
594 FUNCTION_MSG("DeviceHandle = %p\n", DeviceHandle);
595 FUNCTION_MSG("*DeviceHandle = %p\n", *DeviceHandle);
596 FUNCTION_MSG("HubDeviceHandle = %p\n", HubDeviceHandle);
597 FUNCTION_MSG("PortStatus = %04X\n", PortStatus);
598 FUNCTION_MSG("PortNumber = %d\n", PortNumber);
599 usb_device = ExAllocatePoolWithTag(NonPagedPool, sizeof(xenusb_device_t), XENUSB_POOL_TAG);
600 if (!usb_device) {
601 FUNCTION_EXIT();
602 return STATUS_INSUFFICIENT_RESOURCES;
603 }
604 usb_device->port_number = PortNumber;
605 *DeviceHandle = usb_device;
607 FUNCTION_EXIT();
608 return status;
609 }
611 static NTSTATUS
612 XenUsbHub_UBIH_InitializeUsbDevice(
613 PVOID BusContext,
614 PUSB_DEVICE_HANDLE DeviceHandle)
615 {
616 NTSTATUS status = STATUS_SUCCESS;
617 WDFDEVICE device = BusContext;
618 PXENUSB_PDO_DEVICE_DATA xupdd = GetXupdd(device);
619 //PXENUSB_DEVICE_DATA xudd = GetXudd(xupdd->wdf_device_bus_fdo);
620 WDF_IO_QUEUE_CONFIG queue_config;
621 xenusb_device_t *usb_device = DeviceHandle;
622 PUCHAR ptr;
623 PVOID buf;
624 PMDL mdl;
625 pvurb_t pvurb; /* this can be local because it never leaves this routine */
626 PUSB_DEVICE_DESCRIPTOR device_descriptor;
627 PUSB_CONFIGURATION_DESCRIPTOR config_descriptor;
628 PUSB_INTERFACE_DESCRIPTOR interface_descriptor;
629 PUSB_ENDPOINT_DESCRIPTOR endpoint_descriptor;
630 int i, j, k;
631 PUSB_DEFAULT_PIPE_SETUP_PACKET setup_packet;
632 WDF_MEMORY_DESCRIPTOR pvurb_descriptor;
633 WDF_REQUEST_SEND_OPTIONS send_options;
635 FUNCTION_ENTER();
637 KdPrint((__DRIVER_NAME " device = %p\n", device));
638 KdPrint((__DRIVER_NAME " usb_device = %p\n", usb_device));
639 usb_device->pdo_device = BusContext;
641 // TODO: get address from freelist and assign it to the device...
642 usb_device->address = 2;
643 // TODO: get this stuff properly ...
644 xupdd->usb_device->device_speed = UsbHighSpeed;
645 xupdd->usb_device->device_type = Usb20Device;
647 buf = ExAllocatePoolWithTag(NonPagedPool, PAGE_SIZE, XENUSB_POOL_TAG);
648 if (!buf) {
649 FUNCTION_MSG("ExAllocatePoolWithTag(buf) failed\n");
650 return STATUS_INSUFFICIENT_RESOURCES;
651 }
652 mdl = IoAllocateMdl(buf, PAGE_SIZE, FALSE, FALSE, NULL);
653 if (!mdl) {
654 FUNCTION_MSG("IoAllocateMdl(buf) failed\n", status);
655 return STATUS_INSUFFICIENT_RESOURCES;
656 }
657 MmBuildMdlForNonPagedPool(mdl);
659 WDF_MEMORY_DESCRIPTOR_INIT_BUFFER(&pvurb_descriptor, &pvurb, sizeof(pvurb));
660 WDF_REQUEST_SEND_OPTIONS_INIT(&send_options, WDF_REQUEST_SEND_OPTION_TIMEOUT);
661 WDF_REQUEST_SEND_OPTIONS_SET_TIMEOUT(&send_options, WDF_REL_TIMEOUT_IN_SEC(10));
663 /* set the address */
664 pvurb.req.pipe = LINUX_PIPE_TYPE_CTRL | usb_device->port_number;
665 pvurb.req.transfer_flags = 0;
666 pvurb.req.buffer_length = 0;
667 setup_packet = (PUSB_DEFAULT_PIPE_SETUP_PACKET)pvurb.req.u.ctrl;
668 setup_packet->bmRequestType.Recipient = BMREQUEST_TO_DEVICE;
669 setup_packet->bmRequestType.Type = BMREQUEST_STANDARD;
670 setup_packet->bmRequestType.Dir = BMREQUEST_HOST_TO_DEVICE;
671 setup_packet->bRequest = USB_REQUEST_SET_ADDRESS;
672 setup_packet->wValue.W = usb_device->address;
673 setup_packet->wIndex.W = 0;
674 setup_packet->wLength = pvurb.req.buffer_length;
675 pvurb.mdl = NULL;
676 status = WdfIoTargetSendInternalIoctlOthersSynchronously(xupdd->bus_fdo_target, NULL, IOCTL_INTERNAL_PVUSB_SUBMIT_URB, &pvurb_descriptor, NULL, NULL, &send_options, NULL);
677 if (!NT_SUCCESS(status)) {
678 FUNCTION_MSG("WdfIoTargetSendInternalIoctlOthersSynchronously(USB_REQUEST_SET_ADDRESS) = %08x\n", status);
679 return status;
680 }
681 FUNCTION_MSG("IOCTL_INTERNAL_PVUSB_SUBMIT_URB status = %08x\n", status);
682 FUNCTION_MSG("rsp start_frame = %d\n", pvurb.rsp.start_frame);
683 FUNCTION_MSG("rsp status = %d\n", pvurb.rsp.status);
684 FUNCTION_MSG("rsp actual_length = %d\n", pvurb.rsp.actual_length);
685 FUNCTION_MSG("rsp error_count = %d\n", pvurb.rsp.error_count);
687 /* get the device descriptor */
688 pvurb.req.pipe = LINUX_PIPE_DIRECTION_IN | LINUX_PIPE_TYPE_CTRL | (usb_device->address << 8) | usb_device->port_number;
689 pvurb.req.transfer_flags = 0;
690 pvurb.req.buffer_length = PAGE_SIZE;
691 setup_packet = (PUSB_DEFAULT_PIPE_SETUP_PACKET)pvurb.req.u.ctrl;
692 setup_packet->bmRequestType.Recipient = BMREQUEST_TO_DEVICE;
693 setup_packet->bmRequestType.Type = BMREQUEST_STANDARD;
694 setup_packet->bmRequestType.Dir = BMREQUEST_DEVICE_TO_HOST;
695 setup_packet->bRequest = USB_REQUEST_GET_DESCRIPTOR;
696 setup_packet->wValue.LowByte = 0;
697 setup_packet->wValue.HiByte = USB_DEVICE_DESCRIPTOR_TYPE; //device descriptor
698 setup_packet->wIndex.W = 0;
699 setup_packet->wLength = pvurb.req.buffer_length;
700 pvurb.mdl = mdl;
701 status = WdfIoTargetSendInternalIoctlOthersSynchronously(xupdd->bus_fdo_target, NULL, IOCTL_INTERNAL_PVUSB_SUBMIT_URB, &pvurb_descriptor, NULL, NULL, &send_options, NULL);
702 if (!NT_SUCCESS(status)) {
703 FUNCTION_MSG("WdfIoTargetSendInternalIoctlOthersSynchronously(USB_REQUEST_GET_DESCRIPTOR, USB_DEVICE_DESCRIPTOR_TYPE) = %08x\n", status);
704 return status;
705 }
706 KdPrint((__DRIVER_NAME " rsp start_frame = %d\n", pvurb.rsp.start_frame));
707 KdPrint((__DRIVER_NAME " rsp status = %d\n", pvurb.rsp.status));
708 KdPrint((__DRIVER_NAME " rsp actual_length = %d\n", pvurb.rsp.actual_length));
709 KdPrint((__DRIVER_NAME " rsp error_count = %d\n", pvurb.rsp.error_count));
710 ptr = buf;
711 device_descriptor = (PUSB_DEVICE_DESCRIPTOR)ptr;
712 KdPrint((__DRIVER_NAME " bLength = %d\n", device_descriptor->bLength));
713 KdPrint((__DRIVER_NAME " bNumConfigurations = %d\n", device_descriptor->bNumConfigurations));
714 memcpy(&usb_device->device_descriptor, device_descriptor, device_descriptor->bLength);
715 usb_device->configs = ExAllocatePoolWithTag(NonPagedPool, sizeof(PVOID) * device_descriptor->bNumConfigurations, XENUSB_POOL_TAG);
716 if (!usb_device->configs) {
717 FUNCTION_MSG("ExAllocatePoolWithTag(usb_device->configs) failed\n");
718 return STATUS_INSUFFICIENT_RESOURCES;
719 }
720 KdPrint((__DRIVER_NAME " bLength = %d\n", device_descriptor->bLength));
721 KdPrint((__DRIVER_NAME " bDescriptorType = %d\n", device_descriptor->bDescriptorType));
722 KdPrint((__DRIVER_NAME " bcdUSB = %04x\n", device_descriptor->bcdUSB));
723 KdPrint((__DRIVER_NAME " bDeviceClass = %02x\n", device_descriptor->bDeviceClass));
724 KdPrint((__DRIVER_NAME " bDeviceSubClass = %02x\n", device_descriptor->bDeviceSubClass));
725 KdPrint((__DRIVER_NAME " bDeviceProtocol = %02x\n", device_descriptor->bDeviceProtocol));
726 KdPrint((__DRIVER_NAME " idVendor = %04x\n", device_descriptor->idVendor));
727 KdPrint((__DRIVER_NAME " idProduct = %04x\n", device_descriptor->idProduct));
728 KdPrint((__DRIVER_NAME " bcdDevice = %04x\n", device_descriptor->bcdDevice));
729 KdPrint((__DRIVER_NAME " bNumConfigurations = %04x\n", device_descriptor->bNumConfigurations));
731 /* get the config descriptor */
732 for (i = 0; i < device_descriptor->bNumConfigurations; i++)
733 {
734 pvurb.req.pipe = LINUX_PIPE_DIRECTION_IN | LINUX_PIPE_TYPE_CTRL | (usb_device->address << 8) | usb_device->port_number;
735 pvurb.req.transfer_flags = 0;
736 pvurb.req.buffer_length = PAGE_SIZE;
737 setup_packet = (PUSB_DEFAULT_PIPE_SETUP_PACKET)pvurb.req.u.ctrl;
738 setup_packet->bmRequestType.Recipient = BMREQUEST_TO_DEVICE;
739 setup_packet->bmRequestType.Type = BMREQUEST_STANDARD;
740 setup_packet->bmRequestType.Dir = BMREQUEST_DEVICE_TO_HOST;
741 setup_packet->bRequest = USB_REQUEST_GET_DESCRIPTOR;
742 setup_packet->wValue.LowByte = (UCHAR)(i + 1);
743 setup_packet->wValue.HiByte = USB_CONFIGURATION_DESCRIPTOR_TYPE; //device descriptor
744 setup_packet->wIndex.W = 0;
745 setup_packet->wLength = pvurb.req.buffer_length;
746 pvurb.mdl = mdl;
747 status = WdfIoTargetSendInternalIoctlOthersSynchronously(xupdd->bus_fdo_target, NULL, IOCTL_INTERNAL_PVUSB_SUBMIT_URB, &pvurb_descriptor, NULL, NULL, &send_options, NULL);
748 if (!NT_SUCCESS(status)) {
749 FUNCTION_MSG("WdfIoTargetSendInternalIoctlOthersSynchronously(USB_REQUEST_GET_DESCRIPTOR, USB_CONFIGURATION_DESCRIPTOR_TYPE) = %08x\n", status);
750 return status;
751 }
752 KdPrint((__DRIVER_NAME " rsp start_frame = %d\n", pvurb.rsp.start_frame));
753 KdPrint((__DRIVER_NAME " rsp status = %d\n", pvurb.rsp.status));
754 KdPrint((__DRIVER_NAME " rsp actual_length = %d\n", pvurb.rsp.actual_length));
755 KdPrint((__DRIVER_NAME " rsp error_count = %d\n", pvurb.rsp.error_count));
756 ptr = buf;
757 config_descriptor = (PUSB_CONFIGURATION_DESCRIPTOR)ptr;
758 KdPrint((__DRIVER_NAME " Config %d\n", i));
759 KdPrint((__DRIVER_NAME " bLength = %d\n", config_descriptor->bLength));
760 KdPrint((__DRIVER_NAME " bDescriptorType = %d\n", config_descriptor->bDescriptorType));
761 KdPrint((__DRIVER_NAME " wTotalLength = %d\n", config_descriptor->wTotalLength));
762 KdPrint((__DRIVER_NAME " bNumInterfaces = %d\n", config_descriptor->bNumInterfaces));
763 KdPrint((__DRIVER_NAME " iConfiguration = %d\n", config_descriptor->iConfiguration));
764 KdPrint((__DRIVER_NAME " bConfigurationValue = %d\n", config_descriptor->bConfigurationValue));
765 KdPrint((__DRIVER_NAME " bmAttributes = %02x\n", config_descriptor->bmAttributes));
766 KdPrint((__DRIVER_NAME " MaxPower = %d\n", config_descriptor->MaxPower));
767 usb_device->configs[i] = ExAllocatePoolWithTag(NonPagedPool, sizeof(xenusb_config_t) + sizeof(PVOID) * config_descriptor->bNumInterfaces, XENUSB_POOL_TAG);
768 if (!usb_device->configs) {
769 FUNCTION_MSG("ExAllocatePoolWithTag(usb_device->configs[i]) failed\n");
770 return STATUS_INSUFFICIENT_RESOURCES;
771 }
772 usb_device->configs[i]->device = usb_device;
773 memcpy(&usb_device->configs[i]->config_descriptor, config_descriptor, sizeof(USB_CONFIGURATION_DESCRIPTOR));
774 usb_device->configs[i]->config_descriptor_all = ExAllocatePoolWithTag(NonPagedPool, config_descriptor->wTotalLength, XENUSB_POOL_TAG);
775 memcpy(usb_device->configs[i]->config_descriptor_all, config_descriptor, config_descriptor->wTotalLength);
776 ptr += config_descriptor->bLength;
777 j = 0;
778 while (j < config_descriptor->bNumInterfaces)
779 {
780 interface_descriptor = (PUSB_INTERFACE_DESCRIPTOR)ptr;
781 KdPrint((__DRIVER_NAME " Interface %d\n", j));
782 KdPrint((__DRIVER_NAME " bLength = %d\n", interface_descriptor->bLength));
783 KdPrint((__DRIVER_NAME " bDescriptorType = %d\n", interface_descriptor->bDescriptorType));
784 KdPrint((__DRIVER_NAME " bInterfaceNumber = %d\n", interface_descriptor->bInterfaceNumber));
785 KdPrint((__DRIVER_NAME " bAlternateSetting = %d\n", interface_descriptor->bAlternateSetting));
786 KdPrint((__DRIVER_NAME " bNumEndpoints = %d\n", interface_descriptor->bNumEndpoints));
787 KdPrint((__DRIVER_NAME " bInterfaceClass = %d\n", interface_descriptor->bInterfaceClass));
788 KdPrint((__DRIVER_NAME " bInterfaceSubClass = %d\n", interface_descriptor->bInterfaceSubClass));
789 KdPrint((__DRIVER_NAME " bInterfaceProtocol = %d\n", interface_descriptor->bInterfaceProtocol));
790 KdPrint((__DRIVER_NAME " iInterface = %d\n", interface_descriptor->iInterface));
791 ptr += interface_descriptor->bLength;
792 usb_device->configs[i]->interfaces[j] = ExAllocatePoolWithTag(NonPagedPool, sizeof(xenusb_interface_t) + sizeof(PVOID) * interface_descriptor->bNumEndpoints, XENUSB_POOL_TAG);
793 usb_device->configs[i]->interfaces[j]->config = usb_device->configs[i];
794 memcpy(&usb_device->configs[i]->interfaces[j]->interface_descriptor, interface_descriptor, sizeof(USB_INTERFACE_DESCRIPTOR));
795 k = 0;
796 while (k < interface_descriptor->bNumEndpoints)
797 {
798 endpoint_descriptor = (PUSB_ENDPOINT_DESCRIPTOR)ptr;
799 if (endpoint_descriptor->bDescriptorType != 5)
800 {
801 KdPrint((__DRIVER_NAME " Unknown bDescriptorType %d found length = %d\n", endpoint_descriptor->bDescriptorType, endpoint_descriptor->bLength));
802 ptr += endpoint_descriptor->bLength;
803 continue;
804 }
806 KdPrint((__DRIVER_NAME " Endpoint %d\n", k));
807 KdPrint((__DRIVER_NAME " bLength = %d\n", endpoint_descriptor->bLength));
808 KdPrint((__DRIVER_NAME " bDescriptorType = %d\n", endpoint_descriptor->bDescriptorType));
809 KdPrint((__DRIVER_NAME " bEndpointAddress = %02x\n", endpoint_descriptor->bEndpointAddress));
810 KdPrint((__DRIVER_NAME " bmAttributes = %02x\n", endpoint_descriptor->bmAttributes));
811 KdPrint((__DRIVER_NAME " wMaxPacketSize = %d\n", endpoint_descriptor->wMaxPacketSize));
812 KdPrint((__DRIVER_NAME " bInterval = %d\n", endpoint_descriptor->bInterval));
813 ptr += endpoint_descriptor->bLength;
814 usb_device->configs[i]->interfaces[j]->endpoints[k] = ExAllocatePoolWithTag(NonPagedPool, sizeof(xenusb_endpoint_t), XENUSB_POOL_TAG);
815 usb_device->configs[i]->interfaces[j]->endpoints[k]->interface = usb_device->configs[i]->interfaces[j];
816 usb_device->configs[i]->interfaces[j]->endpoints[k]->pipe_value = (usb_device->address << 8) | usb_device->port_number;
817 /* linux uses nonstandard endpoint type identifiers... */
818 switch(endpoint_descriptor->bmAttributes & USB_ENDPOINT_TYPE_MASK)
819 {
820 case USB_ENDPOINT_TYPE_CONTROL:
821 usb_device->configs[i]->interfaces[j]->endpoints[k]->pipe_value |= LINUX_PIPE_TYPE_CTRL;
822 break;
823 case USB_ENDPOINT_TYPE_ISOCHRONOUS:
824 usb_device->configs[i]->interfaces[j]->endpoints[k]->pipe_value |= LINUX_PIPE_TYPE_ISOC;
825 break;
826 case USB_ENDPOINT_TYPE_BULK:
827 usb_device->configs[i]->interfaces[j]->endpoints[k]->pipe_value |= LINUX_PIPE_TYPE_BULK;
828 break;
829 case USB_ENDPOINT_TYPE_INTERRUPT:
830 usb_device->configs[i]->interfaces[j]->endpoints[k]->pipe_value |= LINUX_PIPE_TYPE_INTR;
831 break;
832 }
833 usb_device->configs[i]->interfaces[j]->endpoints[k]->pipe_value |= (endpoint_descriptor->bEndpointAddress & 0x80);
834 usb_device->configs[i]->interfaces[j]->endpoints[k]->pipe_value |= (endpoint_descriptor->bEndpointAddress & 0x0F) << 15;
835 memcpy(&usb_device->configs[i]->interfaces[j]->endpoints[k]->endpoint_descriptor, endpoint_descriptor, sizeof(USB_ENDPOINT_DESCRIPTOR));
836 k++;
837 }
838 j++;
839 }
840 }
842 usb_device->active_config = usb_device->configs[0];
843 usb_device->active_interface = usb_device->configs[0]->interfaces[0];
845 WDF_IO_QUEUE_CONFIG_INIT(&queue_config, WdfIoQueueDispatchParallel); // should this be serial?
846 queue_config.EvtIoInternalDeviceControl = XenUsb_EvtIoInternalDeviceControl_DEVICE_SUBMIT_URB;
847 queue_config.PowerManaged = TRUE; /* power managed queue for SUBMIT_URB */
848 status = WdfIoQueueCreate(device, &queue_config, WDF_NO_OBJECT_ATTRIBUTES, &usb_device->urb_queue);
849 if (!NT_SUCCESS(status)) {
850 KdPrint((__DRIVER_NAME " Error creating urb_queue 0x%x\n", status));
851 return status;
852 }
853 FUNCTION_EXIT();
854 return status;
855 }
857 static NTSTATUS
858 XenUsbHub_UBIH_GetUsbDescriptors(
859 PVOID BusContext,
860 PUSB_DEVICE_HANDLE DeviceHandle,
861 PUCHAR DeviceDescriptorBuffer,
862 PULONG DeviceDescriptorBufferLength,
863 PUCHAR ConfigDescriptorBuffer,
864 PULONG ConfigDescriptorBufferLength
865 )
866 {
867 NTSTATUS status = STATUS_SUCCESS;
868 xenusb_device_t *usb_device = DeviceHandle;
869 xenusb_config_t *usb_config;
870 PUCHAR ptr;
872 UNREFERENCED_PARAMETER(BusContext);
874 FUNCTION_ENTER();
876 KdPrint((__DRIVER_NAME " BusContext = %p\n", BusContext));
877 KdPrint((__DRIVER_NAME " DeviceHandle = %p\n", DeviceHandle));
878 KdPrint((__DRIVER_NAME " DeviceDescriptorBuffer = %p\n", DeviceDescriptorBuffer));
879 KdPrint((__DRIVER_NAME " DeviceDescriptorBufferLength = %d\n", *DeviceDescriptorBufferLength));
880 KdPrint((__DRIVER_NAME " ConfigDescriptorBuffer = %p\n", ConfigDescriptorBuffer));
881 KdPrint((__DRIVER_NAME " ConfigDescriptorBufferLength = %d\n", *ConfigDescriptorBufferLength));
883 memcpy(DeviceDescriptorBuffer, &usb_device->device_descriptor, usb_device->device_descriptor.bLength);
884 *DeviceDescriptorBufferLength = usb_device->device_descriptor.bLength;
886 usb_config = usb_device->active_config;
887 ptr = ConfigDescriptorBuffer;
888 memcpy(ptr, usb_config->config_descriptor_all, min(usb_config->config_descriptor.wTotalLength, *ConfigDescriptorBufferLength));
889 *ConfigDescriptorBufferLength = ((PUSB_CONFIGURATION_DESCRIPTOR)ConfigDescriptorBuffer)->wTotalLength;
891 #if 0
892 ptr += sizeof(USB_CONFIGURATION_DESCRIPTOR);
893 // why was this here? ((PUSB_CONFIGURATION_DESCRIPTOR)ConfigDescriptorBuffer)->wTotalLength += 1;
895 for (i = 0; i < usb_config->config_descriptor.bNumInterfaces; i++)
896 {
897 memcpy(ptr, &usb_config->interfaces[i]->interface_descriptor, sizeof(USB_INTERFACE_DESCRIPTOR));
898 ptr += sizeof(USB_INTERFACE_DESCRIPTOR);
899 ((PUSB_CONFIGURATION_DESCRIPTOR)ConfigDescriptorBuffer)->wTotalLength += sizeof(USB_INTERFACE_DESCRIPTOR);
900 for (j = 0; j < usb_config->interfaces[i]->interface_descriptor.bNumEndpoints; j++)
901 {
902 memcpy(ptr, &usb_config->interfaces[i]->endpoints[j]->endpoint_descriptor, sizeof(USB_ENDPOINT_DESCRIPTOR));
903 ptr += sizeof(USB_ENDPOINT_DESCRIPTOR);
904 ((PUSB_CONFIGURATION_DESCRIPTOR)ConfigDescriptorBuffer)->wTotalLength += sizeof(USB_ENDPOINT_DESCRIPTOR);
905 }
906 }
907 *ConfigDescriptorBufferLength = ((PUSB_CONFIGURATION_DESCRIPTOR)ConfigDescriptorBuffer)->wTotalLength;
908 #endif
910 FUNCTION_EXIT();
911 return status;
912 }
914 static NTSTATUS
915 XenUsbHub_UBIH_RemoveUsbDevice (
916 PVOID BusContext,
917 PUSB_DEVICE_HANDLE DeviceHandle,
918 ULONG Flags)
919 {
920 NTSTATUS status = STATUS_SUCCESS;
922 UNREFERENCED_PARAMETER(BusContext);
923 UNREFERENCED_PARAMETER(DeviceHandle);
925 FUNCTION_ENTER();
927 if (Flags & USBD_KEEP_DEVICE_DATA)
928 KdPrint((__DRIVER_NAME " USBD_KEEP_DEVICE_DATA\n"));
930 if (Flags & USBD_MARK_DEVICE_BUSY)
931 KdPrint((__DRIVER_NAME " USBD_MARK_DEVICE_BUSY\n"));
933 FUNCTION_EXIT();
934 return status;
935 }
937 static NTSTATUS
938 XenUsbHub_UBIH_RestoreUsbDevice(
939 PVOID BusContext,
940 PUSB_DEVICE_HANDLE OldDeviceHandle,
941 PUSB_DEVICE_HANDLE NewDeviceHandle)
942 {
943 NTSTATUS status = STATUS_UNSUCCESSFUL;
945 UNREFERENCED_PARAMETER(BusContext);
946 UNREFERENCED_PARAMETER(OldDeviceHandle);
947 UNREFERENCED_PARAMETER(NewDeviceHandle);
949 FUNCTION_ENTER();
951 FUNCTION_EXIT();
952 return status;
953 }
955 static NTSTATUS
956 XenUsbHub_UBIH_GetPortHackFlags(
957 PVOID BusContext,
958 PULONG HackFlags)
959 {
960 NTSTATUS status = STATUS_UNSUCCESSFUL;
962 UNREFERENCED_PARAMETER(BusContext);
963 UNREFERENCED_PARAMETER(HackFlags);
965 FUNCTION_ENTER();
967 FUNCTION_EXIT();
968 return status;
969 }
971 static NTSTATUS
972 XenUsbHub_UBIH_QueryDeviceInformation(
973 PVOID BusContext,
974 PUSB_DEVICE_HANDLE DeviceHandle,
975 PVOID DeviceInformationBuffer,
976 ULONG DeviceInformationBufferLength,
977 PULONG LengthOfDataReturned)
978 {
979 PUSB_DEVICE_INFORMATION_0 udi = DeviceInformationBuffer;
980 xenusb_device_t *usb_device = DeviceHandle;
981 ULONG i;
982 ULONG required_size;
984 UNREFERENCED_PARAMETER(BusContext);
986 FUNCTION_ENTER();
988 KdPrint((__DRIVER_NAME " BusContext = %p\n", BusContext));
989 KdPrint((__DRIVER_NAME " DeviceHandle = %p\n", DeviceHandle));
990 KdPrint((__DRIVER_NAME " DeviceInformationBuffer = %p\n", DeviceInformationBuffer));
991 KdPrint((__DRIVER_NAME " DeviceInformationBufferLength = %d\n", DeviceInformationBufferLength));
992 KdPrint((__DRIVER_NAME " ->InformationLevel = %d\n", udi->InformationLevel));
993 required_size = (ULONG)FIELD_OFFSET(USB_DEVICE_INFORMATION_0, PipeList[usb_device->active_interface->interface_descriptor.bNumEndpoints]);
994 KdPrint((__DRIVER_NAME " required_size = %d\n", required_size));
995 *LengthOfDataReturned = required_size;
996 udi->ActualLength = required_size;
997 if (DeviceInformationBufferLength < required_size)
998 {
999 KdPrint((__DRIVER_NAME " STATUS_BUFFER_TOO_SMALL\n"));
1000 FUNCTION_EXIT();
1001 return STATUS_BUFFER_TOO_SMALL;
1003 if (udi->InformationLevel != 0)
1005 KdPrint((__DRIVER_NAME " STATUS_NOT_SUPPORTED\n"));
1006 FUNCTION_EXIT();
1007 return STATUS_NOT_SUPPORTED;
1009 udi->PortNumber = 1;
1010 memcpy(&udi->DeviceDescriptor, &usb_device->device_descriptor, sizeof(USB_DEVICE_DESCRIPTOR));
1011 udi->CurrentConfigurationValue = usb_device->active_config->config_descriptor.bConfigurationValue;
1012 udi->DeviceAddress = usb_device->address;
1013 udi->HubAddress = 1; // ?
1014 udi->DeviceSpeed = usb_device->device_speed;
1015 udi->DeviceType = usb_device->device_type;
1016 udi->NumberOfOpenPipes = usb_device->active_interface->interface_descriptor.bNumEndpoints;
1017 for (i = 0; i < usb_device->active_interface->interface_descriptor.bNumEndpoints; i++)
1019 memcpy(&udi->PipeList[i].EndpointDescriptor, &usb_device->active_interface->endpoints[i]->endpoint_descriptor, sizeof(USB_ENDPOINT_DESCRIPTOR));
1020 udi->PipeList[0].ScheduleOffset = 0; // not necessarily right
1022 FUNCTION_EXIT();
1023 return STATUS_SUCCESS;
1026 static NTSTATUS
1027 XenUsbHub_UBIH_GetControllerInformation (
1028 PVOID BusContext,
1029 PVOID ControllerInformationBuffer,
1030 ULONG ControllerInformationBufferLength,
1031 PULONG LengthOfDataReturned)
1033 NTSTATUS status = STATUS_UNSUCCESSFUL;
1034 PUSB_CONTROLLER_INFORMATION_0 uci = ControllerInformationBuffer;
1035 //WDFDEVICE device = BusContext;
1036 //xenusb_device_t *usb_device = DeviceHandle;
1038 UNREFERENCED_PARAMETER(BusContext);
1040 FUNCTION_ENTER();
1042 KdPrint((__DRIVER_NAME " BusContext = %p\n", BusContext));
1043 KdPrint((__DRIVER_NAME " ControllerInformationBuffer = %p\n", ControllerInformationBuffer));
1044 KdPrint((__DRIVER_NAME " ControllerInformationBufferLength = %d\n", ControllerInformationBufferLength));
1045 KdPrint((__DRIVER_NAME " ->InformationLevel = %d\n", uci->InformationLevel));
1046 if (ControllerInformationBufferLength < sizeof(USB_CONTROLLER_INFORMATION_0))
1048 KdPrint((__DRIVER_NAME " STATUS_BUFFER_TOO_SMALL\n"));
1049 FUNCTION_EXIT();
1050 return STATUS_BUFFER_TOO_SMALL;
1052 if (uci->InformationLevel != 0)
1054 KdPrint((__DRIVER_NAME " STATUS_NOT_SUPPORTED\n"));
1055 FUNCTION_EXIT();
1056 return STATUS_NOT_SUPPORTED;
1059 uci->ActualLength = sizeof(USB_CONTROLLER_INFORMATION_0);
1060 uci->SelectiveSuspendEnabled = FALSE;
1061 uci->IsHighSpeedController = TRUE;
1062 *LengthOfDataReturned = uci->ActualLength;
1064 FUNCTION_EXIT();
1065 return status;
1068 static NTSTATUS
1069 XenUsbHub_UBIH_ControllerSelectiveSuspend (
1070 PVOID BusContext,
1071 BOOLEAN Enable)
1073 NTSTATUS status = STATUS_UNSUCCESSFUL;
1075 UNREFERENCED_PARAMETER(BusContext);
1076 UNREFERENCED_PARAMETER(Enable);
1078 FUNCTION_ENTER();
1080 FUNCTION_EXIT();
1081 return status;
1084 static NTSTATUS
1085 XenUsbHub_UBIH_GetExtendedHubInformation (
1086 PVOID BusContext,
1087 PDEVICE_OBJECT HubPhysicalDeviceObject,
1088 PVOID HubInformationBuffer,
1089 ULONG HubInformationBufferLength,
1090 PULONG LengthOfDataReturned)
1092 PUSB_EXTHUB_INFORMATION_0 hib = HubInformationBuffer;
1093 ULONG i;
1095 UNREFERENCED_PARAMETER(BusContext);
1096 UNREFERENCED_PARAMETER(HubPhysicalDeviceObject);
1098 FUNCTION_ENTER();
1100 KdPrint((__DRIVER_NAME " BusContext = %p\n", BusContext));
1101 KdPrint((__DRIVER_NAME " HubPhysicalDeviceObject = %p\n", HubPhysicalDeviceObject));
1102 KdPrint((__DRIVER_NAME " HubInformationBuffer = %p\n", HubInformationBuffer));
1103 KdPrint((__DRIVER_NAME " HubInformationBufferLength = %d\n", HubInformationBufferLength));
1104 KdPrint((__DRIVER_NAME " ->InformationLevel = %d\n", hib->InformationLevel));
1105 if (HubInformationBufferLength < (ULONG)FIELD_OFFSET(USB_EXTHUB_INFORMATION_0, Port[8]))
1107 KdPrint((__DRIVER_NAME " STATUS_BUFFER_TOO_SMALL\n"));
1108 FUNCTION_EXIT();
1109 return STATUS_BUFFER_TOO_SMALL;
1111 #if 0
1112 if (hib->InformationLevel != 0)
1114 KdPrint((__DRIVER_NAME " STATUS_NOT_SUPPORTED\n"));
1115 FUNCTION_EXIT();
1116 return STATUS_NOT_SUPPORTED;
1118 #endif
1119 hib->InformationLevel = 0;
1120 hib->NumberOfPorts = 8;
1121 for (i = 0; i < hib->NumberOfPorts; i++)
1123 hib->Port[i].PhysicalPortNumber = i + 1;
1124 hib->Port[i].PortLabelNumber = i + 1;
1125 hib->Port[i].VidOverride = 0;
1126 hib->Port[i].PidOverride = 0;
1127 hib->Port[i].PortAttributes = USB_PORTATTR_SHARED_USB2; // | USB_PORTATTR_NO_OVERCURRENT_UI;
1129 *LengthOfDataReturned = FIELD_OFFSET(USB_EXTHUB_INFORMATION_0, Port[8]);
1130 FUNCTION_EXIT();
1131 return STATUS_SUCCESS;
1134 static NTSTATUS
1135 XenUsbHub_UBIH_GetRootHubSymbolicName(
1136 PVOID BusContext,
1137 PVOID HubInformationBuffer,
1138 ULONG HubInformationBufferLength,
1139 PULONG HubNameActualLength)
1141 NTSTATUS status = STATUS_SUCCESS;
1142 FUNCTION_ENTER();
1144 UNREFERENCED_PARAMETER(BusContext);
1146 KdPrint((__DRIVER_NAME " BusContext = %p\n", BusContext));
1147 KdPrint((__DRIVER_NAME " HubInformationBuffer = %p\n", HubInformationBuffer));
1148 KdPrint((__DRIVER_NAME " HubInformationBufferLength = %d\n", HubInformationBufferLength));
1149 RtlStringCbCopyW(HubInformationBuffer, HubInformationBufferLength, L"ROOT_HUB");
1150 *HubNameActualLength = 16;
1152 FUNCTION_EXIT();
1153 return status;
1156 static PVOID
1157 XenUsbHub_UBIH_GetDeviceBusContext(
1158 PVOID BusContext,
1159 PVOID DeviceHandle)
1161 UNREFERENCED_PARAMETER(BusContext);
1162 UNREFERENCED_PARAMETER(DeviceHandle);
1164 FUNCTION_ENTER();
1166 FUNCTION_EXIT();
1167 return NULL;
1170 static NTSTATUS
1171 XenUsbHub_UBIH_Initialize20Hub (
1172 PVOID BusContext,
1173 PUSB_DEVICE_HANDLE HubDeviceHandle,
1174 ULONG TtCount)
1176 NTSTATUS status = STATUS_SUCCESS;
1178 UNREFERENCED_PARAMETER(BusContext);
1179 UNREFERENCED_PARAMETER(HubDeviceHandle);
1180 UNREFERENCED_PARAMETER(TtCount);
1182 FUNCTION_ENTER();
1183 KdPrint((__DRIVER_NAME " BusContext = %p\n", BusContext));
1184 KdPrint((__DRIVER_NAME " HubDeviceHandle = %p\n", HubDeviceHandle));
1185 KdPrint((__DRIVER_NAME " TtCount = %d\n", TtCount));
1186 FUNCTION_EXIT();
1187 return status;
1190 static NTSTATUS
1191 XenUsbHub_UBIH_RootHubInitNotification(
1192 PVOID BusContext,
1193 PVOID CallbackContext,
1194 PRH_INIT_CALLBACK CallbackFunction)
1196 NTSTATUS status = STATUS_SUCCESS;
1197 WDFDEVICE device = BusContext;
1198 PXENUSB_PDO_DEVICE_DATA xupdd = GetXupdd(device);
1200 FUNCTION_ENTER();
1202 xupdd->BusCallbackFunction = CallbackFunction;
1203 xupdd->BusCallbackContext = CallbackContext;
1205 xupdd->BusCallbackFunction(xupdd->BusCallbackContext);
1207 FUNCTION_EXIT();
1208 return status;
1211 /* This definition is incorrect in the docs */
1212 static VOID
1213 XenUsbHub_UBIH_FlushTransfers(
1214 PVOID BusContext,
1215 PVOID DeviceHandle)
1217 UNREFERENCED_PARAMETER(BusContext);
1218 UNREFERENCED_PARAMETER(DeviceHandle);
1220 FUNCTION_ENTER();
1222 FUNCTION_EXIT();
1225 static VOID
1226 XenUsbHub_UBIH_SetDeviceHandleData(
1227 PVOID BusContext,
1228 PUSB_DEVICE_HANDLE DeviceHandle,
1229 PDEVICE_OBJECT UsbDevicePdo)
1231 UNREFERENCED_PARAMETER(BusContext);
1232 UNREFERENCED_PARAMETER(DeviceHandle);
1233 UNREFERENCED_PARAMETER(UsbDevicePdo);
1235 FUNCTION_ENTER();
1236 FUNCTION_EXIT();
1239 static NTSTATUS
1240 XenUsbHub_UBIH_CreateUsbDeviceEx(
1241 PVOID BusContext,
1242 PUSB_DEVICE_HANDLE *DeviceHandle,
1243 PUSB_DEVICE_HANDLE HubDeviceHandle,
1244 USHORT PortStatus,
1245 USHORT PortNumber,
1246 PUSB_CD_ERROR_INFORMATION CdErrorInfo,
1247 USHORT TtPortNumber)
1249 NTSTATUS status = STATUS_SUCCESS;
1251 UNREFERENCED_PARAMETER(CdErrorInfo);
1252 UNREFERENCED_PARAMETER(TtPortNumber);
1254 FUNCTION_ENTER();
1256 status = XenUsbHub_UBIH_CreateUsbDevice(BusContext, DeviceHandle, HubDeviceHandle, PortStatus, PortNumber);
1258 KdPrint((__DRIVER_NAME " CdErrorInfo = %p\n", CdErrorInfo));
1259 KdPrint((__DRIVER_NAME " TtPortNumber = %d\n", TtPortNumber));
1261 FUNCTION_EXIT();
1262 return status;
1265 #if (NTDDI_VERSION >= NTDDI_VISTA)
1266 static NTSTATUS
1267 XenUsbHub_UBIH_CreateUsbDeviceV7(
1268 PVOID BusContext,
1269 PUSB_DEVICE_HANDLE *NewDeviceHandle,
1270 PUSB_DEVICE_HANDLE HsHubDeviceHandle,
1271 USHORT PortStatus,
1272 PUSB_PORT_PATH PortPath,
1273 PUSB_CD_ERROR_INFORMATION CdErrorInfo,
1274 USHORT TtPortNumber,
1275 PDEVICE_OBJECT PdoDeviceObject,
1276 PUNICODE_STRING PhysicalDeviceObjectName)
1278 NTSTATUS status;
1280 UNREFERENCED_PARAMETER(PdoDeviceObject);
1281 UNREFERENCED_PARAMETER(PhysicalDeviceObjectName);
1283 FUNCTION_ENTER();
1284 KdPrint((__DRIVER_NAME " PortPath->PortPathDepth = %d\n", PortPath->PortPathDepth));
1285 KdPrint((__DRIVER_NAME " PortPath->PortPath[%d] = %d\n", PortPath->PortPathDepth - 1));
1286 status = XenUsbHub_UBIH_CreateUsbDeviceEx(BusContext, NewDeviceHandle, &HsHubDeviceHandle, PortStatus, (USHORT)PortPath->PortPath[PortPath->PortPathDepth-1], CdErrorInfo, TtPortNumber);
1287 KdPrint((__DRIVER_NAME " PdoDeviceObject = %p\n", PdoDeviceObject));
1288 KdPrint((__DRIVER_NAME " PhysicalDeviceObjectName = %S\n", PhysicalDeviceObjectName->Buffer));
1289 FUNCTION_EXIT();
1290 return status;
1292 #endif
1294 static NTSTATUS
1295 XenUsbHub_UBIH_InitializeUsbDeviceEx(
1296 PVOID BusContext,
1297 PUSB_DEVICE_HANDLE DeviceHandle,
1298 PUSB_ID_ERROR_INFORMATION IdErrInfo)
1300 NTSTATUS status;
1302 UNREFERENCED_PARAMETER(BusContext);
1303 UNREFERENCED_PARAMETER(DeviceHandle);
1304 UNREFERENCED_PARAMETER(IdErrInfo);
1305 FUNCTION_ENTER();
1306 FUNCTION_MSG("IdErrInfo->Version = %d\n", IdErrInfo->Version);
1307 FUNCTION_MSG("IdErrInfo->PathError = %d\n", IdErrInfo->PathError);
1308 FUNCTION_MSG("IdErrInfo->Arg1 = %08x\n", IdErrInfo->Arg1);
1309 FUNCTION_MSG("IdErrInfo->UsbAddress = %d\n", IdErrInfo->UsbAddress);
1310 FUNCTION_MSG("IdErrInfo->NtStatus = %08x\n", IdErrInfo->NtStatus);
1311 FUNCTION_MSG("IdErrInfo->UsbdStatus = %08x\n", IdErrInfo->UsbdStatus);
1312 FUNCTION_MSG("IdErrInfo->XtraInfo = %s\n", IdErrInfo->XtraInfo);
1313 status = XenUsbHub_UBIH_InitializeUsbDevice(BusContext, DeviceHandle);
1314 FUNCTION_EXIT();
1315 return status;
1318 static BOOLEAN
1319 XenUsbHub_UBIH_HubIsRoot(
1320 PVOID BusContext,
1321 PVOID DeviceObject)
1323 UNREFERENCED_PARAMETER(BusContext);
1324 UNREFERENCED_PARAMETER(DeviceObject);
1326 FUNCTION_ENTER();
1327 FUNCTION_EXIT();
1328 return TRUE;
1331 static VOID
1332 XenUsbHub_UBIH_AcquireBusSemaphore(
1333 PVOID BusContext)
1335 UNREFERENCED_PARAMETER(BusContext);
1336 FUNCTION_ENTER();
1337 FUNCTION_EXIT();
1338 return;
1341 static VOID
1342 XenUsbHub_UBIH_ReleaseBusSemaphore(
1343 PVOID BusContext)
1345 UNREFERENCED_PARAMETER(BusContext);
1346 FUNCTION_ENTER();
1347 FUNCTION_EXIT();
1348 return;
1351 static ULONG
1352 XenUsbHub_UBIH_CaculatePipeBandwidth(
1353 PVOID BusContext,
1354 PUSBD_PIPE_INFORMATION PipeInfo,
1355 USB_DEVICE_SPEED DeviceSpeed)
1357 UNREFERENCED_PARAMETER(BusContext);
1358 UNREFERENCED_PARAMETER(PipeInfo);
1359 UNREFERENCED_PARAMETER(DeviceSpeed);
1360 FUNCTION_ENTER();
1361 FUNCTION_EXIT();
1362 return (ULONG)-1;
1365 static VOID
1366 XenUsbHub_UBIH_SetBusSystemWakeMode(
1367 PVOID BusContext,
1368 ULONG Mode)
1370 UNREFERENCED_PARAMETER(BusContext);
1371 UNREFERENCED_PARAMETER(Mode);
1372 FUNCTION_ENTER();
1373 FUNCTION_EXIT();
1374 return;
1377 static VOID
1378 XenUsbHub_UBIH_SetDeviceFlag(
1379 PVOID BusContext,
1380 GUID *DeviceFlagGuid,
1381 PVOID ValueData,
1382 ULONG ValueLength)
1384 UNREFERENCED_PARAMETER(BusContext);
1385 UNREFERENCED_PARAMETER(DeviceFlagGuid);
1386 UNREFERENCED_PARAMETER(ValueData);
1387 UNREFERENCED_PARAMETER(ValueLength);
1388 FUNCTION_ENTER();
1389 FUNCTION_EXIT();
1390 return;
1393 static NTSTATUS
1394 XenUsbHub_UBIH_HubTestPoint(
1395 PVOID bus_context,
1396 PVOID device_handle,
1397 ULONG op_code,
1398 PVOID test_data)
1400 UNREFERENCED_PARAMETER(bus_context);
1401 UNREFERENCED_PARAMETER(device_handle);
1402 UNREFERENCED_PARAMETER(op_code);
1403 UNREFERENCED_PARAMETER(test_data);
1404 FUNCTION_ENTER();
1405 FUNCTION_MSG("device_handle = %p\n", device_handle);
1406 FUNCTION_MSG("op_code = %p\n", op_code);
1407 FUNCTION_MSG("test_data = %p\n", test_data);
1408 FUNCTION_EXIT();
1409 return STATUS_SUCCESS;
1412 static NTSTATUS
1413 XenUsbHub_UBIH_GetDevicePerformanceInfo(
1414 PVOID BusContext,
1415 PUSB_DEVICE_HANDLE DeviceHandle,
1416 PVOID DeviceInformationBuffer,
1417 ULONG DeviceInformationBufferLength,
1418 PULONG LengthOfDataCopied)
1420 UNREFERENCED_PARAMETER(BusContext);
1421 UNREFERENCED_PARAMETER(DeviceHandle);
1422 UNREFERENCED_PARAMETER(DeviceInformationBuffer);
1423 UNREFERENCED_PARAMETER(DeviceInformationBufferLength);
1424 UNREFERENCED_PARAMETER(LengthOfDataCopied);
1425 FUNCTION_ENTER();
1426 FUNCTION_EXIT();
1427 return STATUS_UNSUCCESSFUL;
1430 static NTSTATUS
1431 XenUsbHub_UBIH_WaitAsyncPowerUp(
1432 PVOID BusContext)
1434 UNREFERENCED_PARAMETER(BusContext);
1435 FUNCTION_ENTER();
1436 FUNCTION_EXIT();
1437 return STATUS_UNSUCCESSFUL;
1440 static NTSTATUS
1441 XenUsbHub_UBIH_GetDeviceAddress(
1442 PVOID BusContext,
1443 PUSB_DEVICE_HANDLE DeviceHandle,
1444 PUSHORT DeviceAddress)
1446 UNREFERENCED_PARAMETER(BusContext);
1447 UNREFERENCED_PARAMETER(DeviceHandle);
1448 UNREFERENCED_PARAMETER(DeviceAddress);
1449 FUNCTION_ENTER();
1450 FUNCTION_EXIT();
1451 return STATUS_UNSUCCESSFUL;
1454 static NTSTATUS
1455 XenUsbHub_UBIH_RefDeviceHandle(
1456 PVOID BusContext,
1457 PUSB_DEVICE_HANDLE DeviceHandle,
1458 PVOID Object,
1459 ULONG Tag)
1461 UNREFERENCED_PARAMETER(BusContext);
1462 UNREFERENCED_PARAMETER(DeviceHandle);
1463 UNREFERENCED_PARAMETER(Object);
1464 UNREFERENCED_PARAMETER(Tag);
1465 FUNCTION_ENTER();
1466 FUNCTION_MSG("This should do something\n");
1467 FUNCTION_EXIT();
1468 return STATUS_SUCCESS;
1471 static VOID
1472 XenUsbHub_UBIH_DerefDeviceHandle(
1473 PVOID BusContext,
1474 PUSB_DEVICE_HANDLE DeviceHandle,
1475 PVOID Object,
1476 ULONG Tag)
1478 UNREFERENCED_PARAMETER(BusContext);
1479 UNREFERENCED_PARAMETER(DeviceHandle);
1480 UNREFERENCED_PARAMETER(Object);
1481 UNREFERENCED_PARAMETER(Tag);
1482 FUNCTION_ENTER();
1483 FUNCTION_MSG("This should do something\n");
1484 FUNCTION_EXIT();
1487 static ULONG
1488 XenUsbHub_UBIH_SetDeviceHandleIdleReadyState(
1489 PVOID BusContext,
1490 PUSB_DEVICE_HANDLE DeviceHandle,
1491 ULONG NewIdleReadyState)
1493 UNREFERENCED_PARAMETER(BusContext);
1494 UNREFERENCED_PARAMETER(DeviceHandle);
1495 UNREFERENCED_PARAMETER(NewIdleReadyState);
1496 FUNCTION_ENTER();
1497 FUNCTION_EXIT();
1498 return (ULONG)-1;
1501 static NTSTATUS
1502 XenUsbHub_UBIH_GetContainerIdForPort(
1503 PVOID BusContext,
1504 USHORT PortNumber,
1505 LPGUID ContainerId)
1507 UNREFERENCED_PARAMETER(BusContext);
1508 UNREFERENCED_PARAMETER(PortNumber);
1509 UNREFERENCED_PARAMETER(ContainerId);
1510 FUNCTION_ENTER();
1511 FUNCTION_EXIT();
1512 return STATUS_UNSUCCESSFUL;
1515 static VOID
1516 XenUsbHub_UBIH_SetContainerIdForPort(
1517 PVOID BusContext,
1518 USHORT PortNumber,
1519 LPGUID ContainerId)
1521 UNREFERENCED_PARAMETER(BusContext);
1522 UNREFERENCED_PARAMETER(PortNumber);
1523 UNREFERENCED_PARAMETER(ContainerId);
1524 FUNCTION_ENTER();
1525 FUNCTION_EXIT();
1528 static NTSTATUS
1529 XenUsbHub_UBIH_AbortAllDevicePipes(
1530 PVOID BusContext,
1531 PUSB_DEVICE_HANDLE DeviceHandle)
1533 UNREFERENCED_PARAMETER(BusContext);
1534 UNREFERENCED_PARAMETER(DeviceHandle);
1535 FUNCTION_ENTER();
1536 FUNCTION_EXIT();
1537 return STATUS_SUCCESS;
1540 static VOID
1541 XenUsbHub_UBIH_SetDeviceErrataFlag(
1542 PVOID BusContext,
1543 PUSB_DEVICE_HANDLE DeviceHandle,
1544 ULONG DeviceErrataFlag)
1546 UNREFERENCED_PARAMETER(BusContext);
1547 UNREFERENCED_PARAMETER(DeviceHandle);
1548 UNREFERENCED_PARAMETER(DeviceErrataFlag);
1549 FUNCTION_ENTER();
1550 FUNCTION_EXIT();
1551 return;
1554 static NTSTATUS
1555 XenUsbHub_UBIU_GetUSBDIVersion(
1556 PVOID BusContext,
1557 PUSBD_VERSION_INFORMATION VersionInformation,
1558 PULONG HcdCapabilities
1561 NTSTATUS status = STATUS_UNSUCCESSFUL;
1563 UNREFERENCED_PARAMETER(BusContext);
1564 UNREFERENCED_PARAMETER(VersionInformation);
1565 UNREFERENCED_PARAMETER(HcdCapabilities);
1567 FUNCTION_ENTER();
1569 FUNCTION_EXIT();
1570 return status;
1573 static NTSTATUS
1574 XenUsbHub_UBIU_QueryBusTime(
1575 PVOID BusContext,
1576 PULONG CurrentFrame
1579 NTSTATUS status = STATUS_SUCCESS;
1580 static ULONG frame_no = 0;
1582 UNREFERENCED_PARAMETER(BusContext);
1583 UNREFERENCED_PARAMETER(CurrentFrame);
1585 //FUNCTION_ENTER();
1586 *CurrentFrame = frame_no++;
1587 //FUNCTION_EXIT();
1588 return status;
1591 static NTSTATUS
1592 XenUsbHub_UBIU_SubmitIsoOutUrb(
1593 PVOID BusContext,
1594 PURB Urb
1597 NTSTATUS status = STATUS_UNSUCCESSFUL;
1599 UNREFERENCED_PARAMETER(BusContext);
1600 UNREFERENCED_PARAMETER(Urb);
1602 FUNCTION_ENTER();
1604 FUNCTION_EXIT();
1605 return status;
1608 static NTSTATUS
1609 XenUsbHub_UBIU_QueryBusInformation(
1610 PVOID BusContext,
1611 ULONG Level,
1612 PVOID BusInformationBuffer,
1613 PULONG BusInformationBufferLength,
1614 PULONG BusInformationActualLength)
1616 NTSTATUS status = STATUS_UNSUCCESSFUL;
1618 UNREFERENCED_PARAMETER(BusContext);
1619 UNREFERENCED_PARAMETER(Level);
1620 UNREFERENCED_PARAMETER(BusInformationBuffer);
1621 UNREFERENCED_PARAMETER(BusInformationBufferLength);
1622 UNREFERENCED_PARAMETER(BusInformationActualLength);
1624 FUNCTION_ENTER();
1626 FUNCTION_EXIT();
1627 return status;
1630 static BOOLEAN
1631 XenUsbHub_UBIU_IsDeviceHighSpeed(PVOID BusContext)
1633 UNREFERENCED_PARAMETER(BusContext);
1635 FUNCTION_ENTER();
1637 FUNCTION_EXIT();
1638 return TRUE; //TODO: get port value
1641 static NTSTATUS
1642 XenUsbHub_UBIU_EnumLogEntry(
1643 PVOID BusContext,
1644 ULONG DriverTag,
1645 ULONG EnumTag,
1646 ULONG P1,
1647 ULONG P2
1650 NTSTATUS status = STATUS_SUCCESS;
1651 FUNCTION_ENTER();
1653 UNREFERENCED_PARAMETER(BusContext);
1654 UNREFERENCED_PARAMETER(DriverTag);
1655 UNREFERENCED_PARAMETER(EnumTag);
1656 UNREFERENCED_PARAMETER(P1);
1657 UNREFERENCED_PARAMETER(P2);
1659 KdPrint((__DRIVER_NAME " DriverTag = %08x\n", DriverTag));
1660 KdPrint((__DRIVER_NAME " EnumTag = %08x\n", EnumTag));
1661 KdPrint((__DRIVER_NAME " P1 = %08x\n", P1));
1662 KdPrint((__DRIVER_NAME " P2 = %08x\n", P2));
1664 FUNCTION_EXIT();
1665 return status;
1668 static NTSTATUS
1669 XenUsbHub_UBIU_QueryBusTimeEx(
1670 PVOID BusContext,
1671 PULONG HighSpeedFrameCounter)
1673 UNREFERENCED_PARAMETER(BusContext);
1674 UNREFERENCED_PARAMETER(HighSpeedFrameCounter);
1675 FUNCTION_ENTER();
1676 FUNCTION_EXIT();
1677 return STATUS_UNSUCCESSFUL;
1680 static NTSTATUS
1681 XenUsbHub_UBIU_QueryControllerType(
1682 PVOID BusContext,
1683 PULONG HcdiOptionFlags,
1684 PUSHORT PciVendorId,
1685 PUSHORT PciDeviceId,
1686 PUCHAR PciClass,
1687 PUCHAR PciSubClass,
1688 PUCHAR PciRevisionId,
1689 PUCHAR PciProgIf)
1691 UNREFERENCED_PARAMETER(BusContext);
1692 UNREFERENCED_PARAMETER(HcdiOptionFlags);
1693 UNREFERENCED_PARAMETER(PciVendorId);
1694 UNREFERENCED_PARAMETER(PciDeviceId);
1695 UNREFERENCED_PARAMETER(PciClass);
1696 UNREFERENCED_PARAMETER(PciSubClass);
1697 UNREFERENCED_PARAMETER(PciRevisionId);
1698 UNREFERENCED_PARAMETER(PciProgIf);
1699 FUNCTION_ENTER();
1700 FUNCTION_EXIT();
1701 return STATUS_UNSUCCESSFUL;
1704 static NTSTATUS
1705 XenUsbHub_UBIHSS_SuspendHub(
1706 PVOID BusContext)
1708 UNREFERENCED_PARAMETER(BusContext);
1709 FUNCTION_ENTER();
1710 FUNCTION_EXIT();
1711 return STATUS_SUCCESS;
1714 static NTSTATUS
1715 XenUsbHub_UBIHSS_ResumeHub(
1716 PVOID BusContext)
1718 UNREFERENCED_PARAMETER(BusContext);
1719 FUNCTION_ENTER();
1720 FUNCTION_EXIT();
1721 return STATUS_SUCCESS;
1724 VOID
1725 XenUsbHub_ProcessHubInterruptEvent(xenusb_endpoint_t *endpoint)
1727 NTSTATUS status;
1728 WDFDEVICE pdo_device = endpoint->interface->config->device->pdo_device;
1729 PXENUSB_PDO_DEVICE_DATA xupdd = GetXupdd(pdo_device);
1730 PXENUSB_DEVICE_DATA xudd = GetXudd(xupdd->wdf_device_bus_fdo);
1731 WDF_REQUEST_PARAMETERS wrp;
1732 WDFREQUEST request;
1733 PURB urb;
1734 ULONG i;
1735 BOOLEAN port_change_flag = FALSE;
1737 FUNCTION_ENTER();
1738 WdfSpinLockAcquire(endpoint->lock);
1739 status = WdfIoQueueRetrieveNextRequest(endpoint->queue, &request);
1740 if (status == STATUS_NO_MORE_ENTRIES)
1742 WdfSpinLockRelease(endpoint->lock);
1743 KdPrint((__DRIVER_NAME " No More Entries\n", status));
1744 FUNCTION_EXIT();
1745 return;
1747 if (!NT_SUCCESS(status))
1749 WdfSpinLockRelease(endpoint->lock);
1750 KdPrint((__DRIVER_NAME " Failed to get request from queue %08x\n", status));
1751 FUNCTION_EXIT();
1752 return;
1755 WDF_REQUEST_PARAMETERS_INIT(&wrp);
1756 WdfRequestGetParameters(request, &wrp);
1758 urb = (PURB)wrp.Parameters.Others.Arg1;
1759 ASSERT(urb);
1760 ASSERT(urb->UrbHeader.Function == URB_FUNCTION_BULK_OR_INTERRUPT_TRANSFER);
1761 RtlZeroMemory(urb->UrbBulkOrInterruptTransfer.TransferBuffer, urb->UrbBulkOrInterruptTransfer.TransferBufferLength);
1763 for (i = 0; i < xudd->num_ports; i++)
1765 FUNCTION_MSG("port %d - status = %04x, change = %04x\n", xudd->ports[i].port_number, xudd->ports[i].port_status, xudd->ports[i].port_change);
1766 if (xudd->ports[i].port_change) {
1767 FUNCTION_MSG("Port change on port %d - status = %04x, change = %04x\n",
1768 xudd->ports[i].port_number, xudd->ports[i].port_status, xudd->ports[i].port_change);
1769 ((PUCHAR)urb->UrbBulkOrInterruptTransfer.TransferBuffer)[xudd->ports[i].port_number >> 3] |= 1 << (xudd->ports[i].port_number & 7);
1770 port_change_flag = TRUE;
1772 FUNCTION_MSG("port %d - status = %04x, change = %04x\n", xudd->ports[i].port_number, xudd->ports[i].port_status, xudd->ports[i].port_change);
1774 WdfSpinLockRelease(endpoint->lock);
1775 if (port_change_flag)
1777 FUNCTION_MSG("Completing request %p\n", request);
1778 urb->UrbHeader.Status = USBD_STATUS_SUCCESS;
1779 WdfRequestComplete(request, STATUS_SUCCESS);
1781 else
1783 FUNCTION_MSG("Requeuing request %p\n", request);
1784 WdfRequestRequeue(request);
1786 FUNCTION_EXIT();
1787 return;
1790 static NTSTATUS
1791 XenUsbHub_EvtDeviceWdmIrpPreprocessQUERY_INTERFACE(WDFDEVICE device, PIRP irp)
1793 PIO_STACK_LOCATION stack;
1794 union {
1795 USB_BUS_INTERFACE_HUB_V5 ubih5;
1796 #if (NTDDI_VERSION >= NTDDI_VISTA)
1797 USB_BUS_INTERFACE_HUB_V7 ubih6;
1798 USB_BUS_INTERFACE_HUB_V7 ubih7;
1799 #endif
1800 } *ubih;
1801 union {
1802 USB_BUS_INTERFACE_USBDI_V1 ubiu0;
1803 USB_BUS_INTERFACE_USBDI_V1 ubiu1;
1804 USB_BUS_INTERFACE_USBDI_V2 ubiu2;
1805 #if (NTDDI_VERSION >= NTDDI_VISTA)
1806 USB_BUS_INTERFACE_USBDI_V3 ubiu3;
1807 #endif
1808 } *ubiu;
1810 FUNCTION_ENTER();
1812 stack = IoGetCurrentIrpStackLocation(irp);
1814 if (memcmp(stack->Parameters.QueryInterface.InterfaceType, &USB_BUS_INTERFACE_HUB_GUID, sizeof(GUID)) == 0)
1816 KdPrint((__DRIVER_NAME " USB_BUS_INTERFACE_HUB_GUID\n"));
1817 if ((stack->Parameters.QueryInterface.Version == USB_BUSIF_HUB_VERSION_5 && stack->Parameters.QueryInterface.Size == sizeof(USB_BUS_INTERFACE_HUB_V5))
1818 #if (NTDDI_VERSION >= NTDDI_VISTA)
1819 || (stack->Parameters.QueryInterface.Version == USB_BUSIF_HUB_VERSION_6 && stack->Parameters.QueryInterface.Size == sizeof(USB_BUS_INTERFACE_HUB_V6))
1820 || (stack->Parameters.QueryInterface.Version == USB_BUSIF_HUB_VERSION_7 && stack->Parameters.QueryInterface.Size == sizeof(USB_BUS_INTERFACE_HUB_V7))
1821 #endif
1824 ubih = (PVOID)stack->Parameters.QueryInterface.Interface;
1825 ubih->ubih5.Size = stack->Parameters.QueryInterface.Size;
1826 ubih->ubih5.Version = stack->Parameters.QueryInterface.Version;
1827 ubih->ubih5.BusContext = device;
1828 ubih->ubih5.InterfaceReference = WdfDeviceInterfaceReferenceNoOp;
1829 ubih->ubih5.InterfaceDereference = WdfDeviceInterfaceDereferenceNoOp;
1830 /* these two were changed to the Ex functions in v6 so we set them here so they don't get overwritten */
1831 ubih->ubih5.CreateUsbDevice = XenUsbHub_UBIH_CreateUsbDevice;
1832 ubih->ubih5.InitializeUsbDevice = XenUsbHub_UBIH_InitializeUsbDevice;
1833 switch (stack->Parameters.QueryInterface.Version)
1835 #if (NTDDI_VERSION >= NTDDI_VISTA)
1836 case USB_BUSIF_HUB_VERSION_7:
1837 ubih->ubih7.HubTestPoint = XenUsbHub_UBIH_HubTestPoint;
1838 ubih->ubih7.GetDevicePerformanceInfo = XenUsbHub_UBIH_GetDevicePerformanceInfo;
1839 ubih->ubih7.WaitAsyncPowerUp = XenUsbHub_UBIH_WaitAsyncPowerUp;
1840 ubih->ubih7.GetDeviceAddress = XenUsbHub_UBIH_GetDeviceAddress;
1841 ubih->ubih7.RefDeviceHandle = XenUsbHub_UBIH_RefDeviceHandle;
1842 ubih->ubih7.DerefDeviceHandle = XenUsbHub_UBIH_DerefDeviceHandle;
1843 ubih->ubih7.SetDeviceHandleIdleReadyState = XenUsbHub_UBIH_SetDeviceHandleIdleReadyState;
1844 ubih->ubih7.CreateUsbDeviceV7 = XenUsbHub_UBIH_CreateUsbDeviceV7;
1845 ubih->ubih7.GetContainerIdForPort = XenUsbHub_UBIH_GetContainerIdForPort;
1846 ubih->ubih7.SetContainerIdForPort = XenUsbHub_UBIH_SetContainerIdForPort;
1847 ubih->ubih7.AbortAllDevicePipes = XenUsbHub_UBIH_AbortAllDevicePipes;
1848 ubih->ubih7.SetDeviceErrataFlag = XenUsbHub_UBIH_SetDeviceErrataFlag;
1849 /* fall through */
1850 case USB_BUSIF_HUB_VERSION_6:
1851 ubih->ubih6.CreateUsbDevice = XenUsbHub_UBIH_CreateUsbDeviceEx;
1852 ubih->ubih6.InitializeUsbDevice = XenUsbHub_UBIH_InitializeUsbDeviceEx;
1853 ubih->ubih6.HubIsRoot = XenUsbHub_UBIH_HubIsRoot;
1854 ubih->ubih6.AcquireBusSemaphore = XenUsbHub_UBIH_AcquireBusSemaphore;
1855 ubih->ubih6.ReleaseBusSemaphore = XenUsbHub_UBIH_ReleaseBusSemaphore;
1856 ubih->ubih6.CaculatePipeBandwidth = XenUsbHub_UBIH_CaculatePipeBandwidth;
1857 ubih->ubih6.SetBusSystemWakeMode = XenUsbHub_UBIH_SetBusSystemWakeMode;
1858 ubih->ubih6.SetDeviceFlag = XenUsbHub_UBIH_SetDeviceFlag;
1859 /* fall through */
1860 #endif
1861 case USB_BUSIF_HUB_VERSION_5:
1862 ubih->ubih5.GetUsbDescriptors = XenUsbHub_UBIH_GetUsbDescriptors;
1863 ubih->ubih5.RemoveUsbDevice = XenUsbHub_UBIH_RemoveUsbDevice;
1864 ubih->ubih5.RestoreUsbDevice = XenUsbHub_UBIH_RestoreUsbDevice;
1865 ubih->ubih5.GetPortHackFlags = XenUsbHub_UBIH_GetPortHackFlags;
1866 ubih->ubih5.QueryDeviceInformation = XenUsbHub_UBIH_QueryDeviceInformation;
1867 ubih->ubih5.GetControllerInformation = XenUsbHub_UBIH_GetControllerInformation;
1868 ubih->ubih5.ControllerSelectiveSuspend = XenUsbHub_UBIH_ControllerSelectiveSuspend;
1869 ubih->ubih5.GetExtendedHubInformation = XenUsbHub_UBIH_GetExtendedHubInformation;
1870 ubih->ubih5.GetRootHubSymbolicName = XenUsbHub_UBIH_GetRootHubSymbolicName;
1871 ubih->ubih5.GetDeviceBusContext = XenUsbHub_UBIH_GetDeviceBusContext;
1872 ubih->ubih5.Initialize20Hub = XenUsbHub_UBIH_Initialize20Hub;
1873 ubih->ubih5.RootHubInitNotification = XenUsbHub_UBIH_RootHubInitNotification;
1874 ubih->ubih5.FlushTransfers = XenUsbHub_UBIH_FlushTransfers;
1875 ubih->ubih5.SetDeviceHandleData = XenUsbHub_UBIH_SetDeviceHandleData;
1877 irp->IoStatus.Information = 0;
1878 irp->IoStatus.Status = STATUS_SUCCESS;
1880 else
1882 KdPrint((__DRIVER_NAME " size/version mismatch\n"));
1885 else if (memcmp(stack->Parameters.QueryInterface.InterfaceType, &USB_BUS_INTERFACE_USBDI_GUID, sizeof(GUID)) == 0)
1887 KdPrint((__DRIVER_NAME " USB_BUS_INTERFACE_USBDI_GUID\n"));
1888 if ((stack->Parameters.QueryInterface.Version == USB_BUSIF_USBDI_VERSION_0 && stack->Parameters.QueryInterface.Size == sizeof(USB_BUS_INTERFACE_USBDI_V0))
1889 || (stack->Parameters.QueryInterface.Version == USB_BUSIF_USBDI_VERSION_1 && stack->Parameters.QueryInterface.Size == sizeof(USB_BUS_INTERFACE_USBDI_V1))
1890 || (stack->Parameters.QueryInterface.Version == USB_BUSIF_USBDI_VERSION_2 && stack->Parameters.QueryInterface.Size == sizeof(USB_BUS_INTERFACE_USBDI_V2))
1891 #if (NTDDI_VERSION >= NTDDI_VISTA)
1892 || (stack->Parameters.QueryInterface.Version == USB_BUSIF_USBDI_VERSION_3 && stack->Parameters.QueryInterface.Size == sizeof(USB_BUS_INTERFACE_USBDI_V3))
1893 #endif
1896 ubiu = (PVOID)stack->Parameters.QueryInterface.Interface;
1897 ubiu->ubiu0.Size = stack->Parameters.QueryInterface.Size;
1898 ubiu->ubiu0.Version = stack->Parameters.QueryInterface.Version;
1899 ubiu->ubiu0.BusContext = device;
1900 ubiu->ubiu0.InterfaceReference = WdfDeviceInterfaceReferenceNoOp;
1901 ubiu->ubiu0.InterfaceDereference = WdfDeviceInterfaceDereferenceNoOp;
1902 switch (stack->Parameters.QueryInterface.Version)
1904 #if (NTDDI_VERSION >= NTDDI_VISTA)
1905 case USB_BUSIF_USBDI_VERSION_3:
1906 ubiu->ubiu3.QueryBusTimeEx = XenUsbHub_UBIU_QueryBusTimeEx;
1907 ubiu->ubiu3.QueryControllerType = XenUsbHub_UBIU_QueryControllerType;
1908 /* fall through */
1909 #endif
1910 case USB_BUSIF_USBDI_VERSION_2:
1911 ubiu->ubiu2.EnumLogEntry = XenUsbHub_UBIU_EnumLogEntry;
1912 /* fall through */
1913 case USB_BUSIF_USBDI_VERSION_1:
1914 ubiu->ubiu1.IsDeviceHighSpeed = XenUsbHub_UBIU_IsDeviceHighSpeed;
1915 /* fall through */
1916 case USB_BUSIF_USBDI_VERSION_0:
1917 ubiu->ubiu0.GetUSBDIVersion = XenUsbHub_UBIU_GetUSBDIVersion;
1918 ubiu->ubiu0.QueryBusTime = XenUsbHub_UBIU_QueryBusTime;
1919 ubiu->ubiu0.SubmitIsoOutUrb = XenUsbHub_UBIU_SubmitIsoOutUrb;
1920 ubiu->ubiu0.QueryBusInformation = XenUsbHub_UBIU_QueryBusInformation;
1922 irp->IoStatus.Information = 0;
1923 irp->IoStatus.Status = STATUS_SUCCESS;
1925 else
1927 KdPrint((__DRIVER_NAME " size/version mismatch\n"));
1930 else if (memcmp(stack->Parameters.QueryInterface.InterfaceType, &GUID_TRANSLATOR_INTERFACE_STANDARD, sizeof(GUID)) == 0)
1931 KdPrint((__DRIVER_NAME " GUID_TRANSLATOR_INTERFACE_STANDARD\n"));
1932 #if (NTDDI_VERSION >= NTDDI_VISTA)
1933 else if (memcmp(stack->Parameters.QueryInterface.InterfaceType, &GUID_PNP_LOCATION_INTERFACE, sizeof(GUID)) == 0)
1934 KdPrint((__DRIVER_NAME " GUID_PNP_LOCATION_INTERFACE\n"));
1935 #endif
1936 else if (memcmp(stack->Parameters.QueryInterface.InterfaceType, &USB_BUS_INTERFACE_HUB_MINIDUMP_GUID, sizeof(GUID)) == 0)
1937 KdPrint((__DRIVER_NAME " USB_BUS_INTERFACE_HUB_MINIDUMP_GUID\n"));
1938 else if (memcmp(stack->Parameters.QueryInterface.InterfaceType, &USB_BUS_INTERFACE_HUB_SS_GUID, sizeof(GUID)) == 0)
1939 KdPrint((__DRIVER_NAME " USB_BUS_INTERFACE_HUB_SS_GUID\n"));
1940 else
1941 KdPrint((__DRIVER_NAME " GUID = %08X-%04X-%04X-%04X-%02X%02X%02X%02X%02X%02X\n",
1942 stack->Parameters.QueryInterface.InterfaceType->Data1,
1943 stack->Parameters.QueryInterface.InterfaceType->Data2,
1944 stack->Parameters.QueryInterface.InterfaceType->Data3,
1945 (stack->Parameters.QueryInterface.InterfaceType->Data4[0] << 8) |
1946 stack->Parameters.QueryInterface.InterfaceType->Data4[1],
1947 stack->Parameters.QueryInterface.InterfaceType->Data4[2],
1948 stack->Parameters.QueryInterface.InterfaceType->Data4[3],
1949 stack->Parameters.QueryInterface.InterfaceType->Data4[4],
1950 stack->Parameters.QueryInterface.InterfaceType->Data4[5],
1951 stack->Parameters.QueryInterface.InterfaceType->Data4[6],
1952 stack->Parameters.QueryInterface.InterfaceType->Data4[7]));
1954 KdPrint((__DRIVER_NAME " Size = %d\n", stack->Parameters.QueryInterface.Size));
1955 KdPrint((__DRIVER_NAME " Version = %d\n", stack->Parameters.QueryInterface.Version));
1956 KdPrint((__DRIVER_NAME " Interface = %p\n", stack->Parameters.QueryInterface.Interface));
1958 IoSkipCurrentIrpStackLocation(irp);
1960 FUNCTION_EXIT();
1962 return WdfDeviceWdmDispatchPreprocessedIrp(device, irp);
1965 NTSTATUS
1966 XenUsbHub_PLI_GetLocationString(PVOID context, PWCHAR *location_strings) {
1967 UNREFERENCED_PARAMETER(context);
1969 FUNCTION_ENTER();
1970 *location_strings = L"james\0";
1971 FUNCTION_EXIT();
1972 return STATUS_SUCCESS;
1975 NTSTATUS
1976 XenUsb_EvtChildListCreateDevice(WDFCHILDLIST child_list,
1977 PWDF_CHILD_IDENTIFICATION_DESCRIPTION_HEADER identification_header,
1978 PWDFDEVICE_INIT child_init)
1980 NTSTATUS status = STATUS_SUCCESS;
1981 WDFDEVICE bus_device = WdfChildListGetDevice(child_list);
1982 WDF_OBJECT_ATTRIBUTES child_attributes;
1983 WDFDEVICE child_device;
1984 PXENUSB_PDO_IDENTIFICATION_DESCRIPTION identification = (PXENUSB_PDO_IDENTIFICATION_DESCRIPTION)identification_header;
1985 WDF_DEVICE_PNP_CAPABILITIES child_pnp_capabilities;
1986 DECLARE_UNICODE_STRING_SIZE(buffer, 512);
1987 DECLARE_CONST_UNICODE_STRING(location, L"Xen Bus");
1988 PXENUSB_PDO_DEVICE_DATA xupdd;
1989 PXENUSB_DEVICE_DATA xudd = GetXudd(bus_device);
1990 WDF_PNPPOWER_EVENT_CALLBACKS child_pnp_power_callbacks;
1991 WDF_DEVICE_POWER_CAPABILITIES child_power_capabilities;
1992 WDF_IO_QUEUE_CONFIG queue_config;
1993 WDF_IO_TARGET_OPEN_PARAMS target_params;
1994 #if (NTDDI_VERSION >= NTDDI_VISTA)
1995 WDF_QUERY_INTERFACE_CONFIG interface_config;
1996 #if 0
1997 USB_BUS_INTERFACE_HUB_SELECTIVE_SUSPEND ubihss;
1998 #endif
1999 PNP_LOCATION_INTERFACE pli;
2000 #endif
2001 UCHAR pnp_minor_functions[] = { IRP_MN_QUERY_INTERFACE };
2003 FUNCTION_ENTER();
2005 //KdPrint((__DRIVER_NAME " device = %d, port = %d, vendor_id = %04x, product_id = %04x\n",
2007 WdfDeviceInitSetDeviceType(child_init, FILE_DEVICE_UNKNOWN);
2009 status = WdfDeviceInitAssignWdmIrpPreprocessCallback(child_init, XenUsbHub_EvtDeviceWdmIrpPreprocessQUERY_INTERFACE,
2010 IRP_MJ_PNP, pnp_minor_functions, ARRAY_SIZE(pnp_minor_functions));
2011 if (!NT_SUCCESS(status))
2013 return status;
2016 WDF_PNPPOWER_EVENT_CALLBACKS_INIT(&child_pnp_power_callbacks);
2017 child_pnp_power_callbacks.EvtDeviceD0Entry = XenUsbHub_EvtDeviceD0Entry;
2018 child_pnp_power_callbacks.EvtDeviceD0Exit = XenUsbHub_EvtDeviceD0Exit;
2019 child_pnp_power_callbacks.EvtDevicePrepareHardware = XenUsbHub_EvtDevicePrepareHardware;
2020 child_pnp_power_callbacks.EvtDeviceReleaseHardware = XenUsbHub_EvtDeviceReleaseHardware;
2021 child_pnp_power_callbacks.EvtDeviceUsageNotification = XenUsbHub_EvtDeviceUsageNotification;
2022 WdfDeviceInitSetPnpPowerEventCallbacks(child_init, &child_pnp_power_callbacks);
2024 RtlUnicodeStringPrintf(&buffer, L"USB\\ROOT_HUB");
2025 status = WdfPdoInitAssignDeviceID(child_init, &buffer);
2026 status = WdfPdoInitAddHardwareID(child_init, &buffer);
2028 RtlUnicodeStringPrintf(&buffer, L"VUSB_%d", identification->device_number);
2029 status = WdfPdoInitAssignInstanceID(child_init, &buffer);
2030 if (!NT_SUCCESS(status))
2032 return status;
2035 RtlUnicodeStringPrintf(&buffer, L"PVUSB device #%d", identification->device_number, identification);
2036 status = WdfPdoInitAddDeviceText(child_init, &buffer, &location, 0x0409);
2037 if (!NT_SUCCESS(status))
2039 return status;
2041 WdfPdoInitSetDefaultLocale(child_init, 0x0409);
2043 WdfDeviceInitSetPowerNotPageable(child_init);
2045 WdfDeviceInitSetIoType(child_init, WdfDeviceIoDirect);
2047 WdfPdoInitAllowForwardingRequestToParent(child_init);
2049 WDF_OBJECT_ATTRIBUTES_INIT_CONTEXT_TYPE(&child_attributes, XENUSB_PDO_DEVICE_DATA);
2050 status = WdfDeviceCreate(&child_init, &child_attributes, &child_device);
2051 if (!NT_SUCCESS(status))
2053 return status;
2056 xupdd = GetXupdd(child_device);
2058 xudd->root_hub_device = child_device;
2060 xupdd->wdf_device = child_device;
2061 xupdd->wdf_device_bus_fdo = WdfChildListGetDevice(child_list);
2063 status = WdfIoTargetCreate(bus_device, WDF_NO_OBJECT_ATTRIBUTES, &xupdd->bus_fdo_target);
2064 ASSERT(NT_SUCCESS(status));
2065 WDF_IO_TARGET_OPEN_PARAMS_INIT_EXISTING_DEVICE(&target_params, WdfDeviceWdmGetDeviceObject(bus_device));
2066 status = WdfIoTargetOpen(xupdd->bus_fdo_target, &target_params);
2067 ASSERT(NT_SUCCESS(status));
2069 xupdd->usb_device = ExAllocatePoolWithTag(NonPagedPool, sizeof(xenusb_device_t), XENUSB_POOL_TAG);
2070 // get address from freelist...
2071 xupdd->usb_device->pdo_device = child_device;
2072 xupdd->usb_device->address = 1;
2073 xupdd->usb_device->device_speed = UsbHighSpeed;
2074 xupdd->usb_device->device_type = Usb20Device;
2075 xupdd->usb_device->device_descriptor.bLength = sizeof(USB_DEVICE_DESCRIPTOR);
2076 xupdd->usb_device->device_descriptor.bDescriptorType = USB_DEVICE_DESCRIPTOR_TYPE;
2077 xupdd->usb_device->device_descriptor.bcdUSB = 0x0200;
2078 xupdd->usb_device->device_descriptor.bDeviceClass = 9;
2079 xupdd->usb_device->device_descriptor.bDeviceSubClass = 0;
2080 xupdd->usb_device->device_descriptor.bDeviceProtocol = 1;
2081 xupdd->usb_device->device_descriptor.bMaxPacketSize0 = 64;
2082 xupdd->usb_device->device_descriptor.idVendor = 0x0000;
2083 xupdd->usb_device->device_descriptor.idProduct = 0x0000;
2084 xupdd->usb_device->device_descriptor.bcdDevice = 0x0206;
2085 xupdd->usb_device->device_descriptor.iManufacturer = 3;
2086 xupdd->usb_device->device_descriptor.iProduct = 2;
2087 xupdd->usb_device->device_descriptor.iSerialNumber = 1;
2088 xupdd->usb_device->device_descriptor.bNumConfigurations = 1;
2089 xupdd->usb_device->configs = ExAllocatePoolWithTag(NonPagedPool, sizeof(PVOID) * 1, XENUSB_POOL_TAG);
2090 xupdd->usb_device->configs[0] = ExAllocatePoolWithTag(NonPagedPool, sizeof(xenusb_config_t) + sizeof(PVOID) * 1, XENUSB_POOL_TAG);
2091 xupdd->usb_device->active_config = xupdd->usb_device->configs[0];
2092 xupdd->usb_device->configs[0]->device = xupdd->usb_device;
2093 xupdd->usb_device->configs[0]->config_descriptor.bLength = sizeof(USB_CONFIGURATION_DESCRIPTOR);
2094 xupdd->usb_device->configs[0]->config_descriptor.bDescriptorType = USB_CONFIGURATION_DESCRIPTOR_TYPE;
2095 xupdd->usb_device->configs[0]->config_descriptor.wTotalLength = sizeof(USB_CONFIGURATION_DESCRIPTOR);
2096 xupdd->usb_device->configs[0]->config_descriptor.bNumInterfaces = 1;
2097 xupdd->usb_device->configs[0]->config_descriptor.bConfigurationValue = 1;
2098 xupdd->usb_device->configs[0]->config_descriptor.iConfiguration = 0;
2099 xupdd->usb_device->configs[0]->config_descriptor.bmAttributes = 0xe0;
2100 xupdd->usb_device->configs[0]->config_descriptor.MaxPower = 0;
2101 xupdd->usb_device->configs[0]->interfaces[0] = ExAllocatePoolWithTag(NonPagedPool, sizeof(xenusb_interface_t) + sizeof(PVOID) * 1, XENUSB_POOL_TAG);
2102 xupdd->usb_device->active_interface = xupdd->usb_device->configs[0]->interfaces[0];
2103 xupdd->usb_device->configs[0]->interfaces[0]->config = xupdd->usb_device->configs[0];
2104 xupdd->usb_device->configs[0]->interfaces[0]->interface_descriptor.bLength = 9;
2105 xupdd->usb_device->configs[0]->interfaces[0]->interface_descriptor.bDescriptorType = USB_INTERFACE_DESCRIPTOR_TYPE;
2106 xupdd->usb_device->configs[0]->interfaces[0]->interface_descriptor.bInterfaceNumber = 0;
2107 xupdd->usb_device->configs[0]->interfaces[0]->interface_descriptor.bAlternateSetting = 0;
2108 xupdd->usb_device->configs[0]->interfaces[0]->interface_descriptor.bNumEndpoints = 1;
2109 xupdd->usb_device->configs[0]->interfaces[0]->interface_descriptor.bInterfaceClass = 9;
2110 xupdd->usb_device->configs[0]->interfaces[0]->interface_descriptor.bInterfaceSubClass = 0;
2111 xupdd->usb_device->configs[0]->interfaces[0]->interface_descriptor.bInterfaceProtocol = 0;
2112 xupdd->usb_device->configs[0]->interfaces[0]->interface_descriptor.iInterface = 0;
2113 xupdd->usb_device->configs[0]->interfaces[0]->endpoints[0] = ExAllocatePoolWithTag(NonPagedPool, sizeof(xenusb_endpoint_t), XENUSB_POOL_TAG);
2114 xupdd->usb_device->configs[0]->interfaces[0]->endpoints[0]->interface = xupdd->usb_device->configs[0]->interfaces[0];
2115 xupdd->usb_device->configs[0]->interfaces[0]->endpoints[0]->pipe_value = 0;
2116 xupdd->usb_device->configs[0]->interfaces[0]->endpoints[0]->endpoint_descriptor.bLength = 7;
2117 xupdd->usb_device->configs[0]->interfaces[0]->endpoints[0]->endpoint_descriptor.bDescriptorType = USB_ENDPOINT_DESCRIPTOR_TYPE;
2118 xupdd->usb_device->configs[0]->interfaces[0]->endpoints[0]->endpoint_descriptor.bEndpointAddress = 0x81; // EP 1 IN
2119 xupdd->usb_device->configs[0]->interfaces[0]->endpoints[0]->endpoint_descriptor.bmAttributes = USB_ENDPOINT_TYPE_INTERRUPT;
2120 xupdd->usb_device->configs[0]->interfaces[0]->endpoints[0]->endpoint_descriptor.wMaxPacketSize = 2;
2121 xupdd->usb_device->configs[0]->interfaces[0]->endpoints[0]->endpoint_descriptor.bInterval = 12;
2122 WdfSpinLockCreate(WDF_NO_OBJECT_ATTRIBUTES, &xupdd->usb_device->configs[0]->interfaces[0]->endpoints[0]->lock);
2124 WDF_IO_QUEUE_CONFIG_INIT(&queue_config, WdfIoQueueDispatchParallel);
2125 queue_config.EvtIoInternalDeviceControl = XenUsb_EvtIoInternalDeviceControl_ROOTHUB_SUBMIT_URB;
2126 queue_config.PowerManaged = TRUE; /* power managed queue for SUBMIT_URB */
2127 status = WdfIoQueueCreate(child_device, &queue_config, WDF_NO_OBJECT_ATTRIBUTES, &xupdd->usb_device->urb_queue);
2128 if (!NT_SUCCESS(status)) {
2129 KdPrint((__DRIVER_NAME " Error creating urb_queue 0x%x\n", status));
2130 return status;
2133 WDF_IO_QUEUE_CONFIG_INIT(&queue_config, WdfIoQueueDispatchManual);
2134 //WDF_OBJECT_ATTRIBUTES_INIT_CONTEXT_TYPE(&queue_attributes, pxenusb_endpoint_t);
2135 queue_config.PowerManaged = TRUE;
2136 //queue_config.EvtIoInternalDeviceControl = XenUsb_EvtIoInternalDeviceControl_Interrupt_SUBMIT_URB;
2137 status = WdfIoQueueCreate(child_device, &queue_config, WDF_NO_OBJECT_ATTRIBUTES,
2138 &xupdd->usb_device->configs[0]->interfaces[0]->endpoints[0]->queue);
2139 if (!NT_SUCCESS(status)) {
2140 KdPrint((__DRIVER_NAME " Error creating timer io_queue 0x%x\n", status));
2141 return status;
2143 //*GetEndpoint(xupdd->usb_device->configs[0]->interfaces[0]->endpoints[0]->queue) = xupdd->usb_device->configs[0]->interfaces[0]->endpoints[0];
2145 WDF_IO_QUEUE_CONFIG_INIT_DEFAULT_QUEUE(&queue_config, WdfIoQueueDispatchParallel);
2146 queue_config.EvtIoInternalDeviceControl = XenUsbHub_EvtIoInternalDeviceControl;
2147 queue_config.EvtIoDeviceControl = XenUsbHub_EvtIoDeviceControl;
2148 queue_config.EvtIoDefault = XenUsbHub_EvtIoDefault;
2149 /* can't be power managed or deadlocks occur */
2150 queue_config.PowerManaged = FALSE;
2151 status = WdfIoQueueCreate(child_device, &queue_config, WDF_NO_OBJECT_ATTRIBUTES, &xupdd->io_queue);
2152 if (!NT_SUCCESS(status)) {
2153 KdPrint((__DRIVER_NAME " Error creating io_queue 0x%x\n", status));
2154 return status;
2157 WdfDeviceSetSpecialFileSupport(child_device, WdfSpecialFilePaging, TRUE);
2158 WdfDeviceSetSpecialFileSupport(child_device, WdfSpecialFileHibernation, TRUE);
2159 WdfDeviceSetSpecialFileSupport(child_device, WdfSpecialFileDump, TRUE);
2161 WDF_DEVICE_PNP_CAPABILITIES_INIT(&child_pnp_capabilities);
2162 child_pnp_capabilities.LockSupported = WdfFalse;
2163 child_pnp_capabilities.EjectSupported = WdfTrue;
2164 child_pnp_capabilities.Removable = WdfTrue;
2165 child_pnp_capabilities.DockDevice = WdfFalse;
2166 child_pnp_capabilities.UniqueID = WdfTrue;
2167 child_pnp_capabilities.SilentInstall = WdfTrue;
2168 child_pnp_capabilities.SurpriseRemovalOK = WdfTrue;
2169 child_pnp_capabilities.HardwareDisabled = WdfFalse;
2170 WdfDeviceSetPnpCapabilities(child_device, &child_pnp_capabilities);
2172 WDF_DEVICE_POWER_CAPABILITIES_INIT(&child_power_capabilities);
2173 child_power_capabilities.DeviceD1 = WdfTrue;
2174 child_power_capabilities.WakeFromD1 = WdfTrue;
2175 child_power_capabilities.DeviceWake = PowerDeviceD1;
2176 child_power_capabilities.DeviceState[PowerSystemWorking] = PowerDeviceD0;
2177 child_power_capabilities.DeviceState[PowerSystemSleeping1] = PowerDeviceD1;
2178 child_power_capabilities.DeviceState[PowerSystemSleeping2] = PowerDeviceD2;
2179 child_power_capabilities.DeviceState[PowerSystemSleeping3] = PowerDeviceD2;
2180 child_power_capabilities.DeviceState[PowerSystemHibernate] = PowerDeviceD3;
2181 child_power_capabilities.DeviceState[PowerSystemShutdown] = PowerDeviceD3;
2182 WdfDeviceSetPowerCapabilities(child_device, &child_power_capabilities);
2184 #if (NTDDI_VERSION >= NTDDI_VISTA)
2185 #if 0
2186 ubihss.BusContext = child_device;
2187 ubihss.Size = sizeof(USB_BUS_INTERFACE_HUB_SELECTIVE_SUSPEND);
2188 ubihss.Version = USB_BUSIF_HUB_SS_VERSION_0;
2189 ubihss.InterfaceReference = WdfDeviceInterfaceReferenceNoOp;
2190 ubihss.InterfaceDereference = WdfDeviceInterfaceDereferenceNoOp;
2191 ubihss.SuspendHub = XenUsbHub_UBIHSS_SuspendHub;
2192 ubihss.ResumeHub = XenUsbHub_UBIHSS_ResumeHub;
2193 WDF_QUERY_INTERFACE_CONFIG_INIT(&interface_config, (PINTERFACE)&ubihss, &USB_BUS_INTERFACE_HUB_SS_GUID, NULL);
2194 status = WdfDeviceAddQueryInterface(child_device, &interface_config);
2195 if (!NT_SUCCESS(status))
2196 return status;
2197 #endif
2198 pli.Size = sizeof(USB_BUS_INTERFACE_HUB_SELECTIVE_SUSPEND);
2199 pli.Version = 1;
2200 pli.Context = child_device;
2201 pli.InterfaceReference = WdfDeviceInterfaceReferenceNoOp;
2202 pli.InterfaceDereference = WdfDeviceInterfaceDereferenceNoOp;
2203 pli.GetLocationString = XenUsbHub_PLI_GetLocationString;
2204 WDF_QUERY_INTERFACE_CONFIG_INIT(&interface_config, (PINTERFACE)&pli, &GUID_PNP_LOCATION_INTERFACE, NULL);
2205 status = WdfDeviceAddQueryInterface(child_device, &interface_config);
2206 if (!NT_SUCCESS(status))
2207 return status;
2208 #endif
2210 status = WdfDeviceCreateDeviceInterface(child_device, &GUID_DEVINTERFACE_USB_HUB, NULL);
2211 if (!NT_SUCCESS(status))
2212 return status;
2214 FUNCTION_EXIT();
2216 return status;