diff options
author | Valerie Aurora Henson <vaurora@redhat.com> | 2009-06-01 16:15:40 -0400 |
---|---|---|
committer | Theodore Ts'o <tytso@mit.edu> | 2009-06-01 16:15:40 -0400 |
commit | 8717c3a8f31dea3b31ddaeccf74ea3b34ca72c04 (patch) | |
tree | 203fc626dce0e729608efe2550c4bfe17c803474 /lib | |
parent | b4e0163d53613ae47f79c661f7c1e2009a271c79 (diff) | |
download | e2fsprogs-8717c3a8f31dea3b31ddaeccf74ea3b34ca72c04.tar.gz |
libext2fs: Add 64-bit bitops
Signed-off-by: Valerie Aurora Henson <vaurora@redhat.com>
Signed-off-by: "Theodore Ts'o" <tytso@mit.edu>
Diffstat (limited to 'lib')
-rw-r--r-- | lib/ext2fs/bitops.c | 39 | ||||
-rw-r--r-- | lib/ext2fs/bitops.h | 22 | ||||
-rw-r--r-- | lib/ext2fs/tst_bitops.c | 120 |
3 files changed, 181 insertions, 0 deletions
diff --git a/lib/ext2fs/bitops.c b/lib/ext2fs/bitops.c index 485e997b..36901b2d 100644 --- a/lib/ext2fs/bitops.c +++ b/lib/ext2fs/bitops.c @@ -76,3 +76,42 @@ void ext2fs_warn_bitmap(errcode_t errcode, unsigned long arg, com_err(0, errcode, "#%lu", arg); #endif } + +/* + * C-only 64 bit ops. + */ + +int ext2fs_set_bit64(__u64 nr, void * addr) +{ + int mask, retval; + unsigned char *ADDR = (unsigned char *) addr; + + ADDR += nr >> 3; + mask = 1 << (nr & 0x07); + retval = mask & *ADDR; + *ADDR |= mask; + return retval; +} + +int ext2fs_clear_bit64(__u64 nr, void * addr) +{ + int mask, retval; + unsigned char *ADDR = (unsigned char *) addr; + + ADDR += nr >> 3; + mask = 1 << (nr & 0x07); + retval = mask & *ADDR; + *ADDR &= ~mask; + return retval; +} + +int ext2fs_test_bit64(__u64 nr, const void * addr) +{ + int mask; + const unsigned char *ADDR = (const unsigned char *) addr; + + ADDR += nr >> 3; + mask = 1 << (nr & 0x07); + return (mask & *ADDR); +} + diff --git a/lib/ext2fs/bitops.h b/lib/ext2fs/bitops.h index 32111ba6..7c3f056d 100644 --- a/lib/ext2fs/bitops.h +++ b/lib/ext2fs/bitops.h @@ -19,6 +19,11 @@ extern int ext2fs_clear_bit(unsigned int nr, void * addr); extern int ext2fs_test_bit(unsigned int nr, const void * addr); extern void ext2fs_fast_set_bit(unsigned int nr,void * addr); extern void ext2fs_fast_clear_bit(unsigned int nr, void * addr); +extern int ext2fs_set_bit64(__u64 nr,void * addr); +extern int ext2fs_clear_bit64(__u64 nr, void * addr); +extern int ext2fs_test_bit64(__u64 nr, const void * addr); +extern void ext2fs_fast_set_bit64(__u64 nr,void * addr); +extern void ext2fs_fast_clear_bit64(__u64 nr, void * addr); extern __u16 ext2fs_swab16(__u16 val); extern __u32 ext2fs_swab32(__u32 val); extern __u64 ext2fs_swab64(__u64 val); @@ -167,6 +172,23 @@ _INLINE_ void ext2fs_fast_clear_bit(unsigned int nr, void * addr) } +_INLINE_ void ext2fs_fast_set_bit64(__u64 nr, void * addr) +{ + unsigned char *ADDR = (unsigned char *) addr; + + ADDR += nr >> 3; + *ADDR |= (1 << (nr & 0x07)); +} + +_INLINE_ void ext2fs_fast_clear_bit64(__u64 nr, void * addr) +{ + unsigned char *ADDR = (unsigned char *) addr; + + ADDR += nr >> 3; + *ADDR &= ~(1 << (nr & 0x07)); +} + + #if ((defined __GNUC__) && !defined(_EXT2_USE_C_VERSIONS_) && \ (defined(__i386__) || defined(__i486__) || defined(__i586__))) diff --git a/lib/ext2fs/tst_bitops.c b/lib/ext2fs/tst_bitops.c index 6febe685..0f0a4258 100644 --- a/lib/ext2fs/tst_bitops.c +++ b/lib/ext2fs/tst_bitops.c @@ -169,5 +169,125 @@ int main(int argc, char **argv) printf("ext2fs_fast_set_bit big_test successful\n"); + /* Repeat foregoing tests for 64-bit bitops */ + + /* Test test_bit */ + for (i=0,j=0; i < size; i++) { + if (ext2fs_test_bit64(i, bitarray)) { + if (bits_list[j] == i) { + j++; + } else { + printf("64-bit: Bit %d set, not expected\n", + i); + exit(1); + } + } else { + if (bits_list[j] == i) { + printf("64-bit: " + "Expected bit %d to be clear.\n", i); + exit(1); + } + } + } + printf("64-bit: ext2fs_test_bit appears to be correct\n"); + + /* Test ext2fs_set_bit */ + memset(testarray, 0, sizeof(testarray)); + for (i=0; bits_list[i] > 0; i++) { + ext2fs_set_bit64(bits_list[i], testarray); + } + if (memcmp(testarray, bitarray, sizeof(testarray)) == 0) { + printf("64-bit: ext2fs_set_bit test succeeded.\n"); + } else { + printf("64-bit: ext2fs_set_bit test failed.\n"); + for (i=0; i < sizeof(testarray); i++) { + printf("%02x ", testarray[i]); + } + printf("\n"); + exit(1); + } + for (i=0; bits_list[i] > 0; i++) { + ext2fs_clear_bit64(bits_list[i], testarray); + } + for (i=0; i < sizeof(testarray); i++) { + if (testarray[i]) { + printf("64-bit: ext2fs_clear_bit failed, " + "testarray[%d] is %d\n", i, testarray[i]); + exit(1); + } + } + printf("64-bit: ext2fs_clear_bit test succeed.\n"); + + /* Do bigarray test */ + bigarray = malloc(1 << 29); + if (!bigarray) { + fprintf(stderr, "Failed to allocate scratch memory!\n"); + exit(1); + } + + bigarray[BIG_TEST_BIT >> 3] = 0; + + ext2fs_set_bit64(BIG_TEST_BIT, bigarray); + printf("64-bit: big bit number (%u) test: %d, expected %d\n", + BIG_TEST_BIT, bigarray[BIG_TEST_BIT >> 3], + (1 << (BIG_TEST_BIT & 7))); + if (bigarray[BIG_TEST_BIT >> 3] != (1 << (BIG_TEST_BIT & 7))) + exit(1); + + ext2fs_clear_bit64(BIG_TEST_BIT, bigarray); + + printf("64-bit: big bit number (%u) test: %d, expected 0\n", + BIG_TEST_BIT, + bigarray[BIG_TEST_BIT >> 3]); + if (bigarray[BIG_TEST_BIT >> 3] != 0) + exit(1); + + printf("64-bit: ext2fs_set_bit big_test successful\n"); + + /* Now test ext2fs_fast_set_bit */ + memset(testarray, 0, sizeof(testarray)); + for (i=0; bits_list[i] > 0; i++) { + ext2fs_fast_set_bit64(bits_list[i], testarray); + } + if (memcmp(testarray, bitarray, sizeof(testarray)) == 0) { + printf("64-bit: ext2fs_fast_set_bit test succeeded.\n"); + } else { + printf("64-bit: ext2fs_fast_set_bit test failed.\n"); + for (i=0; i < sizeof(testarray); i++) { + printf("%02x ", testarray[i]); + } + printf("\n"); + exit(1); + } + for (i=0; bits_list[i] > 0; i++) { + ext2fs_clear_bit64(bits_list[i], testarray); + } + for (i=0; i < sizeof(testarray); i++) { + if (testarray[i]) { + printf("64-bit: ext2fs_clear_bit failed, " + "testarray[%d] is %d\n", i, testarray[i]); + exit(1); + } + } + printf("64-bit: ext2fs_clear_bit test succeed.\n"); + + bigarray[BIG_TEST_BIT >> 3] = 0; + + ext2fs_fast_set_bit64(BIG_TEST_BIT, bigarray); + printf("64-bit: big bit number (%u) test: %d, expected %d\n", + BIG_TEST_BIT, bigarray[BIG_TEST_BIT >> 3], + (1 << (BIG_TEST_BIT & 7))); + if (bigarray[BIG_TEST_BIT >> 3] != (1 << (BIG_TEST_BIT & 7))) + exit(1); + + ext2fs_fast_clear_bit64(BIG_TEST_BIT, bigarray); + + printf("64-bit: big bit number (%u) test: %d, expected 0\n", + BIG_TEST_BIT, bigarray[BIG_TEST_BIT >> 3]); + if (bigarray[BIG_TEST_BIT >> 3] != 0) + exit(1); + + printf("64-bit: ext2fs_fast_set_bit big_test successful\n"); + exit(0); } |