r185986 - More local mangling fixes.

Eli Friedman eli.friedman at gmail.com
Tue Jul 9 17:30:47 PDT 2013


Author: efriedma
Date: Tue Jul  9 19:30:46 2013
New Revision: 185986

URL: http://llvm.org/viewvc/llvm-project?rev=185986&view=rev
Log:
More local mangling fixes.

Compute mangling numbers for externally visible local variables and tags.
Change the mangler to consistently use discriminators where necessary.
Tweak the scheme we use to number decls which are not externally visible
to avoid unnecessary discriminators in common cases now that we request
them more consistently.

Fixes <rdar://problem/14204721>.

Modified:
    cfe/trunk/include/clang/AST/ASTContext.h
    cfe/trunk/include/clang/AST/MangleNumberingContext.h
    cfe/trunk/include/clang/Sema/Sema.h
    cfe/trunk/lib/AST/ASTContext.cpp
    cfe/trunk/lib/AST/ItaniumMangle.cpp
    cfe/trunk/lib/AST/MangleNumberingContext.cpp
    cfe/trunk/lib/Sema/SemaDecl.cpp
    cfe/trunk/lib/Sema/SemaLambda.cpp
    cfe/trunk/test/CodeGenCXX/linkage.cpp
    cfe/trunk/test/CodeGenCXX/mangle-local-class-names.cpp
    cfe/trunk/test/CodeGenCXX/mangle.cpp

Modified: cfe/trunk/include/clang/AST/ASTContext.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/AST/ASTContext.h?rev=185986&r1=185985&r2=185986&view=diff
==============================================================================
--- cfe/trunk/include/clang/AST/ASTContext.h (original)
+++ cfe/trunk/include/clang/AST/ASTContext.h Tue Jul  9 19:30:46 2013
@@ -344,8 +344,9 @@ class ASTContext : public RefCountedBase
   llvm::DenseMap<const DeclContext *, MangleNumberingContext>
       MangleNumberingContexts;
 
-  llvm::DenseMap<const DeclContext *, unsigned> UnnamedMangleContexts;
-  llvm::DenseMap<const TagDecl *, unsigned> UnnamedMangleNumbers;
+  /// \brief Side-table of mangling numbers for declarations which rarely
+  /// need them (like static local vars).
+  llvm::DenseMap<const NamedDecl *, unsigned> MangleNumbers;
 
   /// \brief Mapping that stores parameterIndex values for ParmVarDecls when
   /// that value exceeds the bitfield size of ParmVarDeclBits.ParameterIndex.
@@ -2086,12 +2087,12 @@ public:
   /// it is not used.
   bool DeclMustBeEmitted(const Decl *D);
 
-  void addUnnamedTag(const TagDecl *Tag);
-  int getUnnamedTagManglingNumber(const TagDecl *Tag) const;
+  void setManglingNumber(const NamedDecl *ND, unsigned Number);
+  unsigned getManglingNumber(const NamedDecl *ND) const;
 
   /// \brief Retrieve the context for computing mangling numbers in the given
   /// DeclContext.
-  MangleNumberingContext &getManglingNumberContext(DeclContext *DC);
+  MangleNumberingContext &getManglingNumberContext(const DeclContext *DC);
 
   /// \brief Used by ParmVarDecl to store on the side the
   /// index of the parameter when it exceeds the size of the normal bitfield.

