Энциклопедия разработчика модулей ядра Linux | страница 23



>  break;

> case IOCTL_GET_NTH_BYTE:

>  /* This ioctl is both input (ioctl_param) and

>  * output (the return value of this function) */

>  return Message[ioctl_param];

>  break;

> }

> return SUCCESS;

>}


>/* Module Declarations *************************** */

>/* This structure will hold the functions to be called

>* when a process does something to the device we

>* created. Since a pointer to this structure is kept in

>* the devices table, it can't be local to

>* init_module. NULL is for unimplemented functions. */

>struct file_operations Fops = {

> NULL, /* seek */

> device_read,

> device_write,

> NULL, /* readdir */

> NULL, /* select */

> device_ioctl, /* ioctl */

> NULL, /* mmap */

> device_open,

>#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,2,0)

> NULL, /* flush */

>#endif

> device_release /* a.k.a. close */

>};


>/* Initialize the module - Register the character device */

>int init_module() {

> int ret_val;

> /* Register the character device (atleast try) */

> ret_val = module_register_chrdev(MAJOR_NUM, DEVICE_NAME, &Fops);

> /* Negative values signify an error */

> if (ret_val < 0) {

>  printk("%s failed with %d\n", "Sorry, registering the character device ", ret_val);

>  return ret_val;

> }

> printk("%s The major device number is %d.\n", "Registeration is a success", MAJOR_NUM);

> printk("If you want to talk to the device driver,\n");

> printk ("you'll have to create a device file. \n");

> printk ("We suggest you use:\n");

> printk ("mknod %s c %d 0\n", DEVICE_FILE_NAME, MAJOR_NUM);

> printk ("The device file name is important, because\n");

> printk ("the ioctl program assumes that's the\n");

> printk ("file you'll use.\n");

> return 0;

>}


>/* Cleanup - unregister the appropriate file from /proc */

>void cleanup_module() {

> int ret;

> /* Unregister the device */

> ret = module_unregister_chrdev(MAJOR_NUM, DEVICE_NAME);

> /* If there's an error, report it */

> if (ret < 0) printk("Error in module_unregister_chrdev: %d\n", ret);

>}

chardev.h 

>/* chardev.h - the header file with the ioctl definitions.

>*

>* The declarations here have to be in a header file,

>* because they need to be known both to the kernel

>* module (in chardev.c) and the process calling ioctl (ioctl.c)

>*/

>#ifndef CHARDEV_H

>#define CHARDEV_H #


>include

>/* The major device number. We can't rely on dynamic

>* registration any more, because ioctls need to know it. */

>#define MAJOR_NUM 100


>/* Set the message of the device driver */

>#define IOCTL_SET_MSG _IOR(MAJOR_NUM, 0, char *)