Index: lib/CodeGen/CodeGenPGO.cpp =================================================================== --- lib/CodeGen/CodeGenPGO.cpp +++ lib/CodeGen/CodeGenPGO.cpp @@ -93,6 +93,7 @@ BinaryOperatorLAnd, BinaryOperatorLOr, BinaryConditionalOperator, + SimpleFunctionHash, // Reserved for functions without aforesaid statements. // Keep this last. It's for the static assert that follows. LastHashType @@ -598,7 +599,10 @@ // No need to byte swap here, since none of the math was endian-dependent. // This number will be byte-swapped as required on endianness transitions, // so we will see the same value on the other side. - return Working; + // If we didn't meet any known statements, return a special hash value, + // so that any used function will have a non-zero hash and won't be + // messed up with non-used functions when reading coverage data. + return Working ? Working : static_cast(SimpleFunctionHash); // Check for remaining work in Working. if (Working) Index: lib/CodeGen/CoverageMappingGen.cpp =================================================================== --- lib/CodeGen/CoverageMappingGen.cpp +++ lib/CodeGen/CoverageMappingGen.cpp @@ -906,9 +906,9 @@ } static void dump(llvm::raw_ostream &OS, StringRef FunctionName, - ArrayRef Expressions, + uint64_t FuncHash, ArrayRef Expressions, ArrayRef Regions) { - OS << FunctionName << ":\n"; + OS << FunctionName << "(" << FuncHash << "):\n"; CounterMappingContext Ctx(Expressions); for (const auto &R : Regions) { OS.indent(2); @@ -974,7 +974,7 @@ Expressions, Regions); if (Reader.read()) return; - dump(llvm::outs(), NameValue, Expressions, Regions); + dump(llvm::outs(), NameValue, FuncHash, Expressions, Regions); } } Index: test/CoverageMapping/block-storage-starts-region.m =================================================================== --- test/CoverageMapping/block-storage-starts-region.m +++ test/CoverageMapping/block-storage-starts-region.m @@ -3,7 +3,7 @@ @interface Foo @end -// CHECK-LABEL: doSomething: +// CHECK-LABEL: doSomething void doSomething() { // CHECK: File 0, [[@LINE]]:20 -> {{[0-9:]+}} = #0 return; __block Foo *f; // CHECK: File 0, [[@LINE]]:3 -> {{[0-9:]+}} = 0 Index: test/CoverageMapping/decl.c =================================================================== --- test/CoverageMapping/decl.c +++ test/CoverageMapping/decl.c @@ -4,12 +4,12 @@ // FileCheck -input-file %t %s // RUN: FileCheck -check-prefix BAR -input-file %t %s -// FOO: foo: -// FOO-NOT: foo: +// FOO: foo +// FOO-NOT: foo inline int foo() { return 0; } extern inline int foo(); -// BAR: bar: -// BAR-NOT: bar: +// BAR: bar +// BAR-NOT: bar int bar() { return 0; } extern int bar(); Index: test/CoverageMapping/implicit-def-in-macro.m =================================================================== --- test/CoverageMapping/implicit-def-in-macro.m +++ test/CoverageMapping/implicit-def-in-macro.m @@ -5,7 +5,7 @@ #define Bar Foo @implementation Blah -// CHECK-LABEL: +[Blah load]: +// CHECK-LABEL: +[Blah load] + load { // CHECK: File 0, [[@LINE]]:8 -> [[END:[0-9:]+]] = #0 return 0; // CHECK: Expansion,File 0, [[@LINE+1]]:3 -> [[@LINE+1]]:6 = 0 Index: test/CoverageMapping/lambda.cpp =================================================================== --- test/CoverageMapping/lambda.cpp +++ test/CoverageMapping/lambda.cpp @@ -1,6 +1,6 @@ // RUN: %clang_cc1 -x c++ -std=c++11 -triple %itanium_abi_triple -fprofile-instrument=clang -fcoverage-mapping -dump-coverage-mapping -emit-llvm-only %s -main-file-name lambda.cpp | FileCheck %s -// CHECK-LABEL: _Z3fooi: +// CHECK-LABEL: _Z3fooi void foo(int i) { // CHECK: File 0, [[@LINE]]:17 -> {{[0-9]+}}:2 = #0 auto f = [](int x) { return x + 1; Index: test/CoverageMapping/loops.cpp =================================================================== --- test/CoverageMapping/loops.cpp +++ test/CoverageMapping/loops.cpp @@ -16,7 +16,7 @@ if (sum) {} } - // CHECK: main: + // CHECK: main int main() { // CHECK-NEXT: File 0, [[@LINE]]:12 -> [[@LINE+24]]:2 = #0 // CHECK-NEXT: File 0, [[@LINE+1]]:18 -> [[@LINE+1]]:24 = (#0 + #1) for(int i = 0; i < 10; ++i) // CHECK-NEXT: File 0, [[@LINE]]:26 -> [[@LINE]]:29 = #1 Index: test/CoverageMapping/macroception.c =================================================================== --- test/CoverageMapping/macroception.c +++ test/CoverageMapping/macroception.c @@ -5,7 +5,7 @@ #define M22 } #define M11 M22 -// CHECK-LABEL: main: +// CHECK-LABEL: main // CHECK-NEXT: Expansion,File 0, [[@LINE+2]]:12 -> [[@LINE+2]]:14 = #0 // CHECK-NEXT: File 0, [[@LINE+1]]:14 -> [[@LINE+3]]:2 = #0 int main() M1 @@ -15,7 +15,7 @@ // CHECK-NEXT: Expansion,File 1, 4:12 -> 4:14 = #0 // CHECK-NEXT: File 2, 3:12 -> 3:13 = #0 -// CHECK-LABEL: func2: +// CHECK-LABEL: func2 // CHECK-NEXT: File 0, [[@LINE+2]]:14 -> [[@LINE+4]]:4 = #0 // CHECK-NEXT: Expansion,File 0, [[@LINE+3]]:1 -> [[@LINE+3]]:4 = #0 void func2() { @@ -25,7 +25,7 @@ // CHECK-NEXT: Expansion,File 1, 6:13 -> 6:16 = #0 // CHECK-NEXT: File 2, 5:13 -> 5:14 = #0 -// CHECK-LABEL: func3: +// CHECK-LABEL: func3 // CHECK-NEXT: Expansion,File 0, [[@LINE+3]]:14 -> [[@LINE+3]]:16 = #0 // CHECK-NEXT: File 0, [[@LINE+2]]:16 -> [[@LINE+4]]:4 = #0 // CHECK-NEXT: Expansion,File 0, [[@LINE+3]]:1 -> [[@LINE+3]]:4 = #0 @@ -39,7 +39,7 @@ // CHECK-NEXT: File 3, 3:12 -> 3:13 = #0 // CHECK-NEXT: File 4, 5:13 -> 5:14 = #0 -// CHECK-LABEL: func4: +// CHECK-LABEL: func4 // CHECK-NEXT: Expansion,File 0, [[@LINE+3]]:14 -> [[@LINE+3]]:16 = #0 // CHECK-NEXT: File 0, [[@LINE+2]]:16 -> [[@LINE+2]]:20 = #0 // CHECK-NEXT: Expansion,File 0, [[@LINE+1]]:17 -> [[@LINE+1]]:20 = #0 Index: test/CoverageMapping/moremacros.c =================================================================== --- test/CoverageMapping/moremacros.c +++ test/CoverageMapping/moremacros.c @@ -3,7 +3,7 @@ #define LBRAC { #define RBRAC } -// CHECK: main: +// CHECK: main // CHECK-NEXT: File 0, [[@LINE+1]]:40 -> {{[0-9]+}}:2 = #0 int main(int argc, const char *argv[]) { // CHECK-NEXT: File 0, [[@LINE+1]]:7 -> [[@LINE+1]]:12 = #0 Index: test/CoverageMapping/simple-function-hash.cpp =================================================================== --- /dev/null +++ test/CoverageMapping/simple-function-hash.cpp @@ -0,0 +1,17 @@ +// RUN: %clang_cc1 -main-file-name simple-function-hash.cpp %s -o %t.o -emit-llvm -fprofile-instrument=clang -fcoverage-mapping -dump-coverage-mapping | FileCheck %s + +// Hash value for unused_func() is 0 because it is an inline function which is not used in the translation unit. +// CHECK-DAG: _Z11unused_funcv(0): +inline int unused_func() { return 1; } + +// Hash value for used_func() is 17 even though it does not contain any statement which affects hash. +// CHECK-DAG: _Z9used_funcv(17): +inline int used_func() { return 1; } + +// Hash value for main() is 10 because it contains the "if" statement. +// CHECK-DAG: main(10): +int main() { + if (used_func()) + return used_func(); + return 0; +} Index: test/CoverageMapping/system_macro.c =================================================================== --- test/CoverageMapping/system_macro.c +++ test/CoverageMapping/system_macro.c @@ -11,7 +11,7 @@ #define IS_SYSHEADER #include __FILE__ -// CHECK-LABEL: doSomething: +// CHECK-LABEL: doSomething void doSomething(int x) { // CHECK: File 0, [[@LINE]]:25 -> {{[0-9:]+}} = #0 Func(x); // CHECK: Expansion,File 0, [[@LINE]]:3 -> [[@LINE]]:7 return; Index: test/CoverageMapping/trymacro.cpp =================================================================== --- test/CoverageMapping/trymacro.cpp +++ test/CoverageMapping/trymacro.cpp @@ -1,19 +1,19 @@ // RUN: %clang_cc1 -triple %itanium_abi_triple -std=c++11 -fexceptions -fcxx-exceptions -fprofile-instrument=clang -fcoverage-mapping -dump-coverage-mapping -emit-llvm-only -main-file-name trymacro.cpp %s | FileCheck %s -// CHECK: Z3fn1v: +// CHECK: Z3fn1v void fn1() try { return; } // CHECK: [[@LINE]]:12 -> [[@LINE+1]]:14 = #1 catch(...) {} // CHECK: [[@LINE]]:12 -> [[@LINE]]:14 = #2 #define RETURN_BLOCK { return; } -// CHECK: Z3fn2v: +// CHECK: Z3fn2v void fn2() try RETURN_BLOCK // CHECK: [[@LINE]]:12 -> [[@LINE+1]]:14 = #1 catch(...) {} // CHECK: [[@LINE]]:12 -> [[@LINE]]:14 = #2 #define TRY try #define CATCH(x) catch (x) -// CHECK: Z3fn3v: +// CHECK: Z3fn3v void fn3() TRY { return; } // CHECK: [[@LINE]]:15 -> [[@LINE+1]]:14 = #1 CATCH(...) {} // CHECK: [[@LINE]]:12 -> [[@LINE]]:14 = #2 Index: test/Profile/Inputs/c-captured.proftext =================================================================== --- test/Profile/Inputs/c-captured.proftext +++ test/Profile/Inputs/c-captured.proftext @@ -12,7 +12,7 @@ 1 main -0 +17 1 1 Index: test/Profile/Inputs/c-general.proftext =================================================================== --- test/Profile/Inputs/c-general.proftext +++ test/Profile/Inputs/c-general.proftext @@ -145,7 +145,7 @@ 8 main -0 +17 1 1 Index: test/Profile/Inputs/c-outdated-data.proftext =================================================================== --- test/Profile/Inputs/c-outdated-data.proftext +++ test/Profile/Inputs/c-outdated-data.proftext @@ -6,7 +6,7 @@ 0 main -0 +17 1 1 Index: test/Profile/Inputs/c-unprofiled.proftext =================================================================== --- test/Profile/Inputs/c-unprofiled.proftext +++ test/Profile/Inputs/c-unprofiled.proftext @@ -5,6 +5,6 @@ 0 main -0 +17 1 1 Index: test/Profile/Inputs/cxx-class.proftext =================================================================== --- test/Profile/Inputs/cxx-class.proftext +++ test/Profile/Inputs/cxx-class.proftext @@ -5,7 +5,7 @@ 100 main -0 +17 1 1 Index: test/Profile/Inputs/cxx-lambda.proftext =================================================================== --- test/Profile/Inputs/cxx-lambda.proftext +++ test/Profile/Inputs/cxx-lambda.proftext @@ -6,7 +6,7 @@ 9 main -0 +17 1 1 Index: test/Profile/Inputs/cxx-rangefor.proftext =================================================================== --- test/Profile/Inputs/cxx-rangefor.proftext +++ test/Profile/Inputs/cxx-rangefor.proftext @@ -8,6 +8,6 @@ 1 main -0 +17 1 1 Index: test/Profile/Inputs/cxx-templates.proftext =================================================================== --- test/Profile/Inputs/cxx-templates.proftext +++ test/Profile/Inputs/cxx-templates.proftext @@ -1,5 +1,5 @@ main -0 +17 1 1 Index: test/Profile/Inputs/func-entry.proftext =================================================================== --- test/Profile/Inputs/func-entry.proftext +++ test/Profile/Inputs/func-entry.proftext @@ -1,5 +1,5 @@ foo -0 +17 1 1000 Index: test/Profile/Inputs/max-function-count.proftext =================================================================== --- test/Profile/Inputs/max-function-count.proftext +++ test/Profile/Inputs/max-function-count.proftext @@ -9,7 +9,7 @@ main # Func Hash: -0 +17 # Num Counters: 1 # Counter Values: Index: test/Profile/Inputs/objc-general.proftext =================================================================== --- test/Profile/Inputs/objc-general.proftext +++ test/Profile/Inputs/objc-general.proftext @@ -11,7 +11,7 @@ 2 main -0 +17 1 1 Index: test/Profile/Inputs/profile-summary.proftext =================================================================== --- test/Profile/Inputs/profile-summary.proftext +++ test/Profile/Inputs/profile-summary.proftext @@ -9,7 +9,7 @@ main # Func Hash: -0 +17 # Num Counters: 1 # Counter Values: