Skip to content

Commit a52c0c7

Browse files
committed
[clang][Interp] Lazily visit constant locals in C++
While we _do_ get them registered via visitInitializer(), they are still local, so gone on the next call to e.g. evaluateAsRValue(). Visit them lazily, similarly like we do in C.
1 parent 7dcca62 commit a52c0c7

File tree

2 files changed

+22
-3
lines changed

2 files changed

+22
-3
lines changed

clang/lib/AST/Interp/ByteCodeExprGen.cpp

Lines changed: 14 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -3237,9 +3237,20 @@ bool ByteCodeExprGen<Emitter>::VisitDeclRefExpr(const DeclRefExpr *E) {
32373237
// Try to lazily visit (or emit dummy pointers for) declarations
32383238
// we haven't seen yet.
32393239
if (Ctx.getLangOpts().CPlusPlus) {
3240-
if (const auto *VD = dyn_cast<VarDecl>(D); VD && VD->isStaticLocal()) {
3241-
if (std::optional<unsigned> I = P.getOrCreateDummy(D))
3242-
return this->emitGetPtrGlobal(*I, E);
3240+
if (const auto *VD = dyn_cast<VarDecl>(D)) {
3241+
// Dummy for static locals
3242+
if (VD->isStaticLocal()) {
3243+
if (std::optional<unsigned> I = P.getOrCreateDummy(D))
3244+
return this->emitGetPtrGlobal(*I, E);
3245+
return false;
3246+
}
3247+
// Visit local const variables like normal.
3248+
if (VD->isLocalVarDecl() && VD->getType().isConstQualified()) {
3249+
if (!this->visitVarDecl(VD))
3250+
return false;
3251+
// Retry.
3252+
return this->VisitDeclRefExpr(E);
3253+
}
32433254
}
32443255
} else {
32453256
if (const auto *VD = dyn_cast<VarDecl>(D);

clang/test/AST/Interp/arrays.cpp

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -537,3 +537,11 @@ namespace SelfComparison {
537537
return s3->array[t.field] == s3->array[t.field]; // both-warning {{self-comparison always evaluates to true}}
538538
};
539539
}
540+
541+
namespace LocalIndex {
542+
void test() {
543+
const int const_subscript = 3;
544+
int array[2]; // both-note {{declared here}}
545+
array[const_subscript] = 0; // both-warning {{array index 3 is past the end of the array (that has type 'int[2]')}}
546+
}
547+
}

0 commit comments

Comments
 (0)