There are two possible approaches here:
- A library-only solution (this patch)
- Some compiler work (updating the __underlying_type intrinsic)
After working on this for a bit, I think this is the better approach.
Differential D63574
Implement P0340R3: Make `underlying_type` SFINAE-friendly mclow.lists on Jun 19 2019, 2:27 PM. Authored by
Details There are two possible approaches here:
After working on this for a bit, I think this is the better approach.
Diff Detail Event TimelineComment Actions Note: There is no feature test macro for this.
Comment Actions How many of these should fail? enum E1 { E1Zero, E1One, E1Two = sizeof(std::underlying_type<E1>::type) }; enum E2 : char { E2Zero, E2One, E2Two = sizeof(std::underlying_type<E2>::type) }; enum class E3 { E3Zero, E3One, E3Two = sizeof(std::underlying_type<E3>::type) }; enum struct E4 : unsigned { E4Zero, E4One, E4Two = sizeof(std::underlying_type<E4>::type) }; enum struct E5 { E5Zero, E5One, E5Two = sizeof(std::underlying_type<E5>::type) }; enum class E6 : unsigned { E6Zero, E6One, E6Two = sizeof(std::underlying_type<E6>::type) }; @rsmith ? Comment Actions Turns out that only the first one should fail - and that's the one that clang rejects. Comment Actions Some test cleanup.; add notes to the failing test to say why the other cases don't fail. Comment Actions That's right. A couple more testcases to exercise the corners here: enum E7 : std::underlying_type_t<E7> {}; enum class E8 : std::underlying_type_t<E8> {}; (Clang gets the point of declaration for enums wrong at the moment and thinks that E7 and E8 are not in scope in the enum-base. But those two should be rejected either way.)
|
This changes the mangling of underlying_type, and potentially it's usage as a "template template".
The specialization trick should be done in a impl base class.