tomasz-kaminski-sonarsource updated this revision to Diff 464657.
tomasz-kaminski-sonarsource added a comment.

Added requested comment for the example.
Included additional false-positive test.


Repository:
  rG LLVM Github Monorepo

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

https://reviews.llvm.org/D134941

Files:
  clang/test/Analysis/NewDeleteLeaks.cpp
  clang/test/Analysis/symbol-reaper-lambda.cpp
  clang/test/Analysis/trivial-copy-struct.cpp

Index: clang/test/Analysis/trivial-copy-struct.cpp
===================================================================
--- clang/test/Analysis/trivial-copy-struct.cpp
+++ clang/test/Analysis/trivial-copy-struct.cpp
@@ -1,6 +1,7 @@
 // RUN: %clang_analyze_cc1 -analyzer-checker=core,debug.ExprInspection -verify %s
 
 template <typename T> void clang_analyzer_dump(T);
+template <typename T> void clang_analyzer_value(T);
 void clang_analyzer_warnIfReached();
 
 struct Node { int* ptr; };
@@ -34,3 +35,25 @@
   (void)(n1->ptr);
   (void)(n2->ptr);
 }
+
+struct List {
+  List* next;
+  int value;
+  int padding;
+};
+
+void deadCode(List orig) {
+  List c = orig;
+  clang_analyzer_dump(c.value);
+  // expected-warning-re@-1 {{reg_${{[0-9]+}}<int orig.value>}}
+  if (c.value == 42)
+    return;
+  clang_analyzer_value(c.value);
+  // expected-warning@-1 {{32s:{ [-2147483648, 2147483647] }}}
+  // The symbol was garbage collected too early, hence we lose the constraints.
+  if (c.value != 42)
+    return;
+
+  // Dead code should be unreachable
+  clang_analyzer_warnIfReached(); // expected-warning {{REACHABLE}}
+}
Index: clang/test/Analysis/symbol-reaper-lambda.cpp
===================================================================
--- /dev/null
+++ clang/test/Analysis/symbol-reaper-lambda.cpp
@@ -0,0 +1,26 @@
+// RUN: %clang_analyze_cc1 -analyzer-checker=core -verify %s
+// expected-no-diagnostics
+
+template <typename... Ts>
+void escape(Ts&...);
+struct Dummy {};
+
+int strange(Dummy param) {
+  Dummy local_pre_lambda;
+  int ref_captured = 0;
+
+  // LambdaExpr is modeled as lazyCompoundVal of tempRegion, that contains
+  // all captures. In this instance, this region contains a pointer/reference
+  // to ref_captured variable.
+  auto fn = [&] {
+    escape(param, local_pre_lambda);
+    return ref_captured; // no-warning: The value is not garbage.
+  };
+
+  int local_defined_after_lambda; // Unused, but necessary! Important that it's before the call.
+
+  // The ref_captured binding should not be pruned at this point, as it is still
+  // accessed via reference captured in operator() of fn.
+  return fn();
+}
+
Index: clang/test/Analysis/NewDeleteLeaks.cpp
===================================================================
--- clang/test/Analysis/NewDeleteLeaks.cpp
+++ clang/test/Analysis/NewDeleteLeaks.cpp
@@ -192,3 +192,29 @@
 // expected-note@-1 {{Potential leak of memory pointed to by 'v'}}
 
 } // namespace refkind_from_unoallocated_to_allocated
+
+// Check that memory leak is reported against a symbol if the last place it's
+// mentioned is a base region of a lazy compound value, as the program cannot
+// possibly free that memory.
+namespace symbol_reaper_lifetime {
+struct Nested {
+  int buf[2];
+};
+struct Wrapping {
+  Nested data;
+};
+
+Nested allocateWrappingAndReturnNested() {
+  // expected-note@+1 {{Memory is allocated}}
+  Wrapping const* p = new Wrapping();
+  // expected-warning@+2 {{Potential leak of memory pointed to by 'p'}}
+  // expected-note@+1    {{Potential leak of memory pointed to by 'p'}}
+  return p->data;
+}
+
+void caller() {
+  // expected-note@+1 {{Calling 'allocateWrappingAndReturnNested'}}
+  Nested n = allocateWrappingAndReturnNested();
+  (void)n;
+} // no-warning: No potential memory leak here, because that's been already reported.
+} // namespace symbol_reaper_lifetime
_______________________________________________
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to