akhuang created this revision.
akhuang added reviewers: rnk, dblaikie.
akhuang requested review of this revision.
Herald added a project: clang.
Herald added a subscriber: cfe-commits.

Currently (for codeview) lambdas have a string like `<lambda_0>` in
their mangled name, and don't have any display name. This change uses the
`<lambda_0>` as the display name, which helps distinguish between lambdas
in -gline-tables-only, since there are no linkage names there. 
It also changes how we display lambda names; previously we used
`<unnamed-tag>`; now it will show `<lambda_0>`.

I added a function to the mangling context code to create this string;
for Itanium it just returns an empty string.

Bug: https://bugs.llvm.org/show_bug.cgi?id=48432


Repository:
  rG LLVM Github Monorepo

https://reviews.llvm.org/D95187

Files:
  clang/include/clang/AST/Mangle.h
  clang/lib/AST/ItaniumMangle.cpp
  clang/lib/AST/MicrosoftMangle.cpp
  clang/lib/CodeGen/CGDebugInfo.cpp
  clang/test/CodeGenCXX/debug-info-codeview-unnamed.cpp
  clang/test/CodeGenCXX/debug-info-gline-tables-only-codeview.cpp

Index: clang/test/CodeGenCXX/debug-info-gline-tables-only-codeview.cpp
===================================================================
--- clang/test/CodeGenCXX/debug-info-gline-tables-only-codeview.cpp
+++ clang/test/CodeGenCXX/debug-info-gline-tables-only-codeview.cpp
@@ -10,6 +10,8 @@
 void f() {}
 }
 
+auto lambda1 = []() { return 1; };
+
 NS::C c;
 
 void test() {
@@ -27,4 +29,10 @@
   // CHECK-NOT: identifier
   // CHECK: ![[MTYPE]] = !DISubroutineType(types: !{{.*}})
   c.m();
+
+  // CHECK: !DISubprogram(name: "operator()", scope: ![[LAMBDA1:[0-9]+]]
+  // CHECK: ![[LAMBDA1]] = !DICompositeType(tag: DW_TAG_class_type,
+  // CHECK-SAME:                            name: "<lambda_0>"
+  // CHECK-SAME:                            flags: DIFlagFwdDecl
+  lambda1();
 }
Index: clang/test/CodeGenCXX/debug-info-codeview-unnamed.cpp
===================================================================
--- clang/test/CodeGenCXX/debug-info-codeview-unnamed.cpp
+++ clang/test/CodeGenCXX/debug-info-codeview-unnamed.cpp
@@ -100,7 +100,7 @@
   // MSVC-SAME:      )
   // MSVC:       [[TYPE_OF_FOUR]] = distinct !DICompositeType
   // MSVC-SAME:      tag: DW_TAG_class_type
-  // MSVC-NOT:       name:
+  // MSVC-SAME:      name: "<lambda_0>"
   // MSVC-SAME:      identifier: ".?AV<lambda_0>@?0??main@@9@"
   // MSVC-SAME:      )
 
Index: clang/lib/CodeGen/CGDebugInfo.cpp
===================================================================
--- clang/lib/CodeGen/CGDebugInfo.cpp
+++ clang/lib/CodeGen/CGDebugInfo.cpp
@@ -342,6 +342,12 @@
         // associate typedef mangled in if they have one.
         Name = TND->getName();
 
+      // Give lambdas a display name based on their name mangling.
+      if (const CXXRecordDecl *CXXRD = dyn_cast<CXXRecordDecl>(RD))
+        if (CXXRD->isLambda())
+          return internString(
+              CGM.getCXXABI().getMangleContext().getLambdaString(CXXRD));
+
       if (!Name.empty()) {
         SmallString<256> UnnamedType("<unnamed-type-");
         UnnamedType += Name;
Index: clang/lib/AST/MicrosoftMangle.cpp
===================================================================
--- clang/lib/AST/MicrosoftMangle.cpp
+++ clang/lib/AST/MicrosoftMangle.cpp
@@ -228,6 +228,34 @@
     return true;
   }
 
