r296806 - Promote ConstantInitBuilder to be a public CodeGen API; it's

John McCall via cfe-commits cfe-commits at lists.llvm.org
Thu Mar 2 12:04:19 PST 2017


Author: rjmccall
Date: Thu Mar  2 14:04:19 2017
New Revision: 296806

URL: http://llvm.org/viewvc/llvm-project?rev=296806&view=rev
Log:
Promote ConstantInitBuilder to be a public CodeGen API; it's
a generally useful utility for other frontends.  NFC.

Added:
    cfe/trunk/include/clang/CodeGen/ConstantInitBuilder.h
      - copied, changed from r296781, cfe/trunk/lib/CodeGen/ConstantBuilder.h
    cfe/trunk/lib/CodeGen/ConstantInitBuilder.cpp
Removed:
    cfe/trunk/lib/CodeGen/ConstantBuilder.h
Modified:
    cfe/trunk/lib/CodeGen/CGBlocks.cpp
    cfe/trunk/lib/CodeGen/CGCUDANV.cpp
    cfe/trunk/lib/CodeGen/CGObjCGNU.cpp
    cfe/trunk/lib/CodeGen/CGObjCMac.cpp
    cfe/trunk/lib/CodeGen/CGOpenMPRuntime.cpp
    cfe/trunk/lib/CodeGen/CGVTables.cpp
    cfe/trunk/lib/CodeGen/CMakeLists.txt
    cfe/trunk/lib/CodeGen/CodeGenModule.cpp
    cfe/trunk/lib/CodeGen/ItaniumCXXABI.cpp
    cfe/trunk/lib/CodeGen/MicrosoftCXXABI.cpp

Copied: cfe/trunk/include/clang/CodeGen/ConstantInitBuilder.h (from r296781, cfe/trunk/lib/CodeGen/ConstantBuilder.h)
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/CodeGen/ConstantInitBuilder.h?p2=cfe/trunk/include/clang/CodeGen/ConstantInitBuilder.h&p1=cfe/trunk/lib/CodeGen/ConstantBuilder.h&r1=296781&r2=296806&rev=296806&view=diff
==============================================================================
--- cfe/trunk/lib/CodeGen/ConstantBuilder.h (original)
+++ cfe/trunk/include/clang/CodeGen/ConstantInitBuilder.h Thu Mar  2 14:04:19 2017
@@ -1,4 +1,4 @@
-//===----- ConstantBuilder.h - Builder for LLVM IR constants ----*- C++ -*-===//
+//===- ConstantInitBuilder.h - Builder for LLVM IR constants ----*- C++ -*-===//
 //
 //                     The LLVM Compiler Infrastructure
 //
@@ -8,24 +8,26 @@
 //===----------------------------------------------------------------------===//
 //
 // This class provides a convenient interface for building complex
-// global initializers.
+// global initializers of the sort that are frequently required for
+// language ABIs.
 //
 //===----------------------------------------------------------------------===//
 
-#ifndef LLVM_CLANG_LIB_CODEGEN_CONSTANTBUILDER_H
-#define LLVM_CLANG_LIB_CODEGEN_CONSTANTBUILDER_H
+#ifndef LLVM_CLANG_CODEGEN_CONSTANTINITBUILDER_H
+#define LLVM_CLANG_CODEGEN_CONSTANTINITBUILDER_H
 
 #include "llvm/ADT/ArrayRef.h"
 #include "llvm/ADT/SmallVector.h"
 #include "llvm/IR/Constants.h"
