Reading cppreference.com:
A static assert declaration may appear at block scope (as a block declaration) and inside a class body (as a member declaration)
OK, now I have the following code:
struct foo_t
{
static constexpr std::size_t maxAlignment()
{
// This is just a sample; I removed real code from this method.
return std::max(alignof(__m128), __alignof(__m256));
}
static_assert(0 == ((maxAlignment() -1) & maxAlignment()), "some message");
};
Neither MSVC 2015 nor Intel C++ 16.0.2 compile this code (the former shows "error C2131: expression did not evaluate to constant" and the latter shows "function call must have a constant value in a constant expression" error and points to call of maxAlignment
in static_assert
).
But MSVC 2015 Update 1 does compile the following code, while Intel C++ 16.0.2 does not:
template <typename T, std::size_t Alignment>
struct foo_t
{
static constexpr std::size_t maxAlignment()
{
return std::max(std::alignment_of<T>::value, Alignment);
}
static_assert(0 == ((maxAlignment() -1) & maxAlignment()), "some message");
};
foo_t<__m128, 16> foo {};
// foo_t<__m128, 33> boo {}; // here `static_assert` will stop compilation
(So, MSVC can handle static_assert
when it's inside a template class body)
But the following code is compiled successfully by both of the compilers (static_assert
is outside of a class body; it appears at a block scope):
struct foo_t
{
static constexpr std::size_t maxAlignment()
{
return std::max(alignof(__m128), __alignof(__m256));
}
};
static_assert(0 == ((foo_t::maxAlignment() -1) & foo_t::maxAlignment()), "some message");
My question is: Did I miss something or is that Intel C++ compiler's error?
If I recall it right constexpr functions can't be used until they are fully defined and class-member constexpr functions are undefined until the class is defined and it means that you can't use constexpr member-function inside the class-scope static_assert
which defines this very function.
But you can make this function standalone(it is already static anyway) and it will do the job. It should compile everywhere.