Modified: cfe/trunk/include/clang/AST/MangleNumberingContext.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/AST/MangleNumberingContext.h?rev=185986&r1=185985&r2=185986&view=diff
==============================================================================
--- cfe/trunk/include/clang/AST/MangleNumberingContext.h (original)
+++ cfe/trunk/include/clang/AST/MangleNumberingContext.h Tue Jul  9 19:30:46 2013
@@ -23,22 +23,35 @@ namespace clang {
 
 class BlockDecl;
 class CXXMethodDecl;
+class IdentifierInfo;
+class TagDecl;
 class Type;
+class VarDecl;
 
 /// \brief Keeps track of the mangled names of lambda expressions and block
 /// literals within a particular context.
 class MangleNumberingContext 
     : public RefCountedBase<MangleNumberingContext> {
   llvm::DenseMap<const Type *, unsigned> ManglingNumbers;
-  
+  llvm::DenseMap<IdentifierInfo*, unsigned> VarManglingNumbers;
+  llvm::DenseMap<IdentifierInfo*, unsigned> TagManglingNumbers;
+
 public:
   /// \brief Retrieve the mangling number of a new lambda expression with the
   /// given call operator within this context.
-  unsigned getManglingNumber(CXXMethodDecl *CallOperator);
+  unsigned getManglingNumber(const CXXMethodDecl *CallOperator);
 
   /// \brief Retrieve the mangling number of a new block literal within this
   /// context.
-  unsigned getManglingNumber(BlockDecl *BD);
+  unsigned getManglingNumber(const BlockDecl *BD);
+
+  /// \brief Retrieve the mangling number of a static local variable within
+  /// this context.
+  unsigned getManglingNumber(const VarDecl *VD);
+
+  /// \brief Retrieve the mangling number of a static local variable within
+  /// this context.
+  unsigned getManglingNumber(const TagDecl *TD);
 };
   
 } // end namespace clang

Modified: cfe/trunk/include/clang/Sema/Sema.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Sema/Sema.h?rev=185986&r1=185985&r2=185986&view=diff
==============================================================================
--- cfe/trunk/include/clang/Sema/Sema.h (original)
+++ cfe/trunk/include/clang/Sema/Sema.h Tue Jul  9 19:30:46 2013
@@ -716,7 +716,7 @@ public:
   /// \param[out] ManglingContextDecl - Returns the ManglingContextDecl
   /// associated with the context, if relevant.
   MangleNumberingContext *getCurrentMangleNumberContext(
-    DeclContext *DC,
+    const DeclContext *DC,
     Decl *&ManglingContextDecl);
 
 

Modified: cfe/trunk/lib/AST/ASTContext.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/ASTContext.cpp?rev=185986&r1=185985&r2=185986&view=diff
==============================================================================
--- cfe/trunk/lib/AST/ASTContext.cpp (original)
+++ cfe/trunk/lib/AST/ASTContext.cpp Tue Jul  9 19:30:46 2013
@@ -7990,24 +7990,19 @@ size_t ASTContext::getSideTableAllocated
     + llvm::capacity_in_bytes(ClassScopeSpecializationPattern);
 }
 
