Skip to content

Commit

Permalink
Update gsl submodule; fix bitflags::all_false
Browse files Browse the repository at this point in the history
Fixes hsutter#23.
  • Loading branch information
CaseyCarter committed Apr 26, 2017
1 parent 9da9af2 commit d2b3e1d
Show file tree
Hide file tree
Showing 4 changed files with 26 additions and 15 deletions.
4 changes: 2 additions & 2 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ cmake_minimum_required(VERSION 3.1)
set(CMAKE_CXX_STANDARD 14)
set(CMAKE_CXX_STANDARD_REQUIRED on)

include_directories(SYSTEM submodules/gsl)
include_directories(SYSTEM submodules/gsl/include)

add_executable(test_basic test.cpp)
add_executable(test_graph test_graph.cpp)
Expand All @@ -12,5 +12,5 @@ enable_testing()

add_test(test_basic ${CMAKE_BINARY_DIR}/test_basic -s)

# FIXME: Fix graph tests which fail with an assertion error on macOS.
# FIXME: Fix graph tests which fail with an assertion error on macOS.
# add_test(test_graph ${CMAKE_BINARY_DIR}/test_graph -s)
15 changes: 10 additions & 5 deletions bitflags.h
Original file line number Diff line number Diff line change
Expand Up @@ -36,14 +36,16 @@ namespace gcpp {
//----------------------------------------------------------------------------

class bitflags {
public:
using unit = unsigned int;
static_assert(std::is_unsigned<unit>::value, "unit must be an unsigned integral type.");

static constexpr auto bits_per_unit = static_cast<int>(sizeof(unit) * CHAR_BIT);

private:
std::unique_ptr<unit[]> bits;
const int size;

static constexpr auto bits_per_unit = static_cast<int>(sizeof(unit) * CHAR_BIT);

// Return a unit with all bits set if "set" is true, or all bits cleared otherwise.
//
static constexpr unit all_bits(bool set) noexcept {
Expand Down Expand Up @@ -96,9 +98,12 @@ namespace gcpp {
// Test whether all bits are false
//
bool all_false() const noexcept {
auto all_false = [](unit u) { return u == unit(0); };
return std::all_of(bits.get(), bits.get() + unit_count(size) - 1, all_false)
&& all_false(*(bits.get() + unit_count(size) - 1) & (bit_mask(size) - 1));
auto const all_false = [](unit const u) { return u == unit(0); };
if (!std::all_of(bits.get(), bits.get() + unit_count(size) - 1, all_false)) {
return false;
}
auto const mask = size % bits_per_unit == 0 ? unit(0) : bit_mask(size);
return all_false(*(bits.get() + unit_count(size) - 1) & (mask - 1));
}

// Set flag value at position
Expand Down
20 changes: 13 additions & 7 deletions test.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -396,15 +396,14 @@ void test_deferred_array() {

}


void test_bitflags() {
const int N = 100; // picked so that we have 3 x 32-bit units + 1 partial unit,
// so we can exercise the boundary and internal unit cases

// Test that we can correctly set any bit range [i,j)
for (auto i = 0; i < N; ++i) {
for (auto j = i; j < N; ++j) {
bitflags flags(100, false);
bitflags flags(N, false);
flags.set(i, j, true);
for (auto test = 0; test < N; ++test) {
assert(flags.get(test) == (i <= test && test < j));
Expand All @@ -414,7 +413,7 @@ void test_bitflags() {

// Test that we can find a true bit set anywhere with any range
for (auto set = 0; set < N; ++set) {
bitflags flags(100, false);
bitflags flags(N, false);
flags.set(set, true);
for (auto i = 0; i <= set; ++i) {
for (auto j = i; j < N; ++j) {
Expand All @@ -425,7 +424,7 @@ void test_bitflags() {

// Test that we can find a false bit set anywhere with any range
for (auto set = 0; set < N; ++set) {
bitflags flags(100, true);
bitflags flags(N, true);
flags.set(set, false);
for (auto i = 0; i <= set; ++i) {
for (auto j = i; j < N; ++j) {
Expand All @@ -434,13 +433,22 @@ void test_bitflags() {
}
}

{
// Regression test for #23:
// Test that all_false observes the bits in the last unit
bitflags flags(bitflags::bits_per_unit, false);
assert(flags.all_false());
flags.set(bitflags::bits_per_unit - 1, true);
assert(!flags.all_false());
}

//flags.debug_print();
}


int main() {
//test_page();
//test_bitflags();
test_bitflags();

//test_deferred_heap();
//time_deferred_heap();
Expand All @@ -457,7 +465,5 @@ int main() {

//heap.collect();
//heap.debug_print();

return 0;
}

0 comments on commit d2b3e1d

Please sign in to comment.