Skip to main content

By clicking Submit, you agree to the developerWorks terms of use.

The first time you sign into developerWorks, a profile is created for you. Select information in your profile (name, country/region, and company) is displayed to the public and will accompany any content you post. You may update your IBM account at any time.

All information submitted is secure.

  • Close [x]

The first time you sign in to developerWorks, a profile is created for you, so you need to choose a display name. Your display name accompanies the content you post on developerworks.

Please choose a display name between 3-31 characters. Your display name must be unique in the developerWorks community and should not be your email address for privacy reasons.

By clicking Submit, you agree to the developerWorks terms of use.

All information submitted is secure.

  • Close [x]

developerWorks Community:

  • Close [x]

IBM AIX device driver development

A tutorial on AIX device driver framework and related APIs

Gautam Raut (, Senior Software Engineer, IBM
Gautam Raut works as a Senior Software Engineer for the Andrew File System (AFS) Team at the IBM Software Labs in Pune, India. He works with kernel and user-level debugging of dumps and crashes, as well as reported bugs on the Linux and AIX platforms. He has also worked on various AFS-specific AIX kernel components. Gautam holds M.S. in Computer Science from the University of Pune. He is a Linux enthusiast who spends his spare time exploring the Linux kernel on his Fedora 8 box.

Summary:  This tutorial illustrates the IBM® AIX® device driver framework and related application programming interfaces (APIs). Here, we shall discuss about the device switch structure, API to register device switch methods, major and minor number management, and moving data from kernel to user space.

Date:  28 Mar 2013
Level:  Intermediate PDF:  A4 and Letter (244 KB | 15 pages)Get Adobe® Reader®

Activity:  20933 views

Driver entry points

Driver entry points are nothing but the members of the struct devsw structure. All these members must be initialized before adding the device into device switch table. It is not mandatory for a device driver to implement all the methods. An unimplemented member can be initialized to nodev. These entry points can accept dev_no (device number of the device or the subdevice to which this operation is directed), chan (channel ID for a multiplexed device), ext ( an integer useful for calls to extended subroutines such as openx, readx, writex and ioctlx that pass extra device-specific parameters to few of the device entry points.)

1) ddconfig or d_config:

 int d_config(dev_t dev_no, int cmd, struct uio *uiop)

It is invoked by the sysconfig() system call. It prepares a device for its first open() call. It can initialize, terminate, request configuration data for device or perform device specific configuration function. The uio structure contains data area for configuration information.

2) ddopen or d_open:

int d_open(dev_t dev_no, ulong flag, chan_t chan, ext_t ext)

It enables device operation and prepares for data transfer. It allocates internal buffers and enforces policies with respect to how a device can be opened based on the current device state. This is invoked by the open() or create() system calls and fp_open() or fp_opendev() kernel service. The input parameter flag specifies open file control flags, such as DREAD, DWRITE, and so on.

3) ddclose or d_close:

int d_close(dev_t dev_no, chan_t chan)

It closes a previously opened device instance. It is called by the close() system call or the fp_close() kernel service. A device instance is considered closed after d_close() returns to the caller even if a non-zero return code is returned.

4) ddread or d_read:

 int d_read(dev_t devno, struct uio *uiop, chan_t chan, int ext)

It reads in data from a character device. It is called by system calls, such as read() or readx() and the fp_rwuio() kernel service. Here, the uio structure describes the data area or areas in which to be written.

5) ddwrite or d_write:

int d_write (dev_t devno, struct uio *uiop, chan_t chan, int ext)

It writes out data to a character device. It is called by system calls, such as write() or writex(), and the fp_rwuio() kernel service. Here, the uio structure describes the data area or areas from which to be written.

6) ddioctl or d_ioctl:

int d_ioctl(dev_t devno, int cmd, void *arg, ulong devflag, chan_t chan, int ext)

It performs special I/O control operations requested in ioctl() or ioctlx() system calls or the fp_ioctl() kernel service. It must respond to the IOCINFO command which returns the devinfo structure that describes the device.

7) ddstrategy or d_strategy:

int d_strategy(struct buf* buffer)

It performs block-oriented I/O by scheduling a read or write to a block device. It maps I/O requests to device requests so that with minimum device requests maximum data transfer is achieved. Buffer is a pointer to a linked list of buffer structures chained with the b_forw pointer. The ddstrategy routine can receive a single request with multiple buf structures. However, it is not required to process requests in any specific order. This routine never returns a return code and never waits for I/O completion.

8) ddselect or d_select:

int d_select(dev_t devno, ushort events, ushort *reventp,  int chan)

It checks for one or more events specified by the events flag occurred on a given device and returns a pointer to the occurred events in reventp. It is called by select and poll system calls or fp_select kernel service.

9) d_mpx or ddmpx:

int d_mpx(dev_t devno, chan_t* chanp, char* channame)

It allocates and deallocates logical channels for multiplexed devices. It is called once for each open() of a device file before the d_open call to allocate a channel and once for each close of a device file after d_close. It is supported by only character class device drivers. chanp is a pointer to channel ID and channame is a path name extension for the channel to be allocated.

10) d_revoke or ddrevoke:

int d_revoke (dev_t devno, chan_t chan, int flag)

For driver for devices requiring trusted computing path, ddrevoke() provides a secure path to the terminal. It is supported only by character class device drivers. It is called by the revoke() system call or the frevoke() kernel API.

11) d_dump or dddump:

int d_dump(dev_t devno, struct uio * uiop, int cmd, int arg, chan_t chan, int ext)

It writes system dump data to a device. This is an optional routine for a device driver. It is required only when the device driver supports a device as a target for a possible kernel dump. This routine must not call any kernel service that can page fault.

7 of 15 | Previous | Next


Zone=AIX and UNIX, Linux
TutorialTitle= IBM AIX device driver development