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.

405 lines
8.8 KiB

  1. /*++
  2. Copyright (c) 1997-2000 Microsoft Corporation
  3. Module Name:
  4. busintrf.c
  5. Abstract:
  6. This module implements the "bus handler" interfaces supported
  7. by the PCI driver.
  8. Author:
  9. Peter Johnston (peterj) 6-Jun-1997
  10. Revision History:
  11. --*/
  12. #include "pcip.h"
  13. #define BUSINTRF_VERSION 1
  14. //
  15. // Prototypes for routines exposed only thru the "interface"
  16. // mechanism.
  17. //
  18. NTSTATUS
  19. busintrf_Constructor(
  20. PVOID DeviceExtension,
  21. PVOID PciInterface,
  22. PVOID InterfaceSpecificData,
  23. USHORT Version,
  24. USHORT Size,
  25. PINTERFACE InterfaceReturn
  26. );
  27. VOID
  28. busintrf_Reference(
  29. IN PVOID Context
  30. );
  31. VOID
  32. busintrf_Dereference(
  33. IN PVOID Context
  34. );
  35. NTSTATUS
  36. busintrf_Initializer(
  37. IN PPCI_ARBITER_INSTANCE Instance
  38. );
  39. BOOLEAN
  40. PciPnpTranslateBusAddress(
  41. IN PVOID Context,
  42. IN PHYSICAL_ADDRESS BusAddress,
  43. IN ULONG Length,
  44. IN OUT PULONG AddressSpace,
  45. OUT PPHYSICAL_ADDRESS TranslatedAddress
  46. );
  47. struct _DMA_ADAPTER *
  48. PciPnpGetDmaAdapter(
  49. IN PVOID Context,
  50. IN struct _DEVICE_DESCRIPTION *DeviceDescriptor,
  51. OUT PULONG NumberOfMapRegisters
  52. );
  53. ULONG
  54. PciPnpReadConfig(
  55. IN PVOID Context,
  56. IN ULONG WhichSpace,
  57. IN PVOID Buffer,
  58. IN ULONG Offset,
  59. IN ULONG Length
  60. );
  61. ULONG
  62. PciPnpWriteConfig(
  63. IN PVOID Context,
  64. IN ULONG WhichSpace,
  65. IN PVOID Buffer,
  66. IN ULONG Offset,
  67. IN ULONG Length
  68. );
  69. //
  70. // Define the Bus Interface "Interface" structure.
  71. //
  72. PCI_INTERFACE BusHandlerInterface = {
  73. &GUID_BUS_INTERFACE_STANDARD, // InterfaceType
  74. sizeof(BUS_INTERFACE_STANDARD), // MinSize
  75. BUSINTRF_VERSION, // MinVersion
  76. BUSINTRF_VERSION, // MaxVersion
  77. PCIIF_PDO, // Flags
  78. 0, // ReferenceCount
  79. PciInterface_BusHandler, // Signature
  80. busintrf_Constructor, // Constructor
  81. busintrf_Initializer // Instance Initializer
  82. };
  83. #ifdef ALLOC_PRAGMA
  84. #pragma alloc_text(PAGE, busintrf_Constructor)
  85. #pragma alloc_text(PAGE, busintrf_Dereference)
  86. #pragma alloc_text(PAGE, busintrf_Initializer)
  87. #pragma alloc_text(PAGE, busintrf_Reference)
  88. #pragma alloc_text(PAGE, PciPnpTranslateBusAddress)
  89. #pragma alloc_text(PAGE, PciPnpGetDmaAdapter)
  90. #endif
  91. VOID
  92. busintrf_Reference(
  93. IN PVOID Context
  94. )
  95. {
  96. PPCI_PDO_EXTENSION pdoExtension = (PPCI_PDO_EXTENSION)Context;
  97. ASSERT_PCI_PDO_EXTENSION(pdoExtension);
  98. InterlockedIncrement(&pdoExtension->BusInterfaceReferenceCount);
  99. }
  100. VOID
  101. busintrf_Dereference(
  102. IN PVOID Context
  103. )
  104. {
  105. PPCI_PDO_EXTENSION pdoExtension = (PPCI_PDO_EXTENSION)Context;
  106. ASSERT_PCI_PDO_EXTENSION(pdoExtension);
  107. InterlockedDecrement(&pdoExtension->BusInterfaceReferenceCount);
  108. }
  109. NTSTATUS
  110. busintrf_Constructor(
  111. PVOID DeviceExtension,
  112. PVOID PciInterface,
  113. PVOID InterfaceSpecificData,
  114. USHORT Version,
  115. USHORT Size,
  116. PINTERFACE InterfaceReturn
  117. )
  118. /*++
  119. Routine Description:
  120. Initialize the BUS_INTERFACE_STANDARD fields.
  121. Arguments:
  122. PciInterface Pointer to the PciInterface record for this
  123. interface type.
  124. InterfaceSpecificData
  125. A ULONG containing the resource type for which
  126. arbitration is required.
  127. InterfaceReturn
  128. Return Value:
  129. TRUE is this device is not known to cause problems, FALSE
  130. if the device should be skipped altogether.
  131. --*/
  132. {
  133. PBUS_INTERFACE_STANDARD standard = (PBUS_INTERFACE_STANDARD)InterfaceReturn;
  134. standard->Size = sizeof( BUS_INTERFACE_STANDARD );
  135. standard->Version = BUSINTRF_VERSION;
  136. standard->Context = DeviceExtension;
  137. standard->InterfaceReference = busintrf_Reference;
  138. standard->InterfaceDereference = busintrf_Dereference;
  139. standard->TranslateBusAddress = PciPnpTranslateBusAddress;
  140. standard->GetDmaAdapter = PciPnpGetDmaAdapter;
  141. standard->SetBusData = PciPnpWriteConfig;
  142. standard->GetBusData = PciPnpReadConfig;
  143. return STATUS_SUCCESS;
  144. }
  145. NTSTATUS
  146. busintrf_Initializer(
  147. IN PPCI_ARBITER_INSTANCE Instance
  148. )
  149. /*++
  150. Routine Description:
  151. For bus interface, does nothing, shouldn't actually be called.
  152. Arguments:
  153. Instance Pointer to the PDO extension.
  154. Return Value:
  155. Returns the status of this operation.
  156. --*/
  157. {
  158. ASSERTMSG("PCI busintrf_Initializer, unexpected call.", 0);
  159. return STATUS_UNSUCCESSFUL;
  160. }
  161. BOOLEAN
  162. PciPnpTranslateBusAddress(
  163. IN PVOID Context,
  164. IN PHYSICAL_ADDRESS BusAddress,
  165. IN ULONG Length,
  166. IN OUT PULONG AddressSpace,
  167. OUT PPHYSICAL_ADDRESS TranslatedAddress
  168. )
  169. /*++
  170. Routine Description:
  171. This function is used to translate bus addresses from legacy drivers.
  172. Arguments:
  173. Context - Supplies a pointer to the interface context. This is actually
  174. the PDO for the root bus.
  175. BusAddress - Supplies the orginal address to be translated.
  176. Length - Supplies the length of the range to be translated.
  177. AddressSpace - Points to the location of of the address space type such as
  178. memory or I/O port. This value is updated by the translation.
  179. TranslatedAddress - Returns the translated address.
  180. Return Value:
  181. Returns a boolean indicating if the operations was a success.
  182. --*/
  183. {
  184. PPCI_PDO_EXTENSION pdoExtension = (PPCI_PDO_EXTENSION)Context;
  185. PPCI_FDO_EXTENSION fdoExtension;
  186. PAGED_CODE();
  187. ASSERT_PCI_PDO_EXTENSION(pdoExtension);
  188. return HalTranslateBusAddress(PCIBus,
  189. PCI_PARENT_FDOX(pdoExtension)->BaseBus,
  190. BusAddress,
  191. AddressSpace,
  192. TranslatedAddress);
  193. }
  194. ULONG
  195. PciPnpReadConfig(
  196. IN PVOID Context,
  197. IN ULONG WhichSpace,
  198. IN PVOID Buffer,
  199. IN ULONG Offset,
  200. IN ULONG Length
  201. )
  202. /*++
  203. Routine Description:
  204. This function reads the PCI configuration space.
  205. Arguments:
  206. Context - Supplies a pointer to the interface context. This is actually
  207. the PDO for the root bus.
  208. Buffer - Supplies a pointer to where the data should be placed.
  209. Offset - Indicates the offset into the data where the reading should begin.
  210. Length - Indicates the count of bytes which should be read.
  211. Return Value:
  212. Returns the number of bytes read.
  213. --*/
  214. {
  215. PPCI_PDO_EXTENSION pdoExtension = (PPCI_PDO_EXTENSION)Context;
  216. ULONG lengthRead;
  217. ASSERT_PCI_PDO_EXTENSION(pdoExtension);
  218. PciReadDeviceSpace(pdoExtension,
  219. WhichSpace,
  220. Buffer,
  221. Offset,
  222. Length,
  223. &lengthRead
  224. );
  225. return lengthRead;
  226. }
  227. ULONG
  228. PciPnpWriteConfig(
  229. IN PVOID Context,
  230. IN ULONG WhichSpace,
  231. IN PVOID Buffer,
  232. IN ULONG Offset,
  233. IN ULONG Length
  234. )
  235. /*++
  236. Routine Description:
  237. This function writes the PCI configuration space.
  238. Arguments:
  239. Context - Supplies a pointer to the interface context. This is actually
  240. the PDO for the root bus.
  241. Buffer - Supplies a pointer to where the data to be written is.
  242. Offset - Indicates the offset into the data where the writing should begin.
  243. Length - Indicates the count of bytes which should be written.
  244. Return Value:
  245. Returns the number of bytes read.
  246. --*/
  247. {
  248. PPCI_PDO_EXTENSION pdoExtension = (PPCI_PDO_EXTENSION)Context;
  249. ULONG lengthWritten;
  250. ASSERT_PCI_PDO_EXTENSION(pdoExtension);
  251. PciWriteDeviceSpace(pdoExtension,
  252. WhichSpace,
  253. Buffer,
  254. Offset,
  255. Length,
  256. &lengthWritten
  257. );
  258. return lengthWritten;
  259. }
  260. PDMA_ADAPTER
  261. PciPnpGetDmaAdapter(
  262. IN PVOID Context,
  263. IN struct _DEVICE_DESCRIPTION *DeviceDescriptor,
  264. OUT PULONG NumberOfMapRegisters
  265. )
  266. /*++
  267. Routine Description:
  268. This function writes the PCI configuration space.
  269. Arguments:
  270. Context - Supplies a pointer to the interface context. This is actually
  271. the PDO for the root bus.
  272. DeviceDescriptor - Supplies the device descriptor used to allocate the dma
  273. adapter object.
  274. NubmerOfMapRegisters - Returns the maximum number of map registers a device
  275. can allocate at one time.
  276. Return Value:
  277. Returns a DMA adapter or NULL.
  278. --*/
  279. {
  280. PPCI_PDO_EXTENSION pdoExtension = (PPCI_PDO_EXTENSION)Context;
  281. PAGED_CODE();
  282. ASSERT_PCI_PDO_EXTENSION(pdoExtension);
  283. //
  284. // If this is DMA on a PCI bus update the bus number, otherwise leave well
  285. // alone
  286. //
  287. if (DeviceDescriptor->InterfaceType == PCIBus) {
  288. DeviceDescriptor->BusNumber = PCI_PARENT_FDOX(pdoExtension)->BaseBus;
  289. }
  290. return IoGetDmaAdapter(
  291. pdoExtension->ParentFdoExtension->PhysicalDeviceObject,
  292. DeviceDescriptor,
  293. NumberOfMapRegisters);
  294. }