Skip to content

Commit ff80cca

Browse files
committed
fixup size literals
1 parent 9a55793 commit ff80cca

File tree

1 file changed

+14
-12
lines changed

1 file changed

+14
-12
lines changed

libraries/libfc/include/fc/utility.hpp

Lines changed: 14 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -208,37 +208,39 @@ namespace fc {
208208
//TODO: these should really be consteval, but they're getting pulled in by a few of our c++17 compiled files
209209
namespace size_literals {
210210
namespace detail {
211-
template <unsigned ShiftAmount>
212-
constexpr unsigned long long to_bytes(const unsigned long long val) {
211+
constexpr unsigned long long multiply_pow2(const unsigned long long val, const unsigned long long shift) {
212+
if(shift >= std::numeric_limits<unsigned long long>::digits)
213+
throw std::invalid_argument("exponent for pow2 too large");
214+
213215
constexpr unsigned long long max_ull = std::numeric_limits<unsigned long long>::max();
214-
constexpr unsigned long long multiplier = 1ull << ShiftAmount;
215-
if(val > max_ull/multiplier)
216+
217+
if(val > (max_ull >> shift))
216218
throw std::invalid_argument("literal too large");
217-
return val * multiplier;
219+
220+
return val << shift;
218221
}
219222
}
220223

221224
constexpr unsigned long long operator""_KiB(const unsigned long long val) {
222-
return detail::to_bytes<10>(val);
225+
return detail::multiply_pow2(val, 10);
223226
}
224227
constexpr unsigned long long operator""_MiB(const unsigned long long val) {
225-
return detail::to_bytes<20>(val);
228+
return detail::multiply_pow2(val, 20);
226229
}
227230
constexpr unsigned long long operator""_GiB(const unsigned long long val) {
228-
return detail::to_bytes<30>(val);
231+
return detail::multiply_pow2(val, 30);
229232
}
230233
constexpr unsigned long long operator""_TiB(const unsigned long long val) {
231-
return detail::to_bytes<40>(val);
234+
return detail::multiply_pow2(val, 40);
232235
}
233236

234237
constexpr unsigned long long operator""_pow2(const unsigned long long n) {
235-
if(n >= std::numeric_limits<unsigned long long>::digits)
236-
throw std::invalid_argument("exponent for _pow2 too large");
237-
return 1ull << n;
238+
return detail::multiply_pow2(1, n);
238239
}
239240

240241
static_assert(4_MiB == 4*1024*1024);
241242
static_assert(16_pow2 == 64*1024);
243+
static_assert(63_pow2 == 9223372036854775808ull);
242244
}
243245

244246
}

0 commit comments

Comments
 (0)