From a742b49f2c92a7e70b776124e9acd21dc35a41ea Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=CE=B6eh=20Matt?= <5415177+ZehMatt@users.noreply.github.com> Date: Mon, 13 Dec 2021 03:44:42 +0200 Subject: [PATCH] Pass const data by template parameters --- src/openrct2/core/BitSet.hpp | 84 ++++++++++++++++++++---------------- test/tests/BitSetTests.cpp | 2 +- 2 files changed, 48 insertions(+), 38 deletions(-) diff --git a/src/openrct2/core/BitSet.hpp b/src/openrct2/core/BitSet.hpp index 7b2c193293..02b1f0e577 100644 --- a/src/openrct2/core/BitSet.hpp +++ b/src/openrct2/core/BitSet.hpp @@ -24,46 +24,56 @@ namespace OpenRCT2 { static constexpr size_t byte_bits = std::numeric_limits>::digits; - static constexpr size_t round_bits(size_t v) + template static constexpr size_t round_bits() { - const auto reminder = v % byte_bits; - if (reminder == 0u) - return v; - return v + (byte_bits - (v % byte_bits)); + const auto reminder = TNumBits % byte_bits; + if constexpr (reminder == 0u) + { + return TNumBits; + } + else + { + return TNumBits + (byte_bits - (TNumBits % byte_bits)); + } } - static_assert(round_bits(1) == 8); - static_assert(round_bits(4) == 8); - static_assert(round_bits(8) == 8); - static_assert(round_bits(9) == 16); - static_assert(round_bits(9) == 16); - static_assert(round_bits(17) == 24); - static_assert(round_bits(24) == 24); - static_assert(round_bits(31) == 32); + static_assert(round_bits<1>() == 8); + static_assert(round_bits<4>() == 8); + static_assert(round_bits<8>() == 8); + static_assert(round_bits<9>() == 16); + static_assert(round_bits<9>() == 16); + static_assert(round_bits<17>() == 24); + static_assert(round_bits<24>() == 24); + static_assert(round_bits<31>() == 32); // Returns the amount of bytes required for a single block. - static constexpr size_t storage_block_size(size_t numBits) + template static constexpr size_t storage_block_size() { - numBits = round_bits(numBits); - if (numBits >= std::numeric_limits::digits) - return sizeof(uintptr_t); - - const auto numBytes = numBits / byte_bits; - auto mask = 1u; - while (mask < numBytes) + constexpr size_t numBits = round_bits(); + if constexpr (numBits >= std::numeric_limits::digits) { - mask <<= 1u; + return sizeof(uintptr_t); + } + else + { + const auto numBytes = numBits / byte_bits; + auto mask = 1u; + while (mask < numBytes) + { + mask <<= 1u; + } + return mask; } - return mask; } - static constexpr size_t storage_block_count(size_t numBits, size_t blockSize) + template static constexpr size_t storage_block_count() { + size_t numBits = TNumBits; size_t numBlocks = 0; while (numBits > 0) { numBlocks++; - numBits -= std::min(blockSize * byte_bits, numBits); + numBits -= std::min(TBlockSizeBytes * byte_bits, numBits); } return numBlocks; } @@ -82,15 +92,15 @@ namespace OpenRCT2 return res; } - static_assert(storage_block_size(1) == sizeof(uint8_t)); - static_assert(storage_block_size(4) == sizeof(uint8_t)); - static_assert(storage_block_size(8) == sizeof(uint8_t)); - static_assert(storage_block_size(9) == sizeof(uint16_t)); - static_assert(storage_block_size(14) == sizeof(uint16_t)); - static_assert(storage_block_size(16) == sizeof(uint16_t)); - static_assert(storage_block_size(18) == sizeof(uint32_t)); - static_assert(storage_block_size(31) == sizeof(uint32_t)); - static_assert(storage_block_size(33) == sizeof(uintptr_t)); + static_assert(storage_block_size<1>() == sizeof(uint8_t)); + static_assert(storage_block_size<4>() == sizeof(uint8_t)); + static_assert(storage_block_size<8>() == sizeof(uint8_t)); + static_assert(storage_block_size<9>() == sizeof(uint16_t)); + static_assert(storage_block_size<14>() == sizeof(uint16_t)); + static_assert(storage_block_size<16>() == sizeof(uint16_t)); + static_assert(storage_block_size<18>() == sizeof(uint32_t)); + static_assert(storage_block_size<31>() == sizeof(uint32_t)); + static_assert(storage_block_size<33>() == sizeof(uintptr_t)); template struct storage_block_type; @@ -116,20 +126,20 @@ namespace OpenRCT2 template struct storage_block_type_aligned { - using value_type = typename storage_block_type::value_type; + using value_type = typename storage_block_type()>::value_type; }; } // namespace BitSet } // namespace Detail template class BitSet { - static constexpr size_t byte_aligned_bitsize = Detail::BitSet::round_bits(TBitSize); + static constexpr size_t byte_aligned_bitsize = Detail::BitSet::round_bits(); using storage_block_type = typename Detail::BitSet::storage_block_type_aligned::value_type; static constexpr size_t block_byte_size = sizeof(storage_block_type); static constexpr size_t block_type_bit_size = block_byte_size * Detail::BitSet::byte_bits; - static constexpr size_t block_count = Detail::BitSet::storage_block_count(byte_aligned_bitsize, block_byte_size); + static constexpr size_t block_count = Detail::BitSet::storage_block_count(); static constexpr size_t capacity_bits = block_count * block_type_bit_size; static constexpr storage_block_type value_zero = storage_block_type{ 0u }; diff --git a/test/tests/BitSetTests.cpp b/test/tests/BitSetTests.cpp index 33700ec0ea..bae044f642 100644 --- a/test/tests/BitSetTests.cpp +++ b/test/tests/BitSetTests.cpp @@ -103,7 +103,7 @@ TEST(BitTest, test_big) ASSERT_EQ(bits.data()[3], ~0ULL); #else static_assert(std::is_same_v); - static_assert(bits.data().size() ==); + static_assert(bits.data().size() == 8); ASSERT_EQ(bits.data()[0], ~0UL); ASSERT_EQ(bits.data()[1], ~0UL); ASSERT_EQ(bits.data()[2], ~0UL);