[gcov/Darwin] Ensure external symbols are exported when using an export list
authorVedant Kumar <vsk@apple.com>
Mon, 3 Dec 2018 20:53:58 +0000 (20:53 +0000)
committerVedant Kumar <vsk@apple.com>
Mon, 3 Dec 2018 20:53:58 +0000 (20:53 +0000)
Make sure that symbols needed to implement runtime support for gcov are
exported when using an export list on Darwin.

Without the clang driver exporting these symbols, the linker hides them,
resulting in tapi verification failures.

rdar://45944768

Differential Revision: https://reviews.llvm.org/D55151

llvm-svn: 348187

clang/include/clang/Driver/ToolChain.h
clang/lib/Driver/ToolChain.cpp
clang/lib/Driver/ToolChains/Darwin.cpp
clang/test/Driver/darwin-ld.c
compiler-rt/test/profile/instrprof-darwin-exports.c

index 9b0590a..73fd914 100644 (file)
@@ -381,6 +381,9 @@ public:
   /// needsProfileRT - returns true if instrumentation profile is on.
   static bool needsProfileRT(const llvm::opt::ArgList &Args);
 
+  /// Returns true if gcov instrumentation (-fprofile-arcs or --coverage) is on.
+  static bool needsGCovInstrumentation(const llvm::opt::ArgList &Args);
+
   /// IsUnwindTablesDefault - Does this tool chain use -funwind-tables
   /// by default.
   virtual bool IsUnwindTablesDefault(const llvm::opt::ArgList &Args) const;
index 1667536..294e775 100644 (file)
@@ -403,19 +403,23 @@ std::string ToolChain::getArchSpecificLibPath() const {
 }
 
 bool ToolChain::needsProfileRT(const ArgList &Args) {
-  if (Args.hasFlag(options::OPT_fprofile_arcs, options::OPT_fno_profile_arcs,
-                   false) ||
+  if (needsGCovInstrumentation(Args) ||
       Args.hasArg(options::OPT_fprofile_generate) ||
       Args.hasArg(options::OPT_fprofile_generate_EQ) ||
       Args.hasArg(options::OPT_fprofile_instr_generate) ||
       Args.hasArg(options::OPT_fprofile_instr_generate_EQ) ||
-      Args.hasArg(options::OPT_fcreate_profile) ||
-      Args.hasArg(options::OPT_coverage))
+      Args.hasArg(options::OPT_fcreate_profile))
     return true;
 
   return false;
 }
 
