You are on page 1of 7

7/18/13

Write For Us Submit Tips

Device Drivers, Part 4: Linux Character Drivers - LINUX For You


Subscribe to Print Edition Search

HOME

REVIEWS

HOW-TOS

CODING

INTERVIEWS

FEATURES

OVERVIEW

BLOGS

SERIES

IT ADMIN

Device Drivers, Part 4: Linux Character Drivers


By Anil Kumar Pugalia on February 1, 2011 in Concepts, Developers, Overview 15 Comments and 0 Reactions

Search for:

Search

Get Connected RSS Feed Twitter

This article, which is part of the series on Linux device drivers, deals with the various concepts related to character drivers and their implementation.
Shweta, at her PC in her hostel room, was all set to explore the characters of Linux character drivers, before it was taught in class. She recalled the following lines from professor Gopis class: todays first driver would be the template for any driver you write in Linux. Writing any specialised/advanced driver is just a matter of what gets filled into its constructor and destructor With that, she took out the first drivers code, and pulled out various reference books, to start writing a character driver on her own. She also downloaded the online book, Linux Device Drivers by Jonathan Corbet, Alessandro Rubini, and Greg Kroah-Hartman. Here is the summary of what she learnt.

Ws of character drivers
We already know what drivers are, and why we need them. What is so special about character drivers? If we write drivers for byte-oriented operations (or, in C lingo, character-oriented operations), then we refer to them as character drivers. Since the majority of devices are byteoriented, the majority of device drivers are character device drivers. Take, for example, serial drivers, audio drivers, video drivers, camera drivers, and basic I/O drivers. In fact, all device drivers that are neither storage nor network device drivers are some type of a character driver. Lets look into the commonalities of these character drivers, and how Shweta wrote one of them.

LINUX For You on

Follow

+2,394

The complete connection

www.linuxforu.com/2011/02/linux-character-drivers/

1/7

7/18/13

Device Drivers, Part 4: Linux Character Drivers - LINUX For You


Find us on Facebook

Open Source For You


Like 250,975 people like Open Source For You.

F acebook social plugin

Popular
Figure 1: Character driver overview

Comments

Tag cloud

April 4, 2013 4 Comments Aditya-Pareek

Crunchbang Linux Minimalist and Mac-Friendly

As shown in Figure 1, for any user-space application to operate on a byte-oriented device (in hardware space), it should use the corresponding character device driver (in kernel space). Character driver usage is done through the corresponding character device file(s), linked to it through the virtual file system (VFS). What this means is that an application does the usual file operations on the character device file. Those operations are translated to the corresponding functions in the linked character device driver by the VFS. Those functions then do the final lowlevel access to the actual device to achieve the desired results. Note that though the application does the usual file operations, their outcome may not be the usual ones. Rather, they would be as driven by the corresponding functions in the device driver. For example, a write followed by a read may not fetch what has just been written to the character device file, unlike for regular files. Remember that this is the usual expected behaviour for device files. Lets take an audio device file as an example. What we write into it is the audio data we want to play back, say through a speaker. However, the read would get us audio data that we are recording, say through a microphone. The recorded data need not be the played-back data. In this complete connection from the application to the device, there are four major entities involved: 1. Application 2. Character device file 3. Character device driver 4. Character device The interesting thing is that all of these can exist independently on a system, without the other being present. The mere existence of these on a system doesnt mean they are linked to form the complete connection. Rather, they need to be explicitly connected. An application gets connected to a device file by invoking the open system call on the device file. Device file(s) are linked to the device driver by specific registrations done by the driver. The driver is linked to a device by its device-specific low-level operations. Thus we form the complete connection. With this, note that the character device file is not the actual device, but just a placeholder for the actual device.

May 6, 2013 4 Comments Priyanka Sarkar

PHP Development: A Smart Career Move


April 1, 2013 2 Comments vinayak-pandey

Learn the Art of Linux Troubleshooting


April 4, 2013 2 Comments Claudia

Top 7 Linux Tips And Tricks For Beginners


June 20, 2013 2 Comments sophie-samuel

New and amazing features of Linux

Major and minor numbers


The connection between the application and the device file is based on the name of the device file. However, the connection between the device file and the device driver is based on the number of the device file, not the name. This allows a user-space application to have any name for the device file, and enables the kernel-space to have a trivial index-based linkage between the device file and the device driver. This device file number is more commonly referred to as the < m a j o r ,m i n o r >pair, or the major and minor numbers of the device file. Earlier (till kernel 2.4), one major number was for one driver, and the minor number used to represent the sub-functionalities of the driver. With kernel 2.6, this distinction is no longer mandatory; there could be multiple drivers under the same major number, but obviously, with different minor number ranges. However, this is more common with the non-reserved major numbers, and standard major numbers are typically preserved for single drivers. For example, 4 for serial interfaces, 13 for mice, 14 for audio devices, and so on. The following command would list the various character

www.linuxforu.com/2011/02/linux-character-drivers/

2/7

7/18/13
device files on your system:
$l sl/ d e v /|g r e p" ^ c "

Device Drivers, Part 4: Linux Character Drivers - LINUX For You

<major, minor> related support in kernel 2.6


Type (defined in kernel header l i n u x / t y p e s . h ):
d e v _ tcontains both major and minor numbers

Macros (defined in kernel header l i n u x / k d e v _ t . h ):


M A J O R ( d e v _ td e v )extracts the major number from d e v M I N O R ( d e v _ td e v )extracts the minor number from d e v M K D E V ( i n tm a j o r ,i n tm i n o r )creates the d e vfrom major and minor.

