]> granicus.if.org Git - clang/commitdiff
Extract ABI-specific parts of MangleContext into separate classes
authorTimur Iskhodzhanov <timurrrr@google.com>
Thu, 3 Oct 2013 06:26:13 +0000 (06:26 +0000)
committerTimur Iskhodzhanov <timurrrr@google.com>
Thu, 3 Oct 2013 06:26:13 +0000 (06:26 +0000)
Reviewed at http://llvm-reviews.chandlerc.com/D1807

git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@191878 91177308-0d34-0410-b5e6-96231b3b80d8

include/clang/AST/Mangle.h
lib/AST/ASTContext.cpp
lib/AST/ItaniumMangle.cpp
lib/AST/MicrosoftMangle.cpp
lib/CodeGen/CGVTT.cpp
lib/CodeGen/CGVTables.cpp
lib/CodeGen/ItaniumCXXABI.cpp
lib/CodeGen/MicrosoftCXXABI.cpp
lib/CodeGen/MicrosoftVBTables.cpp

index b9eb4f0006a701f12a016c27fcc4b578c0d704dd..76d099f938a7fc80817cc3eeb7df79f43499804a 100644 (file)
@@ -19,6 +19,7 @@
 #include "llvm/ADT/DenseMap.h"
 #include "llvm/ADT/SmallString.h"
 #include "llvm/ADT/StringRef.h"
+#include "llvm/Support/Casting.h"
 #include "llvm/Support/raw_ostream.h"
 
 namespace clang {
@@ -64,18 +65,29 @@ private:
 /// MangleContext - Context for tracking state which persists across multiple
 /// calls to the C++ name mangler.
 class MangleContext {
+public:
+  enum ManglerKind {
+    MK_Itanium,
+    MK_Microsoft
+  };
+
+private:
   virtual void anchor();
 
   ASTContext &Context;
   DiagnosticsEngine &Diags;
+  const ManglerKind Kind;
 
   llvm::DenseMap<const BlockDecl*, unsigned> GlobalBlockIds;
   llvm::DenseMap<const BlockDecl*, unsigned> LocalBlockIds;
-  
+
 public:
+  ManglerKind getKind() const { return Kind; }
+
   explicit MangleContext(ASTContext &Context,
-                         DiagnosticsEngine &Diags)
-    : Context(Context), Diags(Diags) { }
+                         DiagnosticsEngine &Diags,
+                         ManglerKind Kind)
+      : Context(Context), Diags(Diags), Kind(Kind) {}
 
   virtual ~MangleContext() { }
 
@@ -97,7 +109,9 @@ public:
   /// @{
 
   virtual bool shouldMangleDeclName(const NamedDecl *D) = 0;
-  virtual void mangleName(const NamedDecl *D, raw_ostream &)=0;
+
+  // FIXME: consider replacing raw_ostream & with something like SmallString &.
+  virtual void mangleName(const NamedDecl *D, raw_ostream &) = 0;
   virtual void mangleThunk(const CXXMethodDecl *MD,
                           const ThunkInfo &Thunk,
                           raw_ostream &) = 0;
@@ -106,27 +120,6 @@ public:
                                   raw_ostream &) = 0;
   virtual void mangleReferenceTemporary(const VarDecl *D,
                                         raw_ostream &) = 0;
-  // FIXME: Some of these objects only exist in select ABIs. We should probably
-  // only declare them in ABI-specific manglers?
-  virtual void mangleCXXVTable(const CXXRecordDecl *RD,
-                               raw_ostream &) = 0;
-  /// \brief Mangle vftable symbols.  Only a subset of the bases along the path
-  /// to the vftable are included in the name.  It's up to the caller to pick
-  /// them correctly.
-  virtual void mangleCXXVFTable(const CXXRecordDecl *Derived,
-                                ArrayRef<const CXXRecordDecl *> BasePath,
-                                raw_ostream &Out) = 0;
-  virtual void mangleCXXVTT(const CXXRecordDecl *RD,
-                            raw_ostream &) = 0;
-  /// \brief Mangle vbtable symbols.  Only a subset of the bases along the path
-  /// to the vbtable are included in the name.  It's up to the caller to pick
-  /// them correctly.
-  virtual void mangleCXXVBTable(const CXXRecordDecl *Derived,
-                                ArrayRef<const CXXRecordDecl *> BasePath,
-                                raw_ostream &Out) = 0;
-  virtual void mangleCXXCtorVTable(const CXXRecordDecl *RD, int64_t Offset,
-                                   const CXXRecordDecl *Type,
-                                   raw_ostream &) = 0;
   virtual void mangleCXXRTTI(QualType T, raw_ostream &) = 0;
   virtual void mangleCXXRTTIName(QualType T, raw_ostream &) = 0;
   virtual void mangleCXXCtor(const CXXConstructorDecl *D, CXXCtorType Type,
@@ -144,35 +137,67 @@ public:
   void mangleBlock(const DeclContext *DC, const BlockDecl *BD,
                    raw_ostream &Out);
 
-  void mangleObjCMethodName(const ObjCMethodDecl *MD,
-                            raw_ostream &);
+  void mangleObjCMethodName(const ObjCMethodDecl *MD, raw_ostream &);
 
-  virtual void mangleStaticGuardVariable(const VarDecl *D,
-                                         raw_ostream &Out) = 0;
+  virtual void mangleStaticGuardVariable(const VarDecl *D, raw_ostream &) = 0;
 
-  virtual void mangleDynamicInitializer(const VarDecl *D, raw_ostream &Out) = 0;
+  virtual void mangleDynamicInitializer(const VarDecl *D, raw_ostream &) = 0;
 
   virtual void mangleDynamicAtExitDestructor(const VarDecl *D,
-                                             raw_ostream &Out) = 0;
+                                             raw_ostream &) = 0;
+
+  /// @}
+};
 
