- 论坛徽章:
- 0
|
以下是scull的头文件。
头文件里把scull内存字符设备的结构给定义好,并声明了相关的宏和外部变量、函数等。而且还定义了简单的调试技术,就是把相关信息通过print系列函数打印到相关的地方。构建驱动代码前先把调试的方法考虑到确实值得学习。
/*
* scull.h -- definitions for the char module
*
* Copyright (C) 2001 Alessandro Rubini and Jonathan Corbet
* Copyright (C) 2001 O'Reilly & Associates
*
* The source code in this file can be freely used, adapted,
* and redistributed in source or binary form, so long as an
* acknowledgment appears in derived source files. The citation
* should list that the code comes from the book "Linux Device
* Drivers" by Alessandro Rubini and Jonathan Corbet, published
* by O'Reilly & Associates. No warranty is attached;
* we cannot take responsibility for errors or fitness for use.
*
* $Id: scull.h,v 1.15 2004/11/04 17:51:18 rubini Exp $
*/
#ifndef _SCULL_H_
#define _SCULL_H_
#include linux/ioctl.h> /* 为了使用_IOW/
/*
* 定义一些宏来帮助调试
*/
#undef PDEBUG /* 取消对PDEBUG的定义,防止重复定义*/
#ifdef SCULL_DEBUG /*开启调试*/
# ifdef __KERNEL__ /*在内核空间下,将调试信息用printk打印*/
# define PDEBUG(fmt, args...) printk( KERN_DEBUG "scull: " fmt, ## args)
# else /*在用户空间下,将信息打印到stderr*/
# define PDEBUG(fmt, args...) fprintf(stderr, fmt, ## args)
# endif
#else
# define PDEBUG(fmt, args...) /* 调试没开启,PDEBUG定义为什么都不做 */
#endif
#undef PDEBUGG
#define PDEBUGG(fmt, args...) /* PDEBUGG不做任何事,充当占位符 */
#ifndef SCULL_MAJOR
#define SCULL_MAJOR 0 /* 默认使用动态分配主设备号 */
#endif
/*这里将SCULL_MAJOR(主设备号)初始化为0,是为了在scull_init_module()中动态分配设备号,
在scull.c中,有一全局变量 int scull_major = SCULL_MAJOR; 用来代表设备号。在scull_init_module中有以下:
if (scull_major)
regidter_chrdev_region -----静态
else
alloc_chrdev_region --------动态
*/
#ifndef SCULL_NR_DEVS
#define SCULL_NR_DEVS 4 /* 设备数目或设备序号,从scull0到scull3 */
#endif
/*
* The bare device is a variable-length region of memory.
* Use a linked list of indirect blocks.
* "scull_dev->data" points to an array of pointers, each
* pointer refers to a memory area of SCULL_QUANTUM bytes.
* The array (quantum-set) is SCULL_QSET long.
scull_dev->data指向一组指针,其中每一个指针指向一个SCULL_QUANTUM字节
的内存空间.
*/
#ifndef SCULL_QUANTUM
#define SCULL_QUANTUM 4000 /*量子的大小,4000字节.指的是数据区域中的指针所引用的内存大小*/
#endif
#ifndef SCULL_QSET
#define SCULL_QSET 1000 /*量子集大小,1000个,指的是共有1000个指针,或者指针数组的长度。每一个指针用来应用4000字节的小的空间*/
#endif
/*
* Representation of scull quantum sets.
scull设备的quantum的实现如下
*/
struct scull_qset { /*设备的实现为一个简单的链表结点。data作为一个指向4000字节的区域*/
void **data;
struct scull_qset *next;
};
struct scull_dev { /*设备的结构*/
struct scull_qset *data; /* 指向第一个量子集 */
int quantum; /* 当前量子的大小 */
int qset; /* 当前数组的大小 */
unsigned long size; /* 保存在其中的数据总量 */
unsigned int access_key; /* 由sculluid和scullpriv使用 */
struct semaphore sem; /* 互斥信号量 */
struct cdev cdev; /* 字符设备结构*/
};
/* 对于字符设备的实现,一般要定义自己的设备类型的结构。scull_dev就是该设备类型。
一般要把信号量,锁之类的保护措施和struct cdev放在其中
*/
/*
* Split minors in two parts
*/
#define TYPE(minor) (((minor) >> 4) & 0xf) /* high nibble */
#define NUM(minor) ((minor) & 0xf) /* low nibble */
/*这两个东西不知道有什么作用*/
/*
* The different configurable parameters
一些外部声明
*/
extern int scull_major; /* main.c */
extern int scull_nr_devs;
extern int scull_quantum;
extern int scull_qset;
/*函数声明*/
int scull_trim(struct scull_dev *dev);
ssize_t scull_read(struct file *filp, char __user *buf, size_t count, loff_t *f_pos);
ssize_t scull_write(struct file *filp, const char __user *buf, size_t count, loff_t *f_pos);
loff_t scull_llseek(struct file *filp, loff_t off, int whence);
int scull_ioctl(struct inode *inode, struct file *filp, unsigned int cmd, unsigned long arg);
/*
* Ioctl definitions
IO控制的定义
*/
/* Use 'k' as magic number
使用k作为幻数*/
#define SCULL_IOC_MAGIC 'k'
/* Please use a different 8-bit number in your code */
#define SCULL_IOCRESET _IO(SCULL_IOC_MAGIC, 0)
/*
* S means 通过指针“设置”
* T means 直接用参数值通知
* G means 表示“获取”,通过设置指针来应答
* Q means 表示“查询”,通过返回值应答
* X means 表示“交换”,原子地交换G S
* H means 表示“切换”,原子地交换T Q
*/
#define SCULL_IOCSQUANTUM _IOW(SCULL_IOC_MAGIC, 1, int)
#define SCULL_IOCSQSET _IOW(SCULL_IOC_MAGIC, 2, int)
#define SCULL_IOCTQUANTUM _IO(SCULL_IOC_MAGIC, 3)
#define SCULL_IOCTQSET _IO(SCULL_IOC_MAGIC, 4)
#define SCULL_IOCGQUANTUM _IOR(SCULL_IOC_MAGIC, 5, int)
#define SCULL_IOCGQSET _IOR(SCULL_IOC_MAGIC, 6, int)
#define SCULL_IOCQQUANTUM _IO(SCULL_IOC_MAGIC, 7)
#define SCULL_IOCQQSET _IO(SCULL_IOC_MAGIC, 8)
#define SCULL_IOCXQUANTUM _IOWR(SCULL_IOC_MAGIC, 9, int)
#define SCULL_IOCXQSET _IOWR(SCULL_IOC_MAGIC,10, int)
#define SCULL_IOCHQUANTUM _IO(SCULL_IOC_MAGIC, 11)
#define SCULL_IOCHQSET _IO(SCULL_IOC_MAGIC, 12)
/*
* The other entities only have "Tell" and "Query", because they're
* not printed in the book, and there's no need to have all six.
* (The previous stuff was only there to show different ways to do it.
*/
#define SCULL_IOC_MAXNR 12
#endif /* _SCULL_H_ */
本文来自ChinaUnix博客,如果查看原文请点:http://blog.chinaunix.net/u2/75473/showart_1272895.html |
|