[clang][Interp] Pass initializer when creating globals
authorTimm Bäder <tbaeder@redhat.com>
Wed, 14 Sep 2022 13:03:04 +0000 (15:03 +0200)
committerTimm Bäder <tbaeder@redhat.com>
Thu, 29 Sep 2022 10:50:54 +0000 (12:50 +0200)
This is dead code right now but will be used for implementing array
fillers, where we need some information from the initializer when
allocaing the Descriptors.

Differential Revision: https://reviews.llvm.org/D133856

clang/lib/AST/Interp/ByteCodeExprGen.cpp
clang/lib/AST/Interp/Program.cpp
clang/lib/AST/Interp/Program.h

index 0abd3ff..f86a7b1 100644 (file)
@@ -513,18 +513,22 @@ ByteCodeExprGen<Emitter>::allocateLocal(DeclTy &&Src, bool IsExtended) {
   QualType Ty;
 
   const ValueDecl *Key = nullptr;
+  const Expr *Init = nullptr;
   bool IsTemporary = false;
-  if (auto *VD = dyn_cast_or_null<ValueDecl>(Src.dyn_cast<const Decl *>())) {
+  if (auto *VD = dyn_cast_if_present<ValueDecl>(Src.dyn_cast<const Decl *>())) {
     Key = VD;
     Ty = VD->getType();
+
+    if (const auto *VarD = dyn_cast<VarDecl>(VD))
+      Init = VarD->getInit();
   }
   if (auto *E = Src.dyn_cast<const Expr *>()) {
     IsTemporary = true;
     Ty = E->getType();
   }
 
-  Descriptor *D = P.createDescriptor(Src, Ty.getTypePtr(),
-                                     Ty.isConstQualified(), IsTemporary);
+  Descriptor *D = P.createDescriptor(
+      Src, Ty.getTypePtr(), Ty.isConstQualified(), IsTemporary, false, Init);
   if (!D)
     return {};
 
@@ -657,7 +661,7 @@ template <class Emitter>
 bool ByteCodeExprGen<Emitter>::visitDecl(const VarDecl *VD) {
   const Expr *Init = VD->getInit();
 
-  if (Optional<unsigned> I = P.createGlobal(VD)) {
+  if (Optional<unsigned> I = P.createGlobal(VD, Init)) {
     if (Optional<PrimType> T = classify(VD->getType())) {
       {
         // Primitive declarations - compute the value and set it.
index 0d4d84e..aa700a1 100644 (file)
@@ -127,7 +127,7 @@ llvm::Optional<unsigned> Program::getOrCreateGlobal(const ValueDecl *VD) {
   if (auto Idx = getGlobal(VD))
     return Idx;
 
-  if (auto Idx = createGlobal(VD)) {
+  if (auto Idx = createGlobal(VD, nullptr)) {
     GlobalIndices[VD] = *Idx;
     return Idx;
   }
@@ -153,7 +153,8 @@ llvm::Optional<unsigned> Program::getOrCreateDummy(const ParmVarDecl *PD) {
   return {};
 }
 
-llvm::Optional<unsigned> Program::createGlobal(const ValueDecl *VD) {
+llvm::Optional<unsigned> Program::createGlobal(const ValueDecl *VD,
+                                               const Expr *Init) {
   bool IsStatic, IsExtern;
   if (auto *Var = dyn_cast<VarDecl>(VD)) {
     IsStatic = !Var->hasLocalStorage();
@@ -162,7 +163,7 @@ llvm::Optional<unsigned> Program::createGlobal(const ValueDecl *VD) {
     IsStatic = false;
     IsExtern = true;
   }
-  if (auto Idx = createGlobal(VD, VD->getType(), IsStatic, IsExtern)) {
+  if (auto Idx = createGlobal(VD, VD->getType(), IsStatic, IsExtern, Init)) {
     for (const Decl *P = VD; P; P = P->getPreviousDecl())
       GlobalIndices[P] = *Idx;
     return *Idx;
@@ -175,7 +176,8 @@ llvm::Optional<unsigned> Program::createGlobal(const Expr *E) {
 }
 
 llvm::Optional<unsigned> Program::createGlobal(const DeclTy &D, QualType Ty,
-                                               bool IsStatic, bool IsExtern) {
+                                               bool IsStatic, bool IsExtern,
+                                               const Expr *Init) {
   // Create a descriptor for the global.
   Descriptor *Desc;
   const bool IsConst = Ty.isConstQualified();
@@ -310,7 +312,7 @@ Record *Program::getOrCreateRecord(const RecordDecl *RD) {
 
 Descriptor *Program::createDescriptor(const DeclTy &D, const Type *Ty,
                                       bool IsConst, bool IsTemporary,
-                                      bool IsMutable) {
+                                      bool IsMutable, const Expr *Init) {
   // Classes and structures.
   if (auto *RT = Ty->getAs<RecordType>()) {
     if (auto *Record = getOrCreateRecord(RT->getDecl()))
index ca985af..b711bd2 100644 (file)
@@ -69,7 +69,7 @@ public:
   llvm::Optional<unsigned> getOrCreateDummy(const ParmVarDecl *PD);
 
   /// Creates a global and returns its index.
-  llvm::Optional<unsigned> createGlobal(const ValueDecl *VD);
+  llvm::Optional<unsigned> createGlobal(const ValueDecl *VD, const Expr *E);
 
   /// Creates a global from a lifetime-extended temporary.
   llvm::Optional<unsigned> createGlobal(const Expr *E);
@@ -111,7 +111,8 @@ public:
   /// Creates a descriptor for a composite type.
   Descriptor *createDescriptor(const DeclTy &D, const Type *Ty,
                                bool IsConst = false, bool IsTemporary = false,
-                               bool IsMutable = false);
+                               bool IsMutable = false,
+                               const Expr *Init = nullptr);
 
   /// Context to manage declaration lifetimes.
   class DeclScope {
@@ -134,7 +135,8 @@ private:
   friend class DeclScope;
 
   llvm::Optional<unsigned> createGlobal(const DeclTy &D, QualType Ty,
-                                        bool IsStatic, bool IsExtern);
+                                        bool IsStatic, bool IsExtern,
+                                        const Expr *Init = nullptr);
 
   /// Reference to the VM context.
   Context &Ctx;