-
-#include "CodeGenModule.h"
+#include "llvm/IR/GlobalValue.h"
+#include "clang/AST/CharUnits.h"
 
 #include <vector>
 
 namespace clang {
 namespace CodeGen {
 
+class CodeGenModule;
 class ConstantStructBuilder;
 class ConstantArrayBuilder;
 
@@ -144,9 +146,7 @@ public:
     }
 
     /// Add an integer value of type size_t.
-    void addSize(CharUnits size) {
-      add(Builder.CGM.getSize(size));
-    }
+    void addSize(CharUnits size);
 
     /// Add an integer value of a specific type.
     void addInt(llvm::IntegerType *intTy, uint64_t value,
@@ -165,7 +165,7 @@ public:
     }
 
     /// Add a bunch of new values to this initializer.
-    void addAll(ArrayRef<llvm::Constant *> values) {
+    void addAll(llvm::ArrayRef<llvm::Constant *> values) {
       assert(!Finished && "cannot add more values after finishing builder");
       assert(!Frozen && "cannot add values while subbuilder is active");
       Builder.Buffer.append(values.begin(), values.end());
@@ -216,20 +216,9 @@ public:
     ///
     /// The returned pointer will have type T*, where T is the given
     /// position.
-    llvm::Constant *getAddrOfCurrentPosition(llvm::Type *type) {
-      // Make a global variable.  We will replace this with a GEP to this
-      // position after installing the initializer.
-      auto dummy =
-        new llvm::GlobalVariable(Builder.CGM.getModule(), type, true,
-                                 llvm::GlobalVariable::PrivateLinkage,
-                                 nullptr, "");
-      Builder.SelfReferences.emplace_back(dummy);
-      auto &entry = Builder.SelfReferences.back();
-      (void) getGEPIndicesToCurrentPosition(entry.Indices);
-      return dummy;
-    }
+    llvm::Constant *getAddrOfCurrentPosition(llvm::Type *type);
 
-    ArrayRef<llvm::Constant*> getGEPIndicesToCurrentPosition(
+    llvm::ArrayRef<llvm::Constant*> getGEPIndicesToCurrentPosition(
                              llvm::SmallVectorImpl<llvm::Constant*> &indices) {
       getGEPIndicesTo(indices, Builder.Buffer.size());
       return indices;
@@ -240,23 +229,7 @@ public:
 
   private:
     void getGEPIndicesTo(llvm::SmallVectorImpl<llvm::Constant*> &indices,
-                         size_t position) const {
-      // Recurse on the parent builder if present.
-      if (Parent) {
-        Parent->getGEPIndicesTo(indices, Begin);
-
-      // Otherwise, add an index to drill into the first level of pointer. 
-      } else {
-        assert(indices.empty());
-        indices.push_back(llvm::ConstantInt::get(Builder.CGM.Int32Ty, 0));
-      }
-
-      assert(position >= Begin);
-      // We have to use i32 here because struct GEPs demand i32 indices.
-      // It's rather unlikely to matter in practice.
-      indices.push_back(llvm::ConstantInt::get(Builder.CGM.Int32Ty,
-                                               position - Begin));
-    }
+                         size_t position) const;
   };
 
   template <class Impl>
@@ -313,36 +286,12 @@ private:
                                      bool constant = false,
                                      llvm::GlobalValue::LinkageTypes linkage
                                        = llvm::GlobalValue::InternalLinkage,
-                                     unsigned addressSpace = 0) {
-    auto GV = new llvm::GlobalVariable(CGM.getModule(),
-                                       initializer->getType(),
-                                       constant,
-                                       linkage,
-                                       initializer,
-                                       name,
-                                       /*insert before*/ nullptr,
-                                       llvm::GlobalValue::NotThreadLocal,
-                                       addressSpace);
-    GV->setAlignment(alignment.getQuantity());
-    resolveSelfReferences(GV);
-    return GV;
-  }
+                                     unsigned addressSpace = 0);
 
   void setGlobalInitializer(llvm::GlobalVariable *GV,
-                            llvm::Constant *initializer) {
-    GV->setInitializer(initializer);
-    resolveSelfReferences(GV);
-  }
+                            llvm::Constant *initializer);
 
-  void resolveSelfReferences(llvm::GlobalVariable *GV) {
-    for (auto &entry : SelfReferences) {
-      llvm::Constant *resolvedReference =
-        llvm::ConstantExpr::getInBoundsGetElementPtr(
-          GV->getValueType(), GV, entry.Indices);
-      entry.Dummy->replaceAllUsesWith(resolvedReference);
-      entry.Dummy->eraseFromParent();
-    }
-  }
+  void resolveSelfReferences(llvm::GlobalVariable *GV);
 };
 
 /// A helper class of ConstantInitBuilder, used for building constant
@@ -370,20 +319,7 @@ public:
 private:
   /// Form an array constant from the values that have been added to this
   /// builder.
-  llvm::Constant *finishImpl() {
-    markFinished();
-
-    auto &buffer = getBuffer();
-    assert((Begin < buffer.size() ||
-            (Begin == buffer.size() && EltTy))
-           && "didn't add any array elements without element type");
-    auto elts = llvm::makeArrayRef(buffer).slice(Begin);
-    auto eltTy = EltTy ? EltTy : elts[0]->getType();
-    auto type = llvm::ArrayType::get(eltTy, elts.size());
-    auto constant = llvm::ConstantArray::get(type, elts);
-    buffer.erase(buffer.begin() + Begin, buffer.end());
-    return constant;
-  }
+  llvm::Constant *finishImpl();
 };
 
 inline ConstantArrayBuilder
@@ -408,23 +344,7 @@ class ConstantStructBuilder
     : AggregateBuilder(builder, parent), Ty(ty) {}
 
   /// Finish the struct.
-  llvm::Constant *finishImpl() {
-    markFinished();
-
-    auto &buffer = getBuffer();
-    assert(Begin < buffer.size() && "didn't add any struct elements?");
-    auto elts = llvm::makeArrayRef(buffer).slice(Begin);
-
-    llvm::Constant *constant;
-    if (Ty) {
-      constant = llvm::ConstantStruct::get(Ty, elts);
-    } else {
-      constant = llvm::ConstantStruct::getAnon(elts, /*packed*/ false);
-    }
-
-    buffer.erase(buffer.begin() + Begin, buffer.end());
-    return constant;
-  }
+  llvm::Constant *finishImpl();
 };
 
 inline ConstantStructBuilder

Modified: cfe/trunk/lib/CodeGen/CGBlocks.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/CGBlocks.cpp?rev=296806&r1=296805&r2=296806&view=diff
==============================================================================
--- cfe/trunk/lib/CodeGen/CGBlocks.cpp (original)
+++ cfe/trunk/lib/CodeGen/CGBlocks.cpp Thu Mar  2 14:04:19 2017
@@ -16,7 +16,7 @@
 #include "CGObjCRuntime.h"
 #include "CodeGenFunction.h"
 #include "CodeGenModule.h"
