|
NAMEproto —
Generic prototyping and diagnostics driver
SYNOPSISTo compile this driver into the kernel, place the following line in your kernel configuration file:device proto Alternatively, to load the driver as a module at boot time, place the following line in loader.conf(5): proto_load="YES" To have the driver attach to a device instead of its regular driver, mention it in the list of devices assigned to the following loader variable: hw.proto.attach="desc[,desc]"
DESCRIPTIONTheproto device driver attaches to PCI or ISA devices
when no other device drivers are present for those devices and it creates
device special files for all resources associated with the device. The driver
itself has no knowledge of the device it attaches to. Programs can open these
device special files and perform register-level reads and writes. As such, the
proto device driver is nothing but a conduit or
gateway between user space programs and the hardware device.
Examples for why this is useful include hardware diagnostics and prototyping. In both these use cases, it is far more convenient to develop and run the logic in user space. Especially hardware diagnostics requires a somewhat user-friendly interface and adequate reporting. Neither is done easily as kernel code. I/O port resourcesDevice special files created for I/O port resources allow lseek(2), read(2), write(2) and ioctl(2) operations to be performed on them. The read(2) and write(2) system calls are used to perform input and output (resp.) on the port. The amount of data that can be read or written at any single time is either 1, 2 or 4 bytes. While theproto driver does not prevent
reading or writing 8 bytes at a time for some architectures, it should not be
assumed that such actually produces correct results. The
lseek(2)
system call is used to select the port number, relative to the I/O port region
being represented by the device special file. If, for example, the device
special file corresponds to an I/O port region from 0x3f8 to 0x3ff inclusive,
then an offset of 4 given to lseek with a whence value of SEEK_SET will target
port 0x3fc on the next read or write operation. The
ioctl(2)
system call can be used for the PROTO_IOC_REGION
request. This ioctl request returns the extend of the resource covered by this
device special file. The extend is returned in the following structure:
struct proto_ioc_region { unsigned long address; unsigned long size; }; Memory mapped I/O resourcesThe device special files created for memory mapped I/O resources behave in the same way as those created for I/O port resources. Additionally, device special files for memory mapped I/O resources allow the memory to be mapped into the process' address space using mmap(2). Reads and writes to the memory address returned by mmap(2) go directly to the hardware. As such the use of read(2) and write(2) can be avoided, reducing the access overhead significantly. Alignment and access width constraints put forth by the underlying device apply. Also, make sure the compiler does not optimize memory accesses away or has them coalesced into bigger accesses.DMA pseudo resourceA device special file named busdma is created for the purpose of doing DMA. It only supports ioctl(2) and only for thePROTO_IOC_BUSDMA request. This device
special file does not support
read(2) nor
write(2).
The PROTO_IOC_BUSDMA request has an argument that is
both in and out and is defined as follows:
struct proto_ioc_busdma { unsigned int request; unsigned long key; union { struct { unsigned long align; unsigned long bndry; unsigned long maxaddr; unsigned long maxsz; unsigned long maxsegsz; unsigned int nsegs; unsigned int datarate; unsigned int flags; } tag; struct { unsigned long tag; unsigned int flags; unsigned long virt_addr; unsigned long virt_size; unsigned int phys_nsegs; unsigned long phys_addr; unsigned long bus_addr; unsigned int bus_nsegs; } md; struct { unsigned int op; unsigned long base; unsigned long size; } sync; } u; unsigned long result; };
PCI configuration spaceAccess to PCI configuration space is possible through the pcicfg device special file. The device special file supports lseek(2), read(2) and write(2). Usage is the asme as for I/O port resources.FILESAll device special files corresponding to a PCI device are located under /dev/proto/pci<d>:<b>:<s>:<f> with pci<d>:<b>:<s>:<f> representing the location of the PCI device in the PCI hierarchy. A PCI location includes:
Every PCI device has a device special file called pcicfg. This device special file gives access to the PCI configuration space. A device special file called busdma is also created. This device special file provides the interfaces needed for doing DMA. For each valid base address register (BAR), a device special file is created that contains the BAR offset and the resource type. A resource type can be either io or mem representing I/O port or memory mapped I/O space (resp.) ISA devices do not have a location. Instead, they are identified by the first I/O port address or first memory mapped I/O address. Consequently, all device special files corresponding to an ISA device are located under /dev/proto/isa:<addr> with addr the address in hexadecimal notation. For each I/O port or memory mapped I/O address, a device special file is created that contains the resource identification used by the kernel and the resource type. The resource type can be either io or mem representing I/O port or memory mapped I/O space (resp.) When the device has a DMA channel assigned to it, a device special file with the name busdma is created as well. This device special file provides the interfaces needed for doing DMA. If the ISA device is not a Plug-and-Play device nor present in the ACPI device tree, it must have the appropriate hints so that the kernel can reserve the resources for it. EXAMPLESA single function PCI device in domain 0, on bus 1, in slot 2 and having a single memory mapped I/O region will have the following device special files:
A legacy floppy controller will have the following device files:
SEE ALSOioctl(2), lseek(2), mmap(2), read(2), write(2), bus_dma_tag_create(9), bus_dmamap_sync(9), bus_dmamem_alloc(9)AUTHORSTheproto device driver and this manual page were
written by Marcel Moolenaar
<marcel@xcllnt.net>.
SECURITY CONSIDERATIONSBecause programs have direct access to the hardware, theproto driver is inherently insecure. It is not
advisable to use this driver on a production machine.
MISSING FUNCTIONALITYTheproto driver does not fully support memory
descriptors that need multiple physical memory segments or multiple bus space
segments. At the very least, an operation is needed on the DMA pseudo resource
for the application to obtain all segments.
The DMA support for devices other than busmaster devices is not present yet. The details of how a program is to interact with the DMA controller still need to be fleshed out.
Visit the GSP FreeBSD Man Page Interface. |