Skip to content

Commit

Permalink
[clang][Interp] Support MemberExprs pointing to VarDecls
Browse files Browse the repository at this point in the history
  • Loading branch information
tbaederr committed Apr 16, 2024
1 parent 01f7989 commit c09384e
Show file tree
Hide file tree
Showing 2 changed files with 17 additions and 2 deletions.
11 changes: 9 additions & 2 deletions clang/lib/AST/Interp/ByteCodeExprGen.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1267,10 +1267,19 @@ template <class Emitter>
bool ByteCodeExprGen<Emitter>::VisitMemberExpr(const MemberExpr *E) {
// 'Base.Member'
const Expr *Base = E->getBase();
const ValueDecl *Member = E->getMemberDecl();

if (DiscardResult)
return this->discard(Base);

if (const auto *VD = dyn_cast<VarDecl>(Member)) {
// I am almost confident in saying that a var decl must be static
// and therefore registered as a global variable. But this will probably
// turn out to be wrong some time in the future, as always.
if (auto GlobalIndex = P.getGlobal(VD))
return this->emitGetPtrGlobal(*GlobalIndex, E);
}

if (Initializing) {
if (!this->delegate(Base))
return false;
Expand All @@ -1280,8 +1289,6 @@ bool ByteCodeExprGen<Emitter>::VisitMemberExpr(const MemberExpr *E) {
}

// Base above gives us a pointer on the stack.
// TODO: Implement non-FieldDecl members.
const ValueDecl *Member = E->getMemberDecl();
if (const auto *FD = dyn_cast<FieldDecl>(Member)) {
const RecordDecl *RD = FD->getParent();
const Record *R = getRecord(RD);
Expand Down
8 changes: 8 additions & 0 deletions clang/test/AST/Interp/records.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1309,3 +1309,11 @@ namespace pr18633 {
func2<int>();
}
}

namespace {
struct F {
static constexpr int Z = 12;
};
F f;
static_assert(f.Z == 12, "");
}

0 comments on commit c09384e

Please sign in to comment.