-void ASTContext::addUnnamedTag(const TagDecl *Tag) {
-  // FIXME: This mangling should be applied to function local classes too
-  if (!Tag->getName().empty() || Tag->getTypedefNameForAnonDecl() ||
-      !isa<CXXRecordDecl>(Tag->getParent()))
-    return;
-
-  std::pair<llvm::DenseMap<const DeclContext *, unsigned>::iterator, bool> P =
-    UnnamedMangleContexts.insert(std::make_pair(Tag->getParent(), 0));
-  UnnamedMangleNumbers.insert(std::make_pair(Tag, P.first->second++));
+void ASTContext::setManglingNumber(const NamedDecl *ND, unsigned Number) {
+  if (Number > 1)
+    MangleNumbers[ND] = Number;
 }
 
-int ASTContext::getUnnamedTagManglingNumber(const TagDecl *Tag) const {
-  llvm::DenseMap<const TagDecl *, unsigned>::const_iterator I =
-    UnnamedMangleNumbers.find(Tag);
-  return I != UnnamedMangleNumbers.end() ? I->second : -1;
+unsigned ASTContext::getManglingNumber(const NamedDecl *ND) const {
+  llvm::DenseMap<const NamedDecl *, unsigned>::const_iterator I =
+    MangleNumbers.find(ND);
+  return I != MangleNumbers.end() ? I->second : 1;
 }
 
-MangleNumberingContext &ASTContext::getManglingNumberContext(DeclContext *DC) {
+MangleNumberingContext &
+ASTContext::getManglingNumberContext(const DeclContext *DC) {
   return MangleNumberingContexts[DC];
 }
 

Modified: cfe/trunk/lib/AST/ItaniumMangle.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/ItaniumMangle.cpp?rev=185986&r1=185985&r2=185986&view=diff
==============================================================================
--- cfe/trunk/lib/AST/ItaniumMangle.cpp (original)
+++ cfe/trunk/lib/AST/ItaniumMangle.cpp Tue Jul  9 19:30:46 2013
@@ -99,7 +99,8 @@ static const unsigned UnknownArity = ~0U
 
 class ItaniumMangleContext : public MangleContext {
   llvm::DenseMap<const TagDecl *, uint64_t> AnonStructIds;
-  unsigned Discriminator;
+  typedef std::pair<const DeclContext*, IdentifierInfo*> DiscriminatorKeyTy;
+  llvm::DenseMap<DiscriminatorKeyTy, unsigned> Discriminator;
   llvm::DenseMap<const NamedDecl*, unsigned> Uniquifier;
   
 public:
@@ -114,11 +115,6 @@ public:
     return Result.first->second;
   }
 
-  void startNewFunction() {
-    MangleContext::startNewFunction();
-    mangleInitDiscriminator();
-  }
-
   /// @name Mangler Entry Points
   /// @{
 
@@ -153,21 +149,33 @@ public:
   void mangleItaniumThreadLocalInit(const VarDecl *D, raw_ostream &);
   void mangleItaniumThreadLocalWrapper(const VarDecl *D, raw_ostream &);
 
-  void mangleInitDiscriminator() {
-    Discriminator = 0;
-  }
-
   bool getNextDiscriminator(const NamedDecl *ND, unsigned &disc) {
-    // Lambda closure types with external linkage (indicated by a 
-    // non-zero lambda mangling number) have their own numbering scheme, so
-    // they do not need a discriminator.
+    // Lambda closure types are already numbered.
     if (const CXXRecordDecl *RD = dyn_cast<CXXRecordDecl>(ND))
-      if (RD->isLambda() && RD->getLambdaManglingNumber() > 0)
+      if (RD->isLambda())
         return false;
-        
+
+    // Anonymous tags are already numbered.
+    if (const TagDecl *Tag = dyn_cast<TagDecl>(ND)) {
+      if (Tag->getName().empty() && !Tag->getTypedefNameForAnonDecl())
+        return false;
+    }
+
+    // Use the canonical number for externally visible decls.
+    if (ND->isExternallyVisible()) {
+      unsigned discriminator = getASTContext().getManglingNumber(ND);
+      if (discriminator == 1)
+        return false;
+      disc = discriminator - 2;
+      return true;
+    }
+
+    // Make up a reasonable number for internal decls.
     unsigned &discriminator = Uniquifier[ND];
-    if (!discriminator)
-      discriminator = ++Discriminator;
+    if (!discriminator) {
+      const DeclContext *DC = getEffectiveDeclContext(ND);
+      discriminator = ++Discriminator[std::make_pair(DC, ND->getIdentifier())];
+    }
     if (discriminator == 1)
       return false;
     disc = discriminator-2;
@@ -1141,11 +1149,11 @@ void CXXNameMangler::mangleUnqualifiedNa
       }
     }
 
-    int UnnamedMangle = Context.getASTContext().getUnnamedTagManglingNumber(TD);
-    if (UnnamedMangle != -1) {
+    if (TD->isExternallyVisible()) {
+      unsigned UnnamedMangle = getASTContext().getManglingNumber(TD);
       Out << "Ut";
-      if (UnnamedMangle != 0)
-        Out << llvm::utostr(UnnamedMangle - 1);
+      if (UnnamedMangle > 1)
+        Out << llvm::utostr(UnnamedMangle - 2);
       Out << '_';
       break;
     }
@@ -1300,7 +1308,6 @@ void CXXNameMangler::mangleLocalName(con
     // <entity name> will of course contain a <closure-type-name>: Its 
     // numbering will be local to the particular argument in which it appears
     // -- other default arguments do not affect its encoding.
-    bool SkipDiscriminator = false;
     const CXXRecordDecl *CXXRD = dyn_cast<CXXRecordDecl>(RD);
     if (CXXRD->isLambda()) {
       if (const ParmVarDecl *Parm
@@ -1312,7 +1319,6 @@ void CXXNameMangler::mangleLocalName(con
           if (Num > 1)
             mangleNumber(Num - 2);
           Out << '_';
-          SkipDiscriminator = true;
         }
       }
     }
@@ -1328,24 +1334,21 @@ void CXXNameMangler::mangleLocalName(con
       const NamedDecl *ND = cast<NamedDecl>(D);
       mangleNestedName(ND, getEffectiveDeclContext(ND), true /*NoFunction*/);
     }
-
-    if (!SkipDiscriminator) {
-      unsigned disc;
-      if (Context.getNextDiscriminator(RD, disc)) {
-        if (disc < 10)
-          Out << '_' << disc;
-        else
-          Out << "__" << disc << '_';
-      }
+  } else {
+    if (const BlockDecl *BD = dyn_cast<BlockDecl>(D))
+      mangleUnqualifiedBlock(BD);
+    else
+      mangleUnqualifiedName(cast<NamedDecl>(D));
+  }
+  if (const NamedDecl *ND = dyn_cast<NamedDecl>(RD ? RD : D)) {
+    unsigned disc;
+    if (Context.getNextDiscriminator(ND, disc)) {
+      if (disc < 10)
+        Out << '_' << disc;
+      else
+        Out << "__" << disc << '_';
     }
-    
-    return;
   }
-
-  if (const BlockDecl *BD = dyn_cast<BlockDecl>(D))
-    mangleUnqualifiedBlock(BD);
-  else
-    mangleUnqualifiedName(cast<NamedDecl>(D));
 }
 
 void CXXNameMangler::mangleBlockForPrefix(const BlockDecl *Block) {

Modified: cfe/trunk/lib/AST/MangleNumberingContext.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/MangleNumberingContext.cpp?rev=185986&r1=185985&r2=185986&view=diff
==============================================================================
--- cfe/trunk/lib/AST/MangleNumberingContext.cpp (original)
+++ cfe/trunk/lib/AST/MangleNumberingContext.cpp Tue Jul  9 19:30:46 2013
@@ -19,7 +19,7 @@
 using namespace clang;
 
 unsigned
-MangleNumberingContext::getManglingNumber(CXXMethodDecl *CallOperator) {
+MangleNumberingContext::getManglingNumber(const CXXMethodDecl *CallOperator) {
   const FunctionProtoType *Proto
     = CallOperator->getType()->getAs<FunctionProtoType>();
   ASTContext &Context = CallOperator->getASTContext();
@@ -31,8 +31,18 @@ MangleNumberingContext::getManglingNumbe
 }
 
 unsigned
-MangleNumberingContext::getManglingNumber(BlockDecl *BD) {
+MangleNumberingContext::getManglingNumber(const BlockDecl *BD) {
   // FIXME: Compute a BlockPointerType?  Not obvious how.
   const Type *Ty = 0;
   return ++ManglingNumbers[Ty];
 }
+
+unsigned
+MangleNumberingContext::getManglingNumber(const VarDecl *VD) {
+  return ++VarManglingNumbers[VD->getIdentifier()];
+}
+
+unsigned
+MangleNumberingContext::getManglingNumber(const TagDecl *TD) {
+  return ++TagManglingNumbers[TD->getIdentifier()];
+}

Modified: cfe/trunk/lib/Sema/SemaDecl.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaDecl.cpp?rev=185986&r1=185985&r2=185986&view=diff
==============================================================================
--- cfe/trunk/lib/Sema/SemaDecl.cpp (original)
+++ cfe/trunk/lib/Sema/SemaDecl.cpp Tue Jul  9 19:30:46 2013
@@ -3043,6 +3043,27 @@ Decl *Sema::ParsedFreeStandingDeclSpec(S
   return ParsedFreeStandingDeclSpec(S, AS, DS, MultiTemplateParamsArg());
 }
 
+static void HandleTagNumbering(Sema &S, const TagDecl *Tag) {
+  if (isa<CXXRecordDecl>(Tag->getParent())) {
+    // If this tag is the direct child of a class, number it if
+    // it is anonymous.
+    if (!Tag->getName().empty() || Tag->getTypedefNameForAnonDecl())
+      return;
+    MangleNumberingContext &MCtx =
+        S.Context.getManglingNumberContext(Tag->getParent());
+    S.Context.setManglingNumber(Tag, MCtx.getManglingNumber(Tag));
+    return;
+  }
+
+  // If this tag isn't a direct child of a class, number it if it is local.
+  Decl *ManglingContextDecl;
+  if (MangleNumberingContext *MCtx =
+          S.getCurrentMangleNumberContext(Tag->getDeclContext(),
+                                          ManglingContextDecl)) {
+    S.Context.setManglingNumber(Tag, MCtx->getManglingNumber(Tag));
+  }
+}
+
 /// ParsedFreeStandingDeclSpec - This method is invoked when a declspec with
 /// no declarator (e.g. "struct foo;") is parsed. It also accepts template
 /// parameters to cope with template friend declarations.
@@ -3072,7 +3093,7 @@ Decl *Sema::ParsedFreeStandingDeclSpec(S
   }
 
   if (Tag) {
-    getASTContext().addUnnamedTag(Tag);
+    HandleTagNumbering(*this, Tag);
     Tag->setFreeStanding();
     if (Tag->isInvalidDecl())
       return Tag;
@@ -5120,6 +5141,15 @@ Sema::ActOnVariableDeclarator(Scope *S,
       isIncompleteDeclExternC(*this, NewVD))
     RegisterLocallyScopedExternCDecl(NewVD, S);
 
+  if (NewVD->isStaticLocal()) {
+    Decl *ManglingContextDecl;
+    if (MangleNumberingContext *MCtx =
+            getCurrentMangleNumberContext(NewVD->getDeclContext(),
+                                          ManglingContextDecl)) {
+      Context.setManglingNumber(NewVD, MCtx->getManglingNumber(NewVD));
+    }
+  }
+
   return NewVD;
 }
 
@@ -8374,9 +8404,10 @@ Sema::DeclGroupPtrTy Sema::FinalizeDecla
     if (Decl *D = Group[i])
       Decls.push_back(D);
 
-  if (DeclSpec::isDeclRep(DS.getTypeSpecType()))
+  if (DeclSpec::isDeclRep(DS.getTypeSpecType())) {
     if (const TagDecl *Tag = dyn_cast_or_null<TagDecl>(DS.getRepAsDecl()))
-      getASTContext().addUnnamedTag(Tag);
+      HandleTagNumbering(*this, Tag);
+  }
 
   return BuildDeclaratorGroup(Decls, DS.containsPlaceholderType());
 }

Modified: cfe/trunk/lib/Sema/SemaLambda.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaLambda.cpp?rev=185986&r1=185985&r2=185986&view=diff
==============================================================================
--- cfe/trunk/lib/Sema/SemaLambda.cpp (original)
+++ cfe/trunk/lib/Sema/SemaLambda.cpp Tue Jul  9 19:30:46 2013
@@ -53,7 +53,7 @@ static bool isInInlineFunction(const Dec
 }
 
 MangleNumberingContext *
-Sema::getCurrentMangleNumberContext(DeclContext *DC,
+Sema::getCurrentMangleNumberContext(const DeclContext *DC,
                                     Decl *&ManglingContextDecl) {
   // Compute the context for allocating mangling numbers in the current
   // expression, if the ABI requires them.

Modified: cfe/trunk/test/CodeGenCXX/linkage.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/CodeGenCXX/linkage.cpp?rev=185986&r1=185985&r2=185986&view=diff
==============================================================================
--- cfe/trunk/test/CodeGenCXX/linkage.cpp (original)
+++ cfe/trunk/test/CodeGenCXX/linkage.cpp Tue Jul  9 19:30:46 2013
@@ -12,7 +12,7 @@ namespace test1 {
 }
 
 namespace test2 {
-  // CHECK-DAG: define internal void @_ZN5test21fIZNS_L1gEvE1S_0EEvT_(
+  // CHECK-DAG: define internal void @_ZN5test21fIZNS_L1gEvE1SEEvT_(
   template <typename T> void f(T) {}
   static inline void *g() {
     struct S {
@@ -46,7 +46,7 @@ namespace test4 {
 }
 
 namespace test5 {
-  // CHECK-DAG: define linkonce_odr void @_ZN5test51fIZNS_1gILi1EEEPvvE1S_1EEvT_(
+  // CHECK-DAG: define linkonce_odr void @_ZN5test51fIZNS_1gILi1EEEPvvE1SEEvT_(
   template <typename T> void f(T) {}
   template <int N> inline void *g() {
     struct S {
@@ -58,7 +58,7 @@ namespace test5 {
 }
 
 namespace test6 {
-  // CHECK-DAG: define linkonce_odr void @_ZN5test61fIZZNS_1gEvEN1S1hE_2vE1T_3EEvv(
+  // CHECK-DAG: define linkonce_odr void @_ZN5test61fIZZNS_1gEvEN1S1hEvE1TEEvv(
   template <typename T> void f() {}
 
   inline void *g() {
@@ -76,7 +76,7 @@ namespace test6 {
 }
 
 namespace test7 {
-  // CHECK-DAG: define internal void @_ZN5test71fIZZNS_1gEvEN1S1hEvE1T_4EEvv(
+  // CHECK-DAG: define internal void @_ZN5test71fIZZNS_1gEvEN1S1hEvE1TEEvv(
   template <typename T> void f() {}
 
   void *g() {
@@ -105,7 +105,7 @@ namespace test8 {
 }
 
 namespace test9 {
-  // CHECK-DAG: define linkonce_odr void @_ZN5test91fIPZNS_1gEvE1S_5EEvT_(
+  // CHECK-DAG: define linkonce_odr void @_ZN5test91fIPZNS_1gEvE1SEEvT_(
   template <typename T> void f(T) {}
   inline void *g() {
     struct S {
@@ -116,7 +116,7 @@ namespace test9 {
 }
 
 namespace test10 {
-  // CHECK-DAG: define linkonce_odr void @_ZN6test101fIPFZNS_1gEvE1S_6vEEEvT_(
+  // CHECK-DAG: define linkonce_odr void @_ZN6test101fIPFZNS_1gEvE1SvEEEvT_(
   template <typename T> void f(T) {}
   inline void *g() {
     struct S {
@@ -128,7 +128,7 @@ namespace test10 {
 }
 
 namespace test11 {
-  // CHECK-DAG: define internal void @_ZN6test111fIPFZNS_1gEvE1S_7PNS_12_GLOBAL__N_11IEEEEvT_(
+  // CHECK-DAG: define internal void @_ZN6test111fIPFZNS_1gEvE1SPNS_12_GLOBAL__N_11IEEEEvT_(
   namespace {
     struct I {
     };
@@ -172,7 +172,7 @@ namespace test13 {
 }
 
 namespace test14 {
-  // CHECK-DAG: define linkonce_odr void @_ZN6test143fooIZNS_1fEvE1S_8E3barILPS1_0EEEvv(
+  // CHECK-DAG: define linkonce_odr void @_ZN6test143fooIZNS_1fEvE1SE3barILPS1_0EEEvv(
   template <typename T> struct foo {
     template <T *P> static void bar() {}
     static void *g() { return (void *)bar<nullptr>; }
@@ -186,7 +186,7 @@ namespace test14 {
 }
 
 namespace test15 {
-  // CHECK-DAG: define linkonce_odr void @_ZN6test153zedIZNS_3fooIiEEPvvE3bar_9EEvv(
+  // CHECK-DAG: define linkonce_odr void @_ZN6test153zedIZNS_3fooIiEEPvvE3barEEvv(
   template <class T> void zed() {}
   template <class T> void *foo() {
     class bar {
@@ -197,7 +197,7 @@ namespace test15 {
 }
 
 namespace test16 {
-  // CHECK-DAG: define linkonce_odr void @_ZN6test163zedIZNS_3fooIiE3barEvE1S__10_EEvv(
+  // CHECK-DAG: define linkonce_odr void @_ZN6test163zedIZNS_3fooIiE3barEvE1SEEvv(
   template <class T> void zed() {}
   template <class T> struct foo {
     static void *bar();

Modified: cfe/trunk/test/CodeGenCXX/mangle-local-class-names.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/CodeGenCXX/mangle-local-class-names.cpp?rev=185986&r1=185985&r2=185986&view=diff
==============================================================================
--- cfe/trunk/test/CodeGenCXX/mangle-local-class-names.cpp (original)
+++ cfe/trunk/test/CodeGenCXX/mangle-local-class-names.cpp Tue Jul  9 19:30:46 2013
@@ -55,6 +55,26 @@ void GORF (float IVAR1)
    }
 }
 
+// CHECK: @_ZZ12OmittingCodefEN4SSSSC1E_0RKf
+inline void OmittingCode(float x) {
+  if (0) {
+    struct SSSS {
+      float bv;
+      SSSS(const float& from): bv(from) { }
+    };
+
+    SSSS VAR1(x);
+  }
+
+  struct SSSS {
+    float bv;
+    SSSS(const float& from): bv(from) { }
+  };
+
+  SSSS VAR2(x);
+}
+void CallOmittingCode() { OmittingCode(1); }
+
 // CHECK: @_ZZ25LocalTemplateFunctionTestdEN5Local3fooIdEET_S1_
 int LocalTemplateFunctionTest(double d) {
   struct Local {
@@ -64,3 +84,14 @@ int LocalTemplateFunctionTest(double d)
   };
   return Local().foo(d);
 }
+
+// CHECK: @_ZZ15LocalAnonStructvENUt0_1gEv
+inline void LocalAnonStruct() {
+  if (0) {
+    struct { void f() {} } x;
+    x.f();
+  }
+  struct { void g() {} } y;
+  y.g();
+}
+void CallLocalAnonStruct() { LocalAnonStruct(); }

Modified: cfe/trunk/test/CodeGenCXX/mangle.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/CodeGenCXX/mangle.cpp?rev=185986&r1=185985&r2=185986&view=diff
==============================================================================
--- cfe/trunk/test/CodeGenCXX/mangle.cpp (original)
+++ cfe/trunk/test/CodeGenCXX/mangle.cpp Tue Jul  9 19:30:46 2013
@@ -888,7 +888,7 @@ namespace test38 {
 }
 
 namespace test39 {
-  // CHECK: define internal void @"_ZN6test394funcINS_3$_0Ut_EEEvT_"
+  // CHECK: define internal void @"_ZN6test394funcINS_3$_03$_1EEEvT_"
   typedef struct {
     struct {} a;
   } *foo;
@@ -897,3 +897,16 @@ namespace test39 {
     func(x->a);
   }
 }
+
+namespace test40 {
+  // CHECK: i32* @_ZZN6test401fEvE1a_0
+  void h(int&);
+  inline void f() {
+    if (0) {
+      static int a;
+    }
+    static int a;
+    h(a);
+  };
+  void g() { f(); }
+}





More information about the cfe-commits mailing list