Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

New bit manipulation functions and 128-bit value library #7338

Closed
wants to merge 3 commits into from

Conversation

pdillinger
Copy link
Contributor

Summary: These new functions and 128-bit value bit operations are
expected to be used in a forthcoming Bloom filter alternative.

No functional changes to production code, just new code only called by
unit tests, cosmetic changes to existing headers, and fix an existing
function for a yet-unused template instantiation (BitsSetToOne on
something signed and smaller than 32 bits).

Test Plan: Unit tests included. Works with and without
TEST_UINT128_COMPAT=1 to check compatibility with and without
__uint128_t. Also added that parameter to the CircleCI build
build-linux-shared_lib-alt_namespace-status_checked.

Summary: These new functions and 128-bit value bit operations are
expected to be used in a forthcoming Bloom filter alternative.

No functional changes to production code, just new code only called by
unit tests, cosmetic changes to existing headers, and fix an existing
function for a yet-unused template instantiation (BitsSetToOne on
something signed and smaller than 32 bits).

Test Plan: Unit tests included. Works with and without
TEST_UINT128_COMPAT=1 to check compatibility with and without
__uint128_t. Also added that parameter to the CircleCI build
build-linux-shared_lib-alt_namespace-status_checked.
Copy link
Contributor

@jay-zhuang jay-zhuang left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM. just a few comments and questions.

util/math.h Outdated
} else if (sizeof(T) <= sizeof(unsigned long)) {
return __builtin_ctzl(static_cast<unsigned long>(v));
} else {
return __builtin_ctzll(static_cast<unsigned long>(v));
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

should it be static_cast<unsigned long long>?

util/math.h Outdated
Comment on lines 33 to 39
if (sizeof(T) <= sizeof(unsigned int)) {
int lz = __builtin_clz(static_cast<unsigned int>(v));
return int{sizeof(unsigned int)} * 8 - 1 - lz;
} else {
int lz = __builtin_clzll(static_cast<unsigned long long>(v));
return int{sizeof(unsigned long long)} * 8 - 1 - lz;
}
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

do we need to have __buildin_clzl() like other functions do? like:

else if (sizeof(T) <= sizeof(unsigned long)) {
  return lz lz = __buildin_clzl(static_cast<unsigned long>(v));
} else {

util/math.h Outdated
}
#else
static_assert(sizeof(T) <= sizeof(unsigned long long), "type too big");
if (sizeof(T) > sizeof(unsigned long)) {
return __builtin_popcountll(static_cast<unsigned long long>(v));
} else if (sizeof(T) > sizeof(unsigned int)) {
return __builtin_popcountl(static_cast<unsigned long>(v));
} else {
} else if (sizeof(T) == sizeof(unsigned int)) {
return __builtin_popcount(static_cast<unsigned int>(v));
Copy link
Contributor

@jay-zhuang jay-zhuang Sep 2, 2020

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

nit: maybe better to have a consistent ordering of checks for all functions. like from type size from small to big:

if (size < sizeof(unsigned int)) {
} else if (size == sizeof(unsigned int)) {
} else if (size <= sizeof(unsigned long)) {
} else {
}

Makefile Show resolved Hide resolved
util/math128.h Outdated
tmp += uint64_t{b & 0xffffFFFF} * uint64_t{a >> 32};
// Avoid overflow: first add lower 32 of tmp2, and later upper 32
uint64_t tmp2 = uint64_t{b >> 32} * uint64_t{a & 0xffffFFFF};
tmp += static_cast<uint32_t>(tmp2);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

nit: tmp += tmp2 & 0xffffFFFF; to be consistent with others?

Copy link
Contributor

@facebook-github-bot facebook-github-bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@pdillinger has imported this pull request. If you are a Facebook employee, you can view this diff on Phabricator.

uint64_t tmp = uint64_t{b & 0xffffFFFF} * uint64_t{a & 0xffffFFFF};
uint64_t lower = tmp & 0xffffFFFF;
tmp >>= 32;
tmp += uint64_t{b & 0xffffFFFF} * uint64_t{a >> 32};
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It took me a while to figure out that it won't overflow 🤦
UINT_MAX * UINT_MAX + UINT_MAX + UINT_MAX = ULLONG_MAX

@facebook-github-bot
Copy link
Contributor

@pdillinger merged this pull request in c4d8838.

codingrhythm pushed a commit to SafetyCulture/rocksdb that referenced this pull request Mar 5, 2021
Summary:
These new functions and 128-bit value bit operations are
expected to be used in a forthcoming Bloom filter alternative.

No functional changes to production code, just new code only called by
unit tests, cosmetic changes to existing headers, and fix an existing
function for a yet-unused template instantiation (BitsSetToOne on
something signed and smaller than 32 bits).

Pull Request resolved: facebook#7338

Test Plan:
Unit tests included. Works with and without
TEST_UINT128_COMPAT=1 to check compatibility with and without
__uint128_t. Also added that parameter to the CircleCI build
build-linux-shared_lib-alt_namespace-status_checked.

Reviewed By: jay-zhuang

Differential Revision: D23494945

Pulled By: pdillinger

fbshipit-source-id: 5c0dc419100d9df5d4d9abb153b2855d5aea39e8
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

3 participants