-
Notifications
You must be signed in to change notification settings - Fork 12.2k
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
explicitly noexcept destructor incorrectly not constexpr #59854
Comments
@llvm/issue-subscribers-clang-frontend |
@llvm/issue-subscribers-bug |
I am not sure who is correct here but I am curious do you except the non-anonymous union case to be the same: #include <vector>
template <typename T>
union U {
constexpr explicit U(std::initializer_list<int> il) : t(il) {}
T t;
};
template <class E>
struct expected {
constexpr explicit expected(std::initializer_list<int> il) : unex(il) {}
constexpr ~expected()
#ifndef MEOW
noexcept
#endif
{ unex.~E(); }
constexpr explicit operator bool() const { return true; }
U<E> unex;
};
struct Data {
std::vector<int> vec_;
constexpr Data(std::initializer_list<int> il) : vec_(il) {}
};
static_assert(expected<Data>({1, 2, 3})); godbolt: https://godbolt.org/z/5q15jK7hn gcc then agrees with clang that this is ill-formed. If you don't think this is the same case can you give me the specific sections of the draft standard that you believe apply to your original case? |
(EDIT: to be perfectly clear, I do not expect the named union case to behave similarly.) They're obviously unrelated, the error conditions are different. Your named union example is ill-formed because the named union has a deleted destructor. In the anonymous union case, The discrepancy here is that Clang believes the destructor call is valid in a constant expression when it has no noexcept-specifier, but not when it does have a noexcept-specifier regardless of whether it's |
CWG2761 clarified that these two cases are not the same. Reduced to a library-free version (https://godbolt.org/z/TGo3P5cGv): struct my_nontrivial {
my_nontrivial() = default;
constexpr ~my_nontrivial() {} // non-trivial
};
struct my_data {
my_data() = default;
#ifdef EXPLICITLY_DEFAUTLING
~my_data() = default;
#endif
my_nontrivial dat_;
};
template <class E>
struct expected {
expected() = default;
constexpr ~expected()
#ifndef MEOW
noexcept
#endif
{ unex.~E(); }
constexpr explicit operator bool() const { return true; }
union { E unex = E(); };
};
static_assert(expected<my_data>{}); It seems that this bug is trigged when the |
This well-formed C++20 TU:
fails to compile if
MEOW
isn't defined (https://godbolt.org/z/qx1nEzvzW):The repro is admittedly not library-free, but it does reproduce with all of libc++, libstdc++, and MSVCSTL - and not with GCC or MSVC - so I'm reasonably confident the bug is in the compiler and not the implementation of
vector
.The text was updated successfully, but these errors were encountered: