It covers the step by step approach on how to write a simple loadable character device driver in linux. What are Device files in linux detail. How user application interact with character driver using a device file.
Writing Character driver (loadable module) in linux
1. Step by step approach to
write a simple loadable
“character driver” in linux
- Raj Kumar Rampelli
2. Outline
• Introduction to kernel & device driver: Please refer to my previous
PPT https://www.slideshare.net/rampalliraj/kernel-device-drivers
• File types in Linux/Unix
• Device files
• Character driver
• Steps to write a loadable character driver module in linux
• Sample character device driver code
• References
3. File types in Linux/Unix
File Type Definition How they are indicated? How to create? How to see in ls -l command?
Regular File A readable file or a binary file
or an image file or compressed
file
Indicated with “-” in ls -l
command output
Use touch or vi or
vim command
Ex: vim 1.txt
-rw------- 1 rrajk hardware 154
Dec 4 21:15 myscript_dev_t194.sh
Directory File Contains regular files, folders or
special files stored on a physical
device
Indicated with “d” in ls -l
command output
Use mkdir
command
drwx------ 3 rrajk hardware 4096
Dec 3 23:48 obj
Block device file Behave lot like ordinary files.
They are an array of bytes,
values can be read/write
from/to given location.
Indicated with “b” in ls -l
command output. Most
of them present in /dev
directory
Use fdisk
command or
create virtual
partition
brw-rw---- 1 root disk 8, 0 Oct 29
02:07 sda
Character device
file
Provides a serial stream of
input or output
Indicated with “c” in ls -l
command output. Most
of them present in /dev
directory
Use mknod
command
crw-r--r-- 1 root root 1, 11 Oct 29
02:07 kmsg
PIPE file Fist in First out property Indicated with “p” in ls -l
command’s output
Use mkfifo
command
prw-r----- 1 root root 0 2010-02-15
09:35 /dev/.initramfs/usplash_fifo
Symbolic link file Linked files to other files. They
are either directory or regular
file. The inode for this file and
it’s parent file is same.
Indicated with “l” in ls -l
command’s ouput
Use ln command lrwxrwxrwx 1 root root 9 Jun 12
14:16 /var/lock -> /run/lock
Socket files Used to pass information
between applications for
communication purpose
Indicated with “s” in ls -l
command’s ouput
Use socket()
system call
srw-rw-rw- 1 root root 0 Oct 29
02:07 log
4. Device file
• Device file is a file that associates it’s name visible to the user space applications and it’s triplet (type, major,
minor) to the kernel
• Device file is a user interface to communicate with device driver (character and block driver)
• A device file can represent character devices, which emit a stream data one character at a time, or block
devices which allow random access to blocks of data.
• In Linux, every device represented as a device file
• All device files stored in the /dev directory and they are also called as device nodes.
• Example:
• for Character device file /dev/input/mice : represents mouse, exposes the movement of mouse as a character stream.
• for block device file /dev/sda : represents hard disk, exposes the addressable regions of memory of the device.
• Device files (or device nodes) are created by the mknod system call.
• Kernel assigns user requests to the corresponding device driver using triplet information.
• Type: character device (c) or block device (b)
• Major: represents device category
• Minor: identifier of the device.
• When data is read or written to a device file, the request is handled by the kernel driver for that device. Each
device file has an associated number (Major number) which identifies the driver to use.
5. Character driver
• It is a device driver which interacts with character devices.
• Character devices are keyboard, mouse and camera etc.
• Sequential Byte oriented data transfer
• Character device is a device that can be accessed as a stream of bytes.
• Character device doesn’t require buffering and it sends the data with no preconfigured size. (Block devices have a buffer
and it send/receives the data in blocks of a size configured per device)
Run command “cat /proc/devices” on terminal. Output shows all character devices (not
including devices whose modules are not loaded) and their major number associated with it.
Character devices:
1 mem
4 /dev/vc/0
4 tty
4 ttyS
5 /dev/tty
5 /dev/console
5 /dev/ptmx
5 ttyprintk
6 lp
7 vcs
10 misc
13 input
21 sg
29 fb
108 ppp
128 ptm
136 pts
180 usb
189 usb_device
248 hidraw
249 hpilo
250 ptp
251 pps
252 bsg
253 watchdog
254 rtc
Major number
Character
device name
rtc254
6. Top view: User application interacts with character device
Note: This PPT covers
only on how user
application interaction
with character device
driver by a device file.
7. Writing character driver steps
1. Write a simple loadable module in C language (simple_char_module.c)
• Add module_init() and module_exit() functions
• Use register_chrdev() unregister_chrdev() functions to register our module as a character driver.
• Implement basic struct file_operations methods – check all file operation functions at /lib/modules/3.13.0-
119-generic/build/include/linux/fs.h
• open() read()
• close() write()
2. Write a Makefile with content: obj-m := simple_char_module.o
3. Compile module with command: make -C /lib/modules/$(uname -r)/build M=$PWD modules
• simple_char_module.ko file will be generated on successful compilation
4. Create a device file using mknod command: sudo mknod -m 666 /dev/simple_char_dev c 240 0
• Here, ‘-m’ denotes permissions, char ‘c’ tells character device, number 240 is Major number, 0 is Minor
number, simple_char_dev is device file name
• Check device file created or not using “ls -l /dev/simple_char_dev” command
5. Insert simple_char_module.ko module into linux machine using insmod command
• insmod simple_char_module.ko
• Check if module successfully inserted or not using command: cat /proc/devices
• Also, check lsmod command output
• Check linux system log: tail -f /var/log/syslog
• module_init() function will be called with insmod command. Use register_chrdev() function to register our
module with kernel subsystem as a character device driver.
8. Writing character driver steps (contd..)
6. Reading contents of device file: cat /dev/simple_char_dev; Below file system
operations are called in sequence.
• File open() operation will be called in simple_char_module.c
• File read() operation called to read contents from char device
• File release() operation called to close the device.
7. Writing contents to the device file:
echo “hello world” > /dev/simple_char_dev;
Below file system operations are called in sequence.
• File open() operation will be called in simple_char_module.c
• File write() operation called to write contents to char device
• File release() operation called to close the device.
8. Remove simple_char_module module from linux system: rmmod simple_char_module
• module_exit() function will be called.
• Use unregister_chrdev() function to un-register our module from kernel
subsystem.
• Check linux system log at tail -f /var/log/syslog
• Also, check lsmod output if the module successfully removed from system or
not.
9. Sample character driver code:
#include<linux/init.h>
#include<linux/module.h>
#include<linux/fs.h> /* For the character driver support */
int char_drv_open (struct inode *pinode, struct file *pfile) {
printk(KERN_INFO "Inside the %s functionn", __FUNCTION__); return 0;
}
ssize_t char_drv_read (struct file *pfile, char __user *buffer, size_t len, loff_t *offset){
printk(KERN_INFO "Inside the %s functionn", __FUNCTION__); return 0;
}
ssize_t char_drv_write (struct file *pfile, const char __user *buffer, size_t len, loff_t *offset){
printk(KERN_INFO "Inside the %s functionn", __FUNCTION__); return len;
}
int char_drv_release (struct inode *pinode, struct file *pfile){
printk(KERN_INFO "Inside the %s functionn", __FUNCTION__); return 0;
}
struct file_operations char_drv_fops = {/* To hold the file operations on this device */
.owner = THIS_MODULE,
.open = char_drv_open,
.read = char_drv_read,
.write = char_drv_write,
.release = char_drv_release,
};
int simple_char_drv_init(void)
{ printk(KERN_INFO "Inside the %s functionn", __FUNCTION__);
/* Register with kernel and indicate that we are registering a character device driver */
register_chrdev(240 /*Major Number*/, "Simple char drv" /* Name of the driver*/, &char_drv_fops);
return 0;
}
void simple_char_drv_exit(void)
{ printk(KERN_INFO "Inside the %s functionn", __FUNCTION__);
unregister_chrdev(240 /*Major Number*/, "Simple char drv" /* Name of the driver*/);
}
module_init(simple_char_drv_init);
module_exit(simple_char_drv_exit);
Step 0) Makefile: obj-m := filename.o
Step 1) Compilation: make -C /lib/modules/$(uname -r)/build M=$PWD
modules
Output of compilation command:
make: Entering directory `/usr/src/linux-headers-3.13.0-119-generic'
CC [M] /build/rrajk/character_device_driver_module/simple_char_drv.o
Building modules, stage 2.
MODPOST 1 modules
CC
/build/rrajk/character_device_driver_module/simple_char_drv.mod.o
LD [M]
/build/rrajk/character_device_driver_module/simple_char_drv.ko
make: Leaving directory `/usr/src/linux-headers-3.13.0-119-generic'
Step 2) Insert module:
$sudo insmod ./simple_char_drv.ko
Step 3) Check if it inserted properly or not with lsmod
$lsmod | grep simple
Step 4) We registered our driver as character device driver
using register_chrdev(). Check if it is successful or not
$cat /proc/devices
Output: 240 Simple char drv
Step 5) Create device file using mknod with major# 240
$sudo mknod -m 666 /dev/simple_char_dev c 240 0
Note: check “ls –la /dev/simple_char_dev” output
Step 6) perform read (ex: cat simple_char_dev), write (ex: echo
“data” > simple_char_dev) operations on above device file and
check the linux system log simultaneously using command “tail –f
/var/log/syslog” and observe how character driver functions get
invoked with read/write requests performed on device file by
user application.
10. References
• Linux file types: https://www.linuxnix.com/file-types-in-linux/
• Simple character driver implementation: Linux Device Drivers Training
06, Simple Character Driver by KarthikM@youtube.com
• Introduction to char device driver by Vandana_salve@slideshare.com
11. THANK YOU
Have a look at
http://www.slideshare.net/rampalliraj/
http://practicepeople.blogspot.in/