-  // FIXME: Revisit this once we know what we need to do for MSVC compatibility.
+class ItaniumMangleContext : public MangleContext {
+public:
+  explicit ItaniumMangleContext(ASTContext &C, DiagnosticsEngine &D)
+      : MangleContext(C, D, MK_Itanium) {}
+
+  virtual void mangleCXXVTable(const CXXRecordDecl *RD, raw_ostream &) = 0;
+  virtual void mangleCXXVTT(const CXXRecordDecl *RD, raw_ostream &) = 0;
+  virtual void mangleCXXCtorVTable(const CXXRecordDecl *RD, int64_t Offset,
+                                   const CXXRecordDecl *Type,
+                                   raw_ostream &) = 0;
   virtual void mangleItaniumThreadLocalInit(const VarDecl *D,
-                                            raw_ostream &) {
-    llvm_unreachable("Target does not support mangling thread_local variables");
-  }
+                                            raw_ostream &) = 0;
   virtual void mangleItaniumThreadLocalWrapper(const VarDecl *D,
-                                               raw_ostream &) {
-    llvm_unreachable("Target does not support mangling thread_local variables");
+                                               raw_ostream &) = 0;
+
+  static bool classof(const MangleContext *C) {
+    return C->getKind() == MK_Itanium;
   }
 
-  /// @}
+  static ItaniumMangleContext *create(ASTContext &Context,
+                                      DiagnosticsEngine &Diags);
 };
 
-MangleContext *createItaniumMangleContext(ASTContext &Context,
-                                          DiagnosticsEngine &Diags);
-MangleContext *createMicrosoftMangleContext(ASTContext &Context,
-                                            DiagnosticsEngine &Diags);
+class MicrosoftMangleContext : public MangleContext {
+public:
+  explicit MicrosoftMangleContext(ASTContext &C, DiagnosticsEngine &D)
+      : MangleContext(C, D, MK_Microsoft) {}
 
+  /// \brief Mangle vftable symbols.  Only a subset of the bases along the path
+  /// to the vftable are included in the name.  It's up to the caller to pick
+  /// them correctly.
+  virtual void mangleCXXVFTable(const CXXRecordDecl *Derived,
+                                ArrayRef<const CXXRecordDecl *> BasePath,
+                                raw_ostream &Out) = 0;
+
+  /// \brief Mangle vbtable symbols.  Only a subset of the bases along the path
+  /// to the vbtable are included in the name.  It's up to the caller to pick
+  /// them correctly.
+  virtual void mangleCXXVBTable(const CXXRecordDecl *Derived,
+                                ArrayRef<const CXXRecordDecl *> BasePath,
+                                raw_ostream &Out) = 0;
+
+  static bool classof(const MangleContext *C) {
+    return C->getKind() == MK_Microsoft;
+  }
+
+  static MicrosoftMangleContext *create(ASTContext &Context,
+                                        DiagnosticsEngine &Diags);
+};
 }
 
 #endif
index 043ed99c1a08476fe23d539ff4eee26568a1161f..3b5bfe6d8c315bce8cb9db177831520951eb2c60 100644 (file)
@@ -7981,9 +7981,9 @@ MangleContext *ASTContext::createMangleContext() {
   case TargetCXXABI::GenericItanium:
   case TargetCXXABI::GenericARM:
   case TargetCXXABI::iOS:
-    return createItaniumMangleContext(*this, getDiagnostics());
+    return ItaniumMangleContext::create(*this, getDiagnostics());
   case TargetCXXABI::Microsoft:
-    return createMicrosoftMangleContext(*this, getDiagnostics());
+    return MicrosoftMangleContext::create(*this, getDiagnostics());
   }
   llvm_unreachable("Unsupported ABI");
 }
