18.4 Accessing PCI resources

PCI drivers should only access the I/O and memory-mapped I/O resources on the PCI controllers they manage. They should never attempt to access the I/O or memorymapped I/O resource of a PCI controller that they are not managing. They should also never touch the I/O or memory-mapped I/O resources of the chipset or the motherboard.
The PCI I/O Protocol provides services that allow a PCI driver to easily access the resources of the PCI controllers it is currently managing. These services hide platformspecific implementation details and prevent a PCI driver from inadvertently accessing resources of the motherboard or other PCI controllers. The PCI I/O Protocol has also been designed to simplify the implementation of PCI drivers. For example, a PCI driver should never read the BARs in the PCI configuration header. Instead, the PCI driver passes in a BarIndex and Offset into the PCI I/O Protocol services. The PCI bus driver is responsible for managing the PCI controller's BARs.
The services of the PCI I/O Protocol allowing a PCI driver to access the resources of a PCI controller include the following:
  • PciIo->PollMem()
  • PciIo->PollIo()
  • PciIo->Mem.Read()
  • PciIo->Mem.Write()
  • PciIo->Io.Read()
  • PciIo->Io.Write()
  • PciIo->Pci.Read()
  • PciIo->Pci.Write()
  • PciIo->CopyMem()
Another important resource provided through the PCI I/O Protocol is the contents of the PCI option ROM. The RomSize and RomImage fields of the PCI I/O Protocol provide access to a copy of the PCI option ROM contents. These fields may be useful if the PCI driver requires additional information from the contents of the PCI option ROM.
Note: It is important that the PCI option ROM contents not be modified through the RomImage field. Modifications to this buffer only modify the copy of the PCI option ROM contents in system memory. The PCI I/O Protocol does not provide services to modify the content of the actual PCI option ROM.