Hi all, I've recently found myself frustrated due to the amount of boilerplate that bitmask types require. Say, for example, asio::cancellation_type_t: https://www.boost.org/doc/libs/latest/boost/asio/cancellation_type.hpp When using enum class to avoid pouring identifiers into the parent namespace, you need to re-implement all the bitwise operators. This is not a lot of work, but is empty boilerplate, and implies adding tests and docs. Reflection may aid with this. I've written a small proof of concept: https://access_refl.compiler-explorer.com/z/jdaxf9q54 Pasting here the basics, just in case: namespace bitmasks { struct bitmask_t {}; inline constexpr bitmask_t bitmask {}; // Checks that t has our annotation consteval bool has_bitmask_annotation(std::meta::info t) { ... } template <class E> concept BitmaskType = std::is_scoped_enum_v<E> && has_bitmask_annotation(^^E); } // Intentionally in the global namespace template <bitmasks::BitmaskType E> E operator|(E e1, E e2) { using U = std::underlying_type_t<E>; return static_cast<E>(static_cast<U>(e1) | static_cast<U>(e2)); } The idea is that you use the [[=bitmask]] annotation on your enum, and you get all the operators for free. I could also add optional pretty-printing. Questions: * Do you think this is a problem worth solving, or am I being too picky? * Do we already have something similar in Boost? I've found a BOOST_BITMASK macro (https://www.boost.org/doc/libs/latest/boost/detail/bitmask.hpp), but it doesn't seem to be public. * Do you think the approach shown above is sound? In particular, operators are in the global namespace so that they work with any enum in any namespace correctly annotated. * Do you think such a small component could be useful in Boost at some point? Thanks, Ruben.