当前位置: 代码迷 >> 驱动开发 >> 驱动模块移栽到3.2.16
  详细解决方案

驱动模块移栽到3.2.16

热度:73   发布时间:2016-04-28 10:48:56.0
驱动模块移植到3.2.16
这只是一个课程设计
要求写一个块设备的驱动,由于从来没有接触过这个方面,所以只能一点点儿的学习,但是,最后发现,我学习的资料跟现在的内核版本3.2.16有非常大的出入。原先的一些api都已经不存在了。
我只好在网上找了一个例子,参照着新内核的源码对所用的函数进行替换,但是问题却来了,编译好模块后插入内核会造成死机,没有任何响应。
下面是来自http://bbs.chinaunix.net/thread-2017377-1-1.html的代码。
C/C++ code
#define SIMP_BLKDEV_DEVICEMAJOR        COMPAQ_SMART2_MAJOR#define SIMP_BLKDEV_DISKNAME        "simp_blkdev"#define SIMP_BLKDEV_BYTES        (16*1024*1024)unsigned char simp_blkdev_data[SIMP_BLKDEV_BYTES];static struct request_queue *simp_blkdev_queue;static struct gendisk *simp_blkdev_disk;static void simp_blkdev_do_request(struct request_queue *q);struct block_device_operations simp_blkdev_fops = {        .owner                = THIS_MODULE,};static void simp_blkdev_do_request(struct request_queue *q){        struct request *req;        while ((req = elv_next_request(q)) != NULL) {                if ((req->sector + req->current_nr_sectors) << 9                        > SIMP_BLKDEV_BYTES) {                        printk(KERN_ERR SIMP_BLKDEV_DISKNAME                                ": bad request: block=%llu, count=%u\n",                                (unsigned long long)req->sector,                                req->current_nr_sectors);                        end_request(req, 0);                        continue;                }                switch (rq_data_dir(req)) {                case READ:                        memcpy(req->buffer,                                simp_blkdev_data + (req->sector << 9),                                req->current_nr_sectors << 9);                        end_request(req, 1);                        break;                case WRITE:                        memcpy(simp_blkdev_data + (req->sector << 9),                                req->buffer, req->current_nr_sectors << 9);                        end_request(req, 1);                        break;                default:                        /* No default because rq_data_dir(req) is 1 bit */                        break;                }        }}static int __init simp_blkdev_init(void){        int ret;        simp_blkdev_queue = blk_init_queue(simp_blkdev_do_request, NULL);        if (!simp_blkdev_queue) {                ret = -ENOMEM;                goto err_init_queue;        }        simp_blkdev_disk = alloc_disk(1);        if (!simp_blkdev_disk) {                ret = -ENOMEM;                goto err_alloc_disk;        }        strcpy(simp_blkdev_disk->disk_name, SIMP_BLKDEV_DISKNAME);        simp_blkdev_disk->major = SIMP_BLKDEV_DEVICEMAJOR;        simp_blkdev_disk->first_minor = 0;        simp_blkdev_disk->fops = &simp_blkdev_fops;        simp_blkdev_disk->queue = simp_blkdev_queue;        set_capacity(simp_blkdev_disk, SIMP_BLKDEV_BYTES>>9);        add_disk(simp_blkdev_disk);        return 0;err_alloc_disk:        blk_cleanup_queue(simp_blkdev_queue);err_init_queue:        return ret;}static void __exit simp_blkdev_exit(void){        del_gendisk(simp_blkdev_disk);        put_disk(simp_blkdev_disk);        blk_cleanup_queue(simp_blkdev_queue);}module_init(simp_blkdev_init);module_exit(simp_blkdev_exit);

我自己根据源码替代函数后的代码如下
C/C++ code
#include <linux/blkdev.h>#include <linux/genhd.h>#include <linux/init.h>//#include <linux/config.h>新的内核已经不支持该头文件了#include <linux/module.h>#include <linux/kernel.h> /* printk() */#include <linux/slab.h> /* kmalloc() */#include <linux/fs.h> /* everything... */#include <linux/errno.h> /* error codes */#include <linux/types.h> /* size_t */#include <linux/proc_fs.h>#include <linux/ioctl.h>#include <linux/fcntl.h> /* O_ACCMODE */#include <asm/system.h> /* cli(), *_flags */#include <asm/uaccess.h> /* copy_from/to_user */#define SIMP_BLKDEV_DEVICEMAJOR        60#define SIMP_BLKDEV_DISKNAME        "simp_blkdev"#define SIMP_BLKDEV_BYTES        (1024*1024)static struct request_queue *simp_blkdev_queue;static struct gendisk *simp_blkdev_disk;unsigned char simp_blkdev_data[SIMP_BLKDEV_BYTES];static void simp_blkdev_do_request(struct request_queue *q){        struct request *req;        while ((req = blk_fetch_request(q)) != NULL) {                if (((req->__sector + req->__data_len) << 9) > SIMP_BLKDEV_BYTES) {                        printk(KERN_ERR SIMP_BLKDEV_DISKNAME": bad request: block=%llu, count=%u\n",                                (unsigned long long)req->__sector,                                req->__data_len);                        blk_end_request_all(req, 0);                        continue;                }                switch (rq_data_dir(req)) {                case READ:                       memcpy(req->completion_data,                                simp_blkdev_data + (req->__sector << 9),                                req->__data_len << 9);                        blk_end_request_all(req, 1);                        break;                case WRITE:                        memcpy(simp_blkdev_data + (req->__sector << 9),                                req->buffer, req->__data_len << 9);                        blk_end_request_all(req, 1);                        break;                default:                        /* No default because rq_data_dir(req) is 1 bit */                        break;                }        }}struct block_device_operations simp_blkdev_fops = {        .owner                = THIS_MODULE,};static int __init simp_blkdev_init(void){        int ret;        simp_blkdev_queue = blk_init_queue(simp_blkdev_do_request, NULL);        if (!simp_blkdev_queue) {                ret = -ENOMEM;                goto err_init_queue;        }        simp_blkdev_disk = alloc_disk(1);        if (!simp_blkdev_disk) {                ret = -ENOMEM;                goto err_alloc_disk;        }        strcpy(simp_blkdev_disk->disk_name, SIMP_BLKDEV_DISKNAME);        simp_blkdev_disk->major = SIMP_BLKDEV_DEVICEMAJOR;        simp_blkdev_disk->first_minor = 0;        simp_blkdev_disk->fops = &simp_blkdev_fops;        simp_blkdev_disk->queue = simp_blkdev_queue;        set_capacity(simp_blkdev_disk, SIMP_BLKDEV_BYTES>>9);        add_disk(simp_blkdev_disk);    printk("<1>块设备驱动成功加载完成");        return 0;err_alloc_disk:        blk_cleanup_queue(simp_blkdev_queue);err_init_queue:        return ret;}static void __exit simp_blkdev_exit(void){        del_gendisk(simp_blkdev_disk);        put_disk(simp_blkdev_disk);        blk_cleanup_queue(simp_blkdev_queue);    printk("<1>块设备卸载完毕");}module_init(simp_blkdev_init);module_exit(simp_blkdev_exit);
  相关解决方案