Linux内核模块开发实例学习

xiaoxiao2021-02-28  37

 注:以下程序只是在我机器上测试通过,但代码不一定合理或高效,只是想了解一下内核模块的开发流程,以及工作流程

例子来源于网络,在此表示感谢

[cpp]  view plain  copy [root@localhost module]# cat /proc/version    Linux version 2.6.18-194.el5xen (mockbuild@builder16.centos.org) (gcc version 4.1.2 20080704 (Red Hat 4.1.2-48)) #1 SMP Fri Apr 2 16:16:54 EDT 2010  

1、编写最简单的helloworld版本的内核模块

[cpp]  view plain  copy [root@localhost module]# cat hello.c    #ifndef _KERNEL_           #define _KERNEL_   #endif      #ifndef MODULE           #define MODULE   #endif         #include <linux/config.h>   #include <linux/module.h>   #include <linux/kernel.h>      static int hello_init(void)   {           printk(KERN_ALERT "hello, I am Tuotuo\n");           return 0;   }      static void hello_exit(void)   {           printk(KERN_ALERT "googbye Kernel mymodule n");   }      module_init(hello_init);   module_exit(hello_exit);  

Makefile文件为

[cpp]  view plain  copy [root@localhost module]# cat Makefile    obj-m:=hello.o    VERSION_NUM:=$(shell uname -r)   KERNELBUILD := /lib/modules/`uname -r`/build   CURRENT_PATH:=$(shell pwd)      all:           make -C $(KERNELBUILD) M=$(CURRENT_PATH) modules      clean:           make -C $(KERNELBUILD) M=$(CURRENT_PATH) clean  

编译

make

加载模块

insmod hello.ko

卸载模块

[cpp]  view plain  copy rmmod hello.ko   

查看加载和卸载信息

dmesg

2、学习调用模块

学习http://blog.csdn.net/firststp/article/details/395009

内核模块代码

[cpp]  view plain  copy [root@localhost module]# cat TestModule.c    #ifndef _KERNEL_           #define _KERNEL_   #endif      #ifndef MODULE           #define MODULE   #endif         #include <linux/config.h>   #include <linux/module.h>   #include <linux/kernel.h>   #include <linux/version.h>   #include <linux/types.h>   #include <linux/fs.h>   #include <linux/mm.h>   #include <linux/errno.h>   #include <asm/segment.h>   #include <linux/sched.h>   #include <asm/uaccess.h>   #include <linux/utsrelease.h>      #define DATA_LENGTH 10      MODULE_LICENSE("GPL");   MODULE_AUTHOR("TUO LI HENG");      char kernel_version[] = UTS_RELEASE;      unsigned int test_major = 0;      ssize_t read_test(struct file *file, char * buf, size_t count, loff_t *f_ops)   {           int left, i, *p;           int data[DATA_LENGTH];           p = data;           for(i=0; i<10; ++i)                   data[i] = 61;              for(left=count; left>0; --left)           {                   copy_to_user(buf, p, 1);                   ++buf;                   ++p;           }           return 0;      }      ssize_t write_test(struct file *file, char * buf, size_t count, loff_t *f_ops)   {              return 0;   }      static int open_test(struct inode* inode, struct file *file)   {           //      MOD_INC_USE_COUNT;           return 0;      }      static int release_test(struct inode *inode, struct file *file)   {           //      MOD_DEC_USE_COUNT;           return 0;   }      struct file_operations test_fops = {   read: read_test,   write: write_test,   open: open_test,   release: release_test      };         static int hello_init(void)   {           printk(KERN_ALERT "hello, I am Tuotuo\n");           int result = 0;           result = register_chrdev (0, "test", &test_fops);           if(result < 0)           {                   printk(KERN_ALERT "test:can't get major number\n");                   return result;           }           if(test_major == 0)                   test_major = result;           printk(KERN_ALERT "test major:%d/r/n", result);           return 0;   }         static void hello_exit(void)   {           unregister_chrdev(test_major, "test");           printk(KERN_ALERT "googbye Kernel module tuotuo\n");   }      module_init(hello_init);   module_exit(hello_exit);  

在以上的Makefile里第一行修改为:

[cpp]  view plain  copy obj-m:=TestModule.o  

同样

[html]  view plain  copy make      insmod TestModule.ko      dmesg  

测试前,先看看是否已经建立了设备文件。 检查 /dev下是否有test设备文件,如果没有,那我们就手工建立一个。用前面看到的主设备号,使用命令: “mknod test c 268 0”  --引用博文

编写调用程序

[html]  view plain  copy [root@localhost module]# cat TestApp.c    #include <stdio.h>   #include <sys/stat.h>   #include <fcntl.h>   int main()   {           char buf[20] = {0,};           int i = 0;           int p = open("/dev/test", O_RDWR);           if(p == -1)           {                   printf("cannot open\n");                   exit(0);           }           printf("buf addr %ui\r\n",buf);           read(p, buf, 10);           for(i = 0; i<10; i++)           {                   printf("%s\r\n",buf+i);           }           close(p);           return 1;   }  

编译

[html]  view plain  copy gcc TestApp.c -o TestApp  

运行

[cpp]  view plain  copy [root@localhost module]# ./TestApp    buf addr 3218386872i   ==========   =========   ========   =======   ======   =====   ====   ===   ==   =  
转载请注明原文地址: https://www.6miu.com/read-600376.html

最新回复(0)