Leaked source code of windows server 2003
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.

401 lines
9.2 KiB

  1. /*++
  2. Copyright (c) 1995 Microsoft Corporation
  3. Module Name:
  4. initunlo.c
  5. Abstract:
  6. This module contains the code that is very specific to initialization
  7. and unload operations in the irenum driver
  8. Author:
  9. Brian Lieuallen, 7-13-2000
  10. Environment:
  11. Kernel mode
  12. Revision History :
  13. --*/
  14. #include "internal.h"
  15. #pragma alloc_text(PAGE,IrEnumAddDevice)
  16. #pragma alloc_text(PAGE,IrEnumPnP)
  17. #pragma alloc_text(PAGE,IrEnumPower)
  18. #pragma alloc_text(PAGE,IrEnumWmi)
  19. NTSTATUS
  20. IrEnumAddDevice(
  21. IN PDRIVER_OBJECT DriverObject,
  22. IN PDEVICE_OBJECT Pdo
  23. )
  24. {
  25. NTSTATUS Status;
  26. PDEVICE_OBJECT Fdo = NULL;
  27. PDEVICE_OBJECT LowerDevice=NULL;
  28. //
  29. // Pointer to the device extension created for this
  30. // device
  31. //
  32. PFDO_DEVICE_EXTENSION DeviceExtension = NULL;
  33. D_PNP(DbgPrint("IRENUM: AddDevice\n");)
  34. //
  35. // Create the device object for this device.
  36. //
  37. Status = IoCreateDevice(
  38. DriverObject,
  39. sizeof(FDO_DEVICE_EXTENSION),
  40. NULL,
  41. FILE_DEVICE_NULL,
  42. FILE_AUTOGENERATED_DEVICE_NAME,
  43. FALSE,
  44. &Fdo
  45. );
  46. if (!NT_SUCCESS(Status)) {
  47. goto CleanUp;
  48. }
  49. LowerDevice=IoAttachDeviceToDeviceStack(
  50. Fdo,
  51. Pdo
  52. );
  53. if (LowerDevice == NULL) {
  54. D_ERROR(DbgPrint("IRENUM: Could not attach to PDO\n");)
  55. Status=STATUS_INSUFFICIENT_RESOURCES;
  56. goto CleanUp;
  57. }
  58. Fdo->Flags |= LowerDevice->Flags;
  59. Fdo->Flags &= ~DO_DEVICE_INITIALIZING;
  60. Fdo->StackSize=LowerDevice->StackSize+1;
  61. DeviceExtension=Fdo->DeviceExtension;
  62. DeviceExtension->DoType=DO_TYPE_FDO;
  63. DeviceExtension->DeviceObject = Fdo;
  64. DeviceExtension->Pdo=Pdo;
  65. DeviceExtension->LowerDevice=LowerDevice;
  66. DeviceExtension->CreateStaticDevice= (EnumStaticDevice != 0) ;
  67. Status = CreateEnumObject( Fdo,
  68. &DeviceExtension->EnumHandle,
  69. DeviceExtension->CreateStaticDevice );
  70. if ( !NT_SUCCESS(Status) )
  71. {
  72. D_ERROR(DbgPrint("IRENUM: CreateEnumObject failed : 0x%x\n",Status);)
  73. goto CleanUp;
  74. }
  75. return STATUS_SUCCESS;
  76. CleanUp:
  77. if ( Fdo != NULL )
  78. {
  79. IoDeleteDevice(Fdo);
  80. }
  81. return Status;
  82. }
  83. NTSTATUS
  84. IrEnumPnP(
  85. IN PDEVICE_OBJECT DeviceObject,
  86. IN PIRP Irp
  87. )
  88. {
  89. PFDO_DEVICE_EXTENSION DeviceExtension = DeviceObject->DeviceExtension;
  90. PIO_STACK_LOCATION irpSp = IoGetCurrentIrpStackLocation(Irp);
  91. NTSTATUS status;
  92. ULONG i;
  93. if ((DeviceExtension->DoType==DO_TYPE_PDO) || (DeviceExtension->DoType==DO_TYPE_DEL_PDO)) {
  94. //
  95. // this one is for the child
  96. //
  97. return IrEnumPdoPnp(
  98. DeviceObject,
  99. Irp
  100. );
  101. }
  102. if (DeviceExtension->DoType != DO_TYPE_FDO) {
  103. DbgPrint("IRENUM: IrEnumPnp: Bad DevObj\n");
  104. Irp->IoStatus.Status = STATUS_SUCCESS;
  105. IoCompleteRequest(
  106. Irp,
  107. IO_NO_INCREMENT
  108. );
  109. return STATUS_SUCCESS;
  110. }
  111. switch (irpSp->MinorFunction) {
  112. case IRP_MN_START_DEVICE:
  113. Irp->IoStatus.Status = STATUS_SUCCESS;
  114. return ForwardIrp(DeviceExtension->LowerDevice, Irp);
  115. case IRP_MN_QUERY_STOP_DEVICE:
  116. D_PNP(DbgPrint("IRENUM: IRP_MN_QUERY_STOP_DEVICE\n");)
  117. Irp->IoStatus.Status = STATUS_SUCCESS;
  118. return ForwardIrp(DeviceExtension->LowerDevice, Irp);
  119. case IRP_MN_CANCEL_STOP_DEVICE:
  120. D_PNP(DbgPrint("IRENUM: IRP_MN_CANCEL_STOP_DEVICE\n");)
  121. Irp->IoStatus.Status = STATUS_SUCCESS;
  122. return ForwardIrp(DeviceExtension->LowerDevice, Irp);
  123. case IRP_MN_STOP_DEVICE:
  124. D_PNP(DbgPrint("IRENUM: IRP_MN_STOP_DEVICE\n");)
  125. Irp->IoStatus.Status = STATUS_SUCCESS;
  126. return ForwardIrp(DeviceExtension->LowerDevice, Irp);
  127. case IRP_MN_QUERY_DEVICE_RELATIONS: {
  128. PDEVICE_RELATIONS CurrentRelations=(PDEVICE_RELATIONS)Irp->IoStatus.Information;
  129. PDEVICE_RELATIONS NewRelations=NULL;
  130. D_PNP(DbgPrint("IRENUM: IRP_MN_QUERY_DEVICE_RELATIONS type=%d\n",irpSp->Parameters.QueryDeviceRelations.Type);)
  131. D_PNP(DbgPrint(" Information=%p\n",Irp->IoStatus.Information);)
  132. switch (irpSp->Parameters.QueryDeviceRelations.Type ) {
  133. case BusRelations: {
  134. if (DeviceExtension->EnumHandle != NULL) {
  135. status=GetDeviceList(
  136. DeviceExtension->EnumHandle,
  137. Irp
  138. );
  139. Irp->IoStatus.Status = status;
  140. if (!NT_SUCCESS(status)) {
  141. IoCompleteRequest(
  142. Irp,
  143. IO_NO_INCREMENT
  144. );
  145. return status;
  146. }
  147. }
  148. return ForwardIrp(DeviceExtension->LowerDevice, Irp);
  149. }
  150. case TargetDeviceRelation:
  151. default: {
  152. return ForwardIrp(DeviceExtension->LowerDevice, Irp);
  153. }
  154. }
  155. break;
  156. }
  157. case IRP_MN_QUERY_REMOVE_DEVICE:
  158. D_PNP(DbgPrint("IRENUM: IRP_MN_QUERY_REMOVE_DEVICE\n");)
  159. Irp->IoStatus.Status = STATUS_SUCCESS;
  160. return ForwardIrp(DeviceExtension->LowerDevice, Irp);
  161. case IRP_MN_CANCEL_REMOVE_DEVICE:
  162. D_PNP(DbgPrint("IRENUM: IRP_MN_CANCEL_REMOVE_DEVICE\n");)
  163. Irp->IoStatus.Status = STATUS_SUCCESS;
  164. return ForwardIrp(DeviceExtension->LowerDevice, Irp);
  165. case IRP_MN_SURPRISE_REMOVAL: {
  166. D_PNP(DbgPrint("IRENUM: IRP_MN_SURPRISE_REMOVAL\n");)
  167. Irp->IoStatus.Status = STATUS_SUCCESS;
  168. return ForwardIrp(DeviceExtension->LowerDevice, Irp);
  169. }
  170. break;
  171. case IRP_MN_REMOVE_DEVICE: {
  172. ULONG NewReferenceCount;
  173. D_PNP(DbgPrint("IRENUM: IRP_MN_REMOVE_DEVICE\n");)
  174. //
  175. // removing now for sure
  176. //
  177. DeviceExtension->Removing=TRUE;
  178. DeviceExtension->Removed=TRUE;
  179. IoCopyCurrentIrpStackLocationToNext(Irp);
  180. status=IoCallDriver(DeviceExtension->LowerDevice, Irp);
  181. //
  182. // detach from the driver below
  183. //
  184. IoDetachDevice(DeviceExtension->LowerDevice);
  185. DeviceExtension->DoType=DO_TYPE_DEL_FDO;
  186. if (DeviceExtension->EnumHandle != NULL) {
  187. CloseEnumObject(DeviceExtension->EnumHandle);
  188. }
  189. //
  190. // delete our device object
  191. //
  192. IoDeleteDevice(DeviceObject);
  193. D_PNP(DbgPrint("IRENUM: IRP_MN_REMOVE_DEVICE exit, %08lx\n",status);)
  194. return status;
  195. }
  196. default:
  197. D_PNP(DbgPrint("IRENUM: Sending to PDO PnP IRP, MN func=%d\n",irpSp->MinorFunction);)
  198. return ForwardIrp(DeviceExtension->LowerDevice, Irp);
  199. }
  200. IoCompleteRequest(Irp,IO_NO_INCREMENT);
  201. return STATUS_SUCCESS;
  202. }
  203. NTSTATUS
  204. IrEnumPower(
  205. IN PDEVICE_OBJECT DeviceObject,
  206. IN PIRP Irp
  207. )
  208. {
  209. PFDO_DEVICE_EXTENSION DeviceExtension = DeviceObject->DeviceExtension;
  210. if ((DeviceExtension->DoType==DO_TYPE_PDO) || (DeviceExtension->DoType==DO_TYPE_DEL_PDO)) {
  211. //
  212. // this one is for the child
  213. //
  214. return IrEnumPdoPower(
  215. DeviceObject,
  216. Irp
  217. );
  218. }
  219. PoStartNextPowerIrp(Irp);
  220. IoSkipCurrentIrpStackLocation(Irp);
  221. return PoCallDriver(DeviceExtension->LowerDevice, Irp);
  222. }
  223. NTSTATUS
  224. IrEnumWmi(
  225. IN PDEVICE_OBJECT DeviceObject,
  226. IN PIRP Irp
  227. )
  228. {
  229. PFDO_DEVICE_EXTENSION DeviceExtension = DeviceObject->DeviceExtension;
  230. PIO_STACK_LOCATION irpSp=IoGetCurrentIrpStackLocation(Irp);
  231. NTSTATUS Status;
  232. if ((DeviceExtension->DoType==DO_TYPE_PDO) || (DeviceExtension->DoType==DO_TYPE_DEL_PDO)) {
  233. return IrEnumPdoWmi(
  234. DeviceObject,
  235. Irp
  236. );
  237. }
  238. if (irpSp->Parameters.WMI.ProviderId == (ULONG_PTR)DeviceObject) {
  239. //
  240. // The irp was targeted at this device, but we don't support wmi
  241. //
  242. Status = Irp->IoStatus.Status;
  243. IoCompleteRequest(Irp,IO_NO_INCREMENT);
  244. } else {
  245. //
  246. // the irp is targeted at another device object in the stack
  247. //
  248. Status=ForwardIrp(DeviceExtension->LowerDevice, Irp);
  249. }
  250. return Status;
  251. }