Source code of Windows XP (NT5)
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

265 lines
12 KiB

  1. /*
  2. *************************************************************************
  3. * File: USBCCGP.H
  4. *
  5. * Module: USBCCGP.SYS
  6. * USB Common Class Generic Parent driver.
  7. *
  8. * Copyright (c) 1998 Microsoft Corporation
  9. *
  10. *
  11. * Author: ervinp
  12. *
  13. *************************************************************************
  14. */
  15. #include <msosdesc.h> // Internal definitions for MS OS Desc.
  16. /*
  17. * USBCCGP signature tag for memory allocations
  18. */
  19. #define USBCCGP_TAG (ULONG)'CbsU'
  20. #define GUARD_WORD 'draG'
  21. extern PWCHAR GenericCompositeUSBDeviceString;
  22. enum deviceState {
  23. STATE_INITIALIZED,
  24. STATE_STARTING,
  25. STATE_STARTED,
  26. STATE_START_FAILED,
  27. STATE_STOPPING,
  28. STATE_STOPPED, // implies device was previously started successfully
  29. STATE_SUSPENDED,
  30. STATE_REMOVING,
  31. STATE_REMOVED
  32. };
  33. typedef struct PARENT_FDO_EXTENSION {
  34. enum deviceState state;
  35. PDRIVER_OBJECT driverObj;
  36. PDEVICE_OBJECT pdo;
  37. PDEVICE_OBJECT fdo;
  38. PDEVICE_OBJECT topDevObj;
  39. /*
  40. * Counter to keep driver from getting unloaded before all IO completes to us.
  41. */
  42. LONG pendingActionCount;
  43. KEVENT removeEvent;
  44. /*
  45. * This buffer will hold a USB_CONFIGURATION_DESCRIPTOR plus
  46. * the following interface descriptors.
  47. */
  48. PUSB_CONFIGURATION_DESCRIPTOR configDesc;
  49. PUSB_CONFIGURATION_DESCRIPTOR selectedConfigDesc;
  50. USBD_CONFIGURATION_HANDLE selectedConfigHandle;
  51. PUSBD_INTERFACE_LIST_ENTRY interfaceList;
  52. USB_DEVICE_DESCRIPTOR deviceDesc;
  53. /*
  54. * The parent device has some number of functions.
  55. * For each function, we create a PDO and store
  56. * it in the deviceRelations array.
  57. */
  58. ULONG numFunctions;
  59. PDEVICE_RELATIONS deviceRelations;
  60. /*
  61. * deviceCapabilities includes a
  62. * table mapping system power states to device power states.
  63. */
  64. DEVICE_CAPABILITIES deviceCapabilities;
  65. PURB dynamicNotifyUrb;
  66. PIRP parentWaitWakeIrp;
  67. PIRP currentSetPowerIrp;
  68. BOOLEAN isWaitWakePending;
  69. LIST_ENTRY functionWaitWakeIrpQueue; // WW irps from function client drivers
  70. KSPIN_LOCK parentFdoExtSpinLock;
  71. BOOLEAN haveCSInterface;
  72. ULONG CSInterfaceNumber;
  73. ULONG CSChannelId;
  74. BOOLEAN resetPortInProgress;
  75. LIST_ENTRY pendingResetPortIrpQueue;
  76. BOOLEAN cyclePortInProgress;
  77. LIST_ENTRY pendingCyclePortIrpQueue;
  78. PIRP pendingIdleIrp;
  79. USB_IDLE_CALLBACK_INFO idleCallbackInfo;
  80. PMS_EXT_CONFIG_DESC msExtConfigDesc;
  81. } PARENT_FDO_EXT, *PPARENT_FDO_EXT;
  82. typedef struct FUNCTION_PDO_EXTENSION {
  83. ULONG functionIndex;
  84. ULONG baseInterfaceNumber;
  85. ULONG numInterfaces;
  86. enum deviceState state;
  87. PDEVICE_OBJECT pdo;
  88. PPARENT_FDO_EXT parentFdoExt;
  89. /*
  90. * functionInterfaceList is a pointer into the parent's interfaceList array.
  91. */
  92. PUSBD_INTERFACE_LIST_ENTRY functionInterfaceList;
  93. PUSB_CONFIGURATION_DESCRIPTOR dynamicFunctionConfigDesc;
  94. USB_DEVICE_DESCRIPTOR functionDeviceDesc;
  95. KSPIN_LOCK functionPdoExtSpinLock;
  96. PIRP idleNotificationIrp;
  97. } FUNCTION_PDO_EXT, *PFUNCTION_PDO_EXT;
  98. typedef struct DEVICE_EXTENSION {
  99. ULONG signature;
  100. /*
  101. * Does the associated device object represent
  102. * the parent FDO that we attached to the device object
  103. * we got from USBHUB
  104. * (as opposed to the function PDO we created
  105. * to represent a single function on that device) ?
  106. */
  107. BOOLEAN isParentFdo;
  108. union {
  109. PARENT_FDO_EXT parentFdoExt;
  110. FUNCTION_PDO_EXT functionPdoExt;
  111. };
  112. } DEVEXT, *PDEVEXT;
  113. typedef struct _USB_REQUEST_TIMEOUT_CONTEXT {
  114. PKEVENT event;
  115. PLONG lock;
  116. } USB_REQUEST_TIMEOUT_CONTEXT, *PUSB_REQUEST_TIMEOUT_CONTEXT;
  117. #define ALLOCPOOL(pooltype, size) ExAllocatePoolWithTag(pooltype, size, USBCCGP_TAG)
  118. #define FREEPOOL(ptr) ExFreePool(ptr)
  119. #define MAX(a, b) (((a) >= (b)) ? (a) : (b))
  120. #define MIN(a, b) (((a) <= (b)) ? (a) : (b))
  121. #define POINTER_DISTANCE(ptr1, ptr2) (ULONG)(((PUCHAR)(ptr1))-((PUCHAR)(ptr2)))
  122. // Counting the byte count of an ascii string or wide char string
  123. //
  124. #define STRLEN( Length, p )\
  125. {\
  126. int i;\
  127. for ( i=0; (p)[i]; i++ );\
  128. Length = i*sizeof(*p);\
  129. }
  130. /*
  131. * We use this value, which is guaranteed to never be defined as a status by the kernel,
  132. * as a default status code to indicate "do nothing and pass the irp down".
  133. */
  134. #define NO_STATUS 0x80000000
  135. NTSTATUS DriverEntry(IN PDRIVER_OBJECT DriverObject, IN PUNICODE_STRING UniRegistryPath);
  136. NTSTATUS USBC_AddDevice(IN PDRIVER_OBJECT DriverObject, IN PDEVICE_OBJECT PhysicalDeviceObject);
  137. VOID USBC_DriverUnload(IN PDRIVER_OBJECT DriverObject);
  138. NTSTATUS USBC_Dispatch(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp);
  139. NTSTATUS USBC_Create(PDEVEXT devExt, PIRP irp);
  140. NTSTATUS USBC_Close(PDEVEXT devExt, PIRP irp);
  141. NTSTATUS USBC_DeviceControl(PDEVEXT devExt, PIRP irp);
  142. NTSTATUS USBC_SystemControl(PDEVEXT devExt, PIRP irp);
  143. NTSTATUS USBC_InternalDeviceControl(PDEVEXT devExt, PIRP irp);
  144. NTSTATUS USBC_PnP(PDEVEXT devExt, PIRP irp);
  145. NTSTATUS USBC_PnpComplete(IN PDEVICE_OBJECT devObj, IN PIRP irp, IN PVOID context);
  146. NTSTATUS USBC_Power(PDEVEXT devExt, PIRP irp);
  147. NTSTATUS CreateStaticFunctionPDOs(PPARENT_FDO_EXT fdoExt);
  148. NTSTATUS TryGetConfigDescriptor(PPARENT_FDO_EXT parentFdoExt);
  149. NTSTATUS GetConfigDescriptor(PPARENT_FDO_EXT fdoExt);
  150. VOID PrepareParentFDOForRemove(PPARENT_FDO_EXT parentFdoExt);
  151. VOID FreeParentFDOResources(PPARENT_FDO_EXT fdoExt);
  152. PWCHAR BuildCompatibleIDs(IN PUCHAR CompatibleID, IN PUCHAR SubCompatibleID, IN UCHAR Class, IN UCHAR SubClass, IN UCHAR Protocol);
  153. NTSTATUS QueryFunctionPdoID(PFUNCTION_PDO_EXT functionPdoExt, PIRP irp);
  154. NTSTATUS QueryParentDeviceRelations(PPARENT_FDO_EXT parentFdoExt, PIRP irp);
  155. NTSTATUS QueryFunctionDeviceRelations(PFUNCTION_PDO_EXT functionPdoExt, PIRP irp);
  156. NTSTATUS QueryFunctionCapabilities(PFUNCTION_PDO_EXT functionPdoExt, PIRP irp);
  157. NTSTATUS HandleParentFdoPower(PPARENT_FDO_EXT parentFdoExt, PIRP irp);
  158. NTSTATUS HandleFunctionPdoPower(PFUNCTION_PDO_EXT functionPdoExt, PIRP irp);
  159. VOID ParentPowerRequestCompletion(IN PDEVICE_OBJECT devObj, IN UCHAR minorFunction, IN POWER_STATE powerState, IN PVOID context, IN PIO_STATUS_BLOCK ioStatus);
  160. NTSTATUS StartParentFdo(PPARENT_FDO_EXT parentFdoExt, PIRP irp);
  161. NTSTATUS QueryFunctionCapabilities(PFUNCTION_PDO_EXT functionPdoExt, PIRP irp);
  162. NTSTATUS ParentPdoPowerCompletion(IN PDEVICE_OBJECT devObj, IN PIRP irp, IN PVOID context);
  163. NTSTATUS FunctionInternalDeviceControl(PFUNCTION_PDO_EXT functionPdoExt, PIRP irp);
  164. NTSTATUS ParentInternalDeviceControl(PPARENT_FDO_EXT parentFdoExt, PIRP irp);
  165. NTSTATUS ParentResetOrCyclePort(PPARENT_FDO_EXT parentFdoExt, PIRP irp, ULONG ioControlCode);
  166. NTSTATUS BuildFunctionConfigurationDescriptor(PFUNCTION_PDO_EXT functionPdoExt, PUCHAR buffer, ULONG bufferLength, PULONG bytesReturned);
  167. VOID FreeFunctionPDOResources(PFUNCTION_PDO_EXT functionPdoExt);
  168. NTSTATUS GetParentFdoCapabilities(PPARENT_FDO_EXT parentFdoExt);
  169. NTSTATUS CallDriverSyncCompletion(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp, IN PVOID Context);
  170. NTSTATUS CallDriverSync(IN PDEVICE_OBJECT DeviceObject, IN OUT PIRP Irp);
  171. NTSTATUS CallNextDriverSync(PPARENT_FDO_EXT parentFdoExt, PIRP irp);
  172. VOID IncrementPendingActionCount(PPARENT_FDO_EXT parentFdoExt);
  173. VOID DecrementPendingActionCount(PPARENT_FDO_EXT parentFdoExt);
  174. PWCHAR AppendInterfaceNumber(PWCHAR oldIDs, ULONG interfaceNum);
  175. PVOID MemDup(PVOID dataPtr, ULONG length);
  176. ULONG WStrLen(PWCHAR str);
  177. ULONG WStrCpy(PWCHAR dest, PWCHAR src);
  178. BOOLEAN WStrCompareN(PWCHAR str1, PWCHAR str2, ULONG maxChars);
  179. NTSTATUS GetDeviceDescriptor(PPARENT_FDO_EXT parentFdoExt);
  180. NTSTATUS SubmitUrb(PPARENT_FDO_EXT parentFdoExt, PURB urb, BOOLEAN synchronous, PVOID completionRoutine, PVOID completionContext);
  181. NTSTATUS UrbFunctionSelectConfiguration(PFUNCTION_PDO_EXT functionPdoExt, PURB urb);
  182. NTSTATUS UrbFunctionGetDescriptorFromDevice(PFUNCTION_PDO_EXT functionPdoExt, PURB urb);
  183. PFUNCTION_PDO_EXT FindFunctionByIndex(PPARENT_FDO_EXT parentFdoExt, ULONG functionIndex);
  184. PUSBD_INTERFACE_LIST_ENTRY GetFunctionInterfaceListBase(PPARENT_FDO_EXT parentFdoExt, ULONG functionIndex, PULONG numFunctionInterfaces);
  185. PDEVICE_RELATIONS CopyDeviceRelations(PDEVICE_RELATIONS deviceRelations);
  186. PUSBD_INTERFACE_LIST_ENTRY GetInterfaceList(PPARENT_FDO_EXT parentFdoExt, PUSB_CONFIGURATION_DESCRIPTOR configDesc);
  187. VOID FreeInterfaceList(PPARENT_FDO_EXT parentFdoExt, BOOLEAN freeListItself);
  188. NTSTATUS ParentSelectConfiguration(PPARENT_FDO_EXT parentFdoExt, PUSB_CONFIGURATION_DESCRIPTOR configDesc, PUSBD_INTERFACE_LIST_ENTRY interfaceList);
  189. VOID ParentCloseConfiguration(PPARENT_FDO_EXT parentFdoExt);
  190. NTSTATUS GetStringDescriptor(PPARENT_FDO_EXT parentFdoExt, UCHAR stringIndex, LANGID langId, PUSB_STRING_DESCRIPTOR stringDesc, ULONG bufferLen);
  191. NTSTATUS SetPdoRegistryParameter(IN PDEVICE_OBJECT PhysicalDeviceObject, IN PWCHAR KeyName, IN PVOID Data, IN ULONG DataLength, IN ULONG KeyType, IN ULONG DevInstKeyType);
  192. NTSTATUS GetPdoRegistryParameter(IN PDEVICE_OBJECT PhysicalDeviceObject, IN PWCHAR ValueName, OUT PVOID Data, IN ULONG DataLength, OUT PULONG Type, OUT PULONG ActualDataLength);
  193. NTSTATUS GetMsOsFeatureDescriptor(PPARENT_FDO_EXT ParentFdoExt, UCHAR Recipient, UCHAR InterfaceNumber, USHORT Index, PVOID DataBuffer, ULONG DataBufferLength, PULONG BytesReturned);
  194. NTSTATUS GetMsExtendedConfigDescriptor(IN PPARENT_FDO_EXT ParentFdoExt);
  195. BOOLEAN ValidateMsExtendedConfigDescriptor(IN PMS_EXT_CONFIG_DESC MsExtConfigDesc, IN PUSB_CONFIGURATION_DESCRIPTOR ConfigurationDescriptor);
  196. NTSTATUS GetDeviceText(PFUNCTION_PDO_EXT functionPdoExt, PIRP irp);
  197. NTSTATUS EnqueueFunctionWaitWakeIrp(PFUNCTION_PDO_EXT functionPdoExt, PIRP irp);
  198. VOID FunctionWaitWakeIrpCancelRoutine(IN PDEVICE_OBJECT deviceObject, IN PIRP irp);
  199. NTSTATUS SubmitParentWaitWakeIrp(PPARENT_FDO_EXT parentFdoExt);
  200. NTSTATUS ParentWaitWakeComplete(IN PDEVICE_OBJECT deviceObject, IN UCHAR minorFunction, IN POWER_STATE powerState, IN PVOID context, IN PIO_STATUS_BLOCK ioStatus);
  201. VOID CompleteAllFunctionWaitWakeIrps(PPARENT_FDO_EXT parentFdoExt, NTSTATUS status);
  202. VOID CompleteAllFunctionIdleIrps(PPARENT_FDO_EXT parentFdoExt, NTSTATUS status);
  203. VOID InstallExtPropDesc(IN PFUNCTION_PDO_EXT FunctionPdoExt);
  204. VOID InstallExtPropDescSections(PDEVICE_OBJECT DeviceObject, PMS_EXT_PROP_DESC pMsExtPropDesc);
  205. NTSTATUS ParentDeviceControl(PPARENT_FDO_EXT parentFdoExt, PIRP irp);
  206. VOID CompleteFunctionIdleNotification(PFUNCTION_PDO_EXT functionPdoExt);
  207. VOID CheckParentIdle(PPARENT_FDO_EXT parentFdoExt);
  208. NTSTATUS ParentSetD0(IN PPARENT_FDO_EXT parentFdoExt);
  209. NTSTATUS USBC_SetContentId(IN PIRP irp, IN PVOID pKsProperty, IN PVOID pvData);
  210. NTSTATUS RegQueryGenericCompositeUSBDeviceString(PWCHAR *GenericCompositeUSBDeviceString);