SouraVX updated this revision to Diff 223240.

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D68117/new/

https://reviews.llvm.org/D68117

Files:
  clang/lib/CodeGen/CGDebugInfo.cpp
  clang/test/CodeGenCXX/dbg-info-all-calls-described.cpp
  clang/test/CodeGenCXX/debug-info-defaulted-in-class.cpp
  clang/test/CodeGenCXX/debug-info-defaulted-out-of-class.cpp
  clang/test/CodeGenCXX/debug-info-deleted.cpp
  clang/test/CodeGenCXX/debug-info-not-defaulted.cpp
  llvm/include/llvm/BinaryFormat/Dwarf.h
  llvm/include/llvm/IR/DebugInfoFlags.def
  llvm/include/llvm/IR/DebugInfoMetadata.h
  llvm/lib/BinaryFormat/Dwarf.cpp
  llvm/lib/CodeGen/AsmPrinter/DwarfUnit.cpp

Index: llvm/lib/CodeGen/AsmPrinter/DwarfUnit.cpp
===================================================================
--- llvm/lib/CodeGen/AsmPrinter/DwarfUnit.cpp
+++ llvm/lib/CodeGen/AsmPrinter/DwarfUnit.cpp
@@ -1296,6 +1296,19 @@
     addFlag(SPDie, dwarf::DW_AT_elemental);
   if (SP->isRecursive())
     addFlag(SPDie, dwarf::DW_AT_recursive);
+  if (DD->getDwarfVersion() >= 5) {
+    if (SP->isDefaultedInClass())
+      addUInt(SPDie, dwarf::DW_AT_defaulted, dwarf::DW_FORM_data1,
+              dwarf::DW_DEFAULTED_in_class);
+    if (SP->isDefaultedOutOfClass())
+      addUInt(SPDie, dwarf::DW_AT_defaulted, dwarf::DW_FORM_data1,
+              dwarf::DW_DEFAULTED_out_of_class);
+    if (SP->isNotDefaulted())
+      addUInt(SPDie, dwarf::DW_AT_defaulted, dwarf::DW_FORM_data1,
+              dwarf::DW_DEFAULTED_no);
+    if (SP->isDeleted())
+      addFlag(SPDie, dwarf::DW_AT_deleted);
+  }
 }
 
 void DwarfUnit::constructSubrangeDIE(DIE &Buffer, const DISubrange *SR,
Index: llvm/lib/BinaryFormat/Dwarf.cpp
===================================================================
--- llvm/lib/BinaryFormat/Dwarf.cpp
+++ llvm/lib/BinaryFormat/Dwarf.cpp
@@ -271,6 +271,19 @@
   return StringRef();
 }
 
