[lldb-instr] Support LLDB_RECORD_DUMMY
authorJonas Devlieghere <jonas@devlieghere.com>
Fri, 8 Mar 2019 18:33:40 +0000 (18:33 +0000)
committerJonas Devlieghere <jonas@devlieghere.com>
Fri, 8 Mar 2019 18:33:40 +0000 (18:33 +0000)
Extend lldb-instr to insert LLDB_RECORD_DUMMY macros for currently
unsupported signatures (void and function pointers).

llvm-svn: 355710

lldb/lit/tools/lldb-instr/Inputs/foo.cpp
lldb/lit/tools/lldb-instr/Inputs/foo.h
lldb/lit/tools/lldb-instr/TestInstrumentationRecord.test
lldb/lit/tools/lldb-instr/TestInstrumentationRegister.test
lldb/tools/lldb-instr/Instrument.cpp

index bef01dc..36a7323 100644 (file)
@@ -15,3 +15,4 @@ void Foo::G(const char *fmt...) {}
 Foo Foo::H() { return Foo(); }
 void Foo::I() const { MACRO_FOO; }
 Bar Foo::J() const { return MACRO_BAR(Bar()); }
+Bar Foo::K(void *v) const { return Bar(); }
index 95c0c00..9e2608e 100644 (file)
@@ -13,4 +13,5 @@ struct Foo {
   static Foo H();
   void I() const;
   Bar J() const;
+  Bar K(void *v) const;
 };
index af33df0..cd29414 100644 (file)
@@ -18,3 +18,5 @@
 # CHECK-NOT: LLDB_RECORD_METHOD_CONST_NO_ARGS(void, Foo, I);
 # CHECK: LLDB_RECORD_METHOD_CONST_NO_ARGS(Bar, Foo, J);
 # CHECK-NOT: LLDB_RECORD_RESULT(Bar());
+# CHECK: LLDB_RECORD_DUMMY(Bar, Foo, K, (void *), v);
+# CHECK-NOT: LLDB_RECORD_RESULT(Bar());
index 651880c..0b15944 100644 (file)
@@ -13,4 +13,5 @@
 # CHECK: LLDB_REGISTER_STATIC_METHOD(int, Foo, F, (int));
 # CHECK-NOT: LLDB_REGISTER_STATIC_METHOD(void, Foo, G
 # CHECK-NOT: LLDB_REGISTER_METHOD_CONST(void, Foo, I, ());
+# CHECK-NOT: LLDB_REGISTER_METHOD_CONST(Bar, Foo, K, (void*));
 # CHECK: }
index 476b5e6..c46afb4 100644 (file)
@@ -100,6 +100,19 @@ static std::string GetRecordConstructorMacro(StringRef Class,
   return OS.str();
 }
 
+static std::string GetRecordDummyMacro(StringRef Result, StringRef Class,
+                                       StringRef Method, StringRef Signature,
+                                       StringRef Values) {
+  assert(!Values.empty());
+  std::string Macro;
+  llvm::raw_string_ostream OS(Macro);
+
+  OS << "LLDB_RECORD_DUMMY(" << Result << ", " << Class << ", " << Method;
+  OS << ", (" << Signature << "), " << Values << ");\n\n";
+
+  return OS.str();
+}
+
 static std::string GetRegisterConstructorMacro(StringRef Class,
                                                StringRef Signature) {
   std::string Macro;
@@ -170,24 +183,21 @@ public:
     PrintingPolicy Policy(Context.getLangOpts());
     Policy.Bool = true;
 
+    // Unsupported signatures get a dummy macro.
+    bool ShouldInsertDummy = false;
+
     // Collect the functions parameter types and names.
     std::vector<std::string> ParamTypes;
     std::vector<std::string> ParamNames;
     for (auto *P : Decl->parameters()) {
       QualType T = P->getType();
-
-      // Currently we don't support functions that have function pointers as an
-      // argument.
-      if (T->isFunctionPointerType())
-        return false;
-
-      // Currently we don't support functions that have void pointers as an
-      // argument.
-      if (T->isVoidPointerType())
-        return false;
-
       ParamTypes.push_back(T.getAsString(Policy));
       ParamNames.push_back(P->getNameAsString());
+
+      // Currently we don't support functions that have void pointers or
+      // function pointers as an argument, in which case we insert a dummy
+      // macro.
+      ShouldInsertDummy |= T->isFunctionPointerType() || T->isVoidPointerType();
     }
 
     // Convert the two lists to string for the macros.
@@ -199,7 +209,13 @@ public:
 
     // Construct the macros.
     std::string Macro;
-    if (isa<CXXConstructorDecl>(Decl)) {
+    if (ShouldInsertDummy) {
+      // Don't insert a register call for dummy macros.
+      Macro = GetRecordDummyMacro(
+          ReturnType.getAsString(Policy), Record->getNameAsString(),
+          Decl->getNameAsString(), ParamTypesStr, ParamNamesStr);
+
+    } else if (isa<CXXConstructorDecl>(Decl)) {
       llvm::outs() << GetRegisterConstructorMacro(Record->getNameAsString(),
                                                   ParamTypesStr);
 
@@ -229,7 +245,7 @@ public:
 
     // If the function returns a class or struct, we need to wrap its return
     // statement(s).
-    if (ReturnType->isStructureOrClassType()) {
+    if (!ShouldInsertDummy && ReturnType->isStructureOrClassType()) {
       SBReturnVisitor Visitor(MyRewriter);
       Visitor.TraverseDecl(Decl);
     }