2023-07-17 11:46:33

by Alexander Potapenko

[permalink] [raw]
Subject: [PATCH v3 2/5] lib/test_bitmap: add tests for bitmap_{set,get}_value()

Add basic tests ensuring that values can be added at arbitrary positions
of the bitmap, including those spanning into the adjacent unsigned
longs.

Signed-off-by: Alexander Potapenko <[email protected]>

---
This patch was previously called
"lib/test_bitmap: add tests for bitmap_{set,get}_value_unaligned"

v3:
- switch to using bitmap_{set,get}_value()
- change the expected bit pattern in test_set_get_value(),
as the test was incorrectly assuming 0 is the LSB.
---
lib/test_bitmap.c | 33 +++++++++++++++++++++++++++++++++
1 file changed, 33 insertions(+)

diff --git a/lib/test_bitmap.c b/lib/test_bitmap.c
index 187f5b2db4cf1..c2ab54040c249 100644
--- a/lib/test_bitmap.c
+++ b/lib/test_bitmap.c
@@ -71,6 +71,17 @@ __check_eq_uint(const char *srcfile, unsigned int line,
return true;
}

+static bool __init
+__check_eq_ulong(const char *srcfile, unsigned int line,
+ const unsigned long exp_ulong, unsigned long x)
+{
+ if (exp_ulong != x) {
+ pr_err("[%s:%u] expected %lu, got %lu\n",
+ srcfile, line, exp_ulong, x);
+ return false;
+ }
+ return true;
+}

static bool __init
__check_eq_bitmap(const char *srcfile, unsigned int line,
@@ -186,6 +197,7 @@ __check_eq_str(const char *srcfile, unsigned int line,
})

#define expect_eq_uint(...) __expect_eq(uint, ##__VA_ARGS__)
+#define expect_eq_ulong(...) __expect_eq(ulong, ##__VA_ARGS__)
#define expect_eq_bitmap(...) __expect_eq(bitmap, ##__VA_ARGS__)
#define expect_eq_pbl(...) __expect_eq(pbl, ##__VA_ARGS__)
#define expect_eq_u32_array(...) __expect_eq(u32_array, ##__VA_ARGS__)
@@ -1222,6 +1234,25 @@ static void __init test_bitmap_const_eval(void)
BUILD_BUG_ON(~var != ~BIT(25));
}

+static void __init test_set_get_value(void)
+{
+ DECLARE_BITMAP(bitmap, BITS_PER_LONG * 2);
+ unsigned long val;
+ int i;
+
+ for (i = 0; i < BITS_PER_LONG * 2 - 7; i++) {
+ bitmap_zero(bitmap, BITS_PER_LONG * 2);
+ bitmap_set_value(bitmap, 0b10101UL, i, 5);
+ val = bitmap_get_value(bitmap, i, 5);
+ expect_eq_ulong(0b10101UL, val);
+ bitmap_set_value(bitmap, 0b101UL, i + 5, 3);
+ val = bitmap_get_value(bitmap, i + 5, 3);
+ expect_eq_ulong(0b101UL, val);
+ val = bitmap_get_value(bitmap, i, 8);
+ expect_eq_ulong(0b10110101UL, val);
+ }
+}
+
static void __init selftest(void)
{
test_zero_clear();
@@ -1249,6 +1280,8 @@ static void __init selftest(void)
test_for_each_clear_bitrange_from();
test_for_each_set_clump8();
test_for_each_set_bit_wrap();
+
+ test_set_get_value();
}

KSTM_MODULE_LOADERS(test_bitmap);
--
2.41.0.255.g8b1d071c50-goog



2023-07-17 13:17:29

by Andy Shevchenko

[permalink] [raw]
Subject: Re: [PATCH v3 2/5] lib/test_bitmap: add tests for bitmap_{set,get}_value()

On Mon, Jul 17, 2023 at 01:37:05PM +0200, Alexander Potapenko wrote:
> Add basic tests ensuring that values can be added at arbitrary positions
> of the bitmap, including those spanning into the adjacent unsigned
> longs.

I always in favour of a new test case!
Reviewed-by: Andy Shevchenko <[email protected]>

> Signed-off-by: Alexander Potapenko <[email protected]>
>
> ---
> This patch was previously called
> "lib/test_bitmap: add tests for bitmap_{set,get}_value_unaligned"

