Reputation: 313
While working on my own array types, I encountered this issue, where one of my unit tests passes for Clang, but fails on MSVC with the following messages:
error C7595: 'UnitTest': call to immediate function is not a constant expression
note: a non-constant (sub-)expression was encountered
note: the call stack of the evaluation (the oldest call first) is
note: while evaluating function 'void UnitTest(void)'
https://godbolt.org/z/KrbWMe8sM
Code is:
#include <exception>
#include <memory>
template <typename ElementType, size_t ElementCount>
class StaticArray
{
public:
template <typename OA>
constexpr StaticArray(OA&& otherArray)
: m_cxBuffer(std::allocator<ElementType>().allocate(static_cast<size_t>(ElementCount)))
{
using OtherArrayType = decltype(otherArray);
using OtherArrayTypeNoRef = std::remove_reference_t<OtherArrayType>;
m_count = std::extent_v<OtherArrayTypeNoRef>;
ElementType* src = otherArray;
ElementType* srcEnd = src + m_count;
ElementType* dst = m_cxBuffer;
ElementType* srcCurrent = src;
ElementType* dstCurrent = dst;
while (srcCurrent != srcEnd)
{
std::construct_at(dstCurrent, std::move(*srcCurrent));
++srcCurrent;
++dstCurrent;
}
}
constexpr ~StaticArray() noexcept
{
while (m_count > 0)
std::destroy_at(m_cxBuffer + (--m_count));
std::allocator<ElementType>().deallocate(m_cxBuffer, static_cast<size_t>(ElementCount));
}
size_t m_count = 0;
ElementType* m_cxBuffer = nullptr;
}; // class StaticArray
////////////////////////////////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////////////////////////////////
consteval void UnitTest()
{
size_t cppArray[] = { 1, 1, 2, 3, 5, 8, 13, 21, 34, 55 };
StaticArray<size_t, 15> sArr = std::move(cppArray); // line 54
}
static_assert((UnitTest(), true), "failed!");
Removing the std::move
from line 54 makes it work correctly in this whittled-down example, but is not acceptable for the full version where I want to distinguish between moving and copying.
Is this a bug with MSVC, or is Clang incorrect in accepting this code?
Upvotes: 0
Views: 150