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.

378 lines
7.5 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. NTSTATUS
  16. IrCommAddDevice(
  17. IN PDRIVER_OBJECT DriverObject,
  18. IN PDEVICE_OBJECT Pdo
  19. )
  20. {
  21. NTSTATUS Status;
  22. WCHAR TempBuffer[256];
  23. PDEVICE_OBJECT Fdo = NULL;
  24. PDEVICE_OBJECT LowerDevice=NULL;
  25. //
  26. // Pointer to the device extension created for this
  27. // device
  28. //
  29. PFDO_DEVICE_EXTENSION DeviceExtension = NULL;
  30. D_PNP(DbgPrint("IrComm: AddDevice\n");)
  31. //
  32. // Create the device object for this device.
  33. //
  34. Status = IoCreateDevice(
  35. DriverObject,
  36. sizeof(FDO_DEVICE_EXTENSION),
  37. NULL,
  38. FILE_DEVICE_NULL,
  39. FILE_AUTOGENERATED_DEVICE_NAME,
  40. FALSE,
  41. &Fdo
  42. );
  43. if (!NT_SUCCESS(Status)) {
  44. goto CleanUp;
  45. }
  46. LowerDevice=IoAttachDeviceToDeviceStack(
  47. Fdo,
  48. Pdo
  49. );
  50. if (LowerDevice == NULL) {
  51. D_ERROR(DbgPrint("IRCOMM: Could not attach to PDO\n");)
  52. Status=STATUS_INSUFFICIENT_RESOURCES;
  53. goto CleanUp;
  54. }
  55. Fdo->Flags |= DO_BUFFERED_IO | DO_POWER_PAGABLE;
  56. Fdo->Flags &= ~DO_DEVICE_INITIALIZING;
  57. Fdo->StackSize=LowerDevice->StackSize+1;
  58. DeviceExtension=Fdo->DeviceExtension;
  59. D_ERROR(DbgPrint("IRCOMM: Device Extension %p\n",DeviceExtension);)
  60. DeviceExtension->DeviceObject = Fdo;
  61. DeviceExtension->Pdo=Pdo;
  62. DeviceExtension->LowerDevice=LowerDevice;
  63. KeInitializeTimer(
  64. &DeviceExtension->Read.IntervalTimer
  65. );
  66. KeInitializeDpc(
  67. &DeviceExtension->Read.IntervalTimerDpc,
  68. IntervalTimeProc,
  69. DeviceExtension
  70. );
  71. KeInitializeTimer(
  72. &DeviceExtension->Read.TotalTimer
  73. );
  74. KeInitializeDpc(
  75. &DeviceExtension->Read.TotalTimerDpc,
  76. TotalTimerProc,
  77. DeviceExtension
  78. );
  79. KeInitializeSpinLock(
  80. &DeviceExtension->SpinLock
  81. );
  82. KeInitializeSpinLock(
  83. &DeviceExtension->Read.ReadLock
  84. );
  85. KeInitializeSpinLock(
  86. &DeviceExtension->Mask.Lock
  87. );
  88. IrCommHandleSymbolicLink(
  89. Pdo,
  90. &DeviceExtension->InterfaceName,
  91. TRUE
  92. );
  93. {
  94. IRCOMM_BUS_INFO BusInfo;
  95. QueryPdoInformation(
  96. Pdo,
  97. IRENUM_CONFIG_SPACE_INFO,
  98. &BusInfo,
  99. sizeof(BusInfo)
  100. );
  101. DeviceExtension->DeviceAddress=BusInfo.DeviceAddress;
  102. }
  103. InitializePacketQueue(
  104. &DeviceExtension->Write.Queue,
  105. DeviceExtension,
  106. WriteStartRoutine
  107. );
  108. InitializePacketQueue(
  109. &DeviceExtension->Read.Queue,
  110. DeviceExtension,
  111. ReadStartRoutine
  112. );
  113. InitializePacketQueue(
  114. &DeviceExtension->Mask.Queue,
  115. DeviceExtension,
  116. MaskStartRoutine
  117. );
  118. InitializePacketQueue(
  119. &DeviceExtension->Uart.Queue,
  120. DeviceExtension,
  121. UartStartRoutine
  122. );
  123. #if 0
  124. DeviceExtension->LineControl.StopBits=1;
  125. DeviceExtension->LineControl.Parity=0;
  126. DeviceExtension->LineControl.WordLength=8;
  127. DeviceExtension->BaudRate=115200;
  128. #endif
  129. DeviceExtension->Read.BytesInBuffer=0;
  130. DeviceExtension->Read.NextFilledByte=&DeviceExtension->Read.InputBuffer[0];
  131. DeviceExtension->Read.NextEmptyByte=&DeviceExtension->Read.InputBuffer[0];
  132. return STATUS_SUCCESS;
  133. CleanUp:
  134. IoDeleteDevice(Fdo);
  135. return Status;
  136. }
  137. NTSTATUS
  138. IrCommPnP(
  139. IN PDEVICE_OBJECT DeviceObject,
  140. IN PIRP Irp
  141. )
  142. {
  143. PFDO_DEVICE_EXTENSION DeviceExtension = DeviceObject->DeviceExtension;
  144. PIO_STACK_LOCATION irpSp = IoGetCurrentIrpStackLocation(Irp);
  145. NTSTATUS status;
  146. ULONG i;
  147. switch (irpSp->MinorFunction) {
  148. case IRP_MN_START_DEVICE:
  149. D_PNP(DbgPrint("IRCOMM: IRP_MN_START_DEVICE\n");)
  150. Irp->IoStatus.Status = STATUS_SUCCESS;
  151. return ForwardIrp(DeviceExtension->LowerDevice, Irp);
  152. case IRP_MN_QUERY_STOP_DEVICE:
  153. D_PNP(DbgPrint("IRCOMM: IRP_MN_QUERY_STOP_DEVICE\n");)
  154. Irp->IoStatus.Status = STATUS_SUCCESS;
  155. return ForwardIrp(DeviceExtension->LowerDevice, Irp);
  156. case IRP_MN_CANCEL_STOP_DEVICE:
  157. D_PNP(DbgPrint("IRCOMM: IRP_MN_CANCEL_STOP_DEVICE\n");)
  158. Irp->IoStatus.Status = STATUS_SUCCESS;
  159. return ForwardIrp(DeviceExtension->LowerDevice, Irp);
  160. case IRP_MN_STOP_DEVICE:
  161. D_PNP(DbgPrint("IRCOMM: IRP_MN_STOP_DEVICE\n");)
  162. Irp->IoStatus.Status = STATUS_SUCCESS;
  163. return ForwardIrp(DeviceExtension->LowerDevice, Irp);
  164. case IRP_MN_QUERY_REMOVE_DEVICE:
  165. D_PNP(DbgPrint("IrComm: IRP_MN_QUERY_REMOVE_DEVICE\n");)
  166. Irp->IoStatus.Status = STATUS_SUCCESS;
  167. return ForwardIrp(DeviceExtension->LowerDevice, Irp);
  168. case IRP_MN_CANCEL_REMOVE_DEVICE:
  169. D_PNP(DbgPrint("IrComm: IRP_MN_CANCEL_REMOVE_DEVICE\n");)
  170. Irp->IoStatus.Status = STATUS_SUCCESS;
  171. return ForwardIrp(DeviceExtension->LowerDevice, Irp);
  172. case IRP_MN_SURPRISE_REMOVAL: {
  173. D_PNP(DbgPrint("IrComm: IRP_MN_SURPRISE_REMOVAL\n");)
  174. DeviceExtension->Removing=TRUE;
  175. //
  176. // now that new io is blocked, flush out all pended irps
  177. //
  178. CleanupIoRequests(DeviceExtension);
  179. Irp->IoStatus.Status = STATUS_SUCCESS;
  180. return ForwardIrp(DeviceExtension->LowerDevice, Irp);
  181. }
  182. break;
  183. case IRP_MN_REMOVE_DEVICE: {
  184. ULONG NewReferenceCount;
  185. D_PNP(DbgPrint("IrComm: IRP_MN_REMOVE_DEVICE\n");)
  186. //
  187. // removing now for sure
  188. //
  189. DeviceExtension->Removing=TRUE;
  190. DeviceExtension->Removed=TRUE;
  191. if (DeviceExtension->InterfaceName.Buffer != NULL) {
  192. IrCommHandleSymbolicLink(
  193. DeviceExtension->Pdo,
  194. &DeviceExtension->InterfaceName,
  195. FALSE
  196. );
  197. }
  198. IoCopyCurrentIrpStackLocationToNext(Irp);
  199. status=IoCallDriver(DeviceExtension->LowerDevice, Irp);
  200. //
  201. // detach from the driver below
  202. //
  203. IoDetachDevice(DeviceExtension->LowerDevice);
  204. //
  205. // delete our device object
  206. //
  207. IoDeleteDevice(DeviceObject);
  208. D_PNP(DbgPrint("IrComm: IRP_MN_REMOVE_DEVICE exit, %08lx\n",status);)
  209. return status;
  210. }
  211. default:
  212. D_PNP(DbgPrint("IrComm: Sending to PDO PnP IRP, MN func=%d\n",irpSp->MinorFunction);)
  213. return ForwardIrp(DeviceExtension->LowerDevice, Irp);
  214. }
  215. IoCompleteRequest(Irp,IO_NO_INCREMENT);
  216. return STATUS_SUCCESS;
  217. }
  218. NTSTATUS
  219. IrCommPower(
  220. IN PDEVICE_OBJECT DeviceObject,
  221. IN PIRP Irp
  222. )
  223. {
  224. PFDO_DEVICE_EXTENSION DeviceExtension = DeviceObject->DeviceExtension;
  225. PoStartNextPowerIrp(Irp);
  226. IoSkipCurrentIrpStackLocation(Irp);
  227. return PoCallDriver(DeviceExtension->LowerDevice, Irp);
  228. }
  229. NTSTATUS
  230. IrCommWmi(
  231. IN PDEVICE_OBJECT DeviceObject,
  232. IN PIRP Irp
  233. )
  234. {
  235. IoCompleteRequest(Irp,IO_NO_INCREMENT);
  236. return STATUS_SUCCESS;
  237. }