+bool ToolChain::needsGCovInstrumentation(const llvm::opt::ArgList &Args) {
+  return Args.hasFlag(options::OPT_fprofile_arcs, options::OPT_fno_profile_arcs,
+                      false) ||
+         Args.hasArg(options::OPT_coverage);
+}
+
 Tool *ToolChain::SelectTool(const JobAction &JA) const {
   if (getDriver().ShouldUseClangCompiler(JA)) return getClang();
   Action::ActionClass AC = JA.getKind();
index 50c0db5..452b6b8 100644 (file)
@@ -1034,11 +1034,17 @@ void Darwin::addProfileRTLibs(const ArgList &Args,
   // runtime, automatically export symbols necessary to implement some of the
   // runtime's functionality.
   if (hasExportSymbolDirective(Args)) {
-    addExportedSymbol(CmdArgs, "___llvm_profile_filename");
-    addExportedSymbol(CmdArgs, "___llvm_profile_raw_version");
-    addExportedSymbol(CmdArgs, "_lprofCurFilename");
+    if (needsGCovInstrumentation(Args)) {
+      addExportedSymbol(CmdArgs, "___gcov_flush");
+      addExportedSymbol(CmdArgs, "_flush_fn_list");
+      addExportedSymbol(CmdArgs, "_writeout_fn_list");
+    } else {
+      addExportedSymbol(CmdArgs, "___llvm_profile_filename");
+      addExportedSymbol(CmdArgs, "___llvm_profile_raw_version");
+      addExportedSymbol(CmdArgs, "_lprofCurFilename");
+      addExportedSymbol(CmdArgs, "_lprofMergeValueProfData");
+    }
     addExportedSymbol(CmdArgs, "_lprofDirMode");
-    addExportedSymbol(CmdArgs, "_lprofMergeValueProfData");
   }
 }
 
index 3c339a1..5198ef0 100644 (file)
 // RUN: FileCheck -check-prefix=PROFILE_EXPORT %s < %t.log
 // PROFILE_EXPORT: "-exported_symbol" "___llvm_profile_filename" "-exported_symbol" "___llvm_profile_raw_version" "-exported_symbol" "_lprofCurFilename"
 //
-// RUN: %clang -target x86_64-apple-darwin12 -fprofile-instr-generate -### %t.o 2> %t.log
+// RUN: %clang -target x86_64-apple-darwin12 -fprofile-instr-generate --coverage -### %t.o 2> %t.log
 // RUN: FileCheck -check-prefix=NO_PROFILE_EXPORT %s < %t.log
 // NO_PROFILE_EXPORT-NOT: "-exported_symbol"
 //
+// RUN: %clang -target x86_64-apple-darwin12 --coverage -exported_symbols_list /dev/null -### %t.o 2> %t.log
+// RUN: FileCheck -check-prefix=GCOV_EXPORT %s < %t.log
+// RUN: %clang -target x86_64-apple-darwin12 -fprofile-arcs -Wl,-exported_symbols_list,/dev/null -### %t.o 2> %t.log
+// RUN: FileCheck -check-prefix=GCOV_EXPORT %s < %t.log
+// RUN: %clang -target x86_64-apple-darwin12 -fprofile-arcs -Wl,-exported_symbol,foo -### %t.o 2> %t.log
+// RUN: FileCheck -check-prefix=GCOV_EXPORT %s < %t.log
+// RUN: %clang -target x86_64-apple-darwin12 -fprofile-arcs -Xlinker -exported_symbol -Xlinker foo -### %t.o 2> %t.log
+// RUN: FileCheck -check-prefix=GCOV_EXPORT %s < %t.log
+// RUN: %clang -target x86_64-apple-darwin12 -fprofile-arcs -Xlinker -exported_symbols_list -Xlinker /dev/null -### %t.o 2> %t.log
+// RUN: FileCheck -check-prefix=GCOV_EXPORT %s < %t.log
+// GCOV_EXPORT: "-exported_symbol" "___gcov_flush"
+//
 // Check that we can pass the outliner down to the linker.
 // RUN: env IPHONEOS_DEPLOYMENT_TARGET=7.0 \
 // RUN:   %clang -target arm64-apple-darwin -moutline -### %t.o 2> %t.log
index 146ad5e..1ef36ae 100644 (file)
@@ -8,6 +8,9 @@
 // RUN: %clang_profgen -Werror -fcoverage-mapping -Wl,-exported_symbols_list,%t.exports -o %t %s 2>&1 | tee -a %t.log
 // RUN: cat %t.log | count 0
 
+// RUN: %clang -Werror -Wl,-exported_symbols_list,%t.exports --coverage -o %t.gcov %s | tee -a %t.gcov.log
+// RUN: cat %t.gcov.log | count 0
+
 // The default set of weak external symbols should match the set of symbols
 // exported by clang. See Darwin::addProfileRTLibs.
 
@@ -16,4 +19,9 @@
 // RUN: nm -jUg %t > %t.clang.exports
 // RUN: diff %t.default.exports %t.clang.exports
 
+// RUN: %clang -Werror --coverage -o %t.gcov.default %s
+// RUN: nm -jUg %t.gcov | grep -v __mh_execute_header > %t.gcov.exports
+// RUN: nm -jUg %t.gcov.default | grep -v __mh_execute_header > %t.gcov.default.exports
+// RUN: diff %t.gcov.default.exports %t.gcov.exports
+
 int main() {}