- 论坛徽章:
- 1
|
本帖最后由 yangPSO 于 2014-11-22 20:18 编辑
回复 4# 镇水铁牛
【以linux-2.32为例】
个人理解:
xfs文件系统在回写某个page cache到块层时设置了page cache的PG_writeback标志,然后释放了PG_locked标志,具体来说就是:
通过如下的函数关系
mapping->a_ops->writepages(mapping, wbc);
xfs_vm_writepages
generic_writepages
write_cache_pages
调用到函数write_cache_pages(),其中包含如下的代码:- while (!done && (index <= end)) {
- int i;
- nr_pages = pagevec_lookup_tag(&pvec, mapping, &index, tag,
- min(end - index, (pgoff_t)PAGEVEC_SIZE-1) + 1);
- if (nr_pages == 0)
- break;
- for (i = 0; i < nr_pages; i++) {
- struct page *page = pvec.pages[i];
- ..................
- lock_page(page);
- ..................
- if (PageWriteback(page)) {
- if (wbc->sync_mode != WB_SYNC_NONE)
- wait_on_page_writeback(page);
- else
- goto continue_unlock;
- }
- BUG_ON(PageWriteback(page));
- ..................
- ret = (*writepage)(page, wbc, data);
- ..................
- }
复制代码 对于每个待写(刷新)的page cache,首先调用函数lock_page()进行加锁,如果page正在回写过程中并且wbc->sync_mode为WB_SYNC_NONE,
将调用函数wait_on_page_writeback()等待回写过程结束。然后调用writepage回调函数,即函数xfs_vm_writepage()执行写操作。
同时,函数xfs_vm_writepage()通过如下的函数关系
xfs_vm_writepage
xfs_start_page_writeback
set_page_writeback
test_set_page_writeback
ret = TestSetPageWriteback(page);
设置page的PG_writeback标志,表明page处于回写过程中。
同时,函数xfs_start_page_writeback()在设置完page的PG_writeback标志后将调用函数unlock_page()将page解锁,在解锁前一刻将page设置为Uptodate的。
那么某个进程就可能在在该page cache 的PG_locked标志释放后成功设置其PG_locked标志后去写这个page cache,而该page cache可能正在以DMA的方式将page cache中数据写往磁盘。
进程写page cache并不需要判断PG_writeback标志,只会判断PG_locked标志。
另外mmap方式写内存根本不执行系统调用,更不会判断什么锁状态。
|
|