An introduction to block device drivers
We have already seen several macros which are very helpful in writing block device drivers. Many of these are defined in drivers/block/blk.h, and have to be specially set up.
At the top of the device driver, after including the standard include files your driver needs (which must include linux/major.h and linux/blkdrv.h), you should write the following lines:
#define MAJOR_NR FOO_MAJOR #include "blk.h"
This, in turn, requires that you define FOO_MAJOR to be the major number of the device you are writing in linux/major.h.
Now you need to edit blk.h. One section of blk.h, right near the top, includes definitions of macros that depend on the definition of MAJOR_NR. Add an entry to the end which looks like this:
#elif (MAJOR_NR == FOO_MAJOR) #define DEVICE_NAME "foobar" #define DEVICE_REQUEST do_foo_request #define DEVICE_NR(device) (MINOR(device) >> 6) #define DEVICE_ON(device) #define DEVICE_OFF(device) #endif
These are the required macros for each block device driver. There are more macros that can be defined; they are explained in the KHG.
DEVICE_NAME is the name of the driver. The AT hard drive driver uses the abbreviation “hd” in most places; for example, the request() procedure is called do_hd_request(). However, its DEVICE_NAME is “harddisk”. Similarly, the floppy driver, “fd”, has a DEVICE_NAME of “floppy”. Other drivers are even more descriptive; read blk.h and follow suit.
DEVICE_REQUEST is the request() procedure for the driver.
DEVICE_NR is used to determine the actual physical device. For example, the standard AT hard disk driver uses 64 minor devices for each physical device, so DEVICE_NR is defined as (MINOR(device)>6). The SCSI disk driver uses 16 minor device numbers per physical device, so for it, DEVICE_NR is defined as (MINOR(device)>4). If you have only one minor device number per physical device, define DEVICE_NR as (MINOR(device)).
DEVICE_ON and DEVICE_OFF are only used for devices that have to be turned on and off. The floppy driver is the only driver that uses this capability. You will most likely want to define these to be nothing at all.
All these macros, as well as many others, can be used in your driver where appropriate. blk.h includes a lot of macros, and studying how they are used in other drivers will help you use them in your own driver. I won't document them fully here, but I will briefly mention some of them to make your life easier.
DEVICE_INTR, SET_INTR, and CLEAR_INTR make support for interrupt-driven devices much easier. DEVICE_ TIMEOUT, SET_TIMER, and CLEAR_TIMER help you set limits on how long may be taken to satisfy a request.
I've saved the first, and perhaps most important, thing for last. Before you can read or write a single block, the kernel has to be notified that the device exists. All device drivers are required to implement an initialization function, and there are some special requirements for block device drivers. Here is a sample idealized initialization function:
long foo_init(long mem_start, int length)
{
if (register_blkdev(FOO_MAJOR,"foo", & foo_fops)) {
printk("FOOBAR: Unable to get major %d.\n",
FOO_MAJOR);
return 0;
}
if (!foo_exists()) {
/* the foobar device doesn't exist */
return 0;
}
/* initialize hardware if necessary */
/* notify user device found */
printk("FOOBAR: Found at address %d.\n",
foo_addr());
/* tell buffer cache how to process requests */
blk_dev[FOO_MAJOR].request_fn = DEVICE_REQUEST;
/* specify the blocksize */
blksize_size[MAJOR_NR] = 1024;
return(size_of_memory_reserved);
}
The three things here that are specific to block device drivers are:
register_blkdev() registers the file operations structure with the Virtual Filesystem Switch (VFS), which is the system that manages access to files.
blk_dev tells the buffer cache where the request procedure is.
blksize_size tells the buffer cache what size blocks to request.
It is worth noting that the hardware device detection and initialization, which I have denoted as foo_exists() here, is very delicate code. If you can rely on a string somewhere in the BIOS of the computer to determine whether the device exists and where it is, it's relatively easy. However, if you have to check various I/O ports, you can hang the computer by writing the wrong value to the wrong port, or even reading the wrong port. Check only well-known ports if you must check ports, and provide kernel command-line arguments for other ports. To do this, read init/main.c and add a section of your own. If you can't figure out how to do it, an explanation is forthcoming in the next version of the KHG.
Of course, none of this initialization will happen if foo_init() is never called. Add a prototype to the top of blk.h with the other prototypes, and add a call to foo_init() in ll_rw_blk.c in the blk_dev_init() function. That call should be protected by #ifdef CONFIG_FOO like the rest of the *_init() functions there, and a corresponding line should be added to the config.in file:
bool `Foobar disk support' CONFIG_FOO y
drivers/block/Makefile should have a section added that looks like this:
ifdef CONFIG_FOO OBJS := $(OBJS) foo.o SRCS := $(SRCS) foo.c endif
This done, configuration should work correctly. Your device driver file does not need to have any references to CONFIG_FOO; the only specific reference to it is commented out in ll_rw_blk.c, and the makefile only builds it if it has been configured in.
Now all you have to do is write and debug your own new block device driver. I wish you the best of luck, and I hope that this whirlwind tour has given you a head start.
Michael K. Johnson is the editor of Linux Journal, and is also the author of the Linux Kernel Hackers' Guide (the KHG). He is using this column to develop and expand on the KHG.
Realizing the promise of Apache® Hadoop® requires the effective deployment of compute, memory, storage and networking to achieve optimal results. With its flexibility and multitude of options, it is easy to over or under provision the server infrastructure, resulting in poor performance and high TCO. Join us for an in depth, technical discussion with industry experts from leading Hadoop and server companies who will provide insights into the key considerations for designing and deploying an optimal Hadoop cluster.
Sponsored by AMD
If you already use virtualized infrastructure, you are well on your way to leveraging the power of the cloud. Virtualization offers the promise of limitless resources, but how do you manage that scalability when your DevOps team doesn’t scale? In today’s hypercompetitive markets, fast results can make a difference between leading the pack vs. obsolescence. Organizations need more benefits from cloud computing than just raw resources. They need agility, flexibility, convenience, ROI, and control.
Stackato private Platform-as-a-Service technology from ActiveState extends your private cloud infrastructure by creating a private PaaS to provide on-demand availability, flexibility, control, and ultimately, faster time-to-market for your enterprise.
Sponsored by ActiveState
| Non-Linux FOSS: libnotify, OS X Style | Jun 18, 2013 |
| Containers—Not Virtual Machines—Are the Future Cloud | Jun 17, 2013 |
| Lock-Free Multi-Producer Multi-Consumer Queue on Ring Buffer | Jun 12, 2013 |
| Weechat, Irssi's Little Brother | Jun 11, 2013 |
| One Tail Just Isn't Enough | Jun 07, 2013 |
| Introduction to MapReduce with Hadoop on Linux | Jun 05, 2013 |
- Containers—Not Virtual Machines—Are the Future Cloud
- Non-Linux FOSS: libnotify, OS X Style
- Linux Systems Administrator
- Lock-Free Multi-Producer Multi-Consumer Queue on Ring Buffer
- Validate an E-Mail Address with PHP, the Right Way
- Senior Perl Developer
- Technical Support Rep
- UX Designer
- Introduction to MapReduce with Hadoop on Linux
- Web & UI Developer (JavaScript & j Query)
- user namespaces
2 hours 50 min ago - yea
3 hours 16 min ago - One advantage with VMs
5 hours 44 min ago - about info
6 hours 17 min ago - info
6 hours 18 min ago - info
6 hours 19 min ago - info
6 hours 21 min ago - info
6 hours 22 min ago - abut info
6 hours 24 min ago - info
6 hours 25 min ago
Featured Jobs
| Linux Systems Administrator | Houston and Austin, Texas | Host Gator |
| Senior Perl Developer | Austin, Texas | Host Gator |
| Technical Support Rep | Houston and Austin, Texas | Host Gator |
| UX Designer | Austin, Texas | Host Gator |
| Web & UI Developer (JavaScript & j Query) | Austin, Texas | Host Gator |
Free Webinar: Hadoop
How to Build an Optimal Hadoop Cluster to Store and Maintain Unlimited Amounts of Data Using Microservers
Realizing the promise of Apache® Hadoop® requires the effective deployment of compute, memory, storage and networking to achieve optimal results. With its flexibility and multitude of options, it is easy to over or under provision the server infrastructure, resulting in poor performance and high TCO. Join us for an in depth, technical discussion with industry experts from leading Hadoop and server companies who will provide insights into the key considerations for designing and deploying an optimal Hadoop cluster.
Some of key questions to be discussed are:
- What is the “typical” Hadoop cluster and what should be installed on the different machine types?
- Why should you consider the typical workload patterns when making your hardware decisions?
- Are all microservers created equal for Hadoop deployments?
- How do I plan for expansion if I require more compute, memory, storage or networking?




Comments
page 3?
This article has 3 pages, but it seems to end on page 2, because page 3 is empty.
Useful for a newbie
hi...
its really useful for a newbie entering into a block device driver, I am a just a beginner of it.. looking some more information regarding block driver in this forum.. thanks for the article..