Connecting the device file with the device driver involves two steps: 1. Registering for the < m a j o r ,m i n o r >range of device files. 2. Linking the device file operations to the device driver functions. The first step is achieved using either of the following two APIs, defined in the kernel header l i n u x / f s . h :
+i n tr e g i s t e r _ c h r d e v _ r e g i o n ( d e v _ tf i r s t ,u n s i g n e di n tc n t ,c h a r* n a m e ) ; +i n ta l l o c _ c h r d e v _ r e g i o n ( d e v _ t* f i r s t ,u n s i g n e di n tf i r s t m i n o r ,u n s i g n e di n tc n t ,c h a r

The first API registers the cnt number of device file numbers, starting from first, with the given name. The second API dynamically figures out a free major number, and registers the cnt number of device file numbers starting from < t h ef r e em a j o r ,f i r s t m i n o r > , with the given name. In either case, the / p r o c / d e v i c e skernel window lists the name with the registered major number. With this information, Shweta added the following into the first driver code:
# i n c l u d e< l i n u x / t y p e s . h > # i n c l u d e< l i n u x / k d e v _ t . h > # i n c l u d e< l i n u x / f s . h > s t a t i cd e v _ tf i r s t ;/ /G l o b a lv a r i a b l ef o rt h ef i r s td e v i c en u m b e r

In the constructor, she added:


i f( a l l o c _ c h r d e v _ r e g i o n ( & f i r s t ,0 ,3 ," S h w e t a " )<0 ) { r e t u r n1 ; } p r i n t k ( K E R N _ I N F O" < M a j o r ,M i n o r > :< % d ,% d > \ n " ,M A J O R ( f i r s t ) ,M I N O R ( f i r s t ) ) ;

In the destructor, she added:


u n r e g i s t e r _ c h r d e v _ r e g i o n ( f i r s t ,3 ) ;

Its all put together, as follows:


1 2 3 4 5 6 7 8 9 1 0 1 1 1 2 1 3 1 4 1 5 1 6 1 7 1 8 1 9 2 0 2 1 2 2 2 3 2 4 2 5 2 6 2 7 2 8 2 9 3 0 3 1 3 2 # i n c l u d e< l i n u x / m o d u l e . h > # i n c l u d e< l i n u x / v e r s i o n . h > # i n c l u d e< l i n u x / k e r n e l . h > # i n c l u d e< l i n u x / t y p e s . h > # i n c l u d e< l i n u x / k d e v _ t . h > # i n c l u d e< l i n u x / f s . h > s t a t i cd e v _ tf i r s t ;/ /G l o b a lv a r i a b l ef o rt h ef i r s td e v i c en u m b e r s t a t i ci n t_ _ i n i to f c d _ i n i t ( v o i d )/ *C o n s t r u c t o r* / { p r i n t k ( K E R N _ I N F O" N a m a s k a r :o f c dr e g i s t e r e d " ) ; i f( a l l o c _ c h r d e v _ r e g i o n ( & f i r s t ,0 ,3 ," S h w e t a " )<0 ) { r e t u r n1 ; } p r i n t k ( K E R N _ I N F O" < M a j o r ,M i n o r > :< % d ,% d > \ n " ,M A J O R ( f i r s t ) ,M I N O R ( f i r s t ) ) ; r e t u r n0 ; } s t a t i cv o i d_ _ e x i to f c d _ e x i t ( v o i d )/ *D e s t r u c t o r* / { u n r e g i s t e r _ c h r d e v _ r e g i o n ( f i r s t ,3 ) ; p r i n t k ( K E R N _ I N F O" A l v i d a :o f c du n r e g i s t e r e d " ) ; } m o d u l e _ i n i t ( o f c d _ i n i t ) ; m o d u l e _ e x i t ( o f c d _ e x i t ) ; M O D U L E _ L I C E N S E ( " G P L " ) ; M O D U L E _ A U T H O R ( " A n i lK u m a rP u g a l i a< e m a i l _ a t _ s a r i k a p u g s _ d o t _ c o m > " ) ; M O D U L E _ D E S C R I P T I O N ( " O u rF i r s tC h a r a c t e rD r i v e r " ) ;

Then, Shweta repeated the usual steps that shed learnt for the first driver:

www.linuxforu.com/2011/02/linux-character-drivers/

3/7

7/18/13
Build the driver (. k ofile) by running m a k e . Load the driver using i n s m o d . List the loaded modules using l s m o d . Unload the driver using r m m o d .

Device Drivers, Part 4: Linux Character Drivers - LINUX For You

Summing up
Additionally, before unloading the driver, she peeped into the / p r o c / d e v i c e skernel window to look for the registered major number with the name Shweta, using c a t/ p r o c / d e v i c e s . It was right there. However, she couldnt find any device file created under / d e vwith the same major number, so she created them by hand, using m k n o d , and then tried reading and writing those. Figure 2 shows all these steps.

Figure 2: Character device file experiments

Please note that the major number 2 5 0may vary from system to system, based on availability. Figure 2 also shows the results Shweta got from reading and writing one of the device files. That reminded her that the second step to connect the device file with the device driver which is linking the device file operations to the device driver functions was not yet done. She realised that she needed to dig around for more information to complete this step, and also to figure out the reason for the missing device files under / d e v . We will deal with her further learning in our next article.

Related Posts:
Device Drivers, Part 5: Character Device Files Creation & Operations Device Drivers, Part 6: Decoding Character Device File Operations Device Drivers, Part 13: Data Transfer to and from USB Devices Device Drivers, Part 11: USB Drivers in Linux Device Drivers, Part 2: Writing Your First Linux Driver in the Classroom
Tags: Alessandro Rubini, API, audio drivers, camera drivers, character device driver, character driver, constructor and destructor, device drivers, Greg Kroah-Hartman, Jonathan Corbet, kernel space, LFY February 2011, linux device drivers, Linux Device Drivers Series, network device drivers, serial drivers, space character, VFS, video drivers

Article written by:


Anil Kumar Pugalia
The author is a freelance trainer in Linux internals, Linux device drivers, embedded Linux and related topics. Prior to this, he had worked at Intel and Nvidia. He has been exploring Linux since 1994. A gold medallist from the Indian Institute of Science, Linux and knowledge-sharing are two of his many passions. Connect with him: Website - Twitter - Facebook - Google+

www.linuxforu.com/2011/02/linux-character-drivers/

4/7

7/18/13
Previous Post

Device Drivers, Part 4: Linux Character Drivers - LINUX For You


Next Post

Metasploit 101 with Meterpreter Payload

Better Queries with MySQL, Part 2

ALSO ON LINUX FOR YOU

AROUND THE WEB

What's this?

New and amazing features of Linux


2 comments

Don't Get Prostate Cancer: Know These Early Warning Newsmax Health Roommates from Hell: Watch The Dead Kevin Show Comedy Central 6 Simple Tips to Help You Lose Belly Fat Stack 9 Things You Can Do Today to Boost Your Retirement Income Citi Women & Co.

What it Takes to be an Open Source Expert 1 comment PHP Development: A Smart Career Move 4 comments A Simple guide to building your own Linux Kernel 1 comment

15 comments Leave a message...


Newest Community raghu ram

Share

2 months ago

Hi Anil, Your articles are awesome Please give some tutorials on PCI Sound Card drivers using ALSA.
Reply Share

anil_pugalia

> raghu ram


Share

a month ago


LaGuira. c om

For the time being, I have completed the 24 article series on Linux Device Drivers. Currently, writing on mathematics in open source.
Reply

3 months ago

Anil, your posts read like a best seller novel... Congrats! What an awesome job. There are no words to express my gratitude to you. Thanks! Moises.
Reply Share

anil_pugalia

> LaGuira.com
Share

a month ago


alok

Thanks for such a high appreciation.


Reply

7 months ago

Can you please give me some tutorails on network drivers? alokal.123@gmail.com


Reply Share

anil_pugalia 1

> alok

7 months ago

Check out my slides at http://www.slideshare.net/anil...

Reply

Share

Livin Crux

9 months ago

Hi Anil, I am using ur articles as my first steps in drivers. I really appreciate the care you take to describe steps in such detail. I did read this one yesterday and today and still couldn't clearly understand some points. In a paragraph about major and minor numbers, I am a little confused as to what they exactly mean. It says the first API registers 'cnt number' of device file numbers. What is the need to have many numbers for a single driver? is it for redundancy? and most importantly, may be it would help if you can differentiate between major number and minor number in terms of which is required for what purpose. I could understand both together choose the driver for that device file. Thanks
1

Reply

Share

anil_pugalia

> Livin Crux

8 months ago

www.linuxforu.com/2011/02/linux-character-drivers/

5/7

7/18/13

Device Drivers, Part 4: Linux Character Drivers - LINUX For You

Say, major refers to a category of devices, like serial. So, all identical serial ports would be managed by the same driver, and all their device files will have the same major number. Then, how do we differentiate, as to which device file corresponds to which device? And exactly that is done by the minor number - it is not for redundancy.
1 y p_1981

Reply

Share

11 months ago

How she got the 250 major number for her device drive file
Reply Share

A nil P ugalia

> yp_1981

11 months ago


y p_1981

What are you getting? As it is dynamically allocated, you may get a different one. Whatever you get, change the mknod parameter accordingly.
Reply Share

11 months ago


ajman

How she get 0 and 3 for majar and minor number


Reply

Share

a year ago

First, I would like to thank you for the tutorials. I have created a basic char driver called 'physmem'. I compiled, inserted module (insmod) and create a device ( sudo mknod /dev/physmem0 c 250 0 ). then I did cat /dev/physmem0 , with dmesg, I see 'open invoked' and 'read invoked'. however, when I did sudo echo hi > /dev/physmem0. it complained about 'permission denied" so I logged in as superuser 'su' and executed the above command (echo hi....). the system got hunged. I looked at the log (dmesg), i see infinite entries of 'write invoked'. ..so what caused it to call device_write() so many times? //physmem.c #include <linux module.h=""> #include <linux init.h=""> #include <linux kernel.h=""> #include <linux spinlock.h=""> #include <linux pci.h=""> #include <linux fs.h=""> #include <linux etherdevice.h=""> #include <linux cdev.h="">
3

see more

Reply

Share

anil_pugalia

> ajman

a year ago


A run B hos ale

The problem is basically with the return 0 in your write call. With that you are basically failing the write and so the write is getting retried, which again fails, and so on & so forth. Hence it keeps repeating the same, causing the infinite loop. Instead change the "return ret" to "return length".
Reply

Share

2 years ago

When will we get ubuntu again..


Reply Share

anil_pugalia

> Arun Bhosale


Share

a year ago


r
C o m m e n t fe e d

What do you mean by that? Please elaborate.


Reply

Su b s cri b e vi a e m a i l

Reviews

How-Tos

Coding

Interviews

Features

Overview

Blogs

www.linuxforu.com/2011/02/linux-character-drivers/

6/7

7/18/13

Device Drivers, Part 4: Linux Character Drivers - LINUX For You

Search
Popular tags
Linux , ubuntu, Java, MySQL, Google, python, Fedora, Android, PHP, C, html, w eb applications , India, Microsoft, unix , Window s , Red Hat, Oracle, Security , Apache, xml, LFY April 2012, FOSS, GNOME, http, JavaScript, LFY June 2011, open source, RAM, operating systems

For You & Me Developers Sysadmins Open Gurus CXOs Columns

All published articles are released under Creative Commons Attribution-NonCommercial 3.0 Unported License, unless otherw ise noted. LINUX For You is pow ered by WordPress, w hich gladly sits on top of a CentOS-based LEMP stack.

www.linuxforu.com/2011/02/linux-character-drivers/

7/7

You might also like