https://github.com/NeKon69 created 
https://github.com/llvm/llvm-project/pull/191731

Add `UseFact`s for field origins when calling instance methods.

Fixes #182945

>From 382e365ec09c88eb36fbd83874a5923295fe9b95 Mon Sep 17 00:00:00 2001
From: NeKon69 <[email protected]>
Date: Sun, 12 Apr 2026 21:24:43 +0300
Subject: [PATCH 1/2] [LifetimeSafety] implement basic fix, add tests

---
 .../Analyses/LifetimeSafety/FactsGenerator.h  |  2 ++
 .../LifetimeSafety/FactsGenerator.cpp         | 14 ++++++++
 clang/test/Sema/warn-lifetime-safety.cpp      | 32 +++++++++++++++++++
 3 files changed, 48 insertions(+)

diff --git 
a/clang/include/clang/Analysis/Analyses/LifetimeSafety/FactsGenerator.h 
b/clang/include/clang/Analysis/Analyses/LifetimeSafety/FactsGenerator.h
index 2dbadb27981a7..a3b759c473a16 100644
--- a/clang/include/clang/Analysis/Analyses/LifetimeSafety/FactsGenerator.h
+++ b/clang/include/clang/Analysis/Analyses/LifetimeSafety/FactsGenerator.h
@@ -74,6 +74,8 @@ class FactsGenerator : public 
ConstStmtVisitor<FactsGenerator> {
 
   void handleExitBlock();
 
+  void handleImplicitObjectFieldUses(const Expr *Call, const FunctionDecl *FD);
+
   void handleGSLPointerConstruction(const CXXConstructExpr *CCE);
 
   /// Detects arguments passed to rvalue reference parameters and creates
diff --git a/clang/lib/Analysis/LifetimeSafety/FactsGenerator.cpp 
b/clang/lib/Analysis/LifetimeSafety/FactsGenerator.cpp
index 82b890b57817e..eaf26cb49aba5 100644
--- a/clang/lib/Analysis/LifetimeSafety/FactsGenerator.cpp
+++ b/clang/lib/Analysis/LifetimeSafety/FactsGenerator.cpp
@@ -723,6 +723,19 @@ void FactsGenerator::handleInvalidatingCall(const Expr 
*Call,
         ThisList->getOuterOriginID(), Call));
 }
 
+void FactsGenerator::handleImplicitObjectFieldUses(const Expr *Call,
+                                                   const FunctionDecl *FD) {
+  const auto *MD = dyn_cast<CXXMethodDecl>(FD);
+  if (!MD || !MD->isInstance())
+    return;
+
+  for (const auto *Field : MD->getParent()->fields()) {
+    OriginList *FieldList = getOriginsList(*Field);
+    if (FieldList)
+      CurrentBlockFacts.push_back(FactMgr.createFact<UseFact>(Call, 
FieldList));
+  }
+}
+
 void FactsGenerator::handleFunctionCall(const Expr *Call,
                                         const FunctionDecl *FD,
                                         ArrayRef<const Expr *> Args,
@@ -737,6 +750,7 @@ void FactsGenerator::handleFunctionCall(const Expr *Call,
     handleUse(Arg);
   handleInvalidatingCall(Call, FD, Args);
   handleMovedArgsInCall(FD, Args);
+  handleImplicitObjectFieldUses(Call, FD);
   if (!CallList)
     return;
   auto IsArgLifetimeBound = [FD](unsigned I) -> bool {
diff --git a/clang/test/Sema/warn-lifetime-safety.cpp 
b/clang/test/Sema/warn-lifetime-safety.cpp
index 77d8e3370676d..63a82680955ac 100644
--- a/clang/test/Sema/warn-lifetime-safety.cpp
+++ b/clang/test/Sema/warn-lifetime-safety.cpp
@@ -2531,3 +2531,35 @@ int *noreturn_dead_nested(bool cond, bool cond2, int 
*num) {
 }
 
 } // namespace conditional_operator_control_flow
+
+namespace method_call_uses_field_origins {
+// https://github.com/llvm/llvm-project/issues/182945
+
+int val;
+
+struct S {
+public:
+  int* p_;
+  void bar();
+  void foo() {
+    {
+      int num;
+      this->p_ = &num; // expected-warning {{object whose reference is 
captured does not live long enough}}
+    }                  // expected-note {{destroyed here}}
+    bar();             // expected-note {{later used here}}
+    this->p_ = &val;
+  }
+};
+
+// FIXME: False-positive: the analysis tracks a, but not that it belongs to s1.
+void foo() {
+  S s;
+  {
+    int num;
+    s.p_ = &num;
+  }
+  s.bar();
+  s.p_ = &val;
+}
+
+} // namespace method_call_uses_field_origins

>From ae721e42f219fe61c85493c7699673b099838145 Mon Sep 17 00:00:00 2001
From: NeKon69 <[email protected]>
Date: Sun, 12 Apr 2026 21:41:44 +0300
Subject: [PATCH 2/2] add a new test

---
 clang/test/Sema/warn-lifetime-safety.cpp | 10 ++++++++++
 1 file changed, 10 insertions(+)

diff --git a/clang/test/Sema/warn-lifetime-safety.cpp 
b/clang/test/Sema/warn-lifetime-safety.cpp
index 63a82680955ac..1864247e53886 100644
--- a/clang/test/Sema/warn-lifetime-safety.cpp
+++ b/clang/test/Sema/warn-lifetime-safety.cpp
@@ -2551,6 +2551,16 @@ struct S {
   }
 };
 
+struct T {
+public:
+  std::string_view v;
+  void bar();
+  void foo() {
+    v = std::string("tmp"); // expected-warning {{object whose reference is 
captured does not live long enough}} expected-note {{destroyed here}}
+    bar();                  // expected-note {{later used here}}
+  }
+};
+
 // FIXME: False-positive: the analysis tracks a, but not that it belongs to s1.
 void foo() {
   S s;

_______________________________________________
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to