+StringRef llvm::dwarf::DefaultedMemberString(unsigned DefaultedEncodings) {
+  switch (DefaultedEncodings) {
+  // Defaulted Member Encodings codes
+  case DW_DEFAULTED_no:
+    return "DW_DEFAULTED_no";
+  case DW_DEFAULTED_in_class:
+    return "DW_DEFAULTED_in_class";
+  case DW_DEFAULTED_out_of_class:
+    return "DW_DEFAULTED_out_of_class";
+  }
+  return StringRef();
+}
+
 StringRef llvm::dwarf::VisibilityString(unsigned Visibility) {
   switch (Visibility) {
   case DW_VIS_local:
@@ -601,6 +614,8 @@
     return ArrayOrderString(Val);
   case DW_AT_APPLE_runtime_class:
     return LanguageString(Val);
+  case DW_AT_defaulted:
+    return DefaultedMemberString(Val);
   }
 
   return StringRef();
Index: llvm/include/llvm/IR/DebugInfoMetadata.h
===================================================================
--- llvm/include/llvm/IR/DebugInfoMetadata.h
+++ llvm/include/llvm/IR/DebugInfoMetadata.h
@@ -1758,6 +1758,14 @@
   bool isPure() const { return getSPFlags() & SPFlagPure; }
   bool isElemental() const { return getSPFlags() & SPFlagElemental; }
   bool isRecursive() const { return getSPFlags() & SPFlagRecursive; }
+  bool isDefaultedInClass() const {
+    return getSPFlags() & SPFlagDefaultedInClass;
+  }
+  bool isDefaultedOutOfClass() const {
+    return getSPFlags() & SPFlagDefaultedOutOfClass;
+  }
+  bool isNotDefaulted() const { return getSPFlags() & SPFlagNotDefaulted; }
+  bool isDeleted() const { return getSPFlags() & SPFlagDeleted; }
 
   /// Check if this is reference-qualified.
   ///
Index: llvm/include/llvm/IR/DebugInfoFlags.def
===================================================================
--- llvm/include/llvm/IR/DebugInfoFlags.def
+++ llvm/include/llvm/IR/DebugInfoFlags.def
@@ -88,11 +88,15 @@
 HANDLE_DISP_FLAG((1u << 6), Elemental)
 HANDLE_DISP_FLAG((1u << 7), Recursive)
 HANDLE_DISP_FLAG((1u << 8), MainSubprogram)
+HANDLE_DISP_FLAG((1u << 9), Deleted)
+HANDLE_DISP_FLAG((1u << 10), DefaultedInClass)
+HANDLE_DISP_FLAG((1u << 11), DefaultedOutOfClass)
+HANDLE_DISP_FLAG((1u << 12), NotDefaulted)
 
 #ifdef DISP_FLAG_LARGEST_NEEDED
 // Intended to be used with ADT/BitmaskEnum.h.
 // NOTE: Always must be equal to largest flag, check this when adding new flags.
-HANDLE_DISP_FLAG((1 << 8), Largest)
+HANDLE_DISP_FLAG((1 << 12), Largest)
 #undef DISP_FLAG_LARGEST_NEEDED
 #endif
 
Index: llvm/include/llvm/BinaryFormat/Dwarf.h
===================================================================
--- llvm/include/llvm/BinaryFormat/Dwarf.h
+++ llvm/include/llvm/BinaryFormat/Dwarf.h
@@ -411,6 +411,7 @@
 StringRef DecimalSignString(unsigned Sign);
 StringRef EndianityString(unsigned Endian);
 StringRef AccessibilityString(unsigned Access);
+StringRef DefaultedMemberString(unsigned DefaultedEncodings);
 StringRef VisibilityString(unsigned Visibility);
 StringRef VirtualityString(unsigned Virtuality);
 StringRef LanguageString(unsigned Language);
Index: clang/test/CodeGenCXX/debug-info-not-defaulted.cpp
===================================================================
--- /dev/null
+++ clang/test/CodeGenCXX/debug-info-not-defaulted.cpp
@@ -0,0 +1,30 @@
+// Test for debug info for C++11 Not defaulted member functions
+
+//Supported: -O0, standalone DI
+// RUN: %clang_cc1 -emit-llvm -triple x86_64-linux-gnu %s -o - \
+// RUN:   -O0 -disable-llvm-passes \
+// RUN:   -debug-info-kind=standalone \
+// RUN: | FileCheck %s -check-prefix=ATTR
+
+// ATTR: DISubprogram(name: "not_defaulted", {{.*}}, flags: DIFlagPublic | DIFlagPrototyped, spFlags: DISPFlagNotDefaulted
+// ATTR: DISubprogram(name: "not_defaulted", {{.*}}, flags: DIFlagPublic | DIFlagPrototyped, spFlags: DISPFlagNotDefaulted
+// ATTR: DISubprogram(name: "operator=", linkageName: "_ZN13not_defaultedaSERS_", {{.*}}, flags: DIFlagPublic | DIFlagPrototyped, spFlags: DISPFlagNotDefaulted
+// ATTR: DISubprogram(name: "not_defaulted", {{.*}}, flags: DIFlagPublic | DIFlagPrototyped, spFlags: DISPFlagNotDefaulted
+// ATTR: DISubprogram(name: "operator=", linkageName: "_ZN13not_defaultedaSEOS_", {{.*}}, flags: DIFlagPublic | DIFlagPrototyped, spFlags: DISPFlagNotDefaulted
+// ATTR: DISubprogram(name: "~not_defaulted", {{.*}}, flags: DIFlagPublic | DIFlagPrototyped, spFlags: DISPFlagNotDefaulted
+class not_defaulted {
+public:
+  not_defaulted() {}
+
+  not_defaulted(const not_defaulted &) {}
+  not_defaulted &operator=(not_defaulted &param) { return param; }
+
+  not_defaulted(not_defaulted &&param) {}
+  not_defaulted &operator=(not_defaulted &&param) { return param; }
+
+  ~not_defaulted() {}
+};
+
+void foo() {
+  not_defaulted obj1;
+}
Index: clang/test/CodeGenCXX/debug-info-deleted.cpp
===================================================================
--- /dev/null
+++ clang/test/CodeGenCXX/debug-info-deleted.cpp
@@ -0,0 +1,30 @@
+// Test for debug info for C++11 deleted member functions
+
+//Supported: -O0, standalone DI
+// RUN: %clang_cc1 -emit-llvm -triple x86_64-linux-gnu %s -o - \
+// RUN:   -O0 -disable-llvm-passes \
+// RUN:   -debug-info-kind=standalone \
+// RUN: | FileCheck %s -check-prefix=ATTR
+
+// ATTR: DISubprogram(name: "deleted", {{.*}}, flags: DIFlagPublic | DIFlagPrototyped, spFlags: DISPFlagDefaultedInClass
+// ATTR: DISubprogram(name: "deleted", {{.*}}, flags: DIFlagPublic | DIFlagPrototyped, spFlags: DISPFlagDeleted
+// ATTR: DISubprogram(name: "operator=", linkageName: "_ZN7deletedaSERKS_", {{.*}}, flags: DIFlagPublic | DIFlagPrototyped, spFlags: DISPFlagDeleted
+// ATTR: DISubprogram(name: "deleted", {{.*}}, flags: DIFlagPublic | DIFlagPrototyped, spFlags: DISPFlagDeleted
+// ATTR: DISubprogram(name: "operator=", linkageName: "_ZN7deletedaSEOS_", {{.*}}, flags: DIFlagPublic | DIFlagPrototyped, spFlags: DISPFlagDeleted
+// ATTR: DISubprogram(name: "~deleted", {{.*}}, flags: DIFlagPublic | DIFlagPrototyped, spFlags: DISPFlagDefaultedInClass
+class deleted {
+public:
+  deleted() = default; // Defaulted on purpose, so as to facilitate object creation
+
+  deleted(const deleted &) = delete;
+  deleted &operator=(const deleted &) = delete;
+
+  deleted(deleted &&) = delete;
+  deleted &operator=(deleted &&) = delete;
+
+  ~deleted() = default;
+};
+
+void foo() {
+  deleted obj1;
+}
Index: clang/test/CodeGenCXX/debug-info-defaulted-out-of-class.cpp
===================================================================
--- /dev/null
+++ clang/test/CodeGenCXX/debug-info-defaulted-out-of-class.cpp
@@ -0,0 +1,40 @@
+// Test for debug info for C++11 out of defaulted member functions
+
+//Supported: -O0, standalone DI
+// RUN: %clang_cc1 -emit-llvm -triple x86_64-linux-gnu %s -o - \
+// RUN:   -O0 -disable-llvm-passes \
+// RUN:   -debug-info-kind=standalone \
+// RUN: | FileCheck %s -check-prefix=ATTR
+
+// ATTR: DISubprogram(name: "out_of_class_defaulted", {{.*}}, flags: DIFlagPublic | DIFlagPrototyped, spFlags: DISPFlagDefaultedOutOfClass
+// ATTR: DISubprogram(name: "out_of_class_defaulted", {{.*}}, flags: DIFlagPublic | DIFlagPrototyped
+// ATTR: DISubprogram(name: "operator=", linkageName: "_ZN22out_of_class_defaultedaSERKS_", {{.*}}, flags: DIFlagPublic | DIFlagPrototyped
+// ATTR: DISubprogram(name: "out_of_class_defaulted", {{.*}}, flags: DIFlagPublic | DIFlagPrototyped
+// ATTR: DISubprogram(name: "operator=", linkageName: "_ZN22out_of_class_defaultedaSEOS_", {{.*}}, flags: DIFlagPublic | DIFlagPrototyped
+// ATTR: DISubprogram(name: "~out_of_class_defaulted", {{.*}}, flags: DIFlagPublic | DIFlagPrototyped
+class out_of_class_defaulted {
+public:
+  out_of_class_defaulted();
+
+  out_of_class_defaulted(const out_of_class_defaulted &);
+  out_of_class_defaulted &operator=(const out_of_class_defaulted &);
+
+  out_of_class_defaulted(out_of_class_defaulted &&);
+  out_of_class_defaulted &operator=(out_of_class_defaulted &&);
+
+  ~out_of_class_defaulted();
+};
+
+out_of_class_defaulted::out_of_class_defaulted() = default;
+
+out_of_class_defaulted::out_of_class_defaulted(const out_of_class_defaulted &) = default;
+out_of_class_defaulted &out_of_class_defaulted::operator=(const out_of_class_defaulted &) = default;
+
+out_of_class_defaulted::out_of_class_defaulted(out_of_class_defaulted &&) = default;
+out_of_class_defaulted &out_of_class_defaulted::operator=(out_of_class_defaulted &&) = default;
+
+out_of_class_defaulted::~out_of_class_defaulted() = default;
+
+void foo() {
+  out_of_class_defaulted obj1;
+}
Index: clang/test/CodeGenCXX/debug-info-defaulted-in-class.cpp
===================================================================
--- /dev/null
+++ clang/test/CodeGenCXX/debug-info-defaulted-in-class.cpp
@@ -0,0 +1,30 @@
+// Test for debug info for C++11 defaulted member functions
+
+//Supported: -O0, standalone DI
+// RUN: %clang_cc1 -emit-llvm -triple x86_64-linux-gnu %s -o - \
+// RUN:   -O0 -disable-llvm-passes \
+// RUN:   -debug-info-kind=standalone \
+// RUN: | FileCheck %s -check-prefix=ATTR
+
+// ATTR: DISubprogram(name: "inclass_defaulted", {{.*}}, flags: DIFlagPublic | DIFlagPrototyped, spFlags: DISPFlagDefaultedInClass
+// ATTR: DISubprogram(name: "inclass_defaulted", {{.*}}, flags: DIFlagPublic | DIFlagPrototyped, spFlags: DISPFlagDefaultedInClass
+// ATTR: DISubprogram(name: "operator=", linkageName: "_ZN17inclass_defaultedaSERKS_", {{.*}}, flags: DIFlagPublic | DIFlagPrototyped, spFlags: DISPFlagDefaultedInClass
+// ATTR: DISubprogram(name: "inclass_defaulted", {{.*}}, flags: DIFlagPublic | DIFlagPrototyped, spFlags: DISPFlagDefaultedInClass
+// ATTR: DISubprogram(name: "operator=", linkageName: "_ZN17inclass_defaultedaSEOS_", {{.*}}, flags: DIFlagPublic | DIFlagPrototyped, spFlags: DISPFlagDefaultedInClass
+// ATTR: DISubprogram(name: "~inclass_defaulted", {{.*}}, flags: DIFlagPublic | DIFlagPrototyped, spFlags: DISPFlagDefaultedInClass
+class inclass_defaulted {
+public:
+  inclass_defaulted() = default;
+
+  inclass_defaulted(const inclass_defaulted &) = default;
+  inclass_defaulted &operator=(const inclass_defaulted &) = default;
+
+  inclass_defaulted(inclass_defaulted &&) = default;
+  inclass_defaulted &operator=(inclass_defaulted &&) = default;
+
+  ~inclass_defaulted() = default;
+};
+
+void foo() {
+  inclass_defaulted obj1;
+}
Index: clang/test/CodeGenCXX/dbg-info-all-calls-described.cpp
===================================================================
--- clang/test/CodeGenCXX/dbg-info-all-calls-described.cpp
+++ clang/test/CodeGenCXX/dbg-info-all-calls-described.cpp
@@ -57,7 +57,7 @@
 // NO-ATTR-NOT: FlagAllCallsDescribed
 
 // HAS-ATTR-DAG: DISubprogram(name: "declaration2", {{.*}}, flags: DIFlagPrototyped | DIFlagAllCallsDescribed, spFlags: DISPFlagDefinition
-// HAS-ATTR-DAG: DISubprogram(name: "struct1", {{.*}}, flags: DIFlagPrototyped, spFlags: DISPFlagOptimized)
+// HAS-ATTR-DAG: DISubprogram(name: "struct1", {{.*}}, flags: DIFlagPrototyped, spFlags: DISPFlagOptimized | DISPFlagNotDefaulted)
 // HAS-ATTR-DAG: DISubprogram(name: "struct1", {{.*}}, flags: DIFlagPrototyped | DIFlagAllCallsDescribed, spFlags: DISPFlagDefinition
 // HAS-ATTR-DAG: DISubprogram(name: "method1", {{.*}}, flags: DIFlagPrototyped | DIFlagAllCallsDescribed, spFlags: DISPFlagDefinition
 // HAS-ATTR-DAG: DISubprogram(name: "force_irgen", {{.*}}, flags: DIFlagPrototyped | DIFlagAllCallsDescribed, spFlags: DISPFlagDefinition
Index: clang/lib/CodeGen/CGDebugInfo.cpp
===================================================================
--- clang/lib/CodeGen/CGDebugInfo.cpp
+++ clang/lib/CodeGen/CGDebugInfo.cpp
@@ -1605,6 +1605,36 @@
     ContainingType = RecordTy;
   }
 
