Writing Device Drivers

Device Tree

The kernel uses a tree structure to represent various physical machine configurations. Each node in the tree structure is described by a device-information structure. Standard device drivers and their devices are associated with leaf nodes. These drivers are called leaf drivers. Bus drivers are associated with bus nexus nodes and are called bus nexus drivers. This manual documents writing leaf drivers and one type of nexus driver, a SCSI host bus adapter (HBA) driver. This manual does not document any other type of bus nexus driver. Figure 1-1 illustrates two possible device tree configurations.

Figure 1-1 Possible Device Tree Configurations


The topmost node in the device tree is called the root node. The tree structure creates a parent-child relationship between nodes. This parent-child relationship is the key to architectural independence. When a leaf or bus nexus driver requires a service that is architecturally dependent in nature, it requests its parent to provide the service.

The intermediate nodes in the tree are generally associated with buses, such as the SBus, SCSI, and PCI buses. These nodes are called bus nexus nodes and the drivers associated with them are called bus nexus drivers. Bus nexus drivers encapsulate the architectural dependencies associated with a particular bus.

This approach enables drivers to function regardless of the architecture of the machine or the processor. The xyz driver, for example, is source compatible with the architectural configurations shown in Figure 1-1; it can be binary compatible if the system uses the same instruction set architecture.

Additionally, in Figure 1-1, the bus nexus driver associated with the PCI-to-SBus adapter card handles all of the architectural dependencies of the interface. The xyz driver only needs to determine that it is connected to an SBus.

Example Device Tree

In this example, the system builds a tree structure that contains information about the devices connected to the machine at boot time. The system uses this information to create a dependency tree with bus nexus nodes and leaf nodes.

Figure 1-2 illustrates a sample device tree for a frame buffer (SUNW,ffb), a pseudo bus nexus node, and several PCI devices associated with a PCI bus nexus node.

Figure 1-2 Example Device Tree


In Figure 1-2, the SUNW,ffb leaf node represents a system frame buffer. The pseudo bus nexus node is the parent node of any pseudo device drivers (drivers without hardware). The PCI bus nexus node is the parent node for the following children:

Device Drivers

Associated with each leaf or bus nexus node may be a device driver. Each driver has associated with it a device operations structure (see dev_ops(9S)) that defines the operations that the device driver can perform. The device operations structure contains function pointers for generic operations such as getinfo(9E) and attach(9E). It also contains a pointer to operations specific to bus nexus drivers and a pointer to operations specific to leaf drivers.

Displaying the Device Tree

The device tree can be displayed in two ways:

  1. The prtconf(1M) command displays all of the device nodes in the device tree.

  2. The /devices hierarchy is a representation of the device tree; use ls(1) to view it.

    Note -

    /devices displays only devices that have drivers configured into the system. prtconf(1M) shows all device nodes regardless of whether a driver for the device exists on the system or not.


The prtconf(1M) command (excerpted example follows) displays all the devices in the system:

	pci, instance #0
								ebus, instance #0
       auxio (driver not attached)
       power (driver not attached)
       SUNW,pll (driver not attached)
       sc (driver not attached)
       se, instance #0
       su, instance #0
       su, instance #1
       ecpp (driver not attached)
       fdthree (driver not attached)
       eeprom (driver not attached)
       flashprom (driver not attached)
       SUNW,CS4231 (driver not attached)
 								network, instance #0
 								scsi, instance #0
       disk (driver not attached)
       tape (driver not attached)
       sd, instance #0
       sd, instance #1 (driver not attached)
       sd, instance #2 (driver not attached)
       sd, instance #3 (driver not attached)
       sd, instance #4 (driver not attached)
       sd, instance #5 (driver not attached)
pci, instance #1
SUNW,UltraSPARC-II (driver not attached)
SUNW,ffb (driver not attached)
pseudo, instance #0 


The /devices hierarchy provides a name space that represents the device tree. Following is an abbreviated listing of the /devices name space. The sample output corresponds to the example device tree and prtconf(1M) output shown previously.


Binding a Driver to a Device Node

In addition to constructing the device tree, the kernel must also determine the drivers that will be used to manage the devices.

Binding a driver to a device node refers to the process by which the system selects a driver to manage a particular device. The driver binding name is the name that links a driver to a unique device node in the device information tree. For each device in the device tree, the system chooses a driver from a list of drivers.

Each device node has a name property associated with it. This property may be derived either from an external agent such as the PROM during system boot or from a driver.conf file. In either case, the name property represents the node name assigned to a device in the device tree.

Figure 1-3 Device Node Names


A device node may also have a compatible property associated with it. The compatible property (if it exists) contains an ordered list of one or more possible driver names for the device.

The system uses both the name and the compatible properties to select a driver for the device. If the compatible property exists, the system first attempts to match the contents of the compatible property to a driver on the system. The compatible property is simply a list of possible driver names from which the system can determine the specific driver binding name for the device.

Beginning with the first driver name on the compatible property list, the system attempts to match the driver name to a known driver on the system. It processes each entry on the list until either a match is found or the end of the list is reached.

If the contents of either the name property or the compatible property match a driver on the system, then that driver is bound to the device node. If no match is found, no driver is bound to the device node.

Generic Device Names

Some devices with a compatible property use a generic device name as the value for the name property. Generic device names describe the function of a device without actually identifying a specific driver for the device. For example, a SCSI host bus adapter may have a generic device name of scsi. An Ethernet device may have a generic device name of ethernet.

The compatible property allows the system to determine alternate driver names (like glm for scsi HBA device drivers or hme for ethernet device drivers) for devices with a generic device name.

Devices with generic device names must supply a compatible property.

Note -

For a complete description of generic device names, see the IEEE 1275 Open Firmware Boot Standard.

Figure 1-4 and Figure 1-5 show two device nodes: one node uses a specific device name and the other uses a generic device name.

For the device node with a specific device name, the driver binding name SUNW,ffb is the same name as the device node name.

Figure 1-4 Specific Driver Node Binding


For the device node with the generic device name display, the driver binding name SUNW,ffb is the first name on the compatible property driver list that matches a driver on the system driver list. In this case, display is a generic device name for frame buffers.

Figure 1-5 Generic Driver Node Binding