-#include "ConstantBuilder.h"
+#include "clang/CodeGen/ConstantInitBuilder.h"
 #include "clang/AST/DeclObjC.h"
 #include "llvm/ADT/SmallSet.h"
 #include "llvm/IR/CallSite.h"

Modified: cfe/trunk/lib/CodeGen/CGCUDANV.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/CGCUDANV.cpp?rev=296806&r1=296805&r2=296806&view=diff
==============================================================================
--- cfe/trunk/lib/CodeGen/CGCUDANV.cpp (original)
+++ cfe/trunk/lib/CodeGen/CGCUDANV.cpp Thu Mar  2 14:04:19 2017
@@ -15,7 +15,7 @@
 #include "CGCUDARuntime.h"
 #include "CodeGenFunction.h"
 #include "CodeGenModule.h"
-#include "ConstantBuilder.h"
+#include "clang/CodeGen/ConstantInitBuilder.h"
 #include "clang/AST/Decl.h"
 #include "llvm/IR/BasicBlock.h"
 #include "llvm/IR/CallSite.h"

Modified: cfe/trunk/lib/CodeGen/CGObjCGNU.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/CGObjCGNU.cpp?rev=296806&r1=296805&r2=296806&view=diff
==============================================================================
--- cfe/trunk/lib/CodeGen/CGObjCGNU.cpp (original)
+++ cfe/trunk/lib/CodeGen/CGObjCGNU.cpp Thu Mar  2 14:04:19 2017
@@ -18,7 +18,7 @@
 #include "CGCleanup.h"
 #include "CodeGenFunction.h"
 #include "CodeGenModule.h"
-#include "ConstantBuilder.h"
+#include "clang/CodeGen/ConstantInitBuilder.h"
 #include "clang/AST/ASTContext.h"
 #include "clang/AST/Decl.h"
 #include "clang/AST/DeclObjC.h"

Modified: cfe/trunk/lib/CodeGen/CGObjCMac.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/CGObjCMac.cpp?rev=296806&r1=296805&r2=296806&view=diff
==============================================================================
--- cfe/trunk/lib/CodeGen/CGObjCMac.cpp (original)
+++ cfe/trunk/lib/CodeGen/CGObjCMac.cpp Thu Mar  2 14:04:19 2017
@@ -17,7 +17,7 @@
 #include "CGRecordLayout.h"
 #include "CodeGenFunction.h"
 #include "CodeGenModule.h"
-#include "ConstantBuilder.h"
+#include "clang/CodeGen/ConstantInitBuilder.h"
 #include "clang/AST/ASTContext.h"
 #include "clang/AST/Decl.h"
 #include "clang/AST/DeclObjC.h"

Modified: cfe/trunk/lib/CodeGen/CGOpenMPRuntime.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/CGOpenMPRuntime.cpp?rev=296806&r1=296805&r2=296806&view=diff
==============================================================================
--- cfe/trunk/lib/CodeGen/CGOpenMPRuntime.cpp (original)
+++ cfe/trunk/lib/CodeGen/CGOpenMPRuntime.cpp Thu Mar  2 14:04:19 2017
@@ -15,7 +15,7 @@
 #include "CGCleanup.h"
 #include "CGOpenMPRuntime.h"
 #include "CodeGenFunction.h"
-#include "ConstantBuilder.h"
+#include "clang/CodeGen/ConstantInitBuilder.h"
 #include "clang/AST/Decl.h"
 #include "clang/AST/StmtOpenMP.h"
 #include "llvm/ADT/ArrayRef.h"

Modified: cfe/trunk/lib/CodeGen/CGVTables.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/CGVTables.cpp?rev=296806&r1=296805&r2=296806&view=diff
==============================================================================
--- cfe/trunk/lib/CodeGen/CGVTables.cpp (original)
+++ cfe/trunk/lib/CodeGen/CGVTables.cpp Thu Mar  2 14:04:19 2017
@@ -14,7 +14,7 @@
 #include "CGCXXABI.h"
 #include "CodeGenFunction.h"
 #include "CodeGenModule.h"
-#include "ConstantBuilder.h"
+#include "clang/CodeGen/ConstantInitBuilder.h"
 #include "clang/AST/CXXInheritance.h"
 #include "clang/AST/RecordLayout.h"
 #include "clang/CodeGen/CGFunctionInfo.h"

