Skip to content

Commit 5eea586

Browse files
Matthew Wilcox (Oracle)tytso
authored andcommitted
ext4: convert bd_buddy_page to bd_buddy_folio
There is no need to make this a multi-page folio, so leave all the infrastructure around it in pages. But since we're locking it, playing with its refcount and checking whether it's uptodate, it needs to move to the folio API. Signed-off-by: Matthew Wilcox (Oracle) <willy@infradead.org> Link: https://lore.kernel.org/r/20240416172900.244637-3-willy@infradead.org Signed-off-by: Theodore Ts'o <tytso@mit.edu>
1 parent 99b150d commit 5eea586

File tree

2 files changed

+46
-47
lines changed

2 files changed

+46
-47
lines changed

fs/ext4/mballoc.c

Lines changed: 45 additions & 46 deletions
Original file line numberDiff line numberDiff line change
@@ -1443,18 +1443,17 @@ static int ext4_mb_init_cache(struct page *page, char *incore, gfp_t gfp)
14431443
* Lock the buddy and bitmap pages. This make sure other parallel init_group
14441444
* on the same buddy page doesn't happen whild holding the buddy page lock.
14451445
* Return locked buddy and bitmap pages on e4b struct. If buddy and bitmap
1446-
* are on the same page e4b->bd_buddy_page is NULL and return value is 0.
1446+
* are on the same page e4b->bd_buddy_folio is NULL and return value is 0.
14471447
*/
14481448
static int ext4_mb_get_buddy_page_lock(struct super_block *sb,
14491449
ext4_group_t group, struct ext4_buddy *e4b, gfp_t gfp)
14501450
{
14511451
struct inode *inode = EXT4_SB(sb)->s_buddy_cache;
14521452
int block, pnum, poff;
14531453
int blocks_per_page;
1454-
struct page *page;
14551454
struct folio *folio;
14561455

1457-
e4b->bd_buddy_page = NULL;
1456+
e4b->bd_buddy_folio = NULL;
14581457
e4b->bd_bitmap_folio = NULL;
14591458

14601459
blocks_per_page = PAGE_SIZE / sb->s_blocksize;
@@ -1480,11 +1479,12 @@ static int ext4_mb_get_buddy_page_lock(struct super_block *sb,
14801479
}
14811480

14821481
/* blocks_per_page == 1, hence we need another page for the buddy */
1483-
page = find_or_create_page(inode->i_mapping, block + 1, gfp);
1484-
if (!page)
1485-
return -ENOMEM;
1486-
BUG_ON(page->mapping != inode->i_mapping);
1487-
e4b->bd_buddy_page = page;
1482+
folio = __filemap_get_folio(inode->i_mapping, block + 1,
1483+
FGP_LOCK | FGP_ACCESSED | FGP_CREAT, gfp);
1484+
if (IS_ERR(folio))
1485+
return PTR_ERR(folio);
1486+
BUG_ON(folio->mapping != inode->i_mapping);
1487+
e4b->bd_buddy_folio = folio;
14881488
return 0;
14891489
}
14901490

@@ -1494,9 +1494,9 @@ static void ext4_mb_put_buddy_page_lock(struct ext4_buddy *e4b)
14941494
folio_unlock(e4b->bd_bitmap_folio);
14951495
folio_put(e4b->bd_bitmap_folio);
14961496
}
1497-
if (e4b->bd_buddy_page) {
1498-
unlock_page(e4b->bd_buddy_page);
1499-
put_page(e4b->bd_buddy_page);
1497+
if (e4b->bd_buddy_folio) {
1498+
folio_unlock(e4b->bd_buddy_folio);
1499+
folio_put(e4b->bd_buddy_folio);
15001500
}
15011501
}
15021502

@@ -1511,7 +1511,6 @@ int ext4_mb_init_group(struct super_block *sb, ext4_group_t group, gfp_t gfp)
15111511

15121512
struct ext4_group_info *this_grp;
15131513
struct ext4_buddy e4b;
1514-
struct page *page;
15151514
struct folio *folio;
15161515
int ret = 0;
15171516

@@ -1548,7 +1547,7 @@ int ext4_mb_init_group(struct super_block *sb, ext4_group_t group, gfp_t gfp)
15481547
goto err;
15491548
}
15501549

1551-
if (e4b.bd_buddy_page == NULL) {
1550+
if (e4b.bd_buddy_folio == NULL) {
15521551
/*
15531552
* If both the bitmap and buddy are in
15541553
* the same page we don't need to force
@@ -1558,11 +1557,11 @@ int ext4_mb_init_group(struct super_block *sb, ext4_group_t group, gfp_t gfp)
15581557
goto err;
15591558
}
15601559
/* init buddy cache */
1561-
page = e4b.bd_buddy_page;
1562-
ret = ext4_mb_init_cache(page, e4b.bd_bitmap, gfp);
1560+
folio = e4b.bd_buddy_folio;
1561+
ret = ext4_mb_init_cache(&folio->page, e4b.bd_bitmap, gfp);
15631562
if (ret)
15641563
goto err;
1565-
if (!PageUptodate(page)) {
1564+
if (!folio_test_uptodate(folio)) {
15661565
ret = -EIO;
15671566
goto err;
15681567
}
@@ -1584,7 +1583,6 @@ ext4_mb_load_buddy_gfp(struct super_block *sb, ext4_group_t group,
15841583
int block;
15851584
int pnum;
15861585
int poff;
1587-
struct page *page;
15881586
struct folio *folio;
15891587
int ret;
15901588
struct ext4_group_info *grp;
@@ -1603,7 +1601,7 @@ ext4_mb_load_buddy_gfp(struct super_block *sb, ext4_group_t group,
16031601
e4b->bd_info = grp;
16041602
e4b->bd_sb = sb;
16051603
e4b->bd_group = group;
1606-
e4b->bd_buddy_page = NULL;
1604+
e4b->bd_buddy_folio = NULL;
16071605
e4b->bd_bitmap_folio = NULL;
16081606

16091607
if (unlikely(EXT4_MB_GRP_NEED_INIT(grp))) {
@@ -1669,56 +1667,57 @@ ext4_mb_load_buddy_gfp(struct super_block *sb, ext4_group_t group,
16691667
goto err;
16701668
}
16711669

1672-
/* Pages marked accessed already */
1670+
/* Folios marked accessed already */
16731671
e4b->bd_bitmap_folio = folio;
16741672
e4b->bd_bitmap = folio_address(folio) + (poff * sb->s_blocksize);
16751673

16761674
block++;
16771675
pnum = block / blocks_per_page;
16781676
poff = block % blocks_per_page;
16791677

1680-
page = find_get_page_flags(inode->i_mapping, pnum, FGP_ACCESSED);
1681-
if (page == NULL || !PageUptodate(page)) {
1682-
if (page)
1683-
put_page(page);
1684-
page = find_or_create_page(inode->i_mapping, pnum, gfp);
1685-
if (page) {
1686-
if (WARN_RATELIMIT(page->mapping != inode->i_mapping,
1687-
"ext4: buddy bitmap's page->mapping != inode->i_mapping\n")) {
1678+
folio = __filemap_get_folio(inode->i_mapping, pnum, FGP_ACCESSED, 0);
1679+
if (IS_ERR(folio) || !folio_test_uptodate(folio)) {
1680+
if (!IS_ERR(folio))
1681+
folio_put(folio);
1682+
folio = __filemap_get_folio(inode->i_mapping, pnum,
1683+
FGP_LOCK | FGP_ACCESSED | FGP_CREAT, gfp);
1684+
if (!IS_ERR(folio)) {
1685+
if (WARN_RATELIMIT(folio->mapping != inode->i_mapping,
1686+
"ext4: buddy bitmap's mapping != inode->i_mapping\n")) {
16881687
/* should never happen */
1689-
unlock_page(page);
1688+
folio_unlock(folio);
16901689
ret = -EINVAL;
16911690
goto err;
16921691
}
1693-
if (!PageUptodate(page)) {
1694-
ret = ext4_mb_init_cache(page, e4b->bd_bitmap,
1692+
if (!folio_test_uptodate(folio)) {
1693+
ret = ext4_mb_init_cache(&folio->page, e4b->bd_bitmap,
16951694
gfp);
16961695
if (ret) {
1697-
unlock_page(page);
1696+
folio_unlock(folio);
16981697
goto err;
16991698
}
17001699
}
1701-
unlock_page(page);
1700+
folio_unlock(folio);
17021701
}
17031702
}
1704-
if (page == NULL) {
1705-
ret = -ENOMEM;
1703+
if (IS_ERR(folio)) {
1704+
ret = PTR_ERR(folio);
17061705
goto err;
17071706
}
1708-
if (!PageUptodate(page)) {
1707+
if (!folio_test_uptodate(folio)) {
17091708
ret = -EIO;
17101709
goto err;
17111710
}
17121711

1713-
/* Pages marked accessed already */
1714-
e4b->bd_buddy_page = page;
1715-
e4b->bd_buddy = page_address(page) + (poff * sb->s_blocksize);
1712+
/* Folios marked accessed already */
1713+
e4b->bd_buddy_folio = folio;
1714+
e4b->bd_buddy = folio_address(folio) + (poff * sb->s_blocksize);
17161715

17171716
return 0;
17181717

17191718
err:
1720-
if (page)
1721-
put_page(page);
1719+
if (folio)
1720+
folio_put(folio);
17221721
if (e4b->bd_bitmap_folio)
17231722
folio_put(e4b->bd_bitmap_folio);
17241723

@@ -1737,8 +1736,8 @@ static void ext4_mb_unload_buddy(struct ext4_buddy *e4b)
17371736
{
17381737
if (e4b->bd_bitmap_folio)
17391738
folio_put(e4b->bd_bitmap_folio);
1740-
if (e4b->bd_buddy_page)
1741-
put_page(e4b->bd_buddy_page);
1739+
if (e4b->bd_buddy_folio)
1740+
folio_put(e4b->bd_buddy_folio);
17421741
}
17431742

17441743

@@ -2163,7 +2162,7 @@ static void ext4_mb_use_best_found(struct ext4_allocation_context *ac,
21632162
*/
21642163
ac->ac_bitmap_page = &e4b->bd_bitmap_folio->page;
21652164
get_page(ac->ac_bitmap_page);
2166-
ac->ac_buddy_page = e4b->bd_buddy_page;
2165+
ac->ac_buddy_page = &e4b->bd_buddy_folio->page;
21672166
get_page(ac->ac_buddy_page);
21682167
/* store last allocated for subsequent stream allocation */
21692168
if (ac->ac_flags & EXT4_MB_STREAM_ALLOC) {
@@ -3897,7 +3896,7 @@ static void ext4_free_data_in_buddy(struct super_block *sb,
38973896
/* No more items in the per group rb tree
38983897
* balance refcounts from ext4_mb_free_metadata()
38993898
*/
3900-
put_page(e4b.bd_buddy_page);
3899+
folio_put(e4b.bd_buddy_folio);
39013900
folio_put(e4b.bd_bitmap_folio);
39023901
}
39033902
ext4_unlock_group(sb, entry->efd_group);
@@ -6321,7 +6320,7 @@ ext4_mb_free_metadata(handle_t *handle, struct ext4_buddy *e4b,
63216320

63226321
BUG_ON(!ext4_handle_valid(handle));
63236322
BUG_ON(e4b->bd_bitmap_folio == NULL);
6324-
BUG_ON(e4b->bd_buddy_page == NULL);
6323+
BUG_ON(e4b->bd_buddy_folio == NULL);
63256324

63266325
new_node = &new_entry->efd_node;
63276326
cluster = new_entry->efd_start_cluster;
@@ -6332,7 +6331,7 @@ ext4_mb_free_metadata(handle_t *handle, struct ext4_buddy *e4b,
63326331
* otherwise we'll refresh it from
63336332
* on-disk bitmap and lose not-yet-available
63346333
* blocks */
6335-
get_page(e4b->bd_buddy_page);
6334+
folio_get(e4b->bd_buddy_folio);
63366335
folio_get(e4b->bd_bitmap_folio);
63376336
}
63386337
while (*n) {

fs/ext4/mballoc.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -215,7 +215,7 @@ struct ext4_allocation_context {
215215
#define AC_STATUS_BREAK 3
216216

217217
struct ext4_buddy {
218-
struct page *bd_buddy_page;
218+
struct folio *bd_buddy_folio;
219219
void *bd_buddy;
220220
struct folio *bd_bitmap_folio;
221221
void *bd_bitmap;

0 commit comments

Comments
 (0)