f2fs学习笔记 - 9. f2fs 写文件
1.前言
本文主要介紹f2fs寫入流程. 寫入流程主要分為meta, data, node的寫入,本文主要介紹data的寫入流程。
2.總體流程
sys_writefdgetfile_pos_readvfs_writefile_pos_writefdget是從當(dāng)前進(jìn)程的文件描述符表獲取一個(gè)fd;
file_pos_read獲取文件描述符當(dāng)前的讀寫位置
vfs_write執(zhí)行文件寫入操作
file_pos_write更新文件的寫入位置
3.vfs_write
vfs_writerw_verify_areafile->f_op->write (do_sync_write)generic_file_aio_write__generic_file_aio_writegeneric_segment_checksgeneric_write_checksgeneric_file_direct_write或generic_file_buffered_writesys_write系統(tǒng)調(diào)用會(huì)調(diào)用到vfs_write,進(jìn)而調(diào)用到file->f_op->write,這個(gè)write回調(diào)是在創(chuàng)建文件時(shí)初始化為inode->i_fops->write, 對(duì)于f2fs就是do_sync_write,它會(huì)進(jìn)一步調(diào)用generic_file_aio_write->__generic_file_aio_write
__generic_file_aio_write通過generic_segment_checks來檢查segment的數(shù)目和要寫入數(shù)據(jù)的數(shù)目進(jìn)行必要的檢查,最終確定寫入文件的位置和數(shù)據(jù)的數(shù)目;之后通過generic_write_checks進(jìn)一步對(duì)寫入文件的位置和數(shù)目進(jìn)行檢查
3.1 generic_file_direct_write
generic_file_direct_writefilemap_write_and_wait_range(mapping, pos, pos + write_len - 1)do_writepages(mapping, &wbc)mapping->a_ops->writepages(mapping, wbc)generic_writepages(mapping, wbc)write_cache_pages(mapping, wbc, __writepage, mapping)對(duì)于直寫的情況將執(zhí)行g(shù)eneric_file_direct_write,它調(diào)用writepages回調(diào),對(duì)于f2fs為f2fs_write_data_pages,進(jìn)而它會(huì)執(zhí)行g(shù)eneric_writepages,對(duì)于每一page都將調(diào)用 __writepage,實(shí)際上調(diào)用了mapping->a_ops->writepage(page, wbc)回調(diào),對(duì)于f2fs即為f2fs_write_data_page
3.1.1 f2fs_write_data_page
f2fs_write_data_pagedo_write_data_page(page)get_dnode_of_data(&dn, page->index, RDONLY_NODE)write_data_page(inode, page, &dn,old_blk_addr, &new_blk_addr);set_summary(&sum, dn->nid, dn->ofs_in_node, ni.version)do_write_page(sbi, page, old_blkaddr,new_blkaddr, &sum, DATA)__add_sum_entry(sbi, type, sum, curseg->next_blkoff)__refresh_next_blkoff(sbi, curseg)refresh_sit_entry(sbi, old_blkaddr, *new_blkaddr)submit_write_page(sbi, page, *new_blkaddr, p_type)do_submit_bio(sbi, type, false)get_dnode_of_data:通過page->index查找dnode(直接node)中對(duì)應(yīng)的block地址,保存在dn->data_blkaddr中
write_data_page:old_blk_addr為當(dāng)前要寫入的block的地址,new_blk_addr為下一個(gè)要寫入的block地址
set_summary:由于要寫入數(shù)據(jù),需要更新current segment的summary, 此處是構(gòu)造新的segment summary entry.
do_write_page: 執(zhí)行page寫入操作。
__add_sum_entry:更新current segment中要寫入block的summary entry
__refresh_next_blkoff: 更新current sgement的下一個(gè)block offset, 根據(jù)SSR(thread mode)和LFS模式有所不同;
refresh_sit_entry:
submit_write_page:通過調(diào)用do_submit_bio->submit_bio提交給block層
3.2 .generic_file_buffered_write
generic_file_buffered_writegeneric_perform_write(file, &i, pos)a_ops->write_beginiov_iter_copy_from_user_atomica_ops->write_endf2fs_set_data_page_dirty對(duì)于非直寫的情況將調(diào)用generic_file_buffered_write。它將調(diào)用generic_perform_write(file, &i, pos)執(zhí)行寫入操作
f2fs_write_begin:a_ops->write_begin對(duì)應(yīng)f2fs就是f2fs_write_begin。通過f2fs_write_begin確定了要寫入的page對(duì)應(yīng)的磁盤block地址。
iov_iter_copy_from_user_atomic:將用戶空間數(shù)據(jù)拷貝到page;
a_ops->write_end->generic_write_end:當(dāng)用戶空間數(shù)據(jù)拷貝到page后,用作善后處理,標(biāo)記頁(yè)面為最新且是臟頁(yè),這樣在sync時(shí)就會(huì)將這些頁(yè)面寫入磁盤
f2fs_set_data_page_dirty:在address space 中標(biāo)記page為dirty
總結(jié)
以上是生活随笔為你收集整理的f2fs学习笔记 - 9. f2fs 写文件的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 工程师应用计算机考试题型,IE工程师考试
- 下一篇: linux下挂载F2FS文件系统