+  // DWARF-5 support for, defaulted, deleted member functions
+  auto checkAttrDefaultedOrDeleted = [&SPFlags](const CXXMethodDecl *Method) {
+    if (Method->getCanonicalDecl()->isDeleted()) {
+      SPFlags |= llvm::DISubprogram::SPFlagDeleted;
+      return;
+    }
+
+    if (Method->getCanonicalDecl()->isDefaulted()) {
+      SPFlags |= llvm::DISubprogram::SPFlagDefaultedInClass;
+      return;
+    } else if (const auto Def = Method->getDefinition()) {
+      if (Def->isDefaulted()) {
+        SPFlags |= llvm::DISubprogram::SPFlagDefaultedOutOfClass;
+        return;
+      } else {
+        SPFlags |= llvm::DISubprogram::SPFlagNotDefaulted;
+        return;
+      }
+    }
+  };
+
+  if (const auto *CXXC = dyn_cast<CXXConstructorDecl>(Method))
+    checkAttrDefaultedOrDeleted(CXXC);
+
+  if (const auto *DXXC = dyn_cast<CXXDestructorDecl>(Method))
+    checkAttrDefaultedOrDeleted(DXXC);
+
+  if (Method->isCopyAssignmentOperator() || Method->isMoveAssignmentOperator())
+    checkAttrDefaultedOrDeleted(Method);
+
   if (Method->isStatic())
     Flags |= llvm::DINode::FlagStaticMember;
   if (Method->isImplicit())
_______________________________________________
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to