一个完整的测试模块驱动程序

一个完整的test字符设备驱动程序,以下给出模块加载卸载方法以及简单的测试程序。

首先编写一个test.h,定义各个接口函数以及包含的头文件:

#define __NO_VERSION__
#include <linux/version.h>
#include <linux/module.h>
#include <linux/types.h>
#include <linux/fs.h>
#include <linux/mm.h>
#include <linux/errno.h>
#include <asm/segment.h>
#include <asm/uaccess.h>
#include <asm/page.h>

static ssize_t read_test(struct file *file,char *buf,size_t count,loff_t *ppos);
static ssize_t write_test(struct file *file,const char *buf,size_t count,loff_t *ppos);
static int open_test(struct inode *inode,struct file *file);
static int release_test(struct inode *inode,struct file *file);


struct file_operations test_fops={
        
         owner: THIS_MODULE,
         read: read_test,
         write: write_test,
         open: open_test,
         release: release_test,
        
        
       };

char kernel_version[]=UTS_RELEASE;

源代码test.c如下:

#include "test.h"

unsigned int test_major = 0;
MODULE_LICENSE("GPL");

static ssize_t read_test(struct file *file,char *buf,size_t count,loff_t *ppos)
{
  size_t left;
 /* int x=sizeof(buf);*/
  if(verify_area(VERIFY_WRITE,buf,count)==-EFAULT)
  return EFAULT;
  for(left=count;left>0;left--)
  {
    __put_user(1,buf);                     //将1从内核空间拷到用户空间         
    buf++;
  }
  return count;
}

static ssize_t write_test(struct file *file,const char *buf,size_t count,loff_t *ppos)
{
 
  return count;
}

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;
}


int init_module(void)
{
  int result;
 
  result=register_chrdev(0,"test",&test_fops);                      //注册字符设备模块,动态分配主设备号
  if(result<0)
  {
  printk(KERN_INFO"test:cant get major number/n");
  return result;
  }
  if(test_major==0)
  test_major=result;
  return 0;
}

void cleanup_module(void)
{
  unregister_chrdev(test_major,"test");
}

源代码编译加载方法如下:首先还是要确保linux内核源代码放在/usr/src里面,编译源代码:gcc -O2 -DMODULE -D__KERNEL__ -I/usr/src/linux/include -c test.c

编译结果为test.o,加载模块:insmod test.o,加载成功可以在/proc/drivers下面看到test模块,其中主设备号动态分配为253,接下来建立节点:mknod /dev/test c 253 0,在/dev下建立test节点,c表示test模块为字符设备,253为主设备号,在/proc/driver里面可以找到,0为从设备号。建立节点成功后可以查找一下test模块,在/dev 下面 find -name test。

编写一个简单的测试程序:

#include <stdio.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>

main()
{
int testdev;
int i;
char buf[10];

testdev=open("/dev/test",O_RDWR);
if(testdev==-1)
{
 printf("cant open file/n");
 exit(0);
}

read(testdev,buf,10);
for(i=0;i<9;i++)
{printf("%d",buf[i]);}
printf("%d/n",buf[9]);
close(testdev);
}

编译gcc -o test_app test_app.c,运行./test_app,打印出来的一概是十个1。

卸载test模块:rmmod test,打完收工 :-)

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值