-
Notifications
You must be signed in to change notification settings - Fork 2.4k
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
Add support for _BitInt on clang #4072
base: master
Are you sure you want to change the base?
Conversation
903edfd
to
3666cee
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks for the PR!
@@ -427,6 +427,14 @@ enum class uint128_opt {}; | |||
template <typename T> auto convert_for_visit(T) -> monostate { return {}; } | |||
#endif | |||
|
|||
#ifndef FMT_USE_BITINT | |||
# if FMT_CLANG_VERSION && FMT_CLANG_VERSION >= 1400 |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This can be simplified to
# if FMT_CLANG_VERSION >= 1400
#if FMT_USE_BITINT | ||
# pragma clang diagnostic push | ||
# pragma clang diagnostic ignored "-Wbit-int-extension" | ||
template <class T, int N = 0> struct is_bitint : std::false_type {}; | ||
template <int N> struct is_bitint<_BitInt(N)> : std::true_type {}; | ||
template <int N> struct is_bitint<unsigned _BitInt(N)> : std::true_type {}; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Let's move this out of the mapper, next to the _BitInt
detection above.
#if FMT_USE_BITINT | ||
# pragma clang diagnostic push | ||
# pragma clang diagnostic ignored "-Wbit-int-extension" | ||
template <class T, int N = 0> struct is_bitint : std::false_type {}; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This should be defined outside of conditional block so that the check could be used on all platforms.
template <> struct formatter<BitIntS7> : formatter<int8_t> {}; | ||
|
||
template <> struct formatter<BitIntU32> : formatter<uint32_t> {}; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Defining formatters for _BitInt
should be disallowed.
template <int N> struct is_bitint<unsigned _BitInt(N)> : std::true_type {}; | ||
|
||
template <class T, FMT_ENABLE_IF(is_bitint<remove_cvref_t<T>>::value)> | ||
FMT_MAP_API auto map(T&& val) -> decltype(val) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
_BitInt
should be converted to appropriate integer type.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Are we assuming the maximum width for a _BitInt
is 128 bits here, so we can widen to any of the native integer types (including __int128
)?
I think officially this is what clang supports according to BITINT_MAXWIDTH
for c++ (although from the link in that 5th bullet point, it seems this is more due to a limitation than a design choice. Doesn't seem to be defined for 18 wherever I try it either)
Although for C(23), it supports up to 8388608
https://godbolt.org/z/jzfGYoY6a
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think we can assume that for now and in any case for smaller sizes we should convert to integers for efficiency instead of going through the formatter extension.
@Arghnews, do you plan to update this PR or shall we close it for now (can be reopened later)? |
@vitaut Hi, sorry been busy and now I'm on holiday for 2 weeks, but will update once back and implement your feedback. I'd say leave it open and I'll update in 2-3 weeks, but it's up to you (can reopen of course). Cheers! |
No hurry. Let's keep it open and enjoy your holiday! |
Issue #4007
Only enabled for clang >= 14 as that's all that supports
_BitInt
at the momentWe need a forwarding reference for
map
to be a "more specialized" match;const T&
,T
etc. are ambiguous.I'm not too familiar, would there be a better way to do this by adding an entry into
enum class type
for_BitInt
s? Or this is fine?Fyi this worked in version 9 because of this catch-all overload:
fmt/include/fmt/core.h
Lines 1506 to 1516 in a337011
Which was then subsequently narrowed down to extended FP types (which "broke" the accidental support for this):
fmt/include/fmt/base.h
Lines 1527 to 1537 in 6a192f8