linux 2.6内核编程-一个简单的字符驱动程序源码

/**************************************************************

 module program

**************************************************************/

 

#include <linux/module.h>
#include <linux/init.h>
#include <linux/fd.h>
#include <linux/kernel.h>
#include <linux/vmalloc.h>
#include <asm/uaccess.h>

#include <linux/errno.h>
#include <linux/major.h>
#include <linux/sched.h>
#include <linux/slab.h>
#include <linux/fcntl.h>
#include <linux/delay.h>
#include <linux/poll.h>
#include <linux/console.h>
#include <linux/device.h>
#include <linux/wait.h>
#include <linux/jiffies.h>
#include <linux/smp_lock.h>

#include <linux/parport.h>
#undef LP_STATS
#include <linux/lp.h>

#include <asm/irq.h>
#include <asm/uaccess.h>
#include <asm/system.h>
//#include <sys/stat.h>
 


int __initdata a=20;//a 变量放在.init.data区域
int __exitdata b=30;//b 变量放在.init.data区域

//内核初始化选项
static int count= 1;  
static int mp= 0;        
module_param(mp,int,0);
module_param(count,int,S_IRUSR);   
//module_param(info,char,S_IRUSR); 

//int myint=3;
//MODULE_PARM(myint,"i");
//char *mystr;
//MODULE_PARM(mystr,"s");//编译不通过


MODULE_LICENSE("Dual BSD/GPL");                  //模块代码的许可协议
MODULE_AUTHOR("Li Anqiang");                     //模块作者信息
MODULE_DESCRIPTION("8139 NETWORK CARD DRIVER."); //模块简单描述文本
MODULE_LICENSE("GPL");                           //模块代码的许可协议
MODULE_VERSION("2.6.31");                        //模块的版本信息

//module_param(initstate, int, 0444);

unsigned int fs_major=0;
static char *data;

struct a
{
  int aa;
  char bb;
};
struct a a1={.aa=2,.bb='3'};

static ssize_t test_read(struct file *file,char *buf,size_t count,loff_t *f_pos);
static ssize_t test_write(struct file *file,const char *buffer,size_t count,loff_t *f_pos);

static int test_open(struct inode *inode,struct file *file);


static int test_release(struct inode *inode,struct file *file);

int init_module_1(void);
void cleanup_module_1(void);

struct file_operations chr_fops=
{.read=test_read,
 .write=test_write,
 .open=test_open,
 .release=test_release, //加上,和不加都是对的
};



//2.6 struct file_operations chr_fops={.read=test_read,.write=test_write};

//2.4 struct file_operations chr_fops={read:test_read,write:test_write};
//kmalloc 在2.4<linux/malloc.h>
//kmalloc 在2.6<linux/vmalloc.h>
//在2.6里面没有MOD_INC_USE_COUNT MOD_DEC_USE_COUNT宏




static ssize_t test_read(struct file *file,char *buf,size_t count,loff_t *f_pos)
{
    int len;
        printk("rrrrrrrrrrrrrrrrrr/n");
    if(count<0)
    {
        return -EINVAL;
    }
    len=strlen(data);
    if(len<count)
        count=len;
    copy_to_user(buf,data,count+1);
        printk("read buf=%s/n",buf);
    printk("read data=%s/n",data);
    return count;
}

static ssize_t test_write(struct file *file,const char *buffer,size_t count, /
loff_t *pos)
{       printk("wwwwwwwwwwwwwwwwwwwwwwwww/n");
    if(count<0)
        return -EINVAL;
    kfree(data);
    data=(char *)kmalloc(sizeof(char)*(count+1),GFP_KERNEL);
    if(!data)
        return -ENOMEM;
       
    copy_from_user(data,buffer,count+1);
        printk("write buffer=%s/n",buffer);
    printk("write data=%s/n",data);
    return count;
}

static int test_open(struct inode *inode,struct file *file)
{
    //MOD_INC_USE_COUNT;
    printk("This is open(skull)/n");
    return 0;
}

static int test_release(struct inode *inode,struct file *file)
{
    //MOD_DEC_USE_COUNT;
    printk("This is released/n");
    return 0;
}

int __init init_module_1(void) //函数放在.init.text,.initcall.init区域
{
    int res;
    res=register_chrdev(0,"skull_8",&chr_fops);
    printk(KERN_INFO "init_module/n");
    if(res<0)
    {
        printk("Can/n");
        return res;
    }
    if(fs_major==0)
        fs_major=res;
    return 0;
}

void __exit cleanup_module_1(void)
{
    unregister_chrdev(fs_major,"skull_8");
    printk(KERN_INFO "cleanup_module/n");
}
module_init(init_module_1);//init_module相同 这时就不要module_init
module_exit(cleanup_module_1);//cleanup_module相同 这时就不要module_exit

 

 

 

/**************************************************************

 Makefile

**************************************************************/

#指定内核的位置
KERNELDIR =/usr/src/kernels/2.6.31.12-174.2.3.fc12.i686.PAE/
#/home/laq/linux-2.6.32.7
# The current directory is passed to sub-makes as argument

# 表示当前源文件所在的目录
PWD := $(shell pwd)

#表示安装到哪里
INSTALLDIR=/lib/modules/$(shell uname -r)/build
#/lib/modules/2.6.31.12-174.2.3.fc12.i686.PAE/kernel/sound/core/

#表示编译器的位置
#CROSS_COMPILE=/home/tekkaman/working/crosstool-gcc410-k26222/gcc-4.1.0-glibc-2.3.2/arm-9tdmi-linux-gnu/bin/arm-9tdmi-linux-gnu-
CC    = $(CROSS_COMPILE)gcc

#表示生成的目标(2.6内核的目标文件为.ko)但写还是这样的
obj-m :=skull_8.o

#表示编译内核模块
modules:
    $(MAKE) -w -C $(KERNELDIR) M=$(PWD) modules


#gcc -DMODULE -D__KERNEL__ -c hello1.c
modules_install:
#      cp skull_8.ko $(INSTALLDIR)
#安装模块 模块实际是被安装在/lib/modules/$(shell uname -r)/extra下  注意这是/lib/modules/2.6.31.12-174.2.3.fc12.i686.PAE/modules.dep还没有变化,需要执行depmod命令
    $(MAKE) -C /lib/modules/$(shell uname -r)/build M=$(PWD) modules_install
    depmod



#ifneq ($(KERNELRELEASE),)
#        obj-m := HelloModule.o
#else
#        KERNELDIR ?= /lib/modules/$(shell uname -r)/build
#        PWD := $(shell pwd)

#default:
#        $(MAKE) -C $(KERNELDIR) M=$(PWD) modules

#endif


clean:
    rm -rf *.o *~ core .depend .*.cmd *.ko *.mod.c .tmp_versions

#一次可以执行多个
PHONY: modules modules_install clean

 

 

 

/**************************************************************

 test program

**************************************************************/

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值