================
@@ -0,0 +1,45 @@
+// RUN: %clang_analyze_cc1 -analyzer-checker=cplusplus -verify %s
+// RUN: %clang_analyze_cc1 -analyzer-checker=cplusplus -verify %s -DEMPTY_CLASS
+
+// expected-no-diagnostics
+
+// This test reproduces the issue that previously the static analyzer
+// initialized an [[__no_unique_address__]] empty field to zero,
+// over-writing a non-empty field with the same offset.
+
+namespace std {
+#ifdef EMPTY_CLASS
+
+  template <typename T>
+  class default_delete {
+    T dump();
+    static T x;
+  };
+  template <class _Tp, class _Dp = default_delete<_Tp> >
+#else
+
+  struct default_delete {};
+  template <class _Tp, class _Dp = default_delete >
+#endif
+  class unique_ptr {
+    [[__no_unique_address__]]  _Tp * __ptr_;
+    [[__no_unique_address__]] _Dp __deleter_;
+
+  public:
+    explicit unique_ptr(_Tp* __p) noexcept
+      : __ptr_(__p),
+        __deleter_() {}
+
+    ~unique_ptr() {
+      delete __ptr_;
+    }
+  };
+}
+
+struct X {};
+
+int main()
+{
+    std::unique_ptr<X> a(new X());          // previously leak falsely reported
----------------
steakhal wrote:

I think we should mention that how did we have a FP here.
Like first `__ptr_` was assigned in the init-list, then the `__deleter_`, which 
happened to overlap with the previous store and overwrite the pointer causing a 
false leak diagnostic.

If we ever break this test again, that would help us understand the flow of 
events here.
I recall debugging this exact case, and I wasn't happy spending that time. I 
wish I had some pointers about this.

https://github.com/llvm/llvm-project/pull/138594
_______________________________________________
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to