Hint, you may always just link to lore mail archive for easier access and
handling. Also with `b4` at hand the lore link can be used to resurrect
a discussion (in case it's needed).

> v3:
> - switch to using bitmap_{set,get}_value()
> - change the expected bit pattern in test_set_get_value(),
> as the test was incorrectly assuming 0 is the LSB.
> ---
> lib/test_bitmap.c | 33 +++++++++++++++++++++++++++++++++
> 1 file changed, 33 insertions(+)
>
> diff --git a/lib/test_bitmap.c b/lib/test_bitmap.c
> index 187f5b2db4cf1..c2ab54040c249 100644
> --- a/lib/test_bitmap.c
> +++ b/lib/test_bitmap.c
> @@ -71,6 +71,17 @@ __check_eq_uint(const char *srcfile, unsigned int line,
> return true;
> }
>
> +static bool __init
> +__check_eq_ulong(const char *srcfile, unsigned int line,
> + const unsigned long exp_ulong, unsigned long x)
> +{
> + if (exp_ulong != x) {
> + pr_err("[%s:%u] expected %lu, got %lu\n",
> + srcfile, line, exp_ulong, x);
> + return false;
> + }
> + return true;
> +}
>
> static bool __init
> __check_eq_bitmap(const char *srcfile, unsigned int line,
> @@ -186,6 +197,7 @@ __check_eq_str(const char *srcfile, unsigned int line,
> })
>
> #define expect_eq_uint(...) __expect_eq(uint, ##__VA_ARGS__)
> +#define expect_eq_ulong(...) __expect_eq(ulong, ##__VA_ARGS__)
> #define expect_eq_bitmap(...) __expect_eq(bitmap, ##__VA_ARGS__)
> #define expect_eq_pbl(...) __expect_eq(pbl, ##__VA_ARGS__)
> #define expect_eq_u32_array(...) __expect_eq(u32_array, ##__VA_ARGS__)
> @@ -1222,6 +1234,25 @@ static void __init test_bitmap_const_eval(void)
> BUILD_BUG_ON(~var != ~BIT(25));
> }
>
> +static void __init test_set_get_value(void)
> +{
> + DECLARE_BITMAP(bitmap, BITS_PER_LONG * 2);
> + unsigned long val;
> + int i;
> +
> + for (i = 0; i < BITS_PER_LONG * 2 - 7; i++) {
> + bitmap_zero(bitmap, BITS_PER_LONG * 2);
> + bitmap_set_value(bitmap, 0b10101UL, i, 5);
> + val = bitmap_get_value(bitmap, i, 5);
> + expect_eq_ulong(0b10101UL, val);
> + bitmap_set_value(bitmap, 0b101UL, i + 5, 3);
> + val = bitmap_get_value(bitmap, i + 5, 3);
> + expect_eq_ulong(0b101UL, val);
> + val = bitmap_get_value(bitmap, i, 8);
> + expect_eq_ulong(0b10110101UL, val);
> + }
> +}
> +
> static void __init selftest(void)
> {
> test_zero_clear();
> @@ -1249,6 +1280,8 @@ static void __init selftest(void)
> test_for_each_clear_bitrange_from();
> test_for_each_set_clump8();
> test_for_each_set_bit_wrap();
> +
> + test_set_get_value();
> }
>
> KSTM_MODULE_LOADERS(test_bitmap);
> --
> 2.41.0.255.g8b1d071c50-goog
>

--
With Best Regards,
Andy Shevchenko



2023-07-17 16:31:47

by Yury Norov

[permalink] [raw]
Subject: Re: [PATCH v3 2/5] lib/test_bitmap: add tests for bitmap_{set,get}_value()

On Mon, Jul 17, 2023 at 01:37:05PM +0200, Alexander Potapenko wrote:
> Add basic tests ensuring that values can be added at arbitrary positions
> of the bitmap, including those spanning into the adjacent unsigned
> longs.
>
> Signed-off-by: Alexander Potapenko <[email protected]>

Thanks for the test!

