* [PATCH v3] ext4: fix mballoc-test.c is not compiled when EXT4_KUNIT_TESTS=M
@ 2026-02-27 6:55 Ye Bin
2026-02-27 15:53 ` Jan Kara
2026-03-06 9:55 ` Ojaswin Mujoo
0 siblings, 2 replies; 5+ messages in thread
From: Ye Bin @ 2026-02-27 6:55 UTC (permalink / raw)
To: tytso, adilger.kernel, linux-ext4; +Cc: jack
From: Ye Bin <yebin10@huawei.com>
Now, only EXT4_KUNIT_TESTS=Y testcase will be compiled in 'mballoc.c'.
To solve this issue, the ext4 test code needs to be decoupled. The ext4
test module is compiled into a separate module.
Reported-by: ChenXiaoSong <chenxiaosong@kylinos.cn>
Closes: https://patchwork.kernel.org/project/cifs-client/patch/20260118091313.1988168-2-chenxiaosong.chenxiaosong@linux.dev/
Fixes: 7c9fa399a369 ("ext4: add first unit test for ext4_mb_new_blocks_simple in mballoc")
Signed-off-by: Ye Bin <yebin10@huawei.com>
---
fs/ext4/Makefile | 4 +-
fs/ext4/mballoc-test.c | 81 +++++++++++++++----------------
fs/ext4/mballoc.c | 105 +++++++++++++++++++++++++++++++++++++++--
fs/ext4/mballoc.h | 30 ++++++++++++
4 files changed, 175 insertions(+), 45 deletions(-)
diff --git a/fs/ext4/Makefile b/fs/ext4/Makefile
index 72206a292676..d836c3fe311b 100644
--- a/fs/ext4/Makefile
+++ b/fs/ext4/Makefile
@@ -14,7 +14,7 @@ ext4-y := balloc.o bitmap.o block_validity.o dir.o ext4_jbd2.o extents.o \
ext4-$(CONFIG_EXT4_FS_POSIX_ACL) += acl.o
ext4-$(CONFIG_EXT4_FS_SECURITY) += xattr_security.o
-ext4-inode-test-objs += inode-test.o
-obj-$(CONFIG_EXT4_KUNIT_TESTS) += ext4-inode-test.o
+ext4-test-objs += inode-test.o mballoc-test.o
+obj-$(CONFIG_EXT4_KUNIT_TESTS) += ext4-test.o
ext4-$(CONFIG_FS_VERITY) += verity.o
ext4-$(CONFIG_FS_ENCRYPTION) += crypto.o
diff --git a/fs/ext4/mballoc-test.c b/fs/ext4/mballoc-test.c
index 4abb40d4561c..749ed2fc2241 100644
--- a/fs/ext4/mballoc-test.c
+++ b/fs/ext4/mballoc-test.c
@@ -8,6 +8,7 @@
#include <linux/random.h>
#include "ext4.h"
+#include "mballoc.h"
struct mbt_grp_ctx {
struct buffer_head bitmap_bh;
@@ -337,7 +338,7 @@ ext4_mb_mark_context_stub(handle_t *handle, struct super_block *sb, bool state,
if (state)
mb_set_bits(bitmap_bh->b_data, blkoff, len);
else
- mb_clear_bits(bitmap_bh->b_data, blkoff, len);
+ mb_clear_bits_test(bitmap_bh->b_data, blkoff, len);
return 0;
}
@@ -414,14 +415,14 @@ static void test_new_blocks_simple(struct kunit *test)
/* get block at goal */
ar.goal = ext4_group_first_block_no(sb, goal_group);
- found = ext4_mb_new_blocks_simple(&ar, &err);
+ found = ext4_mb_new_blocks_simple_test(&ar, &err);
KUNIT_ASSERT_EQ_MSG(test, ar.goal, found,
"failed to alloc block at goal, expected %llu found %llu",
ar.goal, found);
/* get block after goal in goal group */
ar.goal = ext4_group_first_block_no(sb, goal_group);
- found = ext4_mb_new_blocks_simple(&ar, &err);
+ found = ext4_mb_new_blocks_simple_test(&ar, &err);
KUNIT_ASSERT_EQ_MSG(test, ar.goal + EXT4_C2B(sbi, 1), found,
"failed to alloc block after goal in goal group, expected %llu found %llu",
ar.goal + 1, found);
@@ -429,7 +430,7 @@ static void test_new_blocks_simple(struct kunit *test)
/* get block after goal group */
mbt_ctx_mark_used(sb, goal_group, 0, EXT4_CLUSTERS_PER_GROUP(sb));
ar.goal = ext4_group_first_block_no(sb, goal_group);
- found = ext4_mb_new_blocks_simple(&ar, &err);
+ found = ext4_mb_new_blocks_simple_test(&ar, &err);
KUNIT_ASSERT_EQ_MSG(test,
ext4_group_first_block_no(sb, goal_group + 1), found,
"failed to alloc block after goal group, expected %llu found %llu",
@@ -439,7 +440,7 @@ static void test_new_blocks_simple(struct kunit *test)
for (i = goal_group; i < ext4_get_groups_count(sb); i++)
mbt_ctx_mark_used(sb, i, 0, EXT4_CLUSTERS_PER_GROUP(sb));
ar.goal = ext4_group_first_block_no(sb, goal_group);
- found = ext4_mb_new_blocks_simple(&ar, &err);
+ found = ext4_mb_new_blocks_simple_test(&ar, &err);
KUNIT_ASSERT_EQ_MSG(test,
ext4_group_first_block_no(sb, 0) + EXT4_C2B(sbi, 1), found,
"failed to alloc block before goal group, expected %llu found %llu",
@@ -449,7 +450,7 @@ static void test_new_blocks_simple(struct kunit *test)
for (i = 0; i < ext4_get_groups_count(sb); i++)
mbt_ctx_mark_used(sb, i, 0, EXT4_CLUSTERS_PER_GROUP(sb));
ar.goal = ext4_group_first_block_no(sb, goal_group);
- found = ext4_mb_new_blocks_simple(&ar, &err);
+ found = ext4_mb_new_blocks_simple_test(&ar, &err);
KUNIT_ASSERT_NE_MSG(test, err, 0,
"unexpectedly get block when no block is available");
}
@@ -493,16 +494,16 @@ validate_free_blocks_simple(struct kunit *test, struct super_block *sb,
continue;
bitmap = mbt_ctx_bitmap(sb, i);
- bit = mb_find_next_zero_bit(bitmap, max, 0);
+ bit = mb_find_next_zero_bit_test(bitmap, max, 0);
KUNIT_ASSERT_EQ_MSG(test, bit, max,
"free block on unexpected group %d", i);
}
bitmap = mbt_ctx_bitmap(sb, goal_group);
- bit = mb_find_next_zero_bit(bitmap, max, 0);
+ bit = mb_find_next_zero_bit_test(bitmap, max, 0);
KUNIT_ASSERT_EQ(test, bit, start);
- bit = mb_find_next_bit(bitmap, max, bit + 1);
+ bit = mb_find_next_bit_test(bitmap, max, bit + 1);
KUNIT_ASSERT_EQ(test, bit, start + len);
}
@@ -525,7 +526,7 @@ test_free_blocks_simple_range(struct kunit *test, ext4_group_t goal_group,
block = ext4_group_first_block_no(sb, goal_group) +
EXT4_C2B(sbi, start);
- ext4_free_blocks_simple(inode, block, len);
+ ext4_free_blocks_simple_test(inode, block, len);
validate_free_blocks_simple(test, sb, goal_group, start, len);
mbt_ctx_mark_used(sb, goal_group, 0, EXT4_CLUSTERS_PER_GROUP(sb));
}
@@ -567,15 +568,15 @@ test_mark_diskspace_used_range(struct kunit *test,
bitmap = mbt_ctx_bitmap(sb, TEST_GOAL_GROUP);
memset(bitmap, 0, sb->s_blocksize);
- ret = ext4_mb_mark_diskspace_used(ac, NULL);
+ ret = ext4_mb_mark_diskspace_used_test(ac, NULL);
KUNIT_ASSERT_EQ(test, ret, 0);
max = EXT4_CLUSTERS_PER_GROUP(sb);
- i = mb_find_next_bit(bitmap, max, 0);
+ i = mb_find_next_bit_test(bitmap, max, 0);
KUNIT_ASSERT_EQ(test, i, start);
- i = mb_find_next_zero_bit(bitmap, max, i + 1);
+ i = mb_find_next_zero_bit_test(bitmap, max, i + 1);
KUNIT_ASSERT_EQ(test, i, start + len);
- i = mb_find_next_bit(bitmap, max, i + 1);
+ i = mb_find_next_bit_test(bitmap, max, i + 1);
KUNIT_ASSERT_EQ(test, max, i);
}
@@ -618,54 +619,54 @@ static void mbt_generate_buddy(struct super_block *sb, void *buddy,
max = EXT4_CLUSTERS_PER_GROUP(sb);
bb_h = buddy + sbi->s_mb_offsets[1];
- off = mb_find_next_zero_bit(bb, max, 0);
+ off = mb_find_next_zero_bit_test(bb, max, 0);
grp->bb_first_free = off;
while (off < max) {
grp->bb_counters[0]++;
grp->bb_free++;
- if (!(off & 1) && !mb_test_bit(off + 1, bb)) {
+ if (!(off & 1) && !mb_test_bit_test(off + 1, bb)) {
grp->bb_free++;
grp->bb_counters[0]--;
- mb_clear_bit(off >> 1, bb_h);
+ mb_clear_bit_test(off >> 1, bb_h);
grp->bb_counters[1]++;
grp->bb_largest_free_order = 1;
off++;
}
- off = mb_find_next_zero_bit(bb, max, off + 1);
+ off = mb_find_next_zero_bit_test(bb, max, off + 1);
}
for (order = 1; order < MB_NUM_ORDERS(sb) - 1; order++) {
bb = buddy + sbi->s_mb_offsets[order];
bb_h = buddy + sbi->s_mb_offsets[order + 1];
max = max >> 1;
- off = mb_find_next_zero_bit(bb, max, 0);
+ off = mb_find_next_zero_bit_test(bb, max, 0);
while (off < max) {
- if (!(off & 1) && !mb_test_bit(off + 1, bb)) {
+ if (!(off & 1) && !mb_test_bit_test(off + 1, bb)) {
mb_set_bits(bb, off, 2);
grp->bb_counters[order] -= 2;
- mb_clear_bit(off >> 1, bb_h);
+ mb_clear_bit_test(off >> 1, bb_h);
grp->bb_counters[order + 1]++;
grp->bb_largest_free_order = order + 1;
off++;
}
- off = mb_find_next_zero_bit(bb, max, off + 1);
+ off = mb_find_next_zero_bit_test(bb, max, off + 1);
}
}
max = EXT4_CLUSTERS_PER_GROUP(sb);
- off = mb_find_next_zero_bit(bitmap, max, 0);
+ off = mb_find_next_zero_bit_test(bitmap, max, 0);
while (off < max) {
grp->bb_fragments++;
- off = mb_find_next_bit(bitmap, max, off + 1);
+ off = mb_find_next_bit_test(bitmap, max, off + 1);
if (off + 1 >= max)
break;
- off = mb_find_next_zero_bit(bitmap, max, off + 1);
+ off = mb_find_next_zero_bit_test(bitmap, max, off + 1);
}
}
@@ -707,7 +708,7 @@ do_test_generate_buddy(struct kunit *test, struct super_block *sb, void *bitmap,
/* needed by validation in ext4_mb_generate_buddy */
ext4_grp->bb_free = mbt_grp->bb_free;
memset(ext4_buddy, 0xff, sb->s_blocksize);
- ext4_mb_generate_buddy(sb, ext4_buddy, bitmap, TEST_GOAL_GROUP,
+ ext4_mb_generate_buddy_test(sb, ext4_buddy, bitmap, TEST_GOAL_GROUP,
ext4_grp);
KUNIT_ASSERT_EQ(test, memcmp(mbt_buddy, ext4_buddy, sb->s_blocksize),
@@ -761,7 +762,7 @@ test_mb_mark_used_range(struct kunit *test, struct ext4_buddy *e4b,
ex.fe_group = TEST_GOAL_GROUP;
ext4_lock_group(sb, TEST_GOAL_GROUP);
- mb_mark_used(e4b, &ex);
+ mb_mark_used_test(e4b, &ex);
ext4_unlock_group(sb, TEST_GOAL_GROUP);
mb_set_bits(bitmap, start, len);
@@ -770,7 +771,7 @@ test_mb_mark_used_range(struct kunit *test, struct ext4_buddy *e4b,
memset(buddy, 0xff, sb->s_blocksize);
for (i = 0; i < MB_NUM_ORDERS(sb); i++)
grp->bb_counters[i] = 0;
- ext4_mb_generate_buddy(sb, buddy, bitmap, 0, grp);
+ ext4_mb_generate_buddy_test(sb, buddy, bitmap, 0, grp);
KUNIT_ASSERT_EQ(test, memcmp(buddy, e4b->bd_buddy, sb->s_blocksize),
0);
@@ -799,7 +800,7 @@ static void test_mb_mark_used(struct kunit *test)
bb_counters[MB_NUM_ORDERS(sb)]), GFP_KERNEL);
KUNIT_ASSERT_NOT_ERR_OR_NULL(test, grp);
- ret = ext4_mb_load_buddy(sb, TEST_GOAL_GROUP, &e4b);
+ ret = ext4_mb_load_buddy_test(sb, TEST_GOAL_GROUP, &e4b);
KUNIT_ASSERT_EQ(test, ret, 0);
grp->bb_free = EXT4_CLUSTERS_PER_GROUP(sb);
@@ -810,7 +811,7 @@ static void test_mb_mark_used(struct kunit *test)
test_mb_mark_used_range(test, &e4b, ranges[i].start,
ranges[i].len, bitmap, buddy, grp);
- ext4_mb_unload_buddy(&e4b);
+ ext4_mb_unload_buddy_test(&e4b);
}
static void
@@ -826,16 +827,16 @@ test_mb_free_blocks_range(struct kunit *test, struct ext4_buddy *e4b,
return;
ext4_lock_group(sb, e4b->bd_group);
- mb_free_blocks(NULL, e4b, start, len);
+ mb_free_blocks_test(NULL, e4b, start, len);
ext4_unlock_group(sb, e4b->bd_group);
- mb_clear_bits(bitmap, start, len);
+ mb_clear_bits_test(bitmap, start, len);
/* bypass bb_free validatoin in ext4_mb_generate_buddy */
grp->bb_free += len;
memset(buddy, 0xff, sb->s_blocksize);
for (i = 0; i < MB_NUM_ORDERS(sb); i++)
grp->bb_counters[i] = 0;
- ext4_mb_generate_buddy(sb, buddy, bitmap, 0, grp);
+ ext4_mb_generate_buddy_test(sb, buddy, bitmap, 0, grp);
KUNIT_ASSERT_EQ(test, memcmp(buddy, e4b->bd_buddy, sb->s_blocksize),
0);
@@ -866,7 +867,7 @@ static void test_mb_free_blocks(struct kunit *test)
bb_counters[MB_NUM_ORDERS(sb)]), GFP_KERNEL);
KUNIT_ASSERT_NOT_ERR_OR_NULL(test, grp);
- ret = ext4_mb_load_buddy(sb, TEST_GOAL_GROUP, &e4b);
+ ret = ext4_mb_load_buddy_test(sb, TEST_GOAL_GROUP, &e4b);
KUNIT_ASSERT_EQ(test, ret, 0);
ex.fe_start = 0;
@@ -874,7 +875,7 @@ static void test_mb_free_blocks(struct kunit *test)
ex.fe_group = TEST_GOAL_GROUP;
ext4_lock_group(sb, TEST_GOAL_GROUP);
- mb_mark_used(&e4b, &ex);
+ mb_mark_used_test(&e4b, &ex);
ext4_unlock_group(sb, TEST_GOAL_GROUP);
grp->bb_free = 0;
@@ -887,7 +888,7 @@ static void test_mb_free_blocks(struct kunit *test)
test_mb_free_blocks_range(test, &e4b, ranges[i].start,
ranges[i].len, bitmap, buddy, grp);
- ext4_mb_unload_buddy(&e4b);
+ ext4_mb_unload_buddy_test(&e4b);
}
#define COUNT_FOR_ESTIMATE 100000
@@ -905,7 +906,7 @@ static void test_mb_mark_used_cost(struct kunit *test)
if (sb->s_blocksize > PAGE_SIZE)
kunit_skip(test, "blocksize exceeds pagesize");
- ret = ext4_mb_load_buddy(sb, TEST_GOAL_GROUP, &e4b);
+ ret = ext4_mb_load_buddy_test(sb, TEST_GOAL_GROUP, &e4b);
KUNIT_ASSERT_EQ(test, ret, 0);
ex.fe_group = TEST_GOAL_GROUP;
@@ -919,7 +920,7 @@ static void test_mb_mark_used_cost(struct kunit *test)
ex.fe_start = ranges[i].start;
ex.fe_len = ranges[i].len;
ext4_lock_group(sb, TEST_GOAL_GROUP);
- mb_mark_used(&e4b, &ex);
+ mb_mark_used_test(&e4b, &ex);
ext4_unlock_group(sb, TEST_GOAL_GROUP);
}
end = jiffies;
@@ -930,14 +931,14 @@ static void test_mb_mark_used_cost(struct kunit *test)
continue;
ext4_lock_group(sb, TEST_GOAL_GROUP);
- mb_free_blocks(NULL, &e4b, ranges[i].start,
+ mb_free_blocks_test(NULL, &e4b, ranges[i].start,
ranges[i].len);
ext4_unlock_group(sb, TEST_GOAL_GROUP);
}
}
kunit_info(test, "costed jiffies %lu\n", all);
- ext4_mb_unload_buddy(&e4b);
+ ext4_mb_unload_buddy_test(&e4b);
}
static const struct mbt_ext4_block_layout mbt_test_layouts[] = {
diff --git a/fs/ext4/mballoc.c b/fs/ext4/mballoc.c
index b99d1a7e580e..e2341489f4d0 100644
--- a/fs/ext4/mballoc.c
+++ b/fs/ext4/mballoc.c
@@ -4086,7 +4086,7 @@ void ext4_exit_mballoc(void)
#define EXT4_MB_BITMAP_MARKED_CHECK 0x0001
#define EXT4_MB_SYNC_UPDATE 0x0002
-static int
+int
ext4_mb_mark_context(handle_t *handle, struct super_block *sb, bool state,
ext4_group_t group, ext4_grpblk_t blkoff,
ext4_grpblk_t len, int flags, ext4_grpblk_t *ret_changed)
@@ -7190,6 +7190,105 @@ ext4_mballoc_query_range(
return error;
}
-#ifdef CONFIG_EXT4_KUNIT_TESTS
-#include "mballoc-test.c"
+#if IS_ENABLED(CONFIG_EXT4_KUNIT_TESTS)
+#define EXPORT_SYMBOL_FOR_EXT4_TEST(sym) \
+ EXPORT_SYMBOL_FOR_MODULES(sym, "ext4-test")
+
+void mb_clear_bits_test(void *bm, int cur, int len)
+{
+ mb_clear_bits(bm, cur, len);
+}
+EXPORT_SYMBOL_FOR_EXT4_TEST(mb_clear_bits_test);
+
+ext4_fsblk_t
+ext4_mb_new_blocks_simple_test(struct ext4_allocation_request *ar,
+ int *errp)
+{
+ return ext4_mb_new_blocks_simple(ar, errp);
+}
+EXPORT_SYMBOL_FOR_EXT4_TEST(ext4_mb_new_blocks_simple_test);
+
+int mb_find_next_zero_bit_test(void *addr, int max, int start)
+{
+ return mb_find_next_zero_bit(addr, max, start);
+}
+EXPORT_SYMBOL_FOR_EXT4_TEST(mb_find_next_zero_bit_test);
+
+int mb_find_next_bit_test(void *addr, int max, int start)
+{
+ return mb_find_next_bit(addr, max, start);
+}
+EXPORT_SYMBOL_FOR_EXT4_TEST(mb_find_next_bit_test);
+
+void mb_clear_bit_test(int bit, void *addr)
+{
+ mb_clear_bit(bit, addr);
+}
+EXPORT_SYMBOL_FOR_EXT4_TEST(mb_clear_bit_test);
+
+int mb_test_bit_test(int bit, void *addr)
+{
+ return mb_test_bit(bit, addr);
+}
+EXPORT_SYMBOL_FOR_EXT4_TEST(mb_test_bit_test);
+
+int ext4_mb_mark_diskspace_used_test(struct ext4_allocation_context *ac,
+ handle_t *handle)
+{
+ return ext4_mb_mark_diskspace_used(ac, handle);
+}
+EXPORT_SYMBOL_FOR_EXT4_TEST(ext4_mb_mark_diskspace_used_test);
+
+int mb_mark_used_test(struct ext4_buddy *e4b, struct ext4_free_extent *ex)
+{
+ return mb_mark_used(e4b, ex);
+}
+EXPORT_SYMBOL_FOR_EXT4_TEST(mb_mark_used_test);
+
+void ext4_mb_generate_buddy_test(struct super_block *sb, void *buddy,
+ void *bitmap, ext4_group_t group,
+ struct ext4_group_info *grp)
+{
+ ext4_mb_generate_buddy(sb, buddy, bitmap, group, grp);
+}
+EXPORT_SYMBOL_FOR_EXT4_TEST(ext4_mb_generate_buddy_test);
+
+int ext4_mb_load_buddy_test(struct super_block *sb, ext4_group_t group,
+ struct ext4_buddy *e4b)
+{
+ return ext4_mb_load_buddy(sb, group, e4b);
+}
+EXPORT_SYMBOL_FOR_EXT4_TEST(ext4_mb_load_buddy_test);
+
+void ext4_mb_unload_buddy_test(struct ext4_buddy *e4b)
+{
+ ext4_mb_unload_buddy(e4b);
+}
+EXPORT_SYMBOL_FOR_EXT4_TEST(ext4_mb_unload_buddy_test);
+
+void mb_free_blocks_test(struct inode *inode, struct ext4_buddy *e4b,
+ int first, int count)
+{
+ mb_free_blocks(inode, e4b, first, count);
+}
+EXPORT_SYMBOL_FOR_EXT4_TEST(mb_free_blocks_test);
+
+void ext4_free_blocks_simple_test(struct inode *inode, ext4_fsblk_t block,
+ unsigned long count)
+{
+ return ext4_free_blocks_simple(inode, block, count);
+}
+EXPORT_SYMBOL_FOR_EXT4_TEST(ext4_free_blocks_simple_test);
+
+EXPORT_SYMBOL_FOR_EXT4_TEST(ext4_wait_block_bitmap);
+EXPORT_SYMBOL_FOR_EXT4_TEST(ext4_mb_init);
+EXPORT_SYMBOL_FOR_EXT4_TEST(ext4_get_group_desc);
+EXPORT_SYMBOL_FOR_EXT4_TEST(ext4_count_free_clusters);
+EXPORT_SYMBOL_FOR_EXT4_TEST(ext4_get_group_info);
+EXPORT_SYMBOL_FOR_EXT4_TEST(ext4_free_group_clusters_set);
+EXPORT_SYMBOL_FOR_EXT4_TEST(ext4_mb_release);
+EXPORT_SYMBOL_FOR_EXT4_TEST(ext4_read_block_bitmap_nowait);
+EXPORT_SYMBOL_FOR_EXT4_TEST(mb_set_bits);
+EXPORT_SYMBOL_FOR_EXT4_TEST(ext4_fc_init_inode);
+EXPORT_SYMBOL_FOR_EXT4_TEST(ext4_mb_mark_context);
#endif
diff --git a/fs/ext4/mballoc.h b/fs/ext4/mballoc.h
index 15a049f05d04..b32e03e7ae8d 100644
--- a/fs/ext4/mballoc.h
+++ b/fs/ext4/mballoc.h
@@ -270,4 +270,34 @@ ext4_mballoc_query_range(
ext4_mballoc_query_range_fn formatter,
void *priv);
+#if IS_ENABLED(CONFIG_EXT4_KUNIT_TESTS)
+extern void mb_clear_bits_test(void *bm, int cur, int len);
+extern int ext4_mb_mark_context(handle_t *handle,
+ struct super_block *sb, bool state,
+ ext4_group_t group, ext4_grpblk_t blkoff,
+ ext4_grpblk_t len, int flags,
+ ext4_grpblk_t *ret_changed);
+extern ext4_fsblk_t
+ext4_mb_new_blocks_simple_test(struct ext4_allocation_request *ar,
+ int *errp);
+extern int mb_find_next_zero_bit_test(void *addr, int max, int start);
+extern int mb_find_next_bit_test(void *addr, int max, int start);
+extern void mb_clear_bit_test(int bit, void *addr);
+extern int mb_test_bit_test(int bit, void *addr);
+extern int
+ext4_mb_mark_diskspace_used_test(struct ext4_allocation_context *ac,
+ handle_t *handle);
+extern int mb_mark_used_test(struct ext4_buddy *e4b,
+ struct ext4_free_extent *ex);
+extern void ext4_mb_generate_buddy_test(struct super_block *sb,
+ void *buddy, void *bitmap, ext4_group_t group,
+ struct ext4_group_info *grp);
+extern int ext4_mb_load_buddy_test(struct super_block *sb,
+ ext4_group_t group, struct ext4_buddy *e4b);
+extern void ext4_mb_unload_buddy_test(struct ext4_buddy *e4b);
+extern void mb_free_blocks_test(struct inode *inode,
+ struct ext4_buddy *e4b, int first, int count);
+extern void ext4_free_blocks_simple_test(struct inode *inode,
+ ext4_fsblk_t block, unsigned long count);
+#endif
#endif
--
2.34.1
^ permalink raw reply related [flat|nested] 5+ messages in thread
* Re: [PATCH v3] ext4: fix mballoc-test.c is not compiled when EXT4_KUNIT_TESTS=M
2026-02-27 6:55 [PATCH v3] ext4: fix mballoc-test.c is not compiled when EXT4_KUNIT_TESTS=M Ye Bin
@ 2026-02-27 15:53 ` Jan Kara
2026-03-06 9:55 ` Ojaswin Mujoo
1 sibling, 0 replies; 5+ messages in thread
From: Jan Kara @ 2026-02-27 15:53 UTC (permalink / raw)
To: Ye Bin; +Cc: tytso, adilger.kernel, linux-ext4, jack
On Fri 27-02-26 14:55:14, Ye Bin wrote:
> From: Ye Bin <yebin10@huawei.com>
>
> Now, only EXT4_KUNIT_TESTS=Y testcase will be compiled in 'mballoc.c'.
> To solve this issue, the ext4 test code needs to be decoupled. The ext4
> test module is compiled into a separate module.
>
> Reported-by: ChenXiaoSong <chenxiaosong@kylinos.cn>
> Closes: https://patchwork.kernel.org/project/cifs-client/patch/20260118091313.1988168-2-chenxiaosong.chenxiaosong@linux.dev/
> Fixes: 7c9fa399a369 ("ext4: add first unit test for ext4_mb_new_blocks_simple in mballoc")
> Signed-off-by: Ye Bin <yebin10@huawei.com>
Looks good. Feel free to add:
Reviewed-by: Jan Kara <jack@suse.cz>
Honza
> ---
> fs/ext4/Makefile | 4 +-
> fs/ext4/mballoc-test.c | 81 +++++++++++++++----------------
> fs/ext4/mballoc.c | 105 +++++++++++++++++++++++++++++++++++++++--
> fs/ext4/mballoc.h | 30 ++++++++++++
> 4 files changed, 175 insertions(+), 45 deletions(-)
>
> diff --git a/fs/ext4/Makefile b/fs/ext4/Makefile
> index 72206a292676..d836c3fe311b 100644
> --- a/fs/ext4/Makefile
> +++ b/fs/ext4/Makefile
> @@ -14,7 +14,7 @@ ext4-y := balloc.o bitmap.o block_validity.o dir.o ext4_jbd2.o extents.o \
>
> ext4-$(CONFIG_EXT4_FS_POSIX_ACL) += acl.o
> ext4-$(CONFIG_EXT4_FS_SECURITY) += xattr_security.o
> -ext4-inode-test-objs += inode-test.o
> -obj-$(CONFIG_EXT4_KUNIT_TESTS) += ext4-inode-test.o
> +ext4-test-objs += inode-test.o mballoc-test.o
> +obj-$(CONFIG_EXT4_KUNIT_TESTS) += ext4-test.o
> ext4-$(CONFIG_FS_VERITY) += verity.o
> ext4-$(CONFIG_FS_ENCRYPTION) += crypto.o
> diff --git a/fs/ext4/mballoc-test.c b/fs/ext4/mballoc-test.c
> index 4abb40d4561c..749ed2fc2241 100644
> --- a/fs/ext4/mballoc-test.c
> +++ b/fs/ext4/mballoc-test.c
> @@ -8,6 +8,7 @@
> #include <linux/random.h>
>
> #include "ext4.h"
> +#include "mballoc.h"
>
> struct mbt_grp_ctx {
> struct buffer_head bitmap_bh;
> @@ -337,7 +338,7 @@ ext4_mb_mark_context_stub(handle_t *handle, struct super_block *sb, bool state,
> if (state)
> mb_set_bits(bitmap_bh->b_data, blkoff, len);
> else
> - mb_clear_bits(bitmap_bh->b_data, blkoff, len);
> + mb_clear_bits_test(bitmap_bh->b_data, blkoff, len);
>
> return 0;
> }
> @@ -414,14 +415,14 @@ static void test_new_blocks_simple(struct kunit *test)
>
> /* get block at goal */
> ar.goal = ext4_group_first_block_no(sb, goal_group);
> - found = ext4_mb_new_blocks_simple(&ar, &err);
> + found = ext4_mb_new_blocks_simple_test(&ar, &err);
> KUNIT_ASSERT_EQ_MSG(test, ar.goal, found,
> "failed to alloc block at goal, expected %llu found %llu",
> ar.goal, found);
>
> /* get block after goal in goal group */
> ar.goal = ext4_group_first_block_no(sb, goal_group);
> - found = ext4_mb_new_blocks_simple(&ar, &err);
> + found = ext4_mb_new_blocks_simple_test(&ar, &err);
> KUNIT_ASSERT_EQ_MSG(test, ar.goal + EXT4_C2B(sbi, 1), found,
> "failed to alloc block after goal in goal group, expected %llu found %llu",
> ar.goal + 1, found);
> @@ -429,7 +430,7 @@ static void test_new_blocks_simple(struct kunit *test)
> /* get block after goal group */
> mbt_ctx_mark_used(sb, goal_group, 0, EXT4_CLUSTERS_PER_GROUP(sb));
> ar.goal = ext4_group_first_block_no(sb, goal_group);
> - found = ext4_mb_new_blocks_simple(&ar, &err);
> + found = ext4_mb_new_blocks_simple_test(&ar, &err);
> KUNIT_ASSERT_EQ_MSG(test,
> ext4_group_first_block_no(sb, goal_group + 1), found,
> "failed to alloc block after goal group, expected %llu found %llu",
> @@ -439,7 +440,7 @@ static void test_new_blocks_simple(struct kunit *test)
> for (i = goal_group; i < ext4_get_groups_count(sb); i++)
> mbt_ctx_mark_used(sb, i, 0, EXT4_CLUSTERS_PER_GROUP(sb));
> ar.goal = ext4_group_first_block_no(sb, goal_group);
> - found = ext4_mb_new_blocks_simple(&ar, &err);
> + found = ext4_mb_new_blocks_simple_test(&ar, &err);
> KUNIT_ASSERT_EQ_MSG(test,
> ext4_group_first_block_no(sb, 0) + EXT4_C2B(sbi, 1), found,
> "failed to alloc block before goal group, expected %llu found %llu",
> @@ -449,7 +450,7 @@ static void test_new_blocks_simple(struct kunit *test)
> for (i = 0; i < ext4_get_groups_count(sb); i++)
> mbt_ctx_mark_used(sb, i, 0, EXT4_CLUSTERS_PER_GROUP(sb));
> ar.goal = ext4_group_first_block_no(sb, goal_group);
> - found = ext4_mb_new_blocks_simple(&ar, &err);
> + found = ext4_mb_new_blocks_simple_test(&ar, &err);
> KUNIT_ASSERT_NE_MSG(test, err, 0,
> "unexpectedly get block when no block is available");
> }
> @@ -493,16 +494,16 @@ validate_free_blocks_simple(struct kunit *test, struct super_block *sb,
> continue;
>
> bitmap = mbt_ctx_bitmap(sb, i);
> - bit = mb_find_next_zero_bit(bitmap, max, 0);
> + bit = mb_find_next_zero_bit_test(bitmap, max, 0);
> KUNIT_ASSERT_EQ_MSG(test, bit, max,
> "free block on unexpected group %d", i);
> }
>
> bitmap = mbt_ctx_bitmap(sb, goal_group);
> - bit = mb_find_next_zero_bit(bitmap, max, 0);
> + bit = mb_find_next_zero_bit_test(bitmap, max, 0);
> KUNIT_ASSERT_EQ(test, bit, start);
>
> - bit = mb_find_next_bit(bitmap, max, bit + 1);
> + bit = mb_find_next_bit_test(bitmap, max, bit + 1);
> KUNIT_ASSERT_EQ(test, bit, start + len);
> }
>
> @@ -525,7 +526,7 @@ test_free_blocks_simple_range(struct kunit *test, ext4_group_t goal_group,
>
> block = ext4_group_first_block_no(sb, goal_group) +
> EXT4_C2B(sbi, start);
> - ext4_free_blocks_simple(inode, block, len);
> + ext4_free_blocks_simple_test(inode, block, len);
> validate_free_blocks_simple(test, sb, goal_group, start, len);
> mbt_ctx_mark_used(sb, goal_group, 0, EXT4_CLUSTERS_PER_GROUP(sb));
> }
> @@ -567,15 +568,15 @@ test_mark_diskspace_used_range(struct kunit *test,
>
> bitmap = mbt_ctx_bitmap(sb, TEST_GOAL_GROUP);
> memset(bitmap, 0, sb->s_blocksize);
> - ret = ext4_mb_mark_diskspace_used(ac, NULL);
> + ret = ext4_mb_mark_diskspace_used_test(ac, NULL);
> KUNIT_ASSERT_EQ(test, ret, 0);
>
> max = EXT4_CLUSTERS_PER_GROUP(sb);
> - i = mb_find_next_bit(bitmap, max, 0);
> + i = mb_find_next_bit_test(bitmap, max, 0);
> KUNIT_ASSERT_EQ(test, i, start);
> - i = mb_find_next_zero_bit(bitmap, max, i + 1);
> + i = mb_find_next_zero_bit_test(bitmap, max, i + 1);
> KUNIT_ASSERT_EQ(test, i, start + len);
> - i = mb_find_next_bit(bitmap, max, i + 1);
> + i = mb_find_next_bit_test(bitmap, max, i + 1);
> KUNIT_ASSERT_EQ(test, max, i);
> }
>
> @@ -618,54 +619,54 @@ static void mbt_generate_buddy(struct super_block *sb, void *buddy,
> max = EXT4_CLUSTERS_PER_GROUP(sb);
> bb_h = buddy + sbi->s_mb_offsets[1];
>
> - off = mb_find_next_zero_bit(bb, max, 0);
> + off = mb_find_next_zero_bit_test(bb, max, 0);
> grp->bb_first_free = off;
> while (off < max) {
> grp->bb_counters[0]++;
> grp->bb_free++;
>
> - if (!(off & 1) && !mb_test_bit(off + 1, bb)) {
> + if (!(off & 1) && !mb_test_bit_test(off + 1, bb)) {
> grp->bb_free++;
> grp->bb_counters[0]--;
> - mb_clear_bit(off >> 1, bb_h);
> + mb_clear_bit_test(off >> 1, bb_h);
> grp->bb_counters[1]++;
> grp->bb_largest_free_order = 1;
> off++;
> }
>
> - off = mb_find_next_zero_bit(bb, max, off + 1);
> + off = mb_find_next_zero_bit_test(bb, max, off + 1);
> }
>
> for (order = 1; order < MB_NUM_ORDERS(sb) - 1; order++) {
> bb = buddy + sbi->s_mb_offsets[order];
> bb_h = buddy + sbi->s_mb_offsets[order + 1];
> max = max >> 1;
> - off = mb_find_next_zero_bit(bb, max, 0);
> + off = mb_find_next_zero_bit_test(bb, max, 0);
>
> while (off < max) {
> - if (!(off & 1) && !mb_test_bit(off + 1, bb)) {
> + if (!(off & 1) && !mb_test_bit_test(off + 1, bb)) {
> mb_set_bits(bb, off, 2);
> grp->bb_counters[order] -= 2;
> - mb_clear_bit(off >> 1, bb_h);
> + mb_clear_bit_test(off >> 1, bb_h);
> grp->bb_counters[order + 1]++;
> grp->bb_largest_free_order = order + 1;
> off++;
> }
>
> - off = mb_find_next_zero_bit(bb, max, off + 1);
> + off = mb_find_next_zero_bit_test(bb, max, off + 1);
> }
> }
>
> max = EXT4_CLUSTERS_PER_GROUP(sb);
> - off = mb_find_next_zero_bit(bitmap, max, 0);
> + off = mb_find_next_zero_bit_test(bitmap, max, 0);
> while (off < max) {
> grp->bb_fragments++;
>
> - off = mb_find_next_bit(bitmap, max, off + 1);
> + off = mb_find_next_bit_test(bitmap, max, off + 1);
> if (off + 1 >= max)
> break;
>
> - off = mb_find_next_zero_bit(bitmap, max, off + 1);
> + off = mb_find_next_zero_bit_test(bitmap, max, off + 1);
> }
> }
>
> @@ -707,7 +708,7 @@ do_test_generate_buddy(struct kunit *test, struct super_block *sb, void *bitmap,
> /* needed by validation in ext4_mb_generate_buddy */
> ext4_grp->bb_free = mbt_grp->bb_free;
> memset(ext4_buddy, 0xff, sb->s_blocksize);
> - ext4_mb_generate_buddy(sb, ext4_buddy, bitmap, TEST_GOAL_GROUP,
> + ext4_mb_generate_buddy_test(sb, ext4_buddy, bitmap, TEST_GOAL_GROUP,
> ext4_grp);
>
> KUNIT_ASSERT_EQ(test, memcmp(mbt_buddy, ext4_buddy, sb->s_blocksize),
> @@ -761,7 +762,7 @@ test_mb_mark_used_range(struct kunit *test, struct ext4_buddy *e4b,
> ex.fe_group = TEST_GOAL_GROUP;
>
> ext4_lock_group(sb, TEST_GOAL_GROUP);
> - mb_mark_used(e4b, &ex);
> + mb_mark_used_test(e4b, &ex);
> ext4_unlock_group(sb, TEST_GOAL_GROUP);
>
> mb_set_bits(bitmap, start, len);
> @@ -770,7 +771,7 @@ test_mb_mark_used_range(struct kunit *test, struct ext4_buddy *e4b,
> memset(buddy, 0xff, sb->s_blocksize);
> for (i = 0; i < MB_NUM_ORDERS(sb); i++)
> grp->bb_counters[i] = 0;
> - ext4_mb_generate_buddy(sb, buddy, bitmap, 0, grp);
> + ext4_mb_generate_buddy_test(sb, buddy, bitmap, 0, grp);
>
> KUNIT_ASSERT_EQ(test, memcmp(buddy, e4b->bd_buddy, sb->s_blocksize),
> 0);
> @@ -799,7 +800,7 @@ static void test_mb_mark_used(struct kunit *test)
> bb_counters[MB_NUM_ORDERS(sb)]), GFP_KERNEL);
> KUNIT_ASSERT_NOT_ERR_OR_NULL(test, grp);
>
> - ret = ext4_mb_load_buddy(sb, TEST_GOAL_GROUP, &e4b);
> + ret = ext4_mb_load_buddy_test(sb, TEST_GOAL_GROUP, &e4b);
> KUNIT_ASSERT_EQ(test, ret, 0);
>
> grp->bb_free = EXT4_CLUSTERS_PER_GROUP(sb);
> @@ -810,7 +811,7 @@ static void test_mb_mark_used(struct kunit *test)
> test_mb_mark_used_range(test, &e4b, ranges[i].start,
> ranges[i].len, bitmap, buddy, grp);
>
> - ext4_mb_unload_buddy(&e4b);
> + ext4_mb_unload_buddy_test(&e4b);
> }
>
> static void
> @@ -826,16 +827,16 @@ test_mb_free_blocks_range(struct kunit *test, struct ext4_buddy *e4b,
> return;
>
> ext4_lock_group(sb, e4b->bd_group);
> - mb_free_blocks(NULL, e4b, start, len);
> + mb_free_blocks_test(NULL, e4b, start, len);
> ext4_unlock_group(sb, e4b->bd_group);
>
> - mb_clear_bits(bitmap, start, len);
> + mb_clear_bits_test(bitmap, start, len);
> /* bypass bb_free validatoin in ext4_mb_generate_buddy */
> grp->bb_free += len;
> memset(buddy, 0xff, sb->s_blocksize);
> for (i = 0; i < MB_NUM_ORDERS(sb); i++)
> grp->bb_counters[i] = 0;
> - ext4_mb_generate_buddy(sb, buddy, bitmap, 0, grp);
> + ext4_mb_generate_buddy_test(sb, buddy, bitmap, 0, grp);
>
> KUNIT_ASSERT_EQ(test, memcmp(buddy, e4b->bd_buddy, sb->s_blocksize),
> 0);
> @@ -866,7 +867,7 @@ static void test_mb_free_blocks(struct kunit *test)
> bb_counters[MB_NUM_ORDERS(sb)]), GFP_KERNEL);
> KUNIT_ASSERT_NOT_ERR_OR_NULL(test, grp);
>
> - ret = ext4_mb_load_buddy(sb, TEST_GOAL_GROUP, &e4b);
> + ret = ext4_mb_load_buddy_test(sb, TEST_GOAL_GROUP, &e4b);
> KUNIT_ASSERT_EQ(test, ret, 0);
>
> ex.fe_start = 0;
> @@ -874,7 +875,7 @@ static void test_mb_free_blocks(struct kunit *test)
> ex.fe_group = TEST_GOAL_GROUP;
>
> ext4_lock_group(sb, TEST_GOAL_GROUP);
> - mb_mark_used(&e4b, &ex);
> + mb_mark_used_test(&e4b, &ex);
> ext4_unlock_group(sb, TEST_GOAL_GROUP);
>
> grp->bb_free = 0;
> @@ -887,7 +888,7 @@ static void test_mb_free_blocks(struct kunit *test)
> test_mb_free_blocks_range(test, &e4b, ranges[i].start,
> ranges[i].len, bitmap, buddy, grp);
>
> - ext4_mb_unload_buddy(&e4b);
> + ext4_mb_unload_buddy_test(&e4b);
> }
>
> #define COUNT_FOR_ESTIMATE 100000
> @@ -905,7 +906,7 @@ static void test_mb_mark_used_cost(struct kunit *test)
> if (sb->s_blocksize > PAGE_SIZE)
> kunit_skip(test, "blocksize exceeds pagesize");
>
> - ret = ext4_mb_load_buddy(sb, TEST_GOAL_GROUP, &e4b);
> + ret = ext4_mb_load_buddy_test(sb, TEST_GOAL_GROUP, &e4b);
> KUNIT_ASSERT_EQ(test, ret, 0);
>
> ex.fe_group = TEST_GOAL_GROUP;
> @@ -919,7 +920,7 @@ static void test_mb_mark_used_cost(struct kunit *test)
> ex.fe_start = ranges[i].start;
> ex.fe_len = ranges[i].len;
> ext4_lock_group(sb, TEST_GOAL_GROUP);
> - mb_mark_used(&e4b, &ex);
> + mb_mark_used_test(&e4b, &ex);
> ext4_unlock_group(sb, TEST_GOAL_GROUP);
> }
> end = jiffies;
> @@ -930,14 +931,14 @@ static void test_mb_mark_used_cost(struct kunit *test)
> continue;
>
> ext4_lock_group(sb, TEST_GOAL_GROUP);
> - mb_free_blocks(NULL, &e4b, ranges[i].start,
> + mb_free_blocks_test(NULL, &e4b, ranges[i].start,
> ranges[i].len);
> ext4_unlock_group(sb, TEST_GOAL_GROUP);
> }
> }
>
> kunit_info(test, "costed jiffies %lu\n", all);
> - ext4_mb_unload_buddy(&e4b);
> + ext4_mb_unload_buddy_test(&e4b);
> }
>
> static const struct mbt_ext4_block_layout mbt_test_layouts[] = {
> diff --git a/fs/ext4/mballoc.c b/fs/ext4/mballoc.c
> index b99d1a7e580e..e2341489f4d0 100644
> --- a/fs/ext4/mballoc.c
> +++ b/fs/ext4/mballoc.c
> @@ -4086,7 +4086,7 @@ void ext4_exit_mballoc(void)
>
> #define EXT4_MB_BITMAP_MARKED_CHECK 0x0001
> #define EXT4_MB_SYNC_UPDATE 0x0002
> -static int
> +int
> ext4_mb_mark_context(handle_t *handle, struct super_block *sb, bool state,
> ext4_group_t group, ext4_grpblk_t blkoff,
> ext4_grpblk_t len, int flags, ext4_grpblk_t *ret_changed)
> @@ -7190,6 +7190,105 @@ ext4_mballoc_query_range(
> return error;
> }
>
> -#ifdef CONFIG_EXT4_KUNIT_TESTS
> -#include "mballoc-test.c"
> +#if IS_ENABLED(CONFIG_EXT4_KUNIT_TESTS)
> +#define EXPORT_SYMBOL_FOR_EXT4_TEST(sym) \
> + EXPORT_SYMBOL_FOR_MODULES(sym, "ext4-test")
> +
> +void mb_clear_bits_test(void *bm, int cur, int len)
> +{
> + mb_clear_bits(bm, cur, len);
> +}
> +EXPORT_SYMBOL_FOR_EXT4_TEST(mb_clear_bits_test);
> +
> +ext4_fsblk_t
> +ext4_mb_new_blocks_simple_test(struct ext4_allocation_request *ar,
> + int *errp)
> +{
> + return ext4_mb_new_blocks_simple(ar, errp);
> +}
> +EXPORT_SYMBOL_FOR_EXT4_TEST(ext4_mb_new_blocks_simple_test);
> +
> +int mb_find_next_zero_bit_test(void *addr, int max, int start)
> +{
> + return mb_find_next_zero_bit(addr, max, start);
> +}
> +EXPORT_SYMBOL_FOR_EXT4_TEST(mb_find_next_zero_bit_test);
> +
> +int mb_find_next_bit_test(void *addr, int max, int start)
> +{
> + return mb_find_next_bit(addr, max, start);
> +}
> +EXPORT_SYMBOL_FOR_EXT4_TEST(mb_find_next_bit_test);
> +
> +void mb_clear_bit_test(int bit, void *addr)
> +{
> + mb_clear_bit(bit, addr);
> +}
> +EXPORT_SYMBOL_FOR_EXT4_TEST(mb_clear_bit_test);
> +
> +int mb_test_bit_test(int bit, void *addr)
> +{
> + return mb_test_bit(bit, addr);
> +}
> +EXPORT_SYMBOL_FOR_EXT4_TEST(mb_test_bit_test);
> +
> +int ext4_mb_mark_diskspace_used_test(struct ext4_allocation_context *ac,
> + handle_t *handle)
> +{
> + return ext4_mb_mark_diskspace_used(ac, handle);
> +}
> +EXPORT_SYMBOL_FOR_EXT4_TEST(ext4_mb_mark_diskspace_used_test);
> +
> +int mb_mark_used_test(struct ext4_buddy *e4b, struct ext4_free_extent *ex)
> +{
> + return mb_mark_used(e4b, ex);
> +}
> +EXPORT_SYMBOL_FOR_EXT4_TEST(mb_mark_used_test);
> +
> +void ext4_mb_generate_buddy_test(struct super_block *sb, void *buddy,
> + void *bitmap, ext4_group_t group,
> + struct ext4_group_info *grp)
> +{
> + ext4_mb_generate_buddy(sb, buddy, bitmap, group, grp);
> +}
> +EXPORT_SYMBOL_FOR_EXT4_TEST(ext4_mb_generate_buddy_test);
> +
> +int ext4_mb_load_buddy_test(struct super_block *sb, ext4_group_t group,
> + struct ext4_buddy *e4b)
> +{
> + return ext4_mb_load_buddy(sb, group, e4b);
> +}
> +EXPORT_SYMBOL_FOR_EXT4_TEST(ext4_mb_load_buddy_test);
> +
> +void ext4_mb_unload_buddy_test(struct ext4_buddy *e4b)
> +{
> + ext4_mb_unload_buddy(e4b);
> +}
> +EXPORT_SYMBOL_FOR_EXT4_TEST(ext4_mb_unload_buddy_test);
> +
> +void mb_free_blocks_test(struct inode *inode, struct ext4_buddy *e4b,
> + int first, int count)
> +{
> + mb_free_blocks(inode, e4b, first, count);
> +}
> +EXPORT_SYMBOL_FOR_EXT4_TEST(mb_free_blocks_test);
> +
> +void ext4_free_blocks_simple_test(struct inode *inode, ext4_fsblk_t block,
> + unsigned long count)
> +{
> + return ext4_free_blocks_simple(inode, block, count);
> +}
> +EXPORT_SYMBOL_FOR_EXT4_TEST(ext4_free_blocks_simple_test);
> +
> +EXPORT_SYMBOL_FOR_EXT4_TEST(ext4_wait_block_bitmap);
> +EXPORT_SYMBOL_FOR_EXT4_TEST(ext4_mb_init);
> +EXPORT_SYMBOL_FOR_EXT4_TEST(ext4_get_group_desc);
> +EXPORT_SYMBOL_FOR_EXT4_TEST(ext4_count_free_clusters);
> +EXPORT_SYMBOL_FOR_EXT4_TEST(ext4_get_group_info);
> +EXPORT_SYMBOL_FOR_EXT4_TEST(ext4_free_group_clusters_set);
> +EXPORT_SYMBOL_FOR_EXT4_TEST(ext4_mb_release);
> +EXPORT_SYMBOL_FOR_EXT4_TEST(ext4_read_block_bitmap_nowait);
> +EXPORT_SYMBOL_FOR_EXT4_TEST(mb_set_bits);
> +EXPORT_SYMBOL_FOR_EXT4_TEST(ext4_fc_init_inode);
> +EXPORT_SYMBOL_FOR_EXT4_TEST(ext4_mb_mark_context);
> #endif
> diff --git a/fs/ext4/mballoc.h b/fs/ext4/mballoc.h
> index 15a049f05d04..b32e03e7ae8d 100644
> --- a/fs/ext4/mballoc.h
> +++ b/fs/ext4/mballoc.h
> @@ -270,4 +270,34 @@ ext4_mballoc_query_range(
> ext4_mballoc_query_range_fn formatter,
> void *priv);
>
> +#if IS_ENABLED(CONFIG_EXT4_KUNIT_TESTS)
> +extern void mb_clear_bits_test(void *bm, int cur, int len);
> +extern int ext4_mb_mark_context(handle_t *handle,
> + struct super_block *sb, bool state,
> + ext4_group_t group, ext4_grpblk_t blkoff,
> + ext4_grpblk_t len, int flags,
> + ext4_grpblk_t *ret_changed);
> +extern ext4_fsblk_t
> +ext4_mb_new_blocks_simple_test(struct ext4_allocation_request *ar,
> + int *errp);
> +extern int mb_find_next_zero_bit_test(void *addr, int max, int start);
> +extern int mb_find_next_bit_test(void *addr, int max, int start);
> +extern void mb_clear_bit_test(int bit, void *addr);
> +extern int mb_test_bit_test(int bit, void *addr);
> +extern int
> +ext4_mb_mark_diskspace_used_test(struct ext4_allocation_context *ac,
> + handle_t *handle);
> +extern int mb_mark_used_test(struct ext4_buddy *e4b,
> + struct ext4_free_extent *ex);
> +extern void ext4_mb_generate_buddy_test(struct super_block *sb,
> + void *buddy, void *bitmap, ext4_group_t group,
> + struct ext4_group_info *grp);
> +extern int ext4_mb_load_buddy_test(struct super_block *sb,
> + ext4_group_t group, struct ext4_buddy *e4b);
> +extern void ext4_mb_unload_buddy_test(struct ext4_buddy *e4b);
> +extern void mb_free_blocks_test(struct inode *inode,
> + struct ext4_buddy *e4b, int first, int count);
> +extern void ext4_free_blocks_simple_test(struct inode *inode,
> + ext4_fsblk_t block, unsigned long count);
> +#endif
> #endif
> --
> 2.34.1
>
--
Jan Kara <jack@suse.com>
SUSE Labs, CR
^ permalink raw reply [flat|nested] 5+ messages in thread
* Re: [PATCH v3] ext4: fix mballoc-test.c is not compiled when EXT4_KUNIT_TESTS=M
2026-02-27 6:55 [PATCH v3] ext4: fix mballoc-test.c is not compiled when EXT4_KUNIT_TESTS=M Ye Bin
2026-02-27 15:53 ` Jan Kara
@ 2026-03-06 9:55 ` Ojaswin Mujoo
2026-03-07 0:02 ` yebin (H)
1 sibling, 1 reply; 5+ messages in thread
From: Ojaswin Mujoo @ 2026-03-06 9:55 UTC (permalink / raw)
To: Ye Bin; +Cc: tytso, adilger.kernel, linux-ext4, jack
On Fri, Feb 27, 2026 at 02:55:14PM +0800, Ye Bin wrote:
> From: Ye Bin <yebin10@huawei.com>
>
> Now, only EXT4_KUNIT_TESTS=Y testcase will be compiled in 'mballoc.c'.
> To solve this issue, the ext4 test code needs to be decoupled. The ext4
> test module is compiled into a separate module.
>
> Reported-by: ChenXiaoSong <chenxiaosong@kylinos.cn>
> Closes: https://patchwork.kernel.org/project/cifs-client/patch/20260118091313.1988168-2-chenxiaosong.chenxiaosong@linux.dev/
> Fixes: 7c9fa399a369 ("ext4: add first unit test for ext4_mb_new_blocks_simple in mballoc")
> Signed-off-by: Ye Bin <yebin10@huawei.com>
Hi Ye,
From my testing I can see that EXPORT_SYMBOL_FOR_MODULE() doesn't
resepect the namespace restriction if EXT4_KUNIT_TESTS=y but I think
that should be okay.
The patch otherwise looks good. Feel free to add:
Reviewed-by: Ojaswin Mujoo <ojaswin@linux.ibm.com>
One thing, recently added extents-test.c is also having the same issue where
it doesn't work when compiled as module. Would you be willing to fix it
as well?
Regards,
ojaswin
^ permalink raw reply [flat|nested] 5+ messages in thread
* Re: [PATCH v3] ext4: fix mballoc-test.c is not compiled when EXT4_KUNIT_TESTS=M
2026-03-06 9:55 ` Ojaswin Mujoo
@ 2026-03-07 0:02 ` yebin (H)
2026-03-07 6:25 ` Ojaswin Mujoo
0 siblings, 1 reply; 5+ messages in thread
From: yebin (H) @ 2026-03-07 0:02 UTC (permalink / raw)
To: Ojaswin Mujoo, Ye Bin; +Cc: tytso, adilger.kernel, linux-ext4, jack
On 2026/3/6 17:55, Ojaswin Mujoo wrote:
> On Fri, Feb 27, 2026 at 02:55:14PM +0800, Ye Bin wrote:
>> From: Ye Bin <yebin10@huawei.com>
>>
>> Now, only EXT4_KUNIT_TESTS=Y testcase will be compiled in 'mballoc.c'.
>> To solve this issue, the ext4 test code needs to be decoupled. The ext4
>> test module is compiled into a separate module.
>>
>> Reported-by: ChenXiaoSong <chenxiaosong@kylinos.cn>
>> Closes: https://patchwork.kernel.org/project/cifs-client/patch/20260118091313.1988168-2-chenxiaosong.chenxiaosong@linux.dev/
>> Fixes: 7c9fa399a369 ("ext4: add first unit test for ext4_mb_new_blocks_simple in mballoc")
>> Signed-off-by: Ye Bin <yebin10@huawei.com>
>
> Hi Ye,
>
>>From my testing I can see that EXPORT_SYMBOL_FOR_MODULE() doesn't
> resepect the namespace restriction if EXT4_KUNIT_TESTS=y but I think
> that should be okay.
>
> The patch otherwise looks good. Feel free to add:
>
> Reviewed-by: Ojaswin Mujoo <ojaswin@linux.ibm.com>
>
> One thing, recently added extents-test.c is also having the same issue where
> it doesn't work when compiled as module. Would you be willing to fix it
> as well?
>
No problem, I will fix this issue.
> Regards,
> ojaswin
>
>
>
> .
>
^ permalink raw reply [flat|nested] 5+ messages in thread
* Re: [PATCH v3] ext4: fix mballoc-test.c is not compiled when EXT4_KUNIT_TESTS=M
2026-03-07 0:02 ` yebin (H)
@ 2026-03-07 6:25 ` Ojaswin Mujoo
0 siblings, 0 replies; 5+ messages in thread
From: Ojaswin Mujoo @ 2026-03-07 6:25 UTC (permalink / raw)
To: yebin (H); +Cc: Ye Bin, tytso, adilger.kernel, linux-ext4, jack
On Sat, Mar 07, 2026 at 08:02:53AM +0800, yebin (H) wrote:
>
>
> On 2026/3/6 17:55, Ojaswin Mujoo wrote:
> > On Fri, Feb 27, 2026 at 02:55:14PM +0800, Ye Bin wrote:
> > > From: Ye Bin <yebin10@huawei.com>
> > >
> > > Now, only EXT4_KUNIT_TESTS=Y testcase will be compiled in 'mballoc.c'.
> > > To solve this issue, the ext4 test code needs to be decoupled. The ext4
> > > test module is compiled into a separate module.
> > >
> > > Reported-by: ChenXiaoSong <chenxiaosong@kylinos.cn>
> > > Closes: https://patchwork.kernel.org/project/cifs-client/patch/20260118091313.1988168-2-chenxiaosong.chenxiaosong@linux.dev/
> > > Fixes: 7c9fa399a369 ("ext4: add first unit test for ext4_mb_new_blocks_simple in mballoc")
> > > Signed-off-by: Ye Bin <yebin10@huawei.com>
> >
> > Hi Ye,
> >
> > > From my testing I can see that EXPORT_SYMBOL_FOR_MODULE() doesn't
> > resepect the namespace restriction if EXT4_KUNIT_TESTS=y but I think
> > that should be okay.
> >
> > The patch otherwise looks good. Feel free to add:
> >
> > Reviewed-by: Ojaswin Mujoo <ojaswin@linux.ibm.com>
> >
> > One thing, recently added extents-test.c is also having the same issue where
> > it doesn't work when compiled as module. Would you be willing to fix it
> > as well?
> >
> No problem, I will fix this issue.
Awesome, thanks :)
Regards,
ojaswin
> > Regards,
> > ojaswin
> >
> >
> >
> > .
> >
^ permalink raw reply [flat|nested] 5+ messages in thread
end of thread, other threads:[~2026-03-07 6:25 UTC | newest]
Thread overview: 5+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2026-02-27 6:55 [PATCH v3] ext4: fix mballoc-test.c is not compiled when EXT4_KUNIT_TESTS=M Ye Bin
2026-02-27 15:53 ` Jan Kara
2026-03-06 9:55 ` Ojaswin Mujoo
2026-03-07 0:02 ` yebin (H)
2026-03-07 6:25 ` Ojaswin Mujoo
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox