Author: Kazu Hirata
Date: 2024-09-18T14:18:04-07:00
New Revision: abb317ff9aba8a58449d91f6162597e54d02a57c

URL: 
https://github.com/llvm/llvm-project/commit/abb317ff9aba8a58449d91f6162597e54d02a57c
DIFF: 
https://github.com/llvm/llvm-project/commit/abb317ff9aba8a58449d91f6162597e54d02a57c.diff

LOG: [clang-tidy] Fix performance-unnecessary-value-param (#109145)

This patch essentially reverts #108674 while adding a testcase that
triggers a crash in clang-tidy.

Fixes #108963.

Added: 
    
clang-tools-extra/test/clang-tidy/checkers/performance/unnecessary-value-param-crash.cpp

Modified: 
    clang/include/clang/Analysis/Analyses/ExprMutationAnalyzer.h

Removed: 
    


################################################################################
diff  --git 
a/clang-tools-extra/test/clang-tidy/checkers/performance/unnecessary-value-param-crash.cpp
 
b/clang-tools-extra/test/clang-tidy/checkers/performance/unnecessary-value-param-crash.cpp
new file mode 100644
index 00000000000000..99c2fe905bdf37
--- /dev/null
+++ 
b/clang-tools-extra/test/clang-tidy/checkers/performance/unnecessary-value-param-crash.cpp
@@ -0,0 +1,23 @@
+// RUN: %check_clang_tidy  -std=c++14-or-later %s 
performance-unnecessary-value-param %t
+
+// The test case used to crash clang-tidy.
+// https://github.com/llvm/llvm-project/issues/108963
+
+struct A
+{
+  template<typename T> A(T&&) {}
+};
+
+struct B
+{
+  ~B();
+};
+
+struct C
+{
+  A a;
+  C(B, int i) : a(i) {}
+  // CHECK-MESSAGES: [[@LINE-1]]:6: warning: the parameter #1 is copied for 
each invocation but only used as a const reference; consider making it a const 
reference
+};
+
+C c(B(), 0);

diff  --git a/clang/include/clang/Analysis/Analyses/ExprMutationAnalyzer.h 
b/clang/include/clang/Analysis/Analyses/ExprMutationAnalyzer.h
index b7b84852168e2e..c7a5b016c949d0 100644
--- a/clang/include/clang/Analysis/Analyses/ExprMutationAnalyzer.h
+++ b/clang/include/clang/Analysis/Analyses/ExprMutationAnalyzer.h
@@ -118,10 +118,19 @@ class FunctionParmMutationAnalyzer {
   static FunctionParmMutationAnalyzer *
   getFunctionParmMutationAnalyzer(const FunctionDecl &Func, ASTContext 
&Context,
                                   ExprMutationAnalyzer::Memoized &Memorized) {
-    auto [it, Inserted] = Memorized.FuncParmAnalyzer.try_emplace(&Func);
-    if (Inserted)
-      it->second = std::unique_ptr<FunctionParmMutationAnalyzer>(
-          new FunctionParmMutationAnalyzer(Func, Context, Memorized));
+    auto it = Memorized.FuncParmAnalyzer.find(&Func);
+    if (it == Memorized.FuncParmAnalyzer.end()) {
+      // Creating a new instance of FunctionParmMutationAnalyzer below may add
+      // additional elements to FuncParmAnalyzer. If we did try_emplace before
+      // creating a new instance, the returned iterator of try_emplace could be
+      // invalidated.
+      it =
+          Memorized.FuncParmAnalyzer
+              .try_emplace(&Func, 
std::unique_ptr<FunctionParmMutationAnalyzer>(
+                                      new FunctionParmMutationAnalyzer(
+                                          Func, Context, Memorized)))
+              .first;
+    }
     return it->getSecond().get();
   }
 


        
_______________________________________________
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to