以cramfs_read爲例,詳細流程如下,
1,發起cramfs superblock讀流程:
2,要讀的page在不address_space, 測發起真正的讀,執行filler函數(blkdev_readpage):
i_blkbits是文件系統定義的文件的塊大小: between 512 and PAGE_SIZE
設置塊大小:
其中create_page_buffers函數:
其中create_empty_buffers函數:
create_empty_buffers函數調用的alloc_page_buffers函數爲:
最終提交bh的函數爲,要將bh轉化爲bio進行提交:
submit_bh -> __submit_bh -> submit_bio:
設備block塊號和文件系統塊號之間的對應關係在_submit_bh函數中決定
bio->bi_sector = bh->b_blocknr * (bh->b_size >> 9);
上面代碼,IO完成後,bio的回調先被調用,然後在bio的回調中會調用buffer_head的回調。
buffer_head的定義:
/*
* Historically, a buffer_head was used to map a single block
* within a page, and of course as the unit of I/O through the
* filesystem and block layers. Nowadays the basic I/O unit
* is the bio, and buffer_heads are used for extracting block
* mappings (via a get_block_t call), for tracking state within
* a page (via a page_mapping) and for wrapping bio submission
* for backward compatibility reasons (e.g. submit_bh).
*/
與buffer_head緩衝區頭對應的磁盤物理塊由b_blocknr 索引,該值是 b_bdev 域指明的塊設備的邏輯塊號。與緩衝區對應的內存物理頁由 b_page 表示。b_data 直接指向相應的塊 ( 它位於b_page 所指明的頁面上的某個位置 ),磁盤塊的大小由 b_size 表示 。所以塊在內存中的起始位置在b_data 處,結束位置在b_data+b_size 處 。 緩衝區頭的目的在於描述磁盤塊和物理內存緩衝區之間的映射關係 .
參考:https://blog.csdn.net/weixin_36145588/article/details/74937592