驱动程序之_2_块设备_2_ll_rw_block分析

驱动程序之_2_块设备_2_ll_rw_block分析

层次结构
在这里插入图片描述

内核目录下有fs文件夹,里面放有各种文件系统以及它们公共的接口,ll_rw_block就位于fs/buffer.c中

以读为例
在ll_rw_block中提取bh呈递

void ll_rw_block(int rw, int nr, struct buffer_head *bhs[])
{
/*******************************************/
	struct buffer_head *bh = bhs[i];
/*******************************************/	
	if (rw == WRITE || rw == SWRITE) {
	}
	else{
		submit_bh(rw, bh);
	}
/*******************************************/
}

在submit_bh中构造bio呈递

int submit_bh(int rw, struct buffer_head * bh)
{
/*******************************************/
	struct bio *bio;
/*******************************************/
	submit_bio(rw, bio);
/*******************************************/
}

在submit_bio中,使用bio构造请求

void submit_bio(int rw, struct bio *bio)
{
/*******************************************/
	generic_make_request(bio);
/*******************************************/
}
void generic_make_request(struct bio *bio)
{
/*******************************************/
	__generic_make_request(bio);
/*******************************************/	
}

在__generic_make_request中找到队列,以此构造请求

static inline void __generic_make_request(struct bio *bio)
{
/*******************************************/
	q = bdev_get_queue(bio->bi_bdev);
/*******************************************/
	ret = q->make_request_fn(q, bio);
/*******************************************/
}

在blk_queue_make_request中设置队列

void blk_queue_make_request(request_queue_t * q, make_request_fn * mfn)
{
/*******************************************/
	q->make_request_fn = mfn;
/*******************************************/
}

在blk_init_queue_node中调用blk_queue_make_request

request_queue_t * blk_init_queue_node(request_fn_proc *rfn, spinlock_t *lock, int node_id)
{
/*******************************************/
	blk_queue_make_request(q, __make_request);
/*******************************************/
}

在__make_request中使用电梯调度算法尝试合并bio
如果合并不成功,就分配队列节点,添加到队列

static int __make_request(request_queue_t *q, struct bio *bio)
{
/*******************************************/
	el_ret = elv_merge(q, &req, bio);
/*******************************************/	
	req = get_request_wait(q, rw_flags, bio);
/*******************************************/
	add_request(q, req);
/*******************************************/	
}

电梯调度算法中,将一个方向(读写)的数据节点处理一次(尽最大可能),处理完毕后再反向处理

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值