> ---
> This patch was previously called
> "lib/test_bitmap: add tests for bitmap_{set,get}_value_unaligned"
>
> v3:
> - switch to using bitmap_{set,get}_value()
> - change the expected bit pattern in test_set_get_value(),
> as the test was incorrectly assuming 0 is the LSB.
> ---
> lib/test_bitmap.c | 33 +++++++++++++++++++++++++++++++++
> 1 file changed, 33 insertions(+)
>
> diff --git a/lib/test_bitmap.c b/lib/test_bitmap.c
> index 187f5b2db4cf1..c2ab54040c249 100644
> --- a/lib/test_bitmap.c
> +++ b/lib/test_bitmap.c
> @@ -71,6 +71,17 @@ __check_eq_uint(const char *srcfile, unsigned int line,
> return true;
> }
>
> +static bool __init
> +__check_eq_ulong(const char *srcfile, unsigned int line,
> + const unsigned long exp_ulong, unsigned long x)
> +{
> + if (exp_ulong != x) {
> + pr_err("[%s:%u] expected %lu, got %lu\n",
> + srcfile, line, exp_ulong, x);
> + return false;
> + }
> + return true;
> +}
>
> static bool __init
> __check_eq_bitmap(const char *srcfile, unsigned int line,
> @@ -186,6 +197,7 @@ __check_eq_str(const char *srcfile, unsigned int line,
> })
>
> #define expect_eq_uint(...) __expect_eq(uint, ##__VA_ARGS__)
> +#define expect_eq_ulong(...) __expect_eq(ulong, ##__VA_ARGS__)
> #define expect_eq_bitmap(...) __expect_eq(bitmap, ##__VA_ARGS__)
> #define expect_eq_pbl(...) __expect_eq(pbl, ##__VA_ARGS__)
> #define expect_eq_u32_array(...) __expect_eq(u32_array, ##__VA_ARGS__)
> @@ -1222,6 +1234,25 @@ static void __init test_bitmap_const_eval(void)
> BUILD_BUG_ON(~var != ~BIT(25));
> }
>
> +static void __init test_set_get_value(void)
> +{
> + DECLARE_BITMAP(bitmap, BITS_PER_LONG * 2);

It's too short. Can you make it long enough to ensure it works as
expected when start is not in the 1st word, and start+nbits is in
the following word.

> + unsigned long val;
> + int i;
> +
> + for (i = 0; i < BITS_PER_LONG * 2 - 7; i++) {
> + bitmap_zero(bitmap, BITS_PER_LONG * 2);
> + bitmap_set_value(bitmap, 0b10101UL, i, 5);
> + val = bitmap_get_value(bitmap, i, 5);
> + expect_eq_ulong(0b10101UL, val);

Can you also check that the rest of bitmap is untouched?
Something like:

DECLARE_BITMAP(bitmap, ...);
DECLARE_BITMAP(orig, ...);

memset(orig, 0x5a, ...);
memset(bitmap, 0x5a, ...);

for (j = start; j < start + nbits; j++)
if (val & BIT(j - start))
__set_bit(j, orig);
else
__clear_bit(j, orig);

bitmap_set_value(bitmap, val, start, nbits);
expect_eq_bitmap(orig, bitmap, ...);

I like this kind of testing because it gives people a better
understanding of what happens behind all that optimization tricks.

Thanks,
Yury

2023-07-17 16:53:38

by Andy Shevchenko

[permalink] [raw]
Subject: Re: [PATCH v3 2/5] lib/test_bitmap: add tests for bitmap_{set,get}_value()

On Mon, Jul 17, 2023 at 09:11:50AM -0700, Yury Norov wrote:
> On Mon, Jul 17, 2023 at 01:37:05PM +0200, Alexander Potapenko wrote:

...

> if (val & BIT(j - start))
> __set_bit(j, orig);
> else
> __clear_bit(j, orig);

JFYI: __asign_bit() can be used here.

--
With Best Regards,
Andy Shevchenko



2023-07-17 16:57:17

by Alexander Potapenko

[permalink] [raw]
Subject: Re: [PATCH v3 2/5] lib/test_bitmap: add tests for bitmap_{set,get}_value()

On Mon, Jul 17, 2023 at 6:11 PM Yury Norov <[email protected]> wrote:
>
> On Mon, Jul 17, 2023 at 01:37:05PM +0200, Alexander Potapenko wrote:
> > Add basic tests ensuring that values can be added at arbitrary positions
> > of the bitmap, including those spanning into the adjacent unsigned
> > longs.
> >
> > Signed-off-by: Alexander Potapenko <[email protected]>
>
> Thanks for the test!
>
> > ---
> > This patch was previously called
> > "lib/test_bitmap: add tests for bitmap_{set,get}_value_unaligned"
> >
> > v3:
> > - switch to using bitmap_{set,get}_value()
> > - change the expected bit pattern in test_set_get_value(),
> > as the test was incorrectly assuming 0 is the LSB.
> > ---
> > lib/test_bitmap.c | 33 +++++++++++++++++++++++++++++++++
> > 1 file changed, 33 insertions(+)
> >
> > diff --git a/lib/test_bitmap.c b/lib/test_bitmap.c
> > index 187f5b2db4cf1..c2ab54040c249 100644
> > --- a/lib/test_bitmap.c
> > +++ b/lib/test_bitmap.c
> > @@ -71,6 +71,17 @@ __check_eq_uint(const char *srcfile, unsigned int line,
> > return true;
> > }
> >
> > +static bool __init
> > +__check_eq_ulong(const char *srcfile, unsigned int line,
> > + const unsigned long exp_ulong, unsigned long x)
> > +{
> > + if (exp_ulong != x) {
> > + pr_err("[%s:%u] expected %lu, got %lu\n",
> > + srcfile, line, exp_ulong, x);
> > + return false;
> > + }
> > + return true;
> > +}
> >
> > static bool __init
> > __check_eq_bitmap(const char *srcfile, unsigned int line,
> > @@ -186,6 +197,7 @@ __check_eq_str(const char *srcfile, unsigned int line,
> > })
> >
> > #define expect_eq_uint(...) __expect_eq(uint, ##__VA_ARGS__)
> > +#define expect_eq_ulong(...) __expect_eq(ulong, ##__VA_ARGS__)
> > #define expect_eq_bitmap(...) __expect_eq(bitmap, ##__VA_ARGS__)
> > #define expect_eq_pbl(...) __expect_eq(pbl, ##__VA_ARGS__)
> > #define expect_eq_u32_array(...) __expect_eq(u32_array, ##__VA_ARGS__)
> > @@ -1222,6 +1234,25 @@ static void __init test_bitmap_const_eval(void)
> > BUILD_BUG_ON(~var != ~BIT(25));
> > }
> >
> > +static void __init test_set_get_value(void)
> > +{
> > + DECLARE_BITMAP(bitmap, BITS_PER_LONG * 2);
>
> It's too short. Can you make it long enough to ensure it works as
> expected when start is not in the 1st word, and start+nbits is in
> the following word.
>
> > + unsigned long val;
> > + int i;
> > +
> > + for (i = 0; i < BITS_PER_LONG * 2 - 7; i++) {
> > + bitmap_zero(bitmap, BITS_PER_LONG * 2);
> > + bitmap_set_value(bitmap, 0b10101UL, i, 5);
> > + val = bitmap_get_value(bitmap, i, 5);
> > + expect_eq_ulong(0b10101UL, val);
>
> Can you also check that the rest of bitmap is untouched?
> Something like:
>
> DECLARE_BITMAP(bitmap, ...);
> DECLARE_BITMAP(orig, ...);
>
> memset(orig, 0x5a, ...);
> memset(bitmap, 0x5a, ...);
>
> for (j = start; j < start + nbits; j++)
> if (val & BIT(j - start))
> __set_bit(j, orig);
> else
> __clear_bit(j, orig);
>
> bitmap_set_value(bitmap, val, start, nbits);
> expect_eq_bitmap(orig, bitmap, ...);
>
> I like this kind of testing because it gives people a better
> understanding of what happens behind all that optimization tricks.

Will do. In fact the difference between GENMASK(n, 0) and GENMASK(n-1,
0) discussed in the other patch requires exactly this kind of testing.

2023-07-18 10:47:38

by Alexander Potapenko

[permalink] [raw]
Subject: Re: [PATCH v3 2/5] lib/test_bitmap: add tests for bitmap_{set,get}_value()

On Mon, Jul 17, 2023 at 3:04 PM Andy Shevchenko
<[email protected]> wrote:
>
> On Mon, Jul 17, 2023 at 01:37:05PM +0200, Alexander Potapenko wrote:
> > Add basic tests ensuring that values can be added at arbitrary positions
> > of the bitmap, including those spanning into the adjacent unsigned
> > longs.
>
> I always in favour of a new test case!
> Reviewed-by: Andy Shevchenko <[email protected]>
>
> > Signed-off-by: Alexander Potapenko <[email protected]>
> >
> > ---
> > This patch was previously called
> > "lib/test_bitmap: add tests for bitmap_{set,get}_value_unaligned"
>
> Hint, you may always just link to lore mail archive for easier access and
> handling. Also with `b4` at hand the lore link can be used to resurrect
> a discussion (in case it's needed).

Will add the link in v4
(guess you didn't want it in the final patch description, correct?)