index 13923ae8f6b3fc5ecb08ad6ad30999786d960a90..fe8575d5d34b997f2ed00862068b02a118a24a5f 100644 (file)
@@ -104,16 +104,16 @@ static const NamedDecl *getStructor(const NamedDecl *decl) {
                                                     
 static const unsigned UnknownArity = ~0U;
 
-class ItaniumMangleContext : public MangleContext {
+class ItaniumMangleContextImpl : public ItaniumMangleContext {
   llvm::DenseMap<const TagDecl *, uint64_t> AnonStructIds;
   typedef std::pair<const DeclContext*, IdentifierInfo*> DiscriminatorKeyTy;
   llvm::DenseMap<DiscriminatorKeyTy, unsigned> Discriminator;
   llvm::DenseMap<const NamedDecl*, unsigned> Uniquifier;
   
 public:
-  explicit ItaniumMangleContext(ASTContext &Context,
-                                DiagnosticsEngine &Diags)
-    : MangleContext(Context, Diags) { }
+  explicit ItaniumMangleContextImpl(ASTContext &Context,
+                                    DiagnosticsEngine &Diags)
+      : ItaniumMangleContext(Context, Diags) {}
 
   uint64_t getAnonymousStructId(const TagDecl *TD) {
     std::pair<llvm::DenseMap<const TagDecl *,
@@ -137,14 +137,8 @@ public:
                                 raw_ostream &);
   void mangleCXXVTable(const CXXRecordDecl *RD,
                        raw_ostream &);
-  void mangleCXXVFTable(const CXXRecordDecl *Derived,
-                        ArrayRef<const CXXRecordDecl *> BasePath,
-                        raw_ostream &Out);
   void mangleCXXVTT(const CXXRecordDecl *RD,
                     raw_ostream &);
-  void mangleCXXVBTable(const CXXRecordDecl *Derived,
-                        ArrayRef<const CXXRecordDecl *> BasePath,
-                        raw_ostream &Out);
   void mangleCXXCtorVTable(const CXXRecordDecl *RD, int64_t Offset,
                            const CXXRecordDecl *Type,
                            raw_ostream &);
@@ -198,7 +192,7 @@ public:
 
 /// CXXNameMangler - Manage the mangling of a single name.
 class CXXNameMangler {
-  ItaniumMangleContext &Context;
+  ItaniumMangleContextImpl &Context;
   raw_ostream &Out;
 
   /// The "structor" is the top-level declaration being mangled, if
@@ -254,7 +248,7 @@ class CXXNameMangler {
   ASTContext &getASTContext() const { return Context.getASTContext(); }
 
 public:
-  CXXNameMangler(ItaniumMangleContext &C, raw_ostream &Out_,
+  CXXNameMangler(ItaniumMangleContextImpl &C, raw_ostream &Out_,
                  const NamedDecl *D = 0)
     : Context(C), Out(Out_), Structor(getStructor(D)), StructorType(0),
       SeqID(0) {
@@ -262,11 +256,11 @@ public:
     assert(!D || (!isa<CXXDestructorDecl>(D) &&
                   !isa<CXXConstructorDecl>(D)));
   }
-  CXXNameMangler(ItaniumMangleContext &C, raw_ostream &Out_,
+  CXXNameMangler(ItaniumMangleContextImpl &C, raw_ostream &Out_,
                  const CXXConstructorDecl *D, CXXCtorType Type)
     : Context(C), Out(Out_), Structor(getStructor(D)), StructorType(Type),
       SeqID(0) { }
-  CXXNameMangler(ItaniumMangleContext &C, raw_ostream &Out_,
+  CXXNameMangler(ItaniumMangleContextImpl &C, raw_ostream &Out_,
                  const CXXDestructorDecl *D, CXXDtorType Type)
     : Context(C), Out(Out_), Structor(getStructor(D)), StructorType(Type),
       SeqID(0) { }
@@ -390,7 +384,7 @@ private:
 
 }
 
-bool ItaniumMangleContext::shouldMangleDeclName(const NamedDecl *D) {
+bool ItaniumMangleContextImpl::shouldMangleDeclName(const NamedDecl *D) {
   // In C, functions with no attributes never need to be mangled. Fastpath them.
   if (!getASTContext().getLangOpts().CPlusPlus && !D->hasAttrs())
     return false;
@@ -3638,8 +3632,8 @@ void CXXNameMangler::addSubstitution(uintptr_t Ptr) {
 /// and this routine will return false. In this case, the caller should just
 /// emit the identifier of the declaration (\c D->getIdentifier()) as its
 /// name.
-void ItaniumMangleContext::mangleName(const NamedDecl *D,
-                                      raw_ostream &Out) {
+void ItaniumMangleContextImpl::mangleName(const NamedDecl *D,
+                                          raw_ostream &Out) {
   assert((isa<FunctionDecl>(D) || isa<VarDecl>(D)) &&
           "Invalid mangleName() call, argument is not a variable or function!");
   assert(!isa<CXXConstructorDecl>(D) && !isa<CXXDestructorDecl>(D) &&
@@ -3653,23 +3647,23 @@ void ItaniumMangleContext::mangleName(const NamedDecl *D,
   return Mangler.mangle(D);
 }
 
-void ItaniumMangleContext::mangleCXXCtor(const CXXConstructorDecl *D,
-                                         CXXCtorType Type,
-                                         raw_ostream &Out) {
+void ItaniumMangleContextImpl::mangleCXXCtor(const CXXConstructorDecl *D,
+                                             CXXCtorType Type,
+                                             raw_ostream &Out) {
   CXXNameMangler Mangler(*this, Out, D, Type);
   Mangler.mangle(D);
 }
 
-void ItaniumMangleContext::mangleCXXDtor(const CXXDestructorDecl *D,
-                                         CXXDtorType Type,
-                                         raw_ostream &Out) {
+void ItaniumMangleContextImpl::mangleCXXDtor(const CXXDestructorDecl *D,
+                                             CXXDtorType Type,
+                                             raw_ostream &Out) {
   CXXNameMangler Mangler(*this, Out, D, Type);
   Mangler.mangle(D);
 }
 
-void ItaniumMangleContext::mangleThunk(const CXXMethodDecl *MD,
-                                       const ThunkInfo &Thunk,
-                                       raw_ostream &Out) {
+void ItaniumMangleContextImpl::mangleThunk(const CXXMethodDecl *MD,
+                                           const ThunkInfo &Thunk,
+                                           raw_ostream &Out) {
   //  <special-name> ::= T <call-offset> <base encoding>
   //                      # base is the nominal target function of thunk
   //  <special-name> ::= Tc <call-offset> <call-offset> <base encoding>
@@ -3695,11 +3689,9 @@ void ItaniumMangleContext::mangleThunk(const CXXMethodDecl *MD,
   Mangler.mangleFunctionEncoding(MD);
 }
 
-void 
-ItaniumMangleContext::mangleCXXDtorThunk(const CXXDestructorDecl *DD,
-                                         CXXDtorType Type,
-                                         const ThisAdjustment &ThisAdjustment,
-                                         raw_ostream &Out) {
+void ItaniumMangleContextImpl::mangleCXXDtorThunk(
+    const CXXDestructorDecl *DD, CXXDtorType Type,
+    const ThisAdjustment &ThisAdjustment, raw_ostream &Out) {
   //  <special-name> ::= T <call-offset> <base encoding>
   //                      # base is the nominal target function of thunk
   CXXNameMangler Mangler(*this, Out, DD, Type);
@@ -3714,8 +3706,8 @@ ItaniumMangleContext::mangleCXXDtorThunk(const CXXDestructorDecl *DD,
 
 /// mangleGuardVariable - Returns the mangled name for a guard variable
 /// for the passed in VarDecl.
-void ItaniumMangleContext::mangleStaticGuardVariable(const VarDecl *D,
-                                                     raw_ostream &Out) {
+void ItaniumMangleContextImpl::mangleStaticGuardVariable(const VarDecl *D,
+                                                         raw_ostream &Out) {
   //  <special-name> ::= GV <object name>       # Guard variable for one-time
   //                                            # initialization
   CXXNameMangler Mangler(*this, Out);
@@ -3723,16 +3715,16 @@ void ItaniumMangleContext::mangleStaticGuardVariable(const VarDecl *D,
   Mangler.mangleName(D);
 }
 
-void ItaniumMangleContext::mangleDynamicInitializer(const VarDecl *MD,
-                                                    raw_ostream &Out) {
+void ItaniumMangleContextImpl::mangleDynamicInitializer(const VarDecl *MD,
+                                                        raw_ostream &Out) {
   // These symbols are internal in the Itanium ABI, so the names don't matter.
   // Clang has traditionally used this symbol and allowed LLVM to adjust it to
   // avoid duplicate symbols.
   Out << "__cxx_global_var_init";
 }
 
-void ItaniumMangleContext::mangleDynamicAtExitDestructor(const VarDecl *D,
-                                                         raw_ostream &Out) {
+void ItaniumMangleContextImpl::mangleDynamicAtExitDestructor(const VarDecl *D,
+                                                             raw_ostream &Out) {
   // Prefix the mangling of D with __dtor_.
   CXXNameMangler Mangler(*this, Out);
   Mangler.getStream() << "__dtor_";
@@ -3742,24 +3734,25 @@ void ItaniumMangleContext::mangleDynamicAtExitDestructor(const VarDecl *D,
     Mangler.getStream() << D->getName();
 }
 
-void ItaniumMangleContext::mangleItaniumThreadLocalInit(const VarDecl *D,
-                                                        raw_ostream &Out) {
+void ItaniumMangleContextImpl::mangleItaniumThreadLocalInit(const VarDecl *D,
+                                                            raw_ostream &Out) {
   //  <special-name> ::= TH <object name>
   CXXNameMangler Mangler(*this, Out);
   Mangler.getStream() << "_ZTH";
   Mangler.mangleName(D);
 }
 
-void ItaniumMangleContext::mangleItaniumThreadLocalWrapper(const VarDecl *D,
-                                                           raw_ostream &Out) {
+void
+ItaniumMangleContextImpl::mangleItaniumThreadLocalWrapper(const VarDecl *D,
+                                                          raw_ostream &Out) {
   //  <special-name> ::= TW <object name>
   CXXNameMangler Mangler(*this, Out);
   Mangler.getStream() << "_ZTW";
   Mangler.mangleName(D);
 }
 
-void ItaniumMangleContext::mangleReferenceTemporary(const VarDecl *D,
-                                                    raw_ostream &Out) {
+void ItaniumMangleContextImpl::mangleReferenceTemporary(const VarDecl *D,
+                                                        raw_ostream &Out) {
   // We match the GCC mangling here.
   //  <special-name> ::= GR <object name>
   CXXNameMangler Mangler(*this, Out);
@@ -3767,41 +3760,26 @@ void ItaniumMangleContext::mangleReferenceTemporary(const VarDecl *D,
   Mangler.mangleName(D);
 }
 
-void ItaniumMangleContext::mangleCXXVTable(const CXXRecordDecl *RD,
-                                           raw_ostream &Out) {
+void ItaniumMangleContextImpl::mangleCXXVTable(const CXXRecordDecl *RD,
+                                               raw_ostream &Out) {
   // <special-name> ::= TV <type>  # virtual table
   CXXNameMangler Mangler(*this, Out);
   Mangler.getStream() << "_ZTV";
   Mangler.mangleNameOrStandardSubstitution(RD);
 }
 
-void
-ItaniumMangleContext::mangleCXXVFTable(const CXXRecordDecl *Derived,
-                                       ArrayRef<const CXXRecordDecl *> BasePath,
-                                       raw_ostream &Out) {
-  llvm_unreachable(
-      "The Itanium C++ ABI does not have vftables (use vtables instead)!");
-}
-
-void ItaniumMangleContext::mangleCXXVTT(const CXXRecordDecl *RD,
-                                        raw_ostream &Out) {
+void ItaniumMangleContextImpl::mangleCXXVTT(const CXXRecordDecl *RD,
+                                            raw_ostream &Out) {
   // <special-name> ::= TT <type>  # VTT structure
   CXXNameMangler Mangler(*this, Out);
   Mangler.getStream() << "_ZTT";
   Mangler.mangleNameOrStandardSubstitution(RD);
 }
 
-void
-ItaniumMangleContext::mangleCXXVBTable(const CXXRecordDecl *Derived,
-                                       ArrayRef<const CXXRecordDecl *> BasePath,
-                                       raw_ostream &Out) {
-  llvm_unreachable("The Itanium C++ ABI does not have virtual base tables!");
-}
-
-void ItaniumMangleContext::mangleCXXCtorVTable(const CXXRecordDecl *RD,
-                                               int64_t Offset,
-                                               const CXXRecordDecl *Type,
-                                               raw_ostream &Out) {
+void ItaniumMangleContextImpl::mangleCXXCtorVTable(const CXXRecordDecl *RD,
+                                                   int64_t Offset,
+                                                   const CXXRecordDecl *Type,
+                                                   raw_ostream &Out) {
   // <special-name> ::= TC <type> <offset number> _ <base type>
   CXXNameMangler Mangler(*this, Out);
   Mangler.getStream() << "_ZTC";
@@ -3811,8 +3789,7 @@ void ItaniumMangleContext::mangleCXXCtorVTable(const CXXRecordDecl *RD,
   Mangler.mangleNameOrStandardSubstitution(Type);
 }
 
-void ItaniumMangleContext::mangleCXXRTTI(QualType Ty,
-                                         raw_ostream &Out) {
+void ItaniumMangleContextImpl::mangleCXXRTTI(QualType Ty, raw_ostream &Out) {
   // <special-name> ::= TI <type>  # typeinfo structure
   assert(!Ty.hasQualifiers() && "RTTI info cannot have top-level qualifiers");
   CXXNameMangler Mangler(*this, Out);
@@ -3820,15 +3797,15 @@ void ItaniumMangleContext::mangleCXXRTTI(QualType Ty,
   Mangler.mangleType(Ty);
 }
 
-void ItaniumMangleContext::mangleCXXRTTIName(QualType Ty,
-                                             raw_ostream &Out) {
+void ItaniumMangleContextImpl::mangleCXXRTTIName(QualType Ty,
+                                                 raw_ostream &Out) {
   // <special-name> ::= TS <type>  # typeinfo name (null terminated byte string)
   CXXNameMangler Mangler(*this, Out);
   Mangler.getStream() << "_ZTS";
   Mangler.mangleType(Ty);
 }
 
-MangleContext *clang::createItaniumMangleContext(ASTContext &Context,
-                                                 DiagnosticsEngine &Diags) {
-  return new ItaniumMangleContext(Context, Diags);
+ItaniumMangleContext *
+ItaniumMangleContext::create(ASTContext &Context, DiagnosticsEngine &Diags) {
+  return new ItaniumMangleContextImpl(Context, Diags);
 }
index 211e6e79314e893ae05f8e2f33218083bf8c87f7..d7237d395f9239120a04d157a1ef759d3f281c3a 100644 (file)
@@ -172,12 +172,12 @@ private:
   void mangleTemplateArg(const TemplateDecl *TD, const TemplateArgument &TA);
 };
 
-/// MicrosoftMangleContext - Overrides the default MangleContext for the
+/// MicrosoftMangleContextImpl - Overrides the default MangleContext for the
 /// Microsoft Visual C++ ABI.
-class MicrosoftMangleContext : public MangleContext {
+class MicrosoftMangleContextImpl : public MicrosoftMangleContext {
 public:
-  MicrosoftMangleContext(ASTContext &Context,
-                   DiagnosticsEngine &Diags) : MangleContext(Context, Diags) { }
+  MicrosoftMangleContextImpl(ASTContext &Context, DiagnosticsEngine &Diags)
+      : MicrosoftMangleContext(Context, Diags) {}
   virtual bool shouldMangleDeclName(const NamedDecl *D);
   virtual void mangleName(const NamedDecl *D, raw_ostream &Out);
   virtual void mangleThunk(const CXXMethodDecl *MD,
@@ -186,19 +186,12 @@ public:
   virtual void mangleCXXDtorThunk(const CXXDestructorDecl *DD, CXXDtorType Type,
                                   const ThisAdjustment &ThisAdjustment,
                                   raw_ostream &);
-  virtual void mangleCXXVTable(const CXXRecordDecl *RD,
-                               raw_ostream &);
   virtual void mangleCXXVFTable(const CXXRecordDecl *Derived,
                                 ArrayRef<const CXXRecordDecl *> BasePath,
                                 raw_ostream &Out);
-  virtual void mangleCXXVTT(const CXXRecordDecl *RD,
-                            raw_ostream &);
   virtual void mangleCXXVBTable(const CXXRecordDecl *Derived,
                                 ArrayRef<const CXXRecordDecl *> BasePath,
                                 raw_ostream &Out);
-  virtual void mangleCXXCtorVTable(const CXXRecordDecl *RD, int64_t Offset,
-                                   const CXXRecordDecl *Type,
-                                   raw_ostream &);
   virtual void mangleCXXRTTI(QualType T, raw_ostream &);
   virtual void mangleCXXRTTIName(QualType T, raw_ostream &);
   virtual void mangleCXXCtor(const CXXConstructorDecl *D, CXXCtorType Type,
@@ -217,7 +210,7 @@ private:
 
 }
 
-bool MicrosoftMangleContext::shouldMangleDeclName(const NamedDecl *D) {
+bool MicrosoftMangleContextImpl::shouldMangleDeclName(const NamedDecl *D) {
   // In C, functions with no attributes never need to be mangled. Fastpath them.
   if (!getASTContext().getLangOpts().CPlusPlus && !D->hasAttrs())
     return false;
@@ -1854,8 +1847,8 @@ void MicrosoftCXXNameMangler::mangleType(const AtomicType *T,
     << Range;
 }
 
-void MicrosoftMangleContext::mangleName(const NamedDecl *D,
-                                        raw_ostream &Out) {
+void MicrosoftMangleContextImpl::mangleName(const NamedDecl *D,
+                                            raw_ostream &Out) {
   assert((isa<FunctionDecl>(D) || isa<VarDecl>(D)) &&
          "Invalid mangleName() call, argument is not a variable or function!");
   assert(!isa<CXXConstructorDecl>(D) && !isa<CXXDestructorDecl>(D) &&
@@ -1869,9 +1862,9 @@ void MicrosoftMangleContext::mangleName(const NamedDecl *D,
   return Mangler.mangle(D);
 }
 
-void MicrosoftMangleContext::mangleThunk(const CXXMethodDecl *MD,
-                                         const ThunkInfo &Thunk,
-                                         raw_ostream &Out) {
+void MicrosoftMangleContextImpl::mangleThunk(const CXXMethodDecl *MD,
+                                             const ThunkInfo &Thunk,
+                                             raw_ostream &Out) {
   // FIXME: this is not yet a complete implementation, but merely a
   // reasonably-working stub to avoid crashing when required to emit a thunk.
   MicrosoftCXXNameMangler Mangler(*this, Out);
@@ -1892,22 +1885,16 @@ void MicrosoftMangleContext::mangleThunk(const CXXMethodDecl *MD,
   Mangler.mangleFunctionType(MD->getType()->castAs<FunctionProtoType>(), MD, false, true);
 }
 
-void MicrosoftMangleContext::mangleCXXDtorThunk(const CXXDestructorDecl *DD,
-                                                CXXDtorType Type,
-                                                const ThisAdjustment &,
-                                                raw_ostream &) {
+void MicrosoftMangleContextImpl::mangleCXXDtorThunk(const CXXDestructorDecl *DD,
+                                                    CXXDtorType Type,
+                                                    const ThisAdjustment &,
+                                                    raw_ostream &) {
   unsigned DiagID = getDiags().getCustomDiagID(DiagnosticsEngine::Error,
     "cannot mangle thunk for this destructor yet");
   getDiags().Report(DD->getLocation(), DiagID);
 }
 
-void MicrosoftMangleContext::mangleCXXVTable(const CXXRecordDecl *RD,
-                                             raw_ostream &Out) {
-  llvm_unreachable(
-      "The Microsoft C++ ABI does not have vtables (use vftables instead)!");
-}
-
-void MicrosoftMangleContext::mangleCXXVFTable(
+void MicrosoftMangleContextImpl::mangleCXXVFTable(
     const CXXRecordDecl *Derived, ArrayRef<const CXXRecordDecl *> BasePath,
     raw_ostream &Out) {
   // <mangled-name> ::= ?_7 <class-name> <storage-class>
@@ -1926,7 +1913,7 @@ void MicrosoftMangleContext::mangleCXXVFTable(
   Mangler.getStream() << '@';
 }
 
-void MicrosoftMangleContext::mangleCXXVBTable(
+void MicrosoftMangleContextImpl::mangleCXXVBTable(
     const CXXRecordDecl *Derived, ArrayRef<const CXXRecordDecl *> BasePath,
     raw_ostream &Out) {
   // <mangled-name> ::= ?_8 <class-name> <storage-class>
@@ -1945,53 +1932,45 @@ void MicrosoftMangleContext::mangleCXXVBTable(
   Mangler.getStream() << '@';
 }
 
-void MicrosoftMangleContext::mangleCXXVTT(const CXXRecordDecl *RD,
-                                          raw_ostream &) {
-  llvm_unreachable("The MS C++ ABI does not have virtual table tables!");
-}
-void MicrosoftMangleContext::mangleCXXCtorVTable(const CXXRecordDecl *RD,
-                                                 int64_t Offset,
-                                                 const CXXRecordDecl *Type,
-                                                 raw_ostream &) {
-  llvm_unreachable("The MS C++ ABI does not have constructor vtables!");
-}
-void MicrosoftMangleContext::mangleCXXRTTI(QualType T,
-                                           raw_ostream &) {
+void MicrosoftMangleContextImpl::mangleCXXRTTI(QualType T, raw_ostream &) {
   // FIXME: Give a location...
   unsigned DiagID = getDiags().getCustomDiagID(DiagnosticsEngine::Error,
     "cannot mangle RTTI descriptors for type %0 yet");
   getDiags().Report(DiagID)
     << T.getBaseTypeIdentifier();
 }
-void MicrosoftMangleContext::mangleCXXRTTIName(QualType T,
-                                               raw_ostream &) {
+
+void MicrosoftMangleContextImpl::mangleCXXRTTIName(QualType T, raw_ostream &) {
   // FIXME: Give a location...
   unsigned DiagID = getDiags().getCustomDiagID(DiagnosticsEngine::Error,
     "cannot mangle the name of type %0 into RTTI descriptors yet");
   getDiags().Report(DiagID)
     << T.getBaseTypeIdentifier();
 }
-void MicrosoftMangleContext::mangleCXXCtor(const CXXConstructorDecl *D,
-                                           CXXCtorType Type,
-                                           raw_ostream & Out) {
+
+void MicrosoftMangleContextImpl::mangleCXXCtor(const CXXConstructorDecl *D,
+                                               CXXCtorType Type,
+                                               raw_ostream &Out) {
   MicrosoftCXXNameMangler mangler(*this, Out);
   mangler.mangle(D);
 }
-void MicrosoftMangleContext::mangleCXXDtor(const CXXDestructorDecl *D,
-                                           CXXDtorType Type,
-                                           raw_ostream & Out) {
+
+void MicrosoftMangleContextImpl::mangleCXXDtor(const CXXDestructorDecl *D,
+                                               CXXDtorType Type,
+                                               raw_ostream &Out) {
   MicrosoftCXXNameMangler mangler(*this, Out, D, Type);
   mangler.mangle(D);
 }
-void MicrosoftMangleContext::mangleReferenceTemporary(const VarDecl *VD,
-                                                      raw_ostream &) {
+
+void MicrosoftMangleContextImpl::mangleReferenceTemporary(const VarDecl *VD,
+                                                          raw_ostream &) {
   unsigned DiagID = getDiags().getCustomDiagID(DiagnosticsEngine::Error,
     "cannot mangle this reference temporary yet");
   getDiags().Report(VD->getLocation(), DiagID);
 }
 
-void MicrosoftMangleContext::mangleStaticGuardVariable(const VarDecl *VD,
-                                                       raw_ostream &Out) {
+void MicrosoftMangleContextImpl::mangleStaticGuardVariable(const VarDecl *VD,
+                                                           raw_ostream &Out) {
   // <guard-name> ::= ?_B <postfix> @51
   //              ::= ?$S <guard-num> @ <postfix> @4IA
 
@@ -2010,9 +1989,9 @@ void MicrosoftMangleContext::mangleStaticGuardVariable(const VarDecl *VD,
   Mangler.getStream() << (Visible ? "@51" : "@4IA");
 }
 
-void MicrosoftMangleContext::mangleInitFiniStub(const VarDecl *D,
-                                                raw_ostream &Out,
-                                                char CharCode) {
+void MicrosoftMangleContextImpl::mangleInitFiniStub(const VarDecl *D,
+                                                    raw_ostream &Out,
+                                                    char CharCode) {
   MicrosoftCXXNameMangler Mangler(*this, Out);
   Mangler.getStream() << "\01??__" << CharCode;
   Mangler.mangleName(D);
@@ -2021,19 +2000,20 @@ void MicrosoftMangleContext::mangleInitFiniStub(const VarDecl *D,
   Mangler.getStream() << "YAXXZ";
 }
 
-void MicrosoftMangleContext::mangleDynamicInitializer(const VarDecl *D,
-                                                      raw_ostream &Out) {
+void MicrosoftMangleContextImpl::mangleDynamicInitializer(const VarDecl *D,
+                                                          raw_ostream &Out) {
   // <initializer-name> ::= ?__E <name> YAXXZ
   mangleInitFiniStub(D, Out, 'E');
 }
 
-void MicrosoftMangleContext::mangleDynamicAtExitDestructor(const VarDecl *D,
-                                                           raw_ostream &Out) {
+void
+MicrosoftMangleContextImpl::mangleDynamicAtExitDestructor(const VarDecl *D,
+                                                          raw_ostream &Out) {
   // <destructor-name> ::= ?__F <name> YAXXZ
   mangleInitFiniStub(D, Out, 'F');
 }
 
-MangleContext *clang::createMicrosoftMangleContext(ASTContext &Context,
-                                                   DiagnosticsEngine &Diags) {
-  return new MicrosoftMangleContext(Context, Diags);
+MicrosoftMangleContext *
+MicrosoftMangleContext::create(ASTContext &Context, DiagnosticsEngine &Diags) {
+  return new MicrosoftMangleContextImpl(Context, Diags);
 }
index ea1456f825151400853dc507884b833c2bce5428..31beb02a52f511c5cecfb7480e2758e4c2d0ba5f 100644 (file)
@@ -102,7 +102,8 @@ llvm::GlobalVariable *CodeGenVTables::GetAddrOfVTT(const CXXRecordDecl *RD) {
 
   SmallString<256> OutName;
   llvm::raw_svector_ostream Out(OutName);
-  CGM.getCXXABI().getMangleContext().mangleCXXVTT(RD, Out);
+  cast<ItaniumMangleContext>(CGM.getCXXABI().getMangleContext())
+      .mangleCXXVTT(RD, Out);
   Out.flush();
   StringRef Name = OutName.str();
 
index 393e723812cf0ad6d4d9808a2dbd61bc36b23afd..b987eb4d079791a1add668b804806bf12d69372a 100644 (file)
@@ -650,9 +650,9 @@ CodeGenVTables::GenerateConstructionVTable(const CXXRecordDecl *RD,
   // Get the mangled construction vtable name.
   SmallString<256> OutName;
   llvm::raw_svector_ostream Out(OutName);
-  CGM.getCXXABI().getMangleContext().
-    mangleCXXCtorVTable(RD, Base.getBaseOffset().getQuantity(), Base.getBase(), 
-                        Out);
+  cast<ItaniumMangleContext>(CGM.getCXXABI().getMangleContext())
+      .mangleCXXCtorVTable(RD, Base.getBaseOffset().getQuantity(),
+                           Base.getBase(), Out);
   Out.flush();
   StringRef Name = OutName.str();
 
index 2934e6307e0d3662f8b11264ae0860ce5559e6b3..ecf5d577981a7ea61a450ed28c810f6918c62c0f 100644 (file)
@@ -41,6 +41,10 @@ protected:
   bool UseARMMethodPtrABI;
   bool UseARMGuardVarABI;
 
+  ItaniumMangleContext &getMangleContext() {
+    return cast<ItaniumMangleContext>(CodeGen::CGCXXABI::getMangleContext());
+  }
+
 public:
   ItaniumCXXABI(CodeGen::CodeGenModule &CGM,
                 bool UseARMMethodPtrABI = false,
@@ -997,7 +1001,7 @@ llvm::GlobalVariable *ItaniumCXXABI::getAddrOfVTable(const CXXRecordDecl *RD,
 
   SmallString<256> OutName;
   llvm::raw_svector_ostream Out(OutName);
-  CGM.getCXXABI().getMangleContext().mangleCXXVTable(RD, Out);
+  getMangleContext().mangleCXXVTable(RD, Out);
   Out.flush();
   StringRef Name = OutName.str();
 
index cfdbaa2957f3a655e02535ef7d745452e9dc55d6..1d73b213b7d8130dd68c4d0952a9c27a0fd5edac 100644 (file)
@@ -215,6 +215,10 @@ public:
                                    CharUnits cookieSize);
 
 private:
+  MicrosoftMangleContext &getMangleContext() {
+    return cast<MicrosoftMangleContext>(CodeGen::CGCXXABI::getMangleContext());
+  }
+
   llvm::Constant *getZeroInt() {
     return llvm::ConstantInt::get(CGM.IntTy, 0);
   }
@@ -678,11 +682,11 @@ llvm::Value *MicrosoftCXXABI::getVTableAddressPointInStructor(
   return VTableAddressPoint;
 }
 
-static void mangleVFTableName(CodeGenModule &CGM, const CXXRecordDecl *RD,
-                              const VFPtrInfo &VFPtr, SmallString<256> &Name) {
+static void mangleVFTableName(MicrosoftMangleContext &MangleContext,
+                              const CXXRecordDecl *RD, const VFPtrInfo &VFPtr,
+                              SmallString<256> &Name) {
   llvm::raw_svector_ostream Out(Name);
-  CGM.getCXXABI().getMangleContext().mangleCXXVFTable(
-      RD, VFPtr.PathToMangle, Out);
+  MangleContext.mangleCXXVFTable(RD, VFPtr.PathToMangle, Out);
 }
 
 llvm::Constant *MicrosoftCXXABI::getVTableAddressPointForConstExpr(
@@ -722,7 +726,7 @@ llvm::GlobalVariable *MicrosoftCXXABI::getAddrOfVTable(const CXXRecordDecl *RD,
     llvm::StringSet<> ObservedMangledNames;
     for (size_t J = 0, F = VFPtrs.size(); J != F; ++J) {
       SmallString<256> Name;
-      mangleVFTableName(CGM, RD, VFPtrs[J], Name);
+      mangleVFTableName(getMangleContext(), RD, VFPtrs[J], Name);
       if (!ObservedMangledNames.insert(Name.str()))
         llvm_unreachable("Already saw this mangling before?");
     }
@@ -739,7 +743,7 @@ llvm::GlobalVariable *MicrosoftCXXABI::getAddrOfVTable(const CXXRecordDecl *RD,
             .getNumVTableComponents());
 
     SmallString<256> Name;
-    mangleVFTableName(CGM, RD, VFPtrs[J], Name);
+    mangleVFTableName(getMangleContext(), RD, VFPtrs[J], Name);
     VTable = CGM.CreateOrReplaceCXXRuntimeVariable(
         Name.str(), ArrayType, llvm::GlobalValue::ExternalLinkage);
     VTable->setUnnamedAddr(true);
index 4523aa82b737a883aa2538f5b01c3128d4eacc12..f901eb562c9e9c4b478851779c0ae2e0c041c7cf 100644 (file)
@@ -170,7 +170,8 @@ VBTableBuilder::getAddrOfVBTable(const CXXRecordDecl *ReusingBase,
 
   SmallString<256> OutName;
   llvm::raw_svector_ostream Out(OutName);
-  MangleContext &Mangler = CGM.getCXXABI().getMangleContext();
+  MicrosoftMangleContext &Mangler =
+      cast<MicrosoftMangleContext>(CGM.getCXXABI().getMangleContext());
   Mangler.mangleCXXVBTable(MostDerived, BasePath, Out);
   Out.flush();
   StringRef Name = OutName.str();