fs/ext4/move_extent.c
Source file repositories/reference/linux-study-clean/fs/ext4/move_extent.c
File Facts
- System
- Linux kernel
- Corpus path
fs/ext4/move_extent.c- Extension
.c- Size
- 18960 bytes
- Lines
- 659
- Domain
- Core OS
- Bucket
- VFS And Filesystem Core
- Inferred role
- Core OS: implementation source
- Status
- source implementation candidate
Why This File Exists
Core operating-system implementation surface: boot, tasks, memory, VFS, syscall-facing interfaces, synchronization, credentials, and isolation.
- Core operating-system implementation surface: boot, tasks, memory, VFS, syscall-facing interfaces, synchronization, credentials, and isolation.
- Allocates kernel memory; connect allocation flags and lifetime to context constraints.
- Defines or uses C structs; map object ownership, embedded links, reference counts, and lock ownership.
Dependency Surface
linux/fs.hlinux/quotaops.hlinux/slab.hlinux/sched/mm.hext4_jbd2.hext4.hext4_extents.htrace/events/ext4.h
Detected Declarations
struct mext_dataenum mext_move_typefunction ext4_double_down_write_data_semfunction inodesfunction mext_folio_double_lockfunction mext_folio_double_unlockfunction mext_folio_mkuptodatefunction mext_move_beginfunction mext_folio_mkwritefunction mext_move_extentfunction mext_check_validityfunction ext4_should_journal_datafunction ext4_move_extentsfunction ext4_move_extents
Annotated Snippet
struct mext_data {
struct inode *orig_inode; /* Origin file inode */
struct inode *donor_inode; /* Donor file inode */
struct ext4_map_blocks orig_map;/* Origin file's move mapping */
ext4_lblk_t donor_lblk; /* Start block of the donor file */
};
/**
* ext4_double_down_write_data_sem() - write lock two inodes's i_data_sem
* @first: inode to be locked
* @second: inode to be locked
*
* Acquire write lock of i_data_sem of the two inodes
*/
void
ext4_double_down_write_data_sem(struct inode *first, struct inode *second)
{
if (first < second) {
down_write(&EXT4_I(first)->i_data_sem);
down_write_nested(&EXT4_I(second)->i_data_sem, I_DATA_SEM_OTHER);
} else {
down_write(&EXT4_I(second)->i_data_sem);
down_write_nested(&EXT4_I(first)->i_data_sem, I_DATA_SEM_OTHER);
}
}
/**
* ext4_double_up_write_data_sem - Release two inodes' write lock of i_data_sem
*
* @orig_inode: original inode structure to be released its lock first
* @donor_inode: donor inode structure to be released its lock second
* Release write lock of i_data_sem of two inodes (orig and donor).
*/
void
ext4_double_up_write_data_sem(struct inode *orig_inode,
struct inode *donor_inode)
{
up_write(&EXT4_I(orig_inode)->i_data_sem);
up_write(&EXT4_I(donor_inode)->i_data_sem);
}
/* Grab and lock folio on both @inode1 and @inode2 by inode order. */
static int mext_folio_double_lock(struct inode *inode1, struct inode *inode2,
pgoff_t index1, pgoff_t index2, size_t len,
struct folio *folio[2])
{
struct address_space *mapping[2];
unsigned int flags;
fgf_t fgp_flags = FGP_WRITEBEGIN;
BUG_ON(!inode1 || !inode2);
if (inode1 < inode2) {
mapping[0] = inode1->i_mapping;
mapping[1] = inode2->i_mapping;
} else {
swap(index1, index2);
mapping[0] = inode2->i_mapping;
mapping[1] = inode1->i_mapping;
}
flags = memalloc_nofs_save();
fgp_flags |= fgf_set_order(len);
folio[0] = __filemap_get_folio(mapping[0], index1, fgp_flags,
mapping_gfp_mask(mapping[0]));
if (IS_ERR(folio[0])) {
memalloc_nofs_restore(flags);
return PTR_ERR(folio[0]);
}
folio[1] = __filemap_get_folio(mapping[1], index2, fgp_flags,
mapping_gfp_mask(mapping[1]));
memalloc_nofs_restore(flags);
if (IS_ERR(folio[1])) {
folio_unlock(folio[0]);
folio_put(folio[0]);
return PTR_ERR(folio[1]);
}
/*
* __filemap_get_folio() may not wait on folio's writeback if
* BDI not demand that. But it is reasonable to be very conservative
* here and explicitly wait on folio's writeback
*/
folio_wait_writeback(folio[0]);
folio_wait_writeback(folio[1]);
if (inode1 > inode2)
swap(folio[0], folio[1]);
return 0;
}
Annotation
- Immediate include surface: `linux/fs.h`, `linux/quotaops.h`, `linux/slab.h`, `linux/sched/mm.h`, `ext4_jbd2.h`, `ext4.h`, `ext4_extents.h`, `trace/events/ext4.h`.
- Detected declarations: `struct mext_data`, `enum mext_move_type`, `function ext4_double_down_write_data_sem`, `function inodes`, `function mext_folio_double_lock`, `function mext_folio_double_unlock`, `function mext_folio_mkuptodate`, `function mext_move_begin`, `function mext_folio_mkwrite`, `function mext_move_extent`.
- Atlas domain: Core OS / VFS And Filesystem Core.
- Implementation status: source implementation candidate.
Implementation Notes
- This generated page is the file-by-file coverage layer; curated subsystem chapters should link here when they synthesize a multi-file control flow.
- Core OS pages should be promoted from atlas-only to deep-reviewed when they explain data structures, invariants, locking, lifecycle, and C implementation snippets.
- Driver-family pages are intentionally pattern-oriented unless they are part of the selected PCIe/NVMe representative device path.