vsk created this revision.
vsk added reviewers: rnk, phosek, manojgupta.

... instead of crashing.

The real bug here is due to clang generating coverage for a conditional
operator expanded from a macro. The location of the end of the
conditional expression is not correct. The actual fix for this requires
chasing down an issue in the lexer/preprocessor.


https://reviews.llvm.org/D65426

Files:
  clang/lib/CodeGen/CoverageMappingGen.cpp
  clang/test/CoverageMapping/bad-coverage-for-condexpr-in-macro-pr39942.cpp


Index: clang/test/CoverageMapping/bad-coverage-for-condexpr-in-macro-pr39942.cpp
===================================================================
--- /dev/null
+++ clang/test/CoverageMapping/bad-coverage-for-condexpr-in-macro-pr39942.cpp
@@ -0,0 +1,24 @@
+// RUN: %clang_cc1 -fprofile-instrument=clang -fcoverage-mapping 
-dump-coverage-mapping -emit-llvm-only -main-file-name pr39942.cpp %s | 
FileCheck %s
+
+class a;
+template <class b> a &operator<<(b &, const char *);
+int c;
+#define d(l) l(__FILE__, __LINE__, c)
+#define COMPACT_GOOGLE_LOG_ERROR d(e)
+#define f(g, condition) 0 ? (void)0 : h() & g
+#define i(j) COMPACT_GOOGLE_LOG_##j.g()
+#define k(j) f(i(j), )
+class e {
+public:
+  e(const char *, int, int);
+  a &g();
+};
+class h {
+public:
+  void operator&(a &);
+};
+#define m(lib, func) \
+#func;               \
+  k(ERROR) << #func; \
+  return 0 // CHECK: File 1, [[@LINE-1]]:4 -> [[@LINE-1]]:4 = (#0 - #1)
+bool n() { m(, ); }
Index: clang/lib/CodeGen/CoverageMappingGen.cpp
===================================================================
--- clang/lib/CodeGen/CoverageMappingGen.cpp
+++ clang/lib/CodeGen/CoverageMappingGen.cpp
@@ -619,7 +619,14 @@
           MostRecentLocation = getIncludeOrExpansionLoc(EndLoc);
 
         assert(SM.isWrittenInSameFile(Region.getBeginLoc(), EndLoc));
-        assert(SpellingRegion(SM, Region).isInSourceOrder());
+
+        // FIXME: See llvm.org/PR39942. The clang preprocessor may not preserve
+        // the correct end location for conditional expressions. Hide coverage
+        // for such regions instead of crashing/asserting. This should be
+        // turned back into an assert.
+        if (!SpellingRegion(SM, Region).isInSourceOrder())
+          Region.setEndLoc(Region.getBeginLoc());
+
         SourceRegions.push_back(Region);
 
         if (ParentOfDeferredRegion) {


Index: clang/test/CoverageMapping/bad-coverage-for-condexpr-in-macro-pr39942.cpp
===================================================================
--- /dev/null
+++ clang/test/CoverageMapping/bad-coverage-for-condexpr-in-macro-pr39942.cpp
@@ -0,0 +1,24 @@
+// RUN: %clang_cc1 -fprofile-instrument=clang -fcoverage-mapping -dump-coverage-mapping -emit-llvm-only -main-file-name pr39942.cpp %s | FileCheck %s
+
+class a;
+template <class b> a &operator<<(b &, const char *);
+int c;
+#define d(l) l(__FILE__, __LINE__, c)
+#define COMPACT_GOOGLE_LOG_ERROR d(e)
+#define f(g, condition) 0 ? (void)0 : h() & g
+#define i(j) COMPACT_GOOGLE_LOG_##j.g()
+#define k(j) f(i(j), )
+class e {
+public:
+  e(const char *, int, int);
+  a &g();
+};
+class h {
+public:
+  void operator&(a &);
+};
+#define m(lib, func) \
+#func;               \
+  k(ERROR) << #func; \
+  return 0 // CHECK: File 1, [[@LINE-1]]:4 -> [[@LINE-1]]:4 = (#0 - #1)
+bool n() { m(, ); }
Index: clang/lib/CodeGen/CoverageMappingGen.cpp
===================================================================
--- clang/lib/CodeGen/CoverageMappingGen.cpp
+++ clang/lib/CodeGen/CoverageMappingGen.cpp
@@ -619,7 +619,14 @@
           MostRecentLocation = getIncludeOrExpansionLoc(EndLoc);
 
         assert(SM.isWrittenInSameFile(Region.getBeginLoc(), EndLoc));
-        assert(SpellingRegion(SM, Region).isInSourceOrder());
+
+        // FIXME: See llvm.org/PR39942. The clang preprocessor may not preserve
+        // the correct end location for conditional expressions. Hide coverage
+        // for such regions instead of crashing/asserting. This should be
+        // turned back into an assert.
+        if (!SpellingRegion(SM, Region).isInSourceOrder())
+          Region.setEndLoc(Region.getBeginLoc());
+
         SourceRegions.push_back(Region);
 
         if (ParentOfDeferredRegion) {
_______________________________________________
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to