#include #include #include #include #include #include #include #include #include #include #include //remap_pfn_range /* 主设备号 */ #define BSP_DEV_MAJOR 0 /* 主设备名 */ #define BSP_DEV_NAME "mem_dump" /* 模块加载函数 */ static int osp_mem_init(void); /* 模块卸载函数 */ static void osp_mem_exit(void); /* 打开设备函数 */ int mem_bsp_open(struct inode *inode, struct file *filp); /* 释放设备函数 */ int mem_bsp_release(struct inode *inode, struct file *filp); /* 读函数 */ static ssize_t mem_bsp_read (struct file *filp, __user char *buf, size_t count, loff_t *f_pos); /* ioctl函数 */ long mem_bsp_ioctl(struct file *filp, unsigned int cmd, unsigned long arg); /* mmap函数 */ int mem_bsp_mmap(struct file *filp, struct vm_area_struct *vma); /* 写函数 */ ssize_t mem_bsp_write(struct file *filp, const char *buf, size_t count, loff_t *f_pos); /******************************* 局部宏定义 ***********************************/ /* bsp 主设备号 */ typedef struct mem_struct{ int g_s32BspDevMajor ; unsigned int g_u32CacheCoherent; struct cdev g_struBspDev; struct class *cls; dev_t g_devno; struct device *parent; struct device *this_device; }mem_st; /******************************* 函数实现 *************************************/ /******************************************************************************* * 函数名: mem_init * 描述: 模块加载时的入口函数 * 相关文档: * 函数存储类型:int * 参数: 无 * 返回值: * 0 成功 * <0 失败 * 说明:具体失败参考Linux错误信息头文件 *******************************************************************************/ static mem_st mem_dev ={ .g_s32BspDevMajor = 0, .g_u32CacheCoherent = 0, .g_devno = 0, }; static struct file_operations g_struBspOp = { .owner = THIS_MODULE, .read = mem_bsp_read, .write = mem_bsp_write, .open = mem_bsp_open, .release = mem_bsp_release, .mmap = mem_bsp_mmap, .unlocked_ioctl = mem_bsp_ioctl, }; static int osp_mem_init(void) { /*函数调用结果*/ int result; /*设备编号*/ dev_t devno; printk("bsp_init.\n"); /* 获取设备号 */ if (0 == mem_dev.g_s32BspDevMajor) { /* 分配设备区域 */ result = alloc_chrdev_region(&devno, 0, 1, BSP_DEV_NAME); /* 判断返回值 */ if (result < 0) { printk(KERN_WARNING "bsp: alloc_chrdev_region error! errno = %d\n", result); return result; } mem_dev.g_devno = devno; /* 保存主设备号信息 */ mem_dev.g_s32BspDevMajor = MAJOR(devno); /* 初始化dev变量 */ cdev_init(&(mem_dev.g_struBspDev), &g_struBspOp); /* 设备dev相应变量值 */ mem_dev.g_struBspDev.owner = THIS_MODULE; mem_dev.g_struBspDev.ops = &g_struBspOp; /* 向系统增加dev设备 */ result = cdev_add(&mem_dev.g_struBspDev, devno, 1); if (result < 0) { printk ("cdev_add error!errno = %d", result); } // ret = device_create_file(ucp_smem_miscdev.this_device, &dev_attr_ucp_smem); mem_dev.cls = class_create(THIS_MODULE, "mem_dump"); device_create(mem_dev.cls, NULL, devno, NULL, "mem_dump"); printk("bsp module init success!\n"); /* 返回成功 */ return 0; } else { printk("bsp module already init!\n"); /* 返回 */ return -EBUSY; } } /******************************************************************************* * 函数名: ad9371_exit * 描述: 模块卸载函数 * 相关文档: * 函数存储类型:void * 参数: 无 * 返回值: 无 * 说明: *******************************************************************************/ static void osp_mem_exit(void) { /* 判断是否执行过模块加载 */ if(mem_dev.g_s32BspDevMajor > 0) { /* 删除该字符设备 */ device_destroy(mem_dev.cls, mem_dev.g_devno); class_destroy(mem_dev.cls); cdev_del(&(mem_dev.g_struBspDev)); /* 释放已分配的空间 */ unregister_chrdev_region(MKDEV(mem_dev.g_s32BspDevMajor, 0), 1); /* 清空主设备号 */ mem_dev.g_s32BspDevMajor = 0; /* 调试信息输出 */ printk("bsp module cleanup success!\n"); } return; } /******************************************************************************* * 函数名: ad9731_bsp_open * 描述: 打开文件 * 相关文档: * 函数存储类型:int * 参数: * * 参数名 类型 输入/输出 描述 * -------- ---- --- ----------- * inode struct inode* input 文件节点结构 * filp struct file* input 文件结构 * 返回值: * 0 成功 * 说明: *******************************************************************************/ int mem_bsp_open(struct inode *inode, struct file *filp) { return 0; } /******************************************************************************* * 函数名: ad9731_bsp_release * 描述: 关闭文件 * 相关文档: * 函数存储类型:int * 参数: * * 参数名 类型 输入/输出 描述 * -------- ---- --- ----------- * inode struct inode* input 文件节点结构 * filp struct file* input 文件结构 * 返回值: * 0 成功 * 说明: *******************************************************************************/ int mem_bsp_release(struct inode *inode, struct file *filp) { /* 操作成功 */ return 0; } /******************************************************************************* * 函数名: ad9731_bsp_read () * * 描述: 读操作。 * 相关文档: <描述此函数的相关协议名称、版本及在协议中的位置> * 函数存储类型: *******************************************************************************/ static ssize_t mem_bsp_read (struct file *filp, char *buf, size_t count, loff_t *f_pos) { return 0; } /******************************************************************************* * 函数名: ad9731_bsp_write () * * 描述: 写操作。 * 相关文档: <描述此函数的相关协议名称、版本及在协议中的位置> * 函数存储类型: *******************************************************************************/ ssize_t mem_bsp_write(struct file *filp, const char *buf, size_t count, loff_t *f_pos) { return 0; } /******************************************************************************* * 函数名: ad9731_bsp_ioctl * 描述: IO控制 * 相关文档: * 函数存储类型:int * 参数: *******************************************************************************/ long mem_bsp_ioctl(struct file *filp, unsigned int cmd, unsigned long arg) { return 0; } /******************************************************************************* * 函数名: mem_bsp_mmap * 描述: IO内存映射 * 相关文档: * 函数存储类型:int * 参数: * *******************************************************************************/ int mem_bsp_mmap(struct file *filp, struct vm_area_struct *vma) { /* 设置IO标志 */ vma->vm_flags |= VM_IO; vma->vm_page_prot = pgprot_noncached(vma->vm_page_prot); printk("mmap start\n\r"); /* 建立映射 */ if (remap_pfn_range(vma, vma->vm_start, vma->vm_pgoff, vma->vm_end-vma->vm_start, vma->vm_page_prot) < 0) { return -EAGAIN; } return 0; } MODULE_AUTHOR ("mr yang"); MODULE_DESCRIPTION ("mem_dump" ); MODULE_LICENSE ("GPL"); module_init(osp_mem_init); module_exit(osp_mem_exit); /******************************* 源文件结束 ***********************************/