Device Access Functions
Drivers use the ddi_get8(9F) and ddi_put8(9F) family of routines in conjunction with the handle returned by ddi_regs_map_setup(9F) to transfer data to and from a device. The DDI framework automatically handles any byte swapping that is required to meet host or device endian formats, and enforces any store-ordering constraints the device might have.
The DDI provides interfaces for transferring data in 8, 16, 32, and 64 bit quantities, as well as interfaces for transferring multiple values repeatedly. See the man pages for the ddi_get8(9F), ddi_put8(9F), ddi_rep_get8(9F) and ddi_rep_put8(9F) families of routines for a complete listing and description of these interfaces.
Example 6-2 builds on Example 6-1 where the driver mapped the device's CSR and data registers. Here, the driver's write(9E) entry point, when called, will write a buffer of data to the device one byte at a time.
Example 6-2
Alternate Device Access Interfaces
While having a driver implement all device accesses using the ddi_get8(9F) and ddi_put8(9F) family of interfaces, Solaris provides interfaces specific to particular bus implementations. While these functions are more efficient on some platforms, use of these routines can limit the ability of the driver to remain portable across different bus versions of the device.
Memory Space Access
With memory mapped access, device registers appear in memory address space. The ddi_getX family of routines (such as ddi_get16(9F)) and the ddi_putX family (such as ddi_put8(9F)) are available for use by drivers as an alternative to the standard device access interfaces.
I/O Space Access
With I/O space access, the device registers appear in I/O space, where each addressable element is called an I/O port. The ddi_io_get8(9F) and ddi_io_put8(9F) family of routines is available for use by drivers as an alternative to the standard device access interfaces.
PCI Configuration Space Access
To access PCI configuration space without using the normal device access interfaces, a driver is required to map PCI configuration space by calling pci_config_setup(9F) in place of ddi_regs_map_setup(9F). The driver can then call the pci_config_get8(9F) and pci_config_put8(9F) family of interfaces to access PCI configuration space.