Skip to content

Commit 7b50803

Browse files
adam900710kdave
authored andcommitted
btrfs: defrag: use defrag_one_cluster() to implement btrfs_defrag_file()
The function defrag_one_cluster() is able to defrag one range well enough, we only need to do preparation for it, including: - Clamp and align the defrag range - Exclude invalid cases - Proper inode locking The old infrastructures will not be removed in this patch, as it would be too noisy to review. Signed-off-by: Qu Wenruo <[email protected]> Reviewed-by: David Sterba <[email protected]> Signed-off-by: David Sterba <[email protected]>
1 parent b18c3ab commit 7b50803

File tree

1 file changed

+55
-149
lines changed

1 file changed

+55
-149
lines changed

fs/btrfs/ioctl.c

Lines changed: 55 additions & 149 deletions
Original file line numberDiff line numberDiff line change
@@ -1760,25 +1760,15 @@ int btrfs_defrag_file(struct inode *inode, struct file_ra_state *ra,
17601760
u64 newer_than, unsigned long max_to_defrag)
17611761
{
17621762
struct btrfs_fs_info *fs_info = btrfs_sb(inode->i_sb);
1763-
struct btrfs_root *root = BTRFS_I(inode)->root;
1764-
unsigned long last_index;
1763+
unsigned long sectors_defragged = 0;
17651764
u64 isize = i_size_read(inode);
1766-
u64 last_len = 0;
1767-
u64 skip = 0;
1768-
u64 defrag_end = 0;
1769-
u64 newer_off = range->start;
1770-
unsigned long i;
1771-
unsigned long ra_index = 0;
1772-
int ret;
1773-
int defrag_count = 0;
1774-
int compress_type = BTRFS_COMPRESS_ZLIB;
1775-
u32 extent_thresh = range->extent_thresh;
1776-
unsigned long max_cluster = SZ_256K >> PAGE_SHIFT;
1777-
unsigned long cluster = max_cluster;
1778-
u64 new_align = ~((u64)SZ_128K - 1);
1779-
struct page **pages = NULL;
1765+
u64 cur;
1766+
u64 last_byte;
17801767
bool do_compress = range->flags & BTRFS_DEFRAG_RANGE_COMPRESS;
17811768
bool ra_allocated = false;
1769+
int compress_type = BTRFS_COMPRESS_ZLIB;
1770+
int ret = 0;
1771+
u32 extent_thresh = range->extent_thresh;
17821772

17831773
if (isize == 0)
17841774
return 0;
@@ -1796,6 +1786,14 @@ int btrfs_defrag_file(struct inode *inode, struct file_ra_state *ra,
17961786
if (extent_thresh == 0)
17971787
extent_thresh = SZ_256K;
17981788

1789+
if (range->start + range->len > range->start) {
1790+
/* Got a specific range */
1791+
last_byte = min(isize, range->start + range->len) - 1;
1792+
} else {
1793+
/* Defrag until file end */
1794+
last_byte = isize - 1;
1795+
}
1796+
17991797
/*
18001798
* If we were not given a ra, allocate a readahead context. As
18011799
* readahead is just an optimization, defrag will work without it so
@@ -1808,159 +1806,67 @@ int btrfs_defrag_file(struct inode *inode, struct file_ra_state *ra,
18081806
file_ra_state_init(ra, inode->i_mapping);
18091807
}
18101808

1811-
pages = kmalloc_array(max_cluster, sizeof(struct page *), GFP_KERNEL);
1812-
if (!pages) {
1813-
ret = -ENOMEM;
1814-
goto out_ra;
1815-
}
1809+
/* Align the range */
1810+
cur = round_down(range->start, fs_info->sectorsize);
1811+
last_byte = round_up(last_byte, fs_info->sectorsize) - 1;
18161812

1817-
/* find the last page to defrag */
1818-
if (range->start + range->len > range->start) {
1819-
last_index = min_t(u64, isize - 1,
1820-
range->start + range->len - 1) >> PAGE_SHIFT;
1821-
} else {
1822-
last_index = (isize - 1) >> PAGE_SHIFT;
1823-
}
1824-
1825-
if (newer_than) {
1826-
ret = find_new_extents(root, inode, newer_than,
1827-
&newer_off, SZ_64K);
1828-
if (!ret) {
1829-
range->start = newer_off;
1830-
/*
1831-
* we always align our defrag to help keep
1832-
* the extents in the file evenly spaced
1833-
*/
1834-
i = (newer_off & new_align) >> PAGE_SHIFT;
1835-
} else
1836-
goto out_ra;
1837-
} else {
1838-
i = range->start >> PAGE_SHIFT;
1839-
}
1840-
if (!max_to_defrag)
1841-
max_to_defrag = last_index - i + 1;
1842-
1843-
/*
1844-
* make writeback starts from i, so the defrag range can be
1845-
* written sequentially.
1846-
*/
1847-
if (i < inode->i_mapping->writeback_index)
1848-
inode->i_mapping->writeback_index = i;
1849-
1850-
while (i <= last_index && defrag_count < max_to_defrag &&
1851-
(i < DIV_ROUND_UP(i_size_read(inode), PAGE_SIZE))) {
1852-
/*
1853-
* make sure we stop running if someone unmounts
1854-
* the FS
1855-
*/
1856-
if (!(inode->i_sb->s_flags & SB_ACTIVE))
1857-
break;
1858-
1859-
if (btrfs_defrag_cancelled(fs_info)) {
1860-
btrfs_debug(fs_info, "defrag_file cancelled");
1861-
ret = -EAGAIN;
1862-
goto error;
1863-
}
1864-
1865-
if (!should_defrag_range(inode, (u64)i << PAGE_SHIFT,
1866-
extent_thresh, &last_len, &skip,
1867-
&defrag_end, do_compress)){
1868-
unsigned long next;
1869-
/*
1870-
* the should_defrag function tells us how much to skip
1871-
* bump our counter by the suggested amount
1872-
*/
1873-
next = DIV_ROUND_UP(skip, PAGE_SIZE);
1874-
i = max(i + 1, next);
1875-
continue;
1876-
}
1813+
while (cur < last_byte) {
1814+
u64 cluster_end;
18771815

1878-
if (!newer_than) {
1879-
cluster = (PAGE_ALIGN(defrag_end) >>
1880-
PAGE_SHIFT) - i;
1881-
cluster = min(cluster, max_cluster);
1882-
} else {
1883-
cluster = max_cluster;
1884-
}
1816+
/* The cluster size 256K should always be page aligned */
1817+
BUILD_BUG_ON(!IS_ALIGNED(CLUSTER_SIZE, PAGE_SIZE));
18851818

1886-
if (i + cluster > ra_index) {
1887-
ra_index = max(i, ra_index);
1888-
if (ra)
1889-
page_cache_sync_readahead(inode->i_mapping, ra,
1890-
NULL, ra_index, cluster);
1891-
ra_index += cluster;
1892-
}
1819+
/* We want the cluster end at page boundary when possible */
1820+
cluster_end = (((cur >> PAGE_SHIFT) +
1821+
(SZ_256K >> PAGE_SHIFT)) << PAGE_SHIFT) - 1;
1822+
cluster_end = min(cluster_end, last_byte);
18931823

18941824
btrfs_inode_lock(inode, 0);
18951825
if (IS_SWAPFILE(inode)) {
18961826
ret = -ETXTBSY;
1897-
} else {
1898-
if (do_compress)
1899-
BTRFS_I(inode)->defrag_compress = compress_type;
1900-
ret = cluster_pages_for_defrag(inode, pages, i, cluster);
1827+
btrfs_inode_unlock(inode, 0);
1828+
break;
19011829
}
1902-
if (ret < 0) {
1830+
if (!(inode->i_sb->s_flags & SB_ACTIVE)) {
19031831
btrfs_inode_unlock(inode, 0);
1904-
goto out_ra;
1832+
break;
19051833
}
1906-
1907-
defrag_count += ret;
1908-
balance_dirty_pages_ratelimited(inode->i_mapping);
1834+
if (do_compress)
1835+
BTRFS_I(inode)->defrag_compress = compress_type;
1836+
ret = defrag_one_cluster(BTRFS_I(inode), ra, cur,
1837+
cluster_end + 1 - cur, extent_thresh,
1838+
newer_than, do_compress,
1839+
&sectors_defragged, max_to_defrag);
19091840
btrfs_inode_unlock(inode, 0);
1910-
1911-
if (newer_than) {
1912-
if (newer_off == (u64)-1)
1913-
break;
1914-
1915-
if (ret > 0)
1916-
i += ret;
1917-
1918-
newer_off = max(newer_off + 1,
1919-
(u64)i << PAGE_SHIFT);
1920-
1921-
ret = find_new_extents(root, inode, newer_than,
1922-
&newer_off, SZ_64K);
1923-
if (!ret) {
1924-
range->start = newer_off;
1925-
i = (newer_off & new_align) >> PAGE_SHIFT;
1926-
} else {
1927-
break;
1928-
}
1929-
} else {
1930-
if (ret > 0) {
1931-
i += ret;
1932-
last_len += ret << PAGE_SHIFT;
1933-
} else {
1934-
i++;
1935-
last_len = 0;
1936-
}
1937-
}
1841+
if (ret < 0)
1842+
break;
1843+
cur = cluster_end + 1;
19381844
}
19391845

1940-
ret = defrag_count;
1941-
error:
1942-
if ((range->flags & BTRFS_DEFRAG_RANGE_START_IO)) {
1943-
filemap_flush(inode->i_mapping);
1944-
if (test_bit(BTRFS_INODE_HAS_ASYNC_EXTENT,
1945-
&BTRFS_I(inode)->runtime_flags))
1846+
if (ra_allocated)
1847+
kfree(ra);
1848+
if (sectors_defragged) {
1849+
/*
1850+
* We have defragged some sectors, for compression case they
1851+
* need to be written back immediately.
1852+
*/
1853+
if (range->flags & BTRFS_DEFRAG_RANGE_START_IO) {
19461854
filemap_flush(inode->i_mapping);
1855+
if (test_bit(BTRFS_INODE_HAS_ASYNC_EXTENT,
1856+
&BTRFS_I(inode)->runtime_flags))
1857+
filemap_flush(inode->i_mapping);
1858+
}
1859+
if (range->compress_type == BTRFS_COMPRESS_LZO)
1860+
btrfs_set_fs_incompat(fs_info, COMPRESS_LZO);
1861+
else if (range->compress_type == BTRFS_COMPRESS_ZSTD)
1862+
btrfs_set_fs_incompat(fs_info, COMPRESS_ZSTD);
1863+
ret = sectors_defragged;
19471864
}
1948-
1949-
if (range->compress_type == BTRFS_COMPRESS_LZO) {
1950-
btrfs_set_fs_incompat(fs_info, COMPRESS_LZO);
1951-
} else if (range->compress_type == BTRFS_COMPRESS_ZSTD) {
1952-
btrfs_set_fs_incompat(fs_info, COMPRESS_ZSTD);
1953-
}
1954-
1955-
out_ra:
19561865
if (do_compress) {
19571866
btrfs_inode_lock(inode, 0);
19581867
BTRFS_I(inode)->defrag_compress = BTRFS_COMPRESS_NONE;
19591868
btrfs_inode_unlock(inode, 0);
19601869
}
1961-
if (ra_allocated)
1962-
kfree(ra);
1963-
kfree(pages);
19641870
return ret;
19651871
}
19661872

0 commit comments

Comments
 (0)