Writing a SCSI peripheral driver


The open(D2osdi) routine opens the device for access and performs interrupt-driven initialization if required.


#include "sys/scsi.h"

int xxopen(dev, rw, bc) dev_t dev; int rw, bc;

The logic is as follows:

  1. Extract the Logical Unit Number (LUN) from the minor device number. If the device is not configured, use the cmn_err(D3oddi) function to issue an error message, set u.u_error to ENXIO, and return.

  2. Call scsi_getdev(D3osdi) to get device information from the SCSI configuration table. If information is not found, use the cmn_err(D3oddi) function to issue an error message, set u.u_error to ENODEV, and return.

  3. Verify that the device is configured by issuing a test command. In the sample driver, this command is coded in the Sflp_test_ready( ) subroutine. If all tests pass, issue the cdistributed(D3oddi) and/or bdistributed(D3oddi) function to register the SCSI peripheral driver as multithreaded.

    The sample driver registers only the strategy( ), read( ), and write( ) routines as multithreaded. Allowing other routines to run only on the base CPU does not significantly impact performance and simplifies multithreading from I/O assymetrical multiprocessor systems where some CPUs cannot access the I/O bus.

    If the test fails, wake up each device served by your driver by sending a command. The sample driver does this in its Sflpopen_exit( ) routine.

  4. Perform any additional setup tasks. For example, the sample SCSI peripheral driver sets up disk-specific information required by the diskinfo structure and other standard disk driver structures.

  5. Issue the printcfg(D3oddi) function tp display configuration information for the device. In particular, the name of the driver must be adapter, and the type of the driver must be the internal name as specified in column 1 of the mdevice(F) file. For example, the following call to printcfg(D3oddi) sets name=adapter and type=dpt:
    The output from this call will be similar to:
       adapter 0x5C80-0x5C90 14 - type=dpt
    See the sample driver to see how this information is gathered throughout the Sflpopen( ) routine.

  6. Exit the routine by releasing the last request block, turning off the flag to indicate that you are opening the device, and then calling splx(D3oddi) to restore any previously set interrupts.

© 2005 The SCO Group, Inc. All rights reserved.