Skip to content

Commit

Permalink
string: introduce memweight()
Browse files Browse the repository at this point in the history
memweight() is the function that counts the total number of bits set in
memory area.  Unlike bitmap_weight(), memweight() takes pointer and size
in bytes to specify a memory area which does not need to be aligned to
long-word boundary.

[[email protected]: rename `w' to `ret']
Signed-off-by: Akinobu Mita <[email protected]>
Cc: Anders Larsen <[email protected]>
Cc: Alasdair Kergon <[email protected]>
Cc: Laurent Pinchart <[email protected]>
Cc: Mark Fasheh <[email protected]>
Cc: Joel Becker <[email protected]>
Cc: Jan Kara <[email protected]>
Cc: Andreas Dilger <[email protected]>
Cc: "Theodore Ts'o" <[email protected]>
Cc: Matthew Wilcox <[email protected]>
Cc: Mauro Carvalho Chehab <[email protected]>
Cc: Tony Luck <[email protected]>
Signed-off-by: Andrew Morton <[email protected]>
Signed-off-by: Linus Torvalds <[email protected]>
  • Loading branch information
mita authored and torvalds committed Jul 31, 2012
1 parent f7f9505 commit 639b9e3
Show file tree
Hide file tree
Showing 3 changed files with 42 additions and 1 deletion.
3 changes: 3 additions & 0 deletions include/linux/string.h
Original file line number Diff line number Diff line change
Expand Up @@ -145,4 +145,7 @@ static inline bool strstarts(const char *str, const char *prefix)
return strncmp(str, prefix, strlen(prefix)) == 0;
}
#endif

extern size_t memweight(const void *ptr, size_t bytes);

#endif /* _LINUX_STRING_H_ */
2 changes: 1 addition & 1 deletion lib/Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ lib-y += kobject.o klist.o
obj-y += bcd.o div64.o sort.o parser.o halfmd4.o debug_locks.o random32.o \
bust_spinlocks.o hexdump.o kasprintf.o bitmap.o scatterlist.o \
string_helpers.o gcd.o lcm.o list_sort.o uuid.o flex_array.o \
bsearch.o find_last_bit.o find_next_bit.o llist.o
bsearch.o find_last_bit.o find_next_bit.o llist.o memweight.o
obj-y += kstrtox.o
obj-$(CONFIG_TEST_KSTRTOX) += test-kstrtox.o

Expand Down
38 changes: 38 additions & 0 deletions lib/memweight.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
#include <linux/export.h>
#include <linux/bug.h>
#include <linux/bitmap.h>

/**
* memweight - count the total number of bits set in memory area
* @ptr: pointer to the start of the area
* @bytes: the size of the area
*/
size_t memweight(const void *ptr, size_t bytes)
{
size_t ret = 0;
size_t longs;
const unsigned char *bitmap = ptr;

for (; bytes > 0 && ((unsigned long)bitmap) % sizeof(long);
bytes--, bitmap++)
ret += hweight8(*bitmap);

longs = bytes / sizeof(long);
if (longs) {
BUG_ON(longs >= INT_MAX / BITS_PER_LONG);
ret += bitmap_weight((unsigned long *)bitmap,
longs * BITS_PER_LONG);
bytes -= longs * sizeof(long);
bitmap += longs * sizeof(long);
}
/*
* The reason that this last loop is distinct from the preceding
* bitmap_weight() call is to compute 1-bits in the last region smaller
* than sizeof(long) properly on big-endian systems.
*/
for (; bytes > 0; bytes--, bitmap++)
ret += hweight8(*bitmap);

return ret;
}
EXPORT_SYMBOL(memweight);

0 comments on commit 639b9e3

Please sign in to comment.