Modified: cfe/trunk/lib/CodeGen/CMakeLists.txt
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/CMakeLists.txt?rev=296806&r1=296805&r2=296806&view=diff
==============================================================================
--- cfe/trunk/lib/CodeGen/CMakeLists.txt (original)
+++ cfe/trunk/lib/CodeGen/CMakeLists.txt Thu Mar  2 14:04:19 2017
@@ -75,6 +75,7 @@ add_clang_library(clangCodeGen
   CodeGenPGO.cpp
   CodeGenTBAA.cpp
   CodeGenTypes.cpp
+  ConstantInitBuilder.cpp
   CoverageMappingGen.cpp
   ItaniumCXXABI.cpp
   MacroPPCallbacks.cpp

Modified: cfe/trunk/lib/CodeGen/CodeGenModule.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/CodeGenModule.cpp?rev=296806&r1=296805&r2=296806&view=diff
==============================================================================
--- cfe/trunk/lib/CodeGen/CodeGenModule.cpp (original)
+++ cfe/trunk/lib/CodeGen/CodeGenModule.cpp Thu Mar  2 14:04:19 2017
@@ -24,7 +24,6 @@
 #include "CodeGenFunction.h"
 #include "CodeGenPGO.h"
 #include "CodeGenTBAA.h"
-#include "ConstantBuilder.h"
 #include "CoverageMappingGen.h"
 #include "TargetInfo.h"
 #include "clang/AST/ASTContext.h"
@@ -42,6 +41,7 @@
 #include "clang/Basic/SourceManager.h"
 #include "clang/Basic/TargetInfo.h"
 #include "clang/Basic/Version.h"
+#include "clang/CodeGen/ConstantInitBuilder.h"
 #include "clang/Frontend/CodeGenOptions.h"
 #include "clang/Sema/SemaDiagnostic.h"
 #include "llvm/ADT/Triple.h"

Removed: cfe/trunk/lib/CodeGen/ConstantBuilder.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/ConstantBuilder.h?rev=296805&view=auto
==============================================================================
--- cfe/trunk/lib/CodeGen/ConstantBuilder.h (original)
+++ cfe/trunk/lib/CodeGen/ConstantBuilder.h (removed)
@@ -1,444 +0,0 @@
-//===----- ConstantBuilder.h - Builder for LLVM IR constants ----*- C++ -*-===//
-//
-//                     The LLVM Compiler Infrastructure
-//
-// This file is distributed under the University of Illinois Open Source
-// License. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-//
-// This class provides a convenient interface for building complex
-// global initializers.
-//
-//===----------------------------------------------------------------------===//
-
-#ifndef LLVM_CLANG_LIB_CODEGEN_CONSTANTBUILDER_H
-#define LLVM_CLANG_LIB_CODEGEN_CONSTANTBUILDER_H
-
-#include "llvm/ADT/ArrayRef.h"
-#include "llvm/ADT/SmallVector.h"
-#include "llvm/IR/Constants.h"
-
-#include "CodeGenModule.h"
-
-#include <vector>
-
-namespace clang {
-namespace CodeGen {
-
-class ConstantStructBuilder;
-class ConstantArrayBuilder;
-
-/// A convenience builder class for complex constant initializers,
-/// especially for anonymous global structures used by various language
-/// runtimes.
-///
-/// The basic usage pattern is expected to be something like:
-///    ConstantInitBuilder builder(CGM);
-///    auto toplevel = builder.beginStruct();
-///    toplevel.addInt(CGM.SizeTy, widgets.size());
-///    auto widgetArray = builder.beginArray();
-///    for (auto &widget : widgets) {
-///      auto widgetDesc = widgetArray.beginStruct();
-///      widgetDesc.addInt(CGM.SizeTy, widget.getPower());
-///      widgetDesc.add(CGM.GetAddrOfConstantString(widget.getName()));
-///      widgetDesc.add(CGM.GetAddrOfGlobal(widget.getInitializerDecl()));
-///      widgetArray.add(widgetDesc.finish());
-///    }
-///    toplevel.add(widgetArray.finish());
-///    auto global = toplevel.finishAndCreateGlobal("WIDGET_LIST", Align,
-///                                                 /*constant*/ true);
-class ConstantInitBuilder {
-  struct SelfReference {
-    llvm::GlobalVariable *Dummy;
-    llvm::SmallVector<llvm::Constant*, 4> Indices;
-
-    SelfReference(llvm::GlobalVariable *dummy) : Dummy(dummy) {}
-  };
-  CodeGenModule &CGM;
-  llvm::SmallVector<llvm::Constant*, 16> Buffer;
-  std::vector<SelfReference> SelfReferences;
-  bool Frozen = false;
-
-public:
-  explicit ConstantInitBuilder(CodeGenModule &CGM) : CGM(CGM) {}
-
-  ~ConstantInitBuilder() {
-    assert(Buffer.empty() && "didn't claim all values out of buffer");
-  }
-
-  class AggregateBuilderBase {
-  protected:
-    ConstantInitBuilder &Builder;
-    AggregateBuilderBase *Parent;
-    size_t Begin;
-    bool Finished = false;
-    bool Frozen = false;
-
-    llvm::SmallVectorImpl<llvm::Constant*> &getBuffer() {
-      return Builder.Buffer;
-    }
-
-    const llvm::SmallVectorImpl<llvm::Constant*> &getBuffer() const {
-      return Builder.Buffer;
-    }
-
-    AggregateBuilderBase(ConstantInitBuilder &builder,
-                         AggregateBuilderBase *parent)
-        : Builder(builder), Parent(parent), Begin(builder.Buffer.size()) {
-      if (parent) {
-        assert(!parent->Frozen && "parent already has child builder active");
-        parent->Frozen = true;
-      } else {
-        assert(!builder.Frozen && "builder already has child builder active");
-        builder.Frozen = true;
-      }
-    }
-
-    ~AggregateBuilderBase() {
-      assert(Finished && "didn't finish aggregate builder");
-    }
-
-    void markFinished() {
-      assert(!Frozen && "child builder still active");
-      assert(!Finished && "builder already finished");
-      Finished = true;
-      if (Parent) {
-        assert(Parent->Frozen &&
-               "parent not frozen while child builder active");
-        Parent->Frozen = false;
-      } else {
-        assert(Builder.Frozen &&
-               "builder not frozen while child builder active");
-        Builder.Frozen = false;
-      }
-    }
-
-  public:
-    // Not copyable.
-    AggregateBuilderBase(const AggregateBuilderBase &) = delete;
-    AggregateBuilderBase &operator=(const AggregateBuilderBase &) = delete;
-
-    // Movable, mostly to allow returning.  But we have to write this out
-    // properly to satisfy the assert in the destructor.
-    AggregateBuilderBase(AggregateBuilderBase &&other)
-      : Builder(other.Builder), Parent(other.Parent), Begin(other.Begin),
-        Finished(other.Finished), Frozen(other.Frozen) {
-      other.Finished = false;
-    }
-    AggregateBuilderBase &operator=(AggregateBuilderBase &&other) = delete;
-
-    /// Abandon this builder completely.
-    void abandon() {
-      markFinished();
-      auto &buffer = Builder.Buffer;
-      buffer.erase(buffer.begin() + Begin, buffer.end());
-    }
-
-    /// Add a new value to this initializer.
-    void add(llvm::Constant *value) {
-      assert(value && "adding null value to constant initializer");
-      assert(!Finished && "cannot add more values after finishing builder");
-      assert(!Frozen && "cannot add values while subbuilder is active");
-      Builder.Buffer.push_back(value);
-    }
-
-    /// Add an integer value of type size_t.
-    void addSize(CharUnits size) {
-      add(Builder.CGM.getSize(size));
-    }
-
-    /// Add an integer value of a specific type.
-    void addInt(llvm::IntegerType *intTy, uint64_t value,
-                bool isSigned = false) {
-      add(llvm::ConstantInt::get(intTy, value, isSigned));
-    }
-
-    /// Add a null pointer of a specific type.
-    void addNullPointer(llvm::PointerType *ptrTy) {
-      add(llvm::ConstantPointerNull::get(ptrTy));
-    }
-
-    /// Add a bitcast of a value to a specific type.
-    void addBitCast(llvm::Constant *value, llvm::Type *type) {
-      add(llvm::ConstantExpr::getBitCast(value, type));
-    }
-
-    /// Add a bunch of new values to this initializer.
-    void addAll(ArrayRef<llvm::Constant *> values) {
-      assert(!Finished && "cannot add more values after finishing builder");
-      assert(!Frozen && "cannot add values while subbuilder is active");
-      Builder.Buffer.append(values.begin(), values.end());
-    }
-
-    /// An opaque class to hold the abstract position of a placeholder.
-    class PlaceholderPosition {
-      size_t Index;
-      friend class AggregateBuilderBase;
-      PlaceholderPosition(size_t index) : Index(index) {}
-    };
-
-    /// Add a placeholder value to the structure.  The returned position
-    /// can be used to set the value later; it will not be invalidated by
-    /// any intermediate operations except (1) filling the same position or
-    /// (2) finishing the entire builder.
-    ///
-    /// This is useful for emitting certain kinds of structure which
-    /// contain some sort of summary field, generaly a count, before any
-    /// of the data.  By emitting a placeholder first, the structure can
-    /// be emitted eagerly.
-    PlaceholderPosition addPlaceholder() {
-      assert(!Finished && "cannot add more values after finishing builder");
-      assert(!Frozen && "cannot add values while subbuilder is active");
-      Builder.Buffer.push_back(nullptr);
-      return Builder.Buffer.size() - 1;
-    }
-
-    /// Fill a previously-added placeholder.
-    void fillPlaceholderWithInt(PlaceholderPosition position,
-                                llvm::IntegerType *type, uint64_t value,
-                                bool isSigned = false) {
-      fillPlaceholder(position, llvm::ConstantInt::get(type, value, isSigned));
-    }
-
-    /// Fill a previously-added placeholder.
-    void fillPlaceholder(PlaceholderPosition position, llvm::Constant *value) {
-      assert(!Finished && "cannot change values after finishing builder");
-      assert(!Frozen && "cannot add values while subbuilder is active");
-      llvm::Constant *&slot = Builder.Buffer[position.Index];
-      assert(slot == nullptr && "placeholder already filled");
-      slot = value;
-    }
-
-    /// Produce an address which will eventually point to the the next
-    /// position to be filled.  This is computed with an indexed
-    /// getelementptr rather than by computing offsets.
-    ///
-    /// The returned pointer will have type T*, where T is the given
-    /// position.
-    llvm::Constant *getAddrOfCurrentPosition(llvm::Type *type) {
-      // Make a global variable.  We will replace this with a GEP to this
-      // position after installing the initializer.
-      auto dummy =
-        new llvm::GlobalVariable(Builder.CGM.getModule(), type, true,
-                                 llvm::GlobalVariable::PrivateLinkage,
-                                 nullptr, "");
-      Builder.SelfReferences.emplace_back(dummy);
-      auto &entry = Builder.SelfReferences.back();
-      (void) getGEPIndicesToCurrentPosition(entry.Indices);
-      return dummy;
-    }
-
-    ArrayRef<llvm::Constant*> getGEPIndicesToCurrentPosition(
-                             llvm::SmallVectorImpl<llvm::Constant*> &indices) {
-      getGEPIndicesTo(indices, Builder.Buffer.size());
-      return indices;
-    }
-
-    ConstantArrayBuilder beginArray(llvm::Type *eltTy = nullptr);
-    ConstantStructBuilder beginStruct(llvm::StructType *structTy = nullptr);
-
-  private:
-    void getGEPIndicesTo(llvm::SmallVectorImpl<llvm::Constant*> &indices,
-                         size_t position) const {
-      // Recurse on the parent builder if present.
-      if (Parent) {
-        Parent->getGEPIndicesTo(indices, Begin);
-
-      // Otherwise, add an index to drill into the first level of pointer. 
-      } else {
-        assert(indices.empty());
-        indices.push_back(llvm::ConstantInt::get(Builder.CGM.Int32Ty, 0));
-      }
-
-      assert(position >= Begin);
-      // We have to use i32 here because struct GEPs demand i32 indices.
-      // It's rather unlikely to matter in practice.
-      indices.push_back(llvm::ConstantInt::get(Builder.CGM.Int32Ty,
-                                               position - Begin));
-    }
-  };
-
-  template <class Impl>
-  class AggregateBuilder : public AggregateBuilderBase {
-  protected:
-    AggregateBuilder(ConstantInitBuilder &builder,
-                     AggregateBuilderBase *parent)
-      : AggregateBuilderBase(builder, parent) {}
-
-    Impl &asImpl() { return *static_cast<Impl*>(this); }
-
-  public:
-    /// Given that this builder was created by beginning an array or struct
-    /// component on the given parent builder, finish the array/struct
-    /// component and add it to the parent.
-    ///
-    /// It is an intentional choice that the parent is passed in explicitly
-    /// despite it being redundant with information already kept in the
-    /// builder.  This aids in readability by making it easier to find the
-    /// places that add components to a builder, as well as "bookending"
-    /// the sub-builder more explicitly.
-    void finishAndAddTo(AggregateBuilderBase &parent) {
-      assert(Parent == &parent && "adding to non-parent builder");
-      parent.add(asImpl().finishImpl());
-    }
-
-    /// Given that this builder was created by beginning an array or struct
-    /// directly on a ConstantInitBuilder, finish the array/struct and
-    /// create a global variable with it as the initializer.
-    template <class... As>
-    llvm::GlobalVariable *finishAndCreateGlobal(As &&...args) {
-      assert(!Parent && "finishing non-root builder");
-      return Builder.createGlobal(asImpl().finishImpl(),
-                                  std::forward<As>(args)...);
-    }
-
-    /// Given that this builder was created by beginning an array or struct
-    /// directly on a ConstantInitBuilder, finish the array/struct and
-    /// set it as the initializer of the given global variable.
-    void finishAndSetAsInitializer(llvm::GlobalVariable *global) {
-      assert(!Parent && "finishing non-root builder");
-      return Builder.setGlobalInitializer(global, asImpl().finishImpl());
-    }
-  };
-
-  ConstantArrayBuilder beginArray(llvm::Type *eltTy = nullptr);
-
-  ConstantStructBuilder beginStruct(llvm::StructType *structTy = nullptr);
-
-private:
-  llvm::GlobalVariable *createGlobal(llvm::Constant *initializer,
-                                     const llvm::Twine &name,
-                                     CharUnits alignment,
-                                     bool constant = false,
-                                     llvm::GlobalValue::LinkageTypes linkage
-                                       = llvm::GlobalValue::InternalLinkage,
-                                     unsigned addressSpace = 0) {
-    auto GV = new llvm::GlobalVariable(CGM.getModule(),
-                                       initializer->getType(),
-                                       constant,
-                                       linkage,
-                                       initializer,
-                                       name,
-                                       /*insert before*/ nullptr,
-                                       llvm::GlobalValue::NotThreadLocal,
-                                       addressSpace);
-    GV->setAlignment(alignment.getQuantity());
-    resolveSelfReferences(GV);
-    return GV;
-  }
-
-  void setGlobalInitializer(llvm::GlobalVariable *GV,
-                            llvm::Constant *initializer) {
-    GV->setInitializer(initializer);
-    resolveSelfReferences(GV);
-  }
-
-  void resolveSelfReferences(llvm::GlobalVariable *GV) {
-    for (auto &entry : SelfReferences) {
-      llvm::Constant *resolvedReference =
-        llvm::ConstantExpr::getInBoundsGetElementPtr(
-          GV->getValueType(), GV, entry.Indices);
-      entry.Dummy->replaceAllUsesWith(resolvedReference);
-      entry.Dummy->eraseFromParent();
-    }
-  }
-};
-
-/// A helper class of ConstantInitBuilder, used for building constant
-/// array initializers.
-class ConstantArrayBuilder
-    : public ConstantInitBuilder::AggregateBuilder<ConstantArrayBuilder> {
-  llvm::Type *EltTy;
-  friend class ConstantInitBuilder;
-  template <class Impl> friend class ConstantInitBuilder::AggregateBuilder;
-  ConstantArrayBuilder(ConstantInitBuilder &builder,
-                       AggregateBuilderBase *parent, llvm::Type *eltTy)
-    : AggregateBuilder(builder, parent), EltTy(eltTy) {}
-public:
-  size_t size() const {
-    assert(!Finished);
-    assert(!Frozen);
-    assert(Begin <= getBuffer().size());
-    return getBuffer().size() - Begin;
-  }
-
-  bool empty() const {
-    return size() == 0;
-  }
-
-private:
-  /// Form an array constant from the values that have been added to this
-  /// builder.
-  llvm::Constant *finishImpl() {
-    markFinished();
-
-    auto &buffer = getBuffer();
-    assert((Begin < buffer.size() ||
-            (Begin == buffer.size() && EltTy))
-           && "didn't add any array elements without element type");
-    auto elts = llvm::makeArrayRef(buffer).slice(Begin);
-    auto eltTy = EltTy ? EltTy : elts[0]->getType();
-    auto type = llvm::ArrayType::get(eltTy, elts.size());
-    auto constant = llvm::ConstantArray::get(type, elts);
-    buffer.erase(buffer.begin() + Begin, buffer.end());
-    return constant;
-  }
-};
-
-inline ConstantArrayBuilder
-ConstantInitBuilder::beginArray(llvm::Type *eltTy) {
-  return ConstantArrayBuilder(*this, nullptr, eltTy);
-}
-
-inline ConstantArrayBuilder
-ConstantInitBuilder::AggregateBuilderBase::beginArray(llvm::Type *eltTy) {
-  return ConstantArrayBuilder(Builder, this, eltTy);
-}
-
-/// A helper class of ConstantInitBuilder, used for building constant
-/// struct initializers.
-class ConstantStructBuilder
-    : public ConstantInitBuilder::AggregateBuilder<ConstantStructBuilder> {
-  llvm::StructType *Ty;
-  friend class ConstantInitBuilder;
-  template <class Impl> friend class ConstantInitBuilder::AggregateBuilder;
-  ConstantStructBuilder(ConstantInitBuilder &builder,
-                        AggregateBuilderBase *parent, llvm::StructType *ty)
-    : AggregateBuilder(builder, parent), Ty(ty) {}
-
-  /// Finish the struct.
-  llvm::Constant *finishImpl() {
-    markFinished();
-
-    auto &buffer = getBuffer();
-    assert(Begin < buffer.size() && "didn't add any struct elements?");
-    auto elts = llvm::makeArrayRef(buffer).slice(Begin);
-
-    llvm::Constant *constant;
-    if (Ty) {
-      constant = llvm::ConstantStruct::get(Ty, elts);
-    } else {
-      constant = llvm::ConstantStruct::getAnon(elts, /*packed*/ false);
-    }
-
-    buffer.erase(buffer.begin() + Begin, buffer.end());
-    return constant;
-  }
-};
-
-inline ConstantStructBuilder
-ConstantInitBuilder::beginStruct(llvm::StructType *structTy) {
-  return ConstantStructBuilder(*this, nullptr, structTy);
-}
-
-inline ConstantStructBuilder
-ConstantInitBuilder::AggregateBuilderBase::beginStruct(
-                                                  llvm::StructType *structTy) {
-  return ConstantStructBuilder(Builder, this, structTy);
-}
-
-}  // end namespace CodeGen
-}  // end namespace clang
-
-#endif

Added: cfe/trunk/lib/CodeGen/ConstantInitBuilder.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/ConstantInitBuilder.cpp?rev=296806&view=auto
==============================================================================
--- cfe/trunk/lib/CodeGen/ConstantInitBuilder.cpp (added)
+++ cfe/trunk/lib/CodeGen/ConstantInitBuilder.cpp Thu Mar  2 14:04:19 2017
@@ -0,0 +1,131 @@
+//===--- ConstantInitBuilder.cpp - Global initializer builder -------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+//
+// This file defines out-of-line routines for building initializers for
+// global variables, in particular the kind of globals that are implicitly
+// introduced by various language ABIs.
+//
+//===----------------------------------------------------------------------===//
+
+#include "clang/CodeGen/ConstantInitBuilder.h"
+#include "CodeGenModule.h"
+
+using namespace clang;
+using namespace CodeGen;
+
+llvm::GlobalVariable *
+ConstantInitBuilder::createGlobal(llvm::Constant *initializer,
+                                  const llvm::Twine &name,
+                                  CharUnits alignment,
+                                  bool constant,
+                                  llvm::GlobalValue::LinkageTypes linkage,
+                                  unsigned addressSpace) {
+  auto GV = new llvm::GlobalVariable(CGM.getModule(),
+                                     initializer->getType(),
+                                     constant,
+                                     linkage,
+                                     initializer,
+                                     name,
+                                     /*insert before*/ nullptr,
+                                     llvm::GlobalValue::NotThreadLocal,
+                                     addressSpace);
+  GV->setAlignment(alignment.getQuantity());
+  resolveSelfReferences(GV);
+  return GV;
+}
+
+void ConstantInitBuilder::setGlobalInitializer(llvm::GlobalVariable *GV,
+                                               llvm::Constant *initializer) {
+  GV->setInitializer(initializer);
+
+  if (!SelfReferences.empty())
+    resolveSelfReferences(GV);
+}
+
+void ConstantInitBuilder::resolveSelfReferences(llvm::GlobalVariable *GV) {
+  for (auto &entry : SelfReferences) {
+    llvm::Constant *resolvedReference =
+      llvm::ConstantExpr::getInBoundsGetElementPtr(
+        GV->getValueType(), GV, entry.Indices);
+    entry.Dummy->replaceAllUsesWith(resolvedReference);
+    entry.Dummy->eraseFromParent();
+  }
+}
+
+void ConstantInitBuilder::AggregateBuilderBase::addSize(CharUnits size) {
+  add(Builder.CGM.getSize(size));
+}
+
+llvm::Constant *
+ConstantInitBuilder::AggregateBuilderBase::getAddrOfCurrentPosition(
+                                                            llvm::Type *type) {
+  // Make a global variable.  We will replace this with a GEP to this
+  // position after installing the initializer.
+  auto dummy =
+    new llvm::GlobalVariable(Builder.CGM.getModule(), type, true,
+                             llvm::GlobalVariable::PrivateLinkage,
+                             nullptr, "");
+  Builder.SelfReferences.emplace_back(dummy);
+  auto &entry = Builder.SelfReferences.back();
+  (void) getGEPIndicesToCurrentPosition(entry.Indices);
+  return dummy;
+}
+
+void ConstantInitBuilder::AggregateBuilderBase::getGEPIndicesTo(
+                               llvm::SmallVectorImpl<llvm::Constant*> &indices,
+                               size_t position) const {
+  // Recurse on the parent builder if present.
+  if (Parent) {
+    Parent->getGEPIndicesTo(indices, Begin);
+
+  // Otherwise, add an index to drill into the first level of pointer. 
+  } else {
+    assert(indices.empty());
+    indices.push_back(llvm::ConstantInt::get(Builder.CGM.Int32Ty, 0));
+  }
+
+  assert(position >= Begin);
+  // We have to use i32 here because struct GEPs demand i32 indices.
+  // It's rather unlikely to matter in practice.
+  indices.push_back(llvm::ConstantInt::get(Builder.CGM.Int32Ty,
+                                           position - Begin));
+}
+
+llvm::Constant *ConstantArrayBuilder::finishImpl() {
+  markFinished();
+
+  auto &buffer = getBuffer();
+  assert((Begin < buffer.size() ||
+          (Begin == buffer.size() && EltTy))
+         && "didn't add any array elements without element type");
+  auto elts = llvm::makeArrayRef(buffer).slice(Begin);
+  auto eltTy = EltTy ? EltTy : elts[0]->getType();
+  auto type = llvm::ArrayType::get(eltTy, elts.size());
+  auto constant = llvm::ConstantArray::get(type, elts);
+  buffer.erase(buffer.begin() + Begin, buffer.end());
+  return constant;
+}
+
+llvm::Constant *ConstantStructBuilder::finishImpl() {
+  markFinished();
+
+  auto &buffer = getBuffer();
+  assert(Begin < buffer.size() && "didn't add any struct elements?");
+  auto elts = llvm::makeArrayRef(buffer).slice(Begin);
+
+  llvm::Constant *constant;
+  if (Ty) {
+    constant = llvm::ConstantStruct::get(Ty, elts);
+  } else {
+    constant = llvm::ConstantStruct::getAnon(elts, /*packed*/ false);
+  }
+
+  buffer.erase(buffer.begin() + Begin, buffer.end());
+  return constant;
+}

Modified: cfe/trunk/lib/CodeGen/ItaniumCXXABI.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/ItaniumCXXABI.cpp?rev=296806&r1=296805&r2=296806&view=diff
==============================================================================
--- cfe/trunk/lib/CodeGen/ItaniumCXXABI.cpp (original)
+++ cfe/trunk/lib/CodeGen/ItaniumCXXABI.cpp Thu Mar  2 14:04:19 2017
@@ -24,8 +24,8 @@
 #include "CGVTables.h"
 #include "CodeGenFunction.h"
 #include "CodeGenModule.h"
-#include "ConstantBuilder.h"
 #include "TargetInfo.h"
+#include "clang/CodeGen/ConstantInitBuilder.h"
 #include "clang/AST/Mangle.h"
 #include "clang/AST/Type.h"
 #include "clang/AST/StmtCXX.h"

Modified: cfe/trunk/lib/CodeGen/MicrosoftCXXABI.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/MicrosoftCXXABI.cpp?rev=296806&r1=296805&r2=296806&view=diff
==============================================================================
--- cfe/trunk/lib/CodeGen/MicrosoftCXXABI.cpp (original)
+++ cfe/trunk/lib/CodeGen/MicrosoftCXXABI.cpp Thu Mar  2 14:04:19 2017
@@ -19,8 +19,8 @@
 #include "CGVTables.h"
 #include "CodeGenModule.h"
 #include "CodeGenTypes.h"
-#include "ConstantBuilder.h"
 #include "TargetInfo.h"
+#include "clang/CodeGen/ConstantInitBuilder.h"
 #include "clang/AST/Decl.h"
 #include "clang/AST/DeclCXX.h"
 #include "clang/AST/StmtCXX.h"




More information about the cfe-commits mailing list