字元裝置驅動第八課 file

2022-05-21 08:48:16 字數 4020 閱讀 7858

裝置驅動中的操作方法集中所有的函式,第乙個引數都是struct file *filp。這個結構體中有個成員,專門標識阻塞和非阻塞。

struct file f_u;

struct path f_path; //路徑

struct inode *f_inode; /* cached value */

const struct file_operations *f_op; //操作方法集

/** protects f_ep_links, f_flags.

* must not be taken from irq context.

*/spinlock_t f_lock;

atomic_long_t f_count;

unsigned int f_flags; //是否阻塞

fmode_t f_mode;

struct mutex f_pos_lock;

loff_t f_pos;

struct fown_struct f_owner;

const struct cred *f_cred;

struct file_ra_state f_ra;

u64 f_version;

#ifdef config_security

void *f_security;

#endif

/* needed for tty driver, and maybe others */

void *private_data;

#ifdef config_epoll

/* used by fs/eventpoll.c to link all the hooks to this file */

struct list_head f_ep_links;

struct list_head f_tfile_llink;

#endif /* #ifdef config_epoll */

struct address_space *f_mapping;

} __attribute__((aligned(4))); /* lest something weird decides that 2 is ok */

o_nonblockif(filp->f_flags & o_nonblock)o_blockif(filp->f_flags & o_block)#include

#include

#include

#include

#include

#include

#include

#include

#include

#include

#include

#include

#include

static struct class *cls = null; //裝置類,為自動建立裝置

static int major = 0;

static int minor = 0;

const int count = 6;

#define devname "demo"

static struct cdev *demop = null; //字元型裝置控制代碼,為自動建立裝置

static atomic_t tv; //定義乙個原子操作

static wait_queue_head_t wq; //定義乙個等待佇列

static int counter = 0;

//開啟裝置

static int demo_open(struct inode *inode, struct file *filp)

return 0;

}//關閉裝置

static int demo_release(struct inode *inode, struct file *filp)

//讀裝置

//ssize_t read(int fd, void *buf, size_t count)

static ssize_t demo_read(struct file *filp, char __user *buf, size_t size, loff_t *offset)

err = wait_event_interruptible(wq, (0 != counter));//若「counter不為0」這個條件成立,則返回值為0且往下走,否則阻塞在此處(但這種阻塞狀態可以被中斷)

if(err)

}//...

counter = 0; //讀完清零,模擬緩衝區已被讀空

return 0;

}//寫裝置

static ssize_t demo_write(struct file *filp, const char __user *buf, size_t size, loff_t *offset)

static struct file_operations fops = ;

static int __init demo_init(void)

//2. init cdev obj

cdev_init(demop, &fops);

ret = alloc_chrdev_region(&devnum, minor, count, devname);//動態申請裝置號

if(ret)

major = major(devnum);

//3. register cdev obj

ret = cdev_add(demop, devnum, count);

if(ret)

cls = class_create(this_module, devname); //建立裝置類,自動建立裝置

if(is_err(cls))

for(i = minor; i < (count+minor); i++)

}// init atomic_t

atomic_set(&tv, 1); // 初始化原子操作,設定原子量的初值為1

init_waitqueue_head(&wq); //初始化等待佇列

//get command and pid

printk(kern_info "(%s:pid=%d), %s : %s : %d - ok.\n",

current->comm, current->pid, __file__, __func__, __line__);

return 0;

err_step2:

for(--i; i >= minor; i--)

class_destroy(cls);

err_step1:

unregister_chrdev_region(devnum, count);

err_step:

cdev_del(demop);

//get command and pid

printk(kern_info "(%s:pid=%d), %s : %s : %d - fail.\n",

current->comm, current->pid, __file__, __func__, __line__);

return ret;

}static void __exit demo_exit(void)

class_destroy(cls);

unregister_chrdev_region(mkdev(major, minor), count);

cdev_del(demop);

}module_init(demo_init);

module_exit(demo_exit);

module_license("gpl");

module_author("farsight");

module_description("demo for kernel module");

字元裝置驅動第八課 讀寫鎖

忙等鎖,臨界區盡量不休眠。rwlock init lock write lock lock write unlock lock read lock lock read unlock lock 搶得到就搶。搶不到鎖也返回往下走,一般下面會對其返回值做判斷 功能 嘗試上讀鎖,不管搶到鎖還是搶不到鎖都返回...

字元裝置驅動第八課 自旋鎖

原始碼目錄下include linux spinlock.hstatic spinlock t lock 定義乙個自旋鎖spin lock init lock spin lock lock spin unlock lock include include include include includ...

字元裝置驅動第八課 互斥鎖

struct mutex lock 定義互斥鎖mutex init mutex 功能 阻塞式上互斥鎖,搶不到就一直阻塞 mutex lock struct mutex lock 功能 非阻塞式上互斥鎖,搶不到也會返回往下走 返回值 成功搶到鎖 1 沒搶到鎖 0 int mutex trylock s...