+  StringRef getLambdaString(const CXXRecordDecl *Lambda) override {
+    assert(Lambda->isLambda() && "RD must be a lambda!");
+    llvm::SmallString<10> Name("<lambda_");
+
+    Decl *LambdaContextDecl = Lambda->getLambdaContextDecl();
+    unsigned LambdaManglingNumber = Lambda->getLambdaManglingNumber();
+    unsigned LambdaId;
+    const ParmVarDecl *Parm = dyn_cast_or_null<ParmVarDecl>(LambdaContextDecl);
+    const FunctionDecl *Func =
+        Parm ? dyn_cast<FunctionDecl>(Parm->getDeclContext()) : nullptr;
+
+    if (Func) {
+      unsigned DefaultArgNo =
+          Func->getNumParams() - Parm->getFunctionScopeIndex();
+      Name += llvm::utostr(DefaultArgNo);
+      Name += "_";
+    }
+
+    if (LambdaManglingNumber)
+      LambdaId = LambdaManglingNumber;
+    else
+      LambdaId = getLambdaId(Lambda);
+
+    Name += llvm::utostr(LambdaId);
+    Name += ">";
+    return StringRef(Name);
+  }
+
   unsigned getLambdaId(const CXXRecordDecl *RD) {
     assert(RD->isLambda() && "RD must be a lambda!");
     assert(!RD->isExternallyVisible() && "RD must not be visible!");
@@ -972,32 +1000,10 @@
 
       if (const CXXRecordDecl *Record = dyn_cast<CXXRecordDecl>(TD)) {
         if (Record->isLambda()) {
-          llvm::SmallString<10> Name("<lambda_");
+          mangleSourceName(Context.getLambdaString(Record).str());
 
-          Decl *LambdaContextDecl = Record->getLambdaContextDecl();
           unsigned LambdaManglingNumber = Record->getLambdaManglingNumber();
-          unsigned LambdaId;
-          const ParmVarDecl *Parm =
-              dyn_cast_or_null<ParmVarDecl>(LambdaContextDecl);
-          const FunctionDecl *Func =
-              Parm ? dyn_cast<FunctionDecl>(Parm->getDeclContext()) : nullptr;
-
-          if (Func) {
-            unsigned DefaultArgNo =
-                Func->getNumParams() - Parm->getFunctionScopeIndex();
-            Name += llvm::utostr(DefaultArgNo);
-            Name += "_";
-          }
-
-          if (LambdaManglingNumber)
-            LambdaId = LambdaManglingNumber;
-          else
-            LambdaId = Context.getLambdaId(Record);
-
-          Name += llvm::utostr(LambdaId);
-          Name += ">";
-
-          mangleSourceName(Name);
+          Decl *LambdaContextDecl = Record->getLambdaContextDecl();
 
           // If the context is a variable or a class member and not a parameter,
           // it is encoded in a qualified name.
Index: clang/lib/AST/ItaniumMangle.cpp
===================================================================
--- clang/lib/AST/ItaniumMangle.cpp
+++ clang/lib/AST/ItaniumMangle.cpp
@@ -203,6 +203,10 @@
     disc = discriminator-2;
     return true;
   }
+
+  StringRef getLambdaString(const CXXRecordDecl *Lambda) override {
+    return StringRef();
+  }
   /// @}
 };
 
Index: clang/include/clang/AST/Mangle.h
===================================================================
--- clang/include/clang/AST/Mangle.h
+++ clang/include/clang/AST/Mangle.h
@@ -89,6 +89,8 @@
     return Result.first->second;
   }
 
+  virtual StringRef getLambdaString(const CXXRecordDecl *Lambda) = 0;
+
   /// @name Mangler Entry Points
   /// @{
 
_______________________________________________
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to