summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorTimm Baeder <tbaeder@redhat.com>2024-08-22 09:51:16 +0200
committerGitHub <noreply@github.com>2024-08-22 09:51:16 +0200
commitc79d1fa540390f6e37e1ea326153559eeadd0de6 (patch)
tree829b6841a9091431e6f5abd9577ce2a0c28b6301
parente3389365b5d62bc9781dc9a23b14d72e333018d7 (diff)
[clang][bytecode] Don't discard all void-typed expressions (#105625)
For void-types InitListExprs, we need to diagnose them as invalid. But only if we are _not_ discarding.
-rw-r--r--clang/lib/AST/ByteCode/Compiler.cpp23
-rw-r--r--clang/test/AST/ByteCode/literals.cpp1
2 files changed, 10 insertions, 14 deletions
diff --git a/clang/lib/AST/ByteCode/Compiler.cpp b/clang/lib/AST/ByteCode/Compiler.cpp
index 6d05f7513164..10f3222726fd 100644
--- a/clang/lib/AST/ByteCode/Compiler.cpp
+++ b/clang/lib/AST/ByteCode/Compiler.cpp
@@ -1318,15 +1318,6 @@ bool Compiler<Emitter>::VisitArraySubscriptExpr(const ArraySubscriptExpr *E) {
template <class Emitter>
bool Compiler<Emitter>::visitInitList(ArrayRef<const Expr *> Inits,
const Expr *ArrayFiller, const Expr *E) {
-
- QualType QT = E->getType();
-
- if (const auto *AT = QT->getAs<AtomicType>())
- QT = AT->getValueType();
-
- if (QT->isVoidType())
- return this->emitInvalid(E);
-
// Handle discarding first.
if (DiscardResult) {
for (const Expr *Init : Inits) {
@@ -1336,6 +1327,13 @@ bool Compiler<Emitter>::visitInitList(ArrayRef<const Expr *> Inits,
return true;
}
+ QualType QT = E->getType();
+ if (const auto *AT = QT->getAs<AtomicType>())
+ QT = AT->getValueType();
+
+ if (QT->isVoidType())
+ return this->emitInvalid(E);
+
// Primitive values.
if (std::optional<PrimType> T = classify(QT)) {
assert(!DiscardResult);
@@ -3251,12 +3249,9 @@ template <class Emitter> bool Compiler<Emitter>::visit(const Expr *E) {
if (E->getType().isNull())
return false;
- if (E->getType()->isVoidType())
- return this->discard(E);
-
// Create local variable to hold the return value.
- if (!E->isGLValue() && !E->getType()->isAnyComplexType() &&
- !classify(E->getType())) {
+ if (!E->getType()->isVoidType() && !E->isGLValue() &&
+ !E->getType()->isAnyComplexType() && !classify(E->getType())) {
std::optional<unsigned> LocalIndex = allocateLocal(E);
if (!LocalIndex)
return false;
diff --git a/clang/test/AST/ByteCode/literals.cpp b/clang/test/AST/ByteCode/literals.cpp
index a46f6ed747ec..2329d4d973f0 100644
--- a/clang/test/AST/ByteCode/literals.cpp
+++ b/clang/test/AST/ByteCode/literals.cpp
@@ -46,6 +46,7 @@ static_assert(Failed2 == 0, ""); // both-error {{not an integral constant expres
// both-note {{initializer of 'Failed2' is not a constant expression}}
const int x = *(volatile int*)0x1234;
+static_assert((void{}, true), "");
namespace ScalarTypes {
constexpr int ScalarInitInt = int();