[clang-tools-extra] [llvm] [clang] Add clang-tidy check to suggest replacement of conditional statement with std::min/std::max (PR #77816)

Bhuminjay Soni via cfe-commits cfe-commits at lists.llvm.org
Tue Jan 30 01:17:02 PST 2024


https://github.com/11happy updated https://github.com/llvm/llvm-project/pull/77816

>From 1883d987b2f83adaef05fdb47ae25c7b06582a64 Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Fri, 12 Jan 2024 00:02:46 +0530
Subject: [PATCH 01/46] Add readability check to suggest replacement of
 conditional statement with std::min/std::max

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../clang-tidy/readability/CMakeLists.txt     |  1 +
 .../ConditionaltostdminmaxCheck.cpp           | 86 +++++++++++++++++++
 .../readability/ConditionaltostdminmaxCheck.h | 30 +++++++
 .../readability/ReadabilityTidyModule.cpp     |  3 +
 clang-tools-extra/docs/ReleaseNotes.rst       |  6 ++
 .../docs/clang-tidy/checks/list.rst           |  1 +
 .../readability/ConditionalToStdMinMax.rst    | 29 +++++++
 .../readability/ConditionalToStdMinMax.cpp    | 27 ++++++
 8 files changed, 183 insertions(+)
 create mode 100644 clang-tools-extra/clang-tidy/readability/ConditionaltostdminmaxCheck.cpp
 create mode 100644 clang-tools-extra/clang-tidy/readability/ConditionaltostdminmaxCheck.h
 create mode 100644 clang-tools-extra/docs/clang-tidy/checks/readability/ConditionalToStdMinMax.rst
 create mode 100644 clang-tools-extra/test/clang-tidy/checkers/readability/ConditionalToStdMinMax.cpp

diff --git a/clang-tools-extra/clang-tidy/readability/CMakeLists.txt b/clang-tools-extra/clang-tidy/readability/CMakeLists.txt
index 408c822b861c5..4bc373bb69bb8 100644
--- a/clang-tools-extra/clang-tidy/readability/CMakeLists.txt
+++ b/clang-tools-extra/clang-tidy/readability/CMakeLists.txt
@@ -8,6 +8,7 @@ add_clang_library(clangTidyReadabilityModule
   AvoidReturnWithVoidValueCheck.cpp
   AvoidUnconditionalPreprocessorIfCheck.cpp
   BracesAroundStatementsCheck.cpp
+  ConditionaltostdminmaxCheck.cpp
   ConstReturnTypeCheck.cpp
   ContainerContainsCheck.cpp
   ContainerDataPointerCheck.cpp
diff --git a/clang-tools-extra/clang-tidy/readability/ConditionaltostdminmaxCheck.cpp b/clang-tools-extra/clang-tidy/readability/ConditionaltostdminmaxCheck.cpp
new file mode 100644
index 0000000000000..fba8c68f73745
--- /dev/null
+++ b/clang-tools-extra/clang-tidy/readability/ConditionaltostdminmaxCheck.cpp
@@ -0,0 +1,86 @@
+//===--- ConditionaltostdminmaxCheck.cpp - clang-tidy ---------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "ConditionaltostdminmaxCheck.h"
+#include "clang/AST/ASTContext.h"
+#include "clang/ASTMatchers/ASTMatchFinder.h"
+
+using namespace clang::ast_matchers;
+
+namespace clang::tidy::readability {
+
+void ConditionaltostdminmaxCheck::registerMatchers(MatchFinder *Finder) {
+  Finder->addMatcher(
+    ifStmt(
+      has(
+        binaryOperator(
+          anyOf(hasOperatorName("<"),hasOperatorName(">")),
+          hasLHS(ignoringImpCasts(declRefExpr().bind("lhsVar1"))),
+          hasRHS(ignoringImpCasts(declRefExpr().bind("rhsVar1")))
+          )
+          )
+        ,
+        hasThen(
+          stmt(
+            binaryOperator(
+              hasOperatorName("="),
+              hasLHS(ignoringImpCasts(declRefExpr().bind("lhsVar2"))),
+              hasRHS(ignoringImpCasts(declRefExpr().bind("rhsVar2")))
+              )
+            )
+          ) 
+    ).bind("ifStmt"),this);
+
+
+
+}
+
+void ConditionaltostdminmaxCheck::check(const MatchFinder::MatchResult &Result) {
+  const DeclRefExpr *lhsVar1 = Result.Nodes.getNodeAs<DeclRefExpr>("lhsVar1");
+  const DeclRefExpr *rhsVar1 = Result.Nodes.getNodeAs<DeclRefExpr>("rhsVar1");
+  const DeclRefExpr *lhsVar2 = Result.Nodes.getNodeAs<DeclRefExpr>("lhsVar2");
+  const DeclRefExpr *rhsVar2 = Result.Nodes.getNodeAs<DeclRefExpr>("rhsVar2");  
+  const IfStmt *ifStmt = Result.Nodes.getNodeAs<IfStmt>("ifStmt");
+
+  if (!lhsVar1 || !rhsVar1 || !lhsVar2 || !rhsVar2 || !ifStmt)
+        return;
+
+  const BinaryOperator *binaryOp = dyn_cast<BinaryOperator>(ifStmt->getCond());
+  if (!binaryOp)
+      return;
+
+  SourceLocation ifLocation = ifStmt->getIfLoc();
+  SourceLocation thenLocation = ifStmt->getEndLoc();
+
+  if(binaryOp->getOpcode() == BO_LT){
+    if(lhsVar1->getDecl() == lhsVar2->getDecl() && rhsVar1->getDecl() == rhsVar2->getDecl()){
+      diag(ifStmt->getIfLoc(), "use std::max instead of <")<<FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
+                                      lhsVar2->getNameInfo().getAsString() + " = std::max(" + lhsVar1->getNameInfo().getAsString() + ", " +
+                                      rhsVar1->getNameInfo().getAsString() + ")");
+    }
+    else if(lhsVar1->getDecl() == rhsVar2->getDecl() && rhsVar1->getDecl() == lhsVar2->getDecl()){
+      diag(ifStmt->getIfLoc(), "use std::min instead of <")<<FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
+                                      lhsVar2->getNameInfo().getAsString() + " = std::min(" + lhsVar1->getNameInfo().getAsString() + ", " +
+                                      rhsVar1->getNameInfo().getAsString() + ")");
+    }
+  }
+  else if(binaryOp->getOpcode() == BO_GT){
+    if(lhsVar1->getDecl() == lhsVar2->getDecl() && rhsVar1->getDecl() == rhsVar2->getDecl()){
+      diag(ifStmt->getIfLoc(), "use std::min instead of >")<<FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
+                                      lhsVar2->getNameInfo().getAsString() + " = std::min(" + lhsVar1->getNameInfo().getAsString() + ", " +
+                                      rhsVar1->getNameInfo().getAsString() + ")");
+    }
+    else if(lhsVar1->getDecl() == rhsVar2->getDecl() && rhsVar1->getDecl() == lhsVar2->getDecl()){
+      diag(ifStmt->getIfLoc(), "use std::max instead of >")<<FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
+                                      lhsVar2->getNameInfo().getAsString() + " = std::max(" + lhsVar1->getNameInfo().getAsString() + ", " +
+                                      rhsVar1->getNameInfo().getAsString() + ")");
+    }
+  }
+}
+
+} // namespace clang::tidy::readability
diff --git a/clang-tools-extra/clang-tidy/readability/ConditionaltostdminmaxCheck.h b/clang-tools-extra/clang-tidy/readability/ConditionaltostdminmaxCheck.h
new file mode 100644
index 0000000000000..b7eabcc7d16d4
--- /dev/null
+++ b/clang-tools-extra/clang-tidy/readability/ConditionaltostdminmaxCheck.h
@@ -0,0 +1,30 @@
+//===--- ConditionaltostdminmaxCheck.h - clang-tidy -------------*- C++ -*-===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_READABILITY_CONDITIONALTOSTDMINMAXCHECK_H
+#define LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_READABILITY_CONDITIONALTOSTDMINMAXCHECK_H
+
+#include "../ClangTidyCheck.h"
+
+namespace clang::tidy::readability {
+
+/// FIXME: replaces certain conditional statements with equivalent std::min or std::max expressions, improving readability and promoting the use of standard library functions."
+///
+/// For the user-facing documentation see:
+/// http://clang.llvm.org/extra/clang-tidy/checks/readability/ConditionalToStdMinMax.html
+class ConditionaltostdminmaxCheck : public ClangTidyCheck {
+public:
+  ConditionaltostdminmaxCheck(StringRef Name, ClangTidyContext *Context)
+      : ClangTidyCheck(Name, Context) {}
+  void registerMatchers(ast_matchers::MatchFinder *Finder) override;
+  void check(const ast_matchers::MatchFinder::MatchResult &Result) override;
+};
+
+} // namespace clang::tidy::readability
+
+#endif // LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_READABILITY_CONDITIONALTOSTDMINMAXCHECK_H
diff --git a/clang-tools-extra/clang-tidy/readability/ReadabilityTidyModule.cpp b/clang-tools-extra/clang-tidy/readability/ReadabilityTidyModule.cpp
index 0b0aad7c0dcb3..63f8f03be6bb9 100644
--- a/clang-tools-extra/clang-tidy/readability/ReadabilityTidyModule.cpp
+++ b/clang-tools-extra/clang-tidy/readability/ReadabilityTidyModule.cpp
@@ -13,6 +13,7 @@
 #include "AvoidReturnWithVoidValueCheck.h"
 #include "AvoidUnconditionalPreprocessorIfCheck.h"
 #include "BracesAroundStatementsCheck.h"
+#include "ConditionaltostdminmaxCheck.h"
 #include "ConstReturnTypeCheck.h"
 #include "ContainerContainsCheck.h"
 #include "ContainerDataPointerCheck.h"
@@ -62,6 +63,8 @@ namespace readability {
 class ReadabilityModule : public ClangTidyModule {
 public:
   void addCheckFactories(ClangTidyCheckFactories &CheckFactories) override {
+    CheckFactories.registerCheck<ConditionaltostdminmaxCheck>(
+        "readability-ConditionalToStdMinMax");
     CheckFactories.registerCheck<AvoidConstParamsInDecls>(
         "readability-avoid-const-params-in-decls");
     CheckFactories.registerCheck<AvoidReturnWithVoidValueCheck>(
diff --git a/clang-tools-extra/docs/ReleaseNotes.rst b/clang-tools-extra/docs/ReleaseNotes.rst
index b4d87e0ed2a67..c3fb990ad6a73 100644
--- a/clang-tools-extra/docs/ReleaseNotes.rst
+++ b/clang-tools-extra/docs/ReleaseNotes.rst
@@ -224,6 +224,12 @@ New checks
   Recommends the smallest possible underlying type for an ``enum`` or ``enum``
   class based on the range of its enumerators.
 
+- New :doc:`readability-ConditionalToStdMinMax
+  <clang-tidy/checks/readability/ConditionalToStdMinMax>` check.
+
+  Replaces certain conditional statements with equivalent std::min or std::max expressions, 
+  improving readability and promoting the use of standard library functions.
+
 - New :doc:`readability-reference-to-constructed-temporary
   <clang-tidy/checks/readability/reference-to-constructed-temporary>` check.
 
diff --git a/clang-tools-extra/docs/clang-tidy/checks/list.rst b/clang-tools-extra/docs/clang-tidy/checks/list.rst
index 2f86121ad8729..c2eac55425c69 100644
--- a/clang-tools-extra/docs/clang-tidy/checks/list.rst
+++ b/clang-tools-extra/docs/clang-tidy/checks/list.rst
@@ -336,6 +336,7 @@ Clang-Tidy Checks
    :doc:`portability-restrict-system-includes <portability/restrict-system-includes>`, "Yes"
    :doc:`portability-simd-intrinsics <portability/simd-intrinsics>`,
    :doc:`portability-std-allocator-const <portability/std-allocator-const>`,
+   :doc:`readability-ConditionalToStdMinMax <readability/ConditionalToStdMinMax>`, "Yes"
    :doc:`readability-avoid-const-params-in-decls <readability/avoid-const-params-in-decls>`, "Yes"
    :doc:`readability-avoid-return-with-void-value <readability/avoid-return-with-void-value>`,
    :doc:`readability-avoid-unconditional-preprocessor-if <readability/avoid-unconditional-preprocessor-if>`,
diff --git a/clang-tools-extra/docs/clang-tidy/checks/readability/ConditionalToStdMinMax.rst b/clang-tools-extra/docs/clang-tidy/checks/readability/ConditionalToStdMinMax.rst
new file mode 100644
index 0000000000000..e95858999b277
--- /dev/null
+++ b/clang-tools-extra/docs/clang-tidy/checks/readability/ConditionalToStdMinMax.rst
@@ -0,0 +1,29 @@
+.. title:: clang-tidy - readability-ConditionalToStdMinMax
+
+readability-ConditionalToStdMinMax
+==================================
+
+Replaces certain conditional statements with equivalent std::min or std::max expressions, 
+improving readability and promoting the use of standard library functions.
+
+Examples:
+
+Before:
+
+.. code-block:: c++
+
+  void foo(){
+    int a,b;
+    if(a < b)
+        a = b;
+    }
+
+
+After:
+
+.. code-block:: c++
+
+  int main(){
+    a = std::max(a, b);
+
+  }
\ No newline at end of file
diff --git a/clang-tools-extra/test/clang-tidy/checkers/readability/ConditionalToStdMinMax.cpp b/clang-tools-extra/test/clang-tidy/checkers/readability/ConditionalToStdMinMax.cpp
new file mode 100644
index 0000000000000..d29e9aa9fec70
--- /dev/null
+++ b/clang-tools-extra/test/clang-tidy/checkers/readability/ConditionalToStdMinMax.cpp
@@ -0,0 +1,27 @@
+// RUN: %check_clang_tidy %s readability-ConditionalToStdMinMax %t
+
+void foo() {
+  int value1,value2;
+
+  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use std::max instead of < [readability-ConditionalToStdMinMax]
+  if (value1 < value2)
+    value1 = value2; // CHECK-FIXES: value1 = std::max(value1, value2);
+
+  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use std::min instead of < [readability-ConditionalToStdMinMax]
+  if (value1 < value2)
+    value2 = value1; // CHECK-FIXES: value2 = std::min(value1, value2);
+
+  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use std::min instead of > [readability-ConditionalToStdMinMax]
+  if (value2 > value1)
+    value2 = value1; // CHECK-FIXES: value2 = std::min(value2, value1);
+
+  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use std::max instead of > [readability-ConditionalToStdMinMax]
+  if (value2 > value1)
+    value1 = value2; // CHECK-FIXES: value1 = std::max(value2, value1);
+
+  // No suggestion needed here
+  if (value1 == value2)
+    value1 = value2;
+
+  
+}
\ No newline at end of file

>From 89be4baf2591918b11b633d2430050dc41068fde Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Fri, 12 Jan 2024 00:03:16 +0530
Subject: [PATCH 02/46] Formatted the code

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../ConditionaltostdminmaxCheck.cpp           | 96 ++++++++++---------
 .../readability/ConditionaltostdminmaxCheck.h |  4 +-
 2 files changed, 52 insertions(+), 48 deletions(-)

diff --git a/clang-tools-extra/clang-tidy/readability/ConditionaltostdminmaxCheck.cpp b/clang-tools-extra/clang-tidy/readability/ConditionaltostdminmaxCheck.cpp
index fba8c68f73745..86420765d6f6c 100644
--- a/clang-tools-extra/clang-tidy/readability/ConditionaltostdminmaxCheck.cpp
+++ b/clang-tools-extra/clang-tidy/readability/ConditionaltostdminmaxCheck.cpp
@@ -16,69 +16,71 @@ namespace clang::tidy::readability {
 
 void ConditionaltostdminmaxCheck::registerMatchers(MatchFinder *Finder) {
   Finder->addMatcher(
-    ifStmt(
-      has(
-        binaryOperator(
-          anyOf(hasOperatorName("<"),hasOperatorName(">")),
-          hasLHS(ignoringImpCasts(declRefExpr().bind("lhsVar1"))),
-          hasRHS(ignoringImpCasts(declRefExpr().bind("rhsVar1")))
-          )
-          )
-        ,
-        hasThen(
-          stmt(
-            binaryOperator(
-              hasOperatorName("="),
-              hasLHS(ignoringImpCasts(declRefExpr().bind("lhsVar2"))),
-              hasRHS(ignoringImpCasts(declRefExpr().bind("rhsVar2")))
-              )
-            )
-          ) 
-    ).bind("ifStmt"),this);
-
-
-
+      ifStmt(has(binaryOperator(
+                 anyOf(hasOperatorName("<"), hasOperatorName(">")),
+                 hasLHS(ignoringImpCasts(declRefExpr().bind("lhsVar1"))),
+                 hasRHS(ignoringImpCasts(declRefExpr().bind("rhsVar1"))))),
+             hasThen(stmt(binaryOperator(
+                 hasOperatorName("="),
+                 hasLHS(ignoringImpCasts(declRefExpr().bind("lhsVar2"))),
+                 hasRHS(ignoringImpCasts(declRefExpr().bind("rhsVar2")))))))
+          .bind("ifStmt"),
+      this);
 }
 
-void ConditionaltostdminmaxCheck::check(const MatchFinder::MatchResult &Result) {
+void ConditionaltostdminmaxCheck::check(
+    const MatchFinder::MatchResult &Result) {
   const DeclRefExpr *lhsVar1 = Result.Nodes.getNodeAs<DeclRefExpr>("lhsVar1");
   const DeclRefExpr *rhsVar1 = Result.Nodes.getNodeAs<DeclRefExpr>("rhsVar1");
   const DeclRefExpr *lhsVar2 = Result.Nodes.getNodeAs<DeclRefExpr>("lhsVar2");
-  const DeclRefExpr *rhsVar2 = Result.Nodes.getNodeAs<DeclRefExpr>("rhsVar2");  
+  const DeclRefExpr *rhsVar2 = Result.Nodes.getNodeAs<DeclRefExpr>("rhsVar2");
   const IfStmt *ifStmt = Result.Nodes.getNodeAs<IfStmt>("ifStmt");
 
   if (!lhsVar1 || !rhsVar1 || !lhsVar2 || !rhsVar2 || !ifStmt)
-        return;
+    return;
 
   const BinaryOperator *binaryOp = dyn_cast<BinaryOperator>(ifStmt->getCond());
   if (!binaryOp)
-      return;
+    return;
 
   SourceLocation ifLocation = ifStmt->getIfLoc();
   SourceLocation thenLocation = ifStmt->getEndLoc();
 
-  if(binaryOp->getOpcode() == BO_LT){
-    if(lhsVar1->getDecl() == lhsVar2->getDecl() && rhsVar1->getDecl() == rhsVar2->getDecl()){
-      diag(ifStmt->getIfLoc(), "use std::max instead of <")<<FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
-                                      lhsVar2->getNameInfo().getAsString() + " = std::max(" + lhsVar1->getNameInfo().getAsString() + ", " +
-                                      rhsVar1->getNameInfo().getAsString() + ")");
-    }
-    else if(lhsVar1->getDecl() == rhsVar2->getDecl() && rhsVar1->getDecl() == lhsVar2->getDecl()){
-      diag(ifStmt->getIfLoc(), "use std::min instead of <")<<FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
-                                      lhsVar2->getNameInfo().getAsString() + " = std::min(" + lhsVar1->getNameInfo().getAsString() + ", " +
-                                      rhsVar1->getNameInfo().getAsString() + ")");
-    }
-  }
-  else if(binaryOp->getOpcode() == BO_GT){
-    if(lhsVar1->getDecl() == lhsVar2->getDecl() && rhsVar1->getDecl() == rhsVar2->getDecl()){
-      diag(ifStmt->getIfLoc(), "use std::min instead of >")<<FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
-                                      lhsVar2->getNameInfo().getAsString() + " = std::min(" + lhsVar1->getNameInfo().getAsString() + ", " +
-                                      rhsVar1->getNameInfo().getAsString() + ")");
+  if (binaryOp->getOpcode() == BO_LT) {
+    if (lhsVar1->getDecl() == lhsVar2->getDecl() &&
+        rhsVar1->getDecl() == rhsVar2->getDecl()) {
+      diag(ifStmt->getIfLoc(), "use std::max instead of <")
+          << FixItHint::CreateReplacement(
+                 SourceRange(ifLocation, thenLocation),
+                 lhsVar2->getNameInfo().getAsString() + " = std::max(" +
+                     lhsVar1->getNameInfo().getAsString() + ", " +
+                     rhsVar1->getNameInfo().getAsString() + ")");
+    } else if (lhsVar1->getDecl() == rhsVar2->getDecl() &&
+               rhsVar1->getDecl() == lhsVar2->getDecl()) {
+      diag(ifStmt->getIfLoc(), "use std::min instead of <")
+          << FixItHint::CreateReplacement(
+                 SourceRange(ifLocation, thenLocation),
+                 lhsVar2->getNameInfo().getAsString() + " = std::min(" +
+                     lhsVar1->getNameInfo().getAsString() + ", " +
+                     rhsVar1->getNameInfo().getAsString() + ")");
     }
-    else if(lhsVar1->getDecl() == rhsVar2->getDecl() && rhsVar1->getDecl() == lhsVar2->getDecl()){
-      diag(ifStmt->getIfLoc(), "use std::max instead of >")<<FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
-                                      lhsVar2->getNameInfo().getAsString() + " = std::max(" + lhsVar1->getNameInfo().getAsString() + ", " +
-                                      rhsVar1->getNameInfo().getAsString() + ")");
+  } else if (binaryOp->getOpcode() == BO_GT) {
+    if (lhsVar1->getDecl() == lhsVar2->getDecl() &&
+        rhsVar1->getDecl() == rhsVar2->getDecl()) {
+      diag(ifStmt->getIfLoc(), "use std::min instead of >")
+          << FixItHint::CreateReplacement(
+                 SourceRange(ifLocation, thenLocation),
+                 lhsVar2->getNameInfo().getAsString() + " = std::min(" +
+                     lhsVar1->getNameInfo().getAsString() + ", " +
+                     rhsVar1->getNameInfo().getAsString() + ")");
+    } else if (lhsVar1->getDecl() == rhsVar2->getDecl() &&
+               rhsVar1->getDecl() == lhsVar2->getDecl()) {
+      diag(ifStmt->getIfLoc(), "use std::max instead of >")
+          << FixItHint::CreateReplacement(
+                 SourceRange(ifLocation, thenLocation),
+                 lhsVar2->getNameInfo().getAsString() + " = std::max(" +
+                     lhsVar1->getNameInfo().getAsString() + ", " +
+                     rhsVar1->getNameInfo().getAsString() + ")");
     }
   }
 }
diff --git a/clang-tools-extra/clang-tidy/readability/ConditionaltostdminmaxCheck.h b/clang-tools-extra/clang-tidy/readability/ConditionaltostdminmaxCheck.h
index b7eabcc7d16d4..02ebed83fed6c 100644
--- a/clang-tools-extra/clang-tidy/readability/ConditionaltostdminmaxCheck.h
+++ b/clang-tools-extra/clang-tidy/readability/ConditionaltostdminmaxCheck.h
@@ -13,7 +13,9 @@
 
 namespace clang::tidy::readability {
 
-/// FIXME: replaces certain conditional statements with equivalent std::min or std::max expressions, improving readability and promoting the use of standard library functions."
+/// FIXME: replaces certain conditional statements with equivalent std::min or
+/// std::max expressions, improving readability and promoting the use of
+/// standard library functions."
 ///
 /// For the user-facing documentation see:
 /// http://clang.llvm.org/extra/clang-tidy/checks/readability/ConditionalToStdMinMax.html

>From e1b65a9fb0ea27d62b568d8d3038c0231927cdad Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Fri, 12 Jan 2024 00:15:54 +0530
Subject: [PATCH 03/46] small fix

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../clang-tidy/checks/readability/ConditionalToStdMinMax.rst    | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/clang-tools-extra/docs/clang-tidy/checks/readability/ConditionalToStdMinMax.rst b/clang-tools-extra/docs/clang-tidy/checks/readability/ConditionalToStdMinMax.rst
index e95858999b277..2b75e78ecb808 100644
--- a/clang-tools-extra/docs/clang-tidy/checks/readability/ConditionalToStdMinMax.rst
+++ b/clang-tools-extra/docs/clang-tidy/checks/readability/ConditionalToStdMinMax.rst
@@ -23,7 +23,7 @@ After:
 
 .. code-block:: c++
 
-  int main(){
+  void foo(){
     a = std::max(a, b);
 
   }
\ No newline at end of file

>From 042ddc3d89ebad999378e6bb8ef29e1f05f81745 Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Fri, 12 Jan 2024 15:43:22 +0530
Subject: [PATCH 04/46] Revert "small fix"

This reverts commit e1b65a9fb0ea27d62b568d8d3038c0231927cdad.
---
 .../clang-tidy/checks/readability/ConditionalToStdMinMax.rst    | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/clang-tools-extra/docs/clang-tidy/checks/readability/ConditionalToStdMinMax.rst b/clang-tools-extra/docs/clang-tidy/checks/readability/ConditionalToStdMinMax.rst
index 2b75e78ecb808..e95858999b277 100644
--- a/clang-tools-extra/docs/clang-tidy/checks/readability/ConditionalToStdMinMax.rst
+++ b/clang-tools-extra/docs/clang-tidy/checks/readability/ConditionalToStdMinMax.rst
@@ -23,7 +23,7 @@ After:
 
 .. code-block:: c++
 
-  void foo(){
+  int main(){
     a = std::max(a, b);
 
   }
\ No newline at end of file

>From c17b298185d50095d964d5afd8f79f52281e85f8 Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Fri, 12 Jan 2024 15:43:38 +0530
Subject: [PATCH 05/46] Revert "Formatted the code"

This reverts commit 89be4baf2591918b11b633d2430050dc41068fde.
---
 .../ConditionaltostdminmaxCheck.cpp           | 96 +++++++++----------
 .../readability/ConditionaltostdminmaxCheck.h |  4 +-
 2 files changed, 48 insertions(+), 52 deletions(-)

diff --git a/clang-tools-extra/clang-tidy/readability/ConditionaltostdminmaxCheck.cpp b/clang-tools-extra/clang-tidy/readability/ConditionaltostdminmaxCheck.cpp
index 86420765d6f6c..fba8c68f73745 100644
--- a/clang-tools-extra/clang-tidy/readability/ConditionaltostdminmaxCheck.cpp
+++ b/clang-tools-extra/clang-tidy/readability/ConditionaltostdminmaxCheck.cpp
@@ -16,71 +16,69 @@ namespace clang::tidy::readability {
 
 void ConditionaltostdminmaxCheck::registerMatchers(MatchFinder *Finder) {
   Finder->addMatcher(
-      ifStmt(has(binaryOperator(
-                 anyOf(hasOperatorName("<"), hasOperatorName(">")),
-                 hasLHS(ignoringImpCasts(declRefExpr().bind("lhsVar1"))),
-                 hasRHS(ignoringImpCasts(declRefExpr().bind("rhsVar1"))))),
-             hasThen(stmt(binaryOperator(
-                 hasOperatorName("="),
-                 hasLHS(ignoringImpCasts(declRefExpr().bind("lhsVar2"))),
-                 hasRHS(ignoringImpCasts(declRefExpr().bind("rhsVar2")))))))
-          .bind("ifStmt"),
-      this);
+    ifStmt(
+      has(
+        binaryOperator(
+          anyOf(hasOperatorName("<"),hasOperatorName(">")),
+          hasLHS(ignoringImpCasts(declRefExpr().bind("lhsVar1"))),
+          hasRHS(ignoringImpCasts(declRefExpr().bind("rhsVar1")))
+          )
+          )
+        ,
+        hasThen(
+          stmt(
+            binaryOperator(
+              hasOperatorName("="),
+              hasLHS(ignoringImpCasts(declRefExpr().bind("lhsVar2"))),
+              hasRHS(ignoringImpCasts(declRefExpr().bind("rhsVar2")))
+              )
+            )
+          ) 
+    ).bind("ifStmt"),this);
+
+
+
 }
 
-void ConditionaltostdminmaxCheck::check(
-    const MatchFinder::MatchResult &Result) {
+void ConditionaltostdminmaxCheck::check(const MatchFinder::MatchResult &Result) {
   const DeclRefExpr *lhsVar1 = Result.Nodes.getNodeAs<DeclRefExpr>("lhsVar1");
   const DeclRefExpr *rhsVar1 = Result.Nodes.getNodeAs<DeclRefExpr>("rhsVar1");
   const DeclRefExpr *lhsVar2 = Result.Nodes.getNodeAs<DeclRefExpr>("lhsVar2");
-  const DeclRefExpr *rhsVar2 = Result.Nodes.getNodeAs<DeclRefExpr>("rhsVar2");
+  const DeclRefExpr *rhsVar2 = Result.Nodes.getNodeAs<DeclRefExpr>("rhsVar2");  
   const IfStmt *ifStmt = Result.Nodes.getNodeAs<IfStmt>("ifStmt");
 
   if (!lhsVar1 || !rhsVar1 || !lhsVar2 || !rhsVar2 || !ifStmt)
-    return;
+        return;
 
   const BinaryOperator *binaryOp = dyn_cast<BinaryOperator>(ifStmt->getCond());
   if (!binaryOp)
-    return;
+      return;
 
   SourceLocation ifLocation = ifStmt->getIfLoc();
   SourceLocation thenLocation = ifStmt->getEndLoc();
 
-  if (binaryOp->getOpcode() == BO_LT) {
-    if (lhsVar1->getDecl() == lhsVar2->getDecl() &&
-        rhsVar1->getDecl() == rhsVar2->getDecl()) {
-      diag(ifStmt->getIfLoc(), "use std::max instead of <")
-          << FixItHint::CreateReplacement(
-                 SourceRange(ifLocation, thenLocation),
-                 lhsVar2->getNameInfo().getAsString() + " = std::max(" +
-                     lhsVar1->getNameInfo().getAsString() + ", " +
-                     rhsVar1->getNameInfo().getAsString() + ")");
-    } else if (lhsVar1->getDecl() == rhsVar2->getDecl() &&
-               rhsVar1->getDecl() == lhsVar2->getDecl()) {
-      diag(ifStmt->getIfLoc(), "use std::min instead of <")
-          << FixItHint::CreateReplacement(
-                 SourceRange(ifLocation, thenLocation),
-                 lhsVar2->getNameInfo().getAsString() + " = std::min(" +
-                     lhsVar1->getNameInfo().getAsString() + ", " +
-                     rhsVar1->getNameInfo().getAsString() + ")");
+  if(binaryOp->getOpcode() == BO_LT){
+    if(lhsVar1->getDecl() == lhsVar2->getDecl() && rhsVar1->getDecl() == rhsVar2->getDecl()){
+      diag(ifStmt->getIfLoc(), "use std::max instead of <")<<FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
+                                      lhsVar2->getNameInfo().getAsString() + " = std::max(" + lhsVar1->getNameInfo().getAsString() + ", " +
+                                      rhsVar1->getNameInfo().getAsString() + ")");
+    }
+    else if(lhsVar1->getDecl() == rhsVar2->getDecl() && rhsVar1->getDecl() == lhsVar2->getDecl()){
+      diag(ifStmt->getIfLoc(), "use std::min instead of <")<<FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
+                                      lhsVar2->getNameInfo().getAsString() + " = std::min(" + lhsVar1->getNameInfo().getAsString() + ", " +
+                                      rhsVar1->getNameInfo().getAsString() + ")");
+    }
+  }
+  else if(binaryOp->getOpcode() == BO_GT){
+    if(lhsVar1->getDecl() == lhsVar2->getDecl() && rhsVar1->getDecl() == rhsVar2->getDecl()){
+      diag(ifStmt->getIfLoc(), "use std::min instead of >")<<FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
+                                      lhsVar2->getNameInfo().getAsString() + " = std::min(" + lhsVar1->getNameInfo().getAsString() + ", " +
+                                      rhsVar1->getNameInfo().getAsString() + ")");
     }
-  } else if (binaryOp->getOpcode() == BO_GT) {
-    if (lhsVar1->getDecl() == lhsVar2->getDecl() &&
-        rhsVar1->getDecl() == rhsVar2->getDecl()) {
-      diag(ifStmt->getIfLoc(), "use std::min instead of >")
-          << FixItHint::CreateReplacement(
-                 SourceRange(ifLocation, thenLocation),
-                 lhsVar2->getNameInfo().getAsString() + " = std::min(" +
-                     lhsVar1->getNameInfo().getAsString() + ", " +
-                     rhsVar1->getNameInfo().getAsString() + ")");
-    } else if (lhsVar1->getDecl() == rhsVar2->getDecl() &&
-               rhsVar1->getDecl() == lhsVar2->getDecl()) {
-      diag(ifStmt->getIfLoc(), "use std::max instead of >")
-          << FixItHint::CreateReplacement(
-                 SourceRange(ifLocation, thenLocation),
-                 lhsVar2->getNameInfo().getAsString() + " = std::max(" +
-                     lhsVar1->getNameInfo().getAsString() + ", " +
-                     rhsVar1->getNameInfo().getAsString() + ")");
+    else if(lhsVar1->getDecl() == rhsVar2->getDecl() && rhsVar1->getDecl() == lhsVar2->getDecl()){
+      diag(ifStmt->getIfLoc(), "use std::max instead of >")<<FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
+                                      lhsVar2->getNameInfo().getAsString() + " = std::max(" + lhsVar1->getNameInfo().getAsString() + ", " +
+                                      rhsVar1->getNameInfo().getAsString() + ")");
     }
   }
 }
diff --git a/clang-tools-extra/clang-tidy/readability/ConditionaltostdminmaxCheck.h b/clang-tools-extra/clang-tidy/readability/ConditionaltostdminmaxCheck.h
index 02ebed83fed6c..b7eabcc7d16d4 100644
--- a/clang-tools-extra/clang-tidy/readability/ConditionaltostdminmaxCheck.h
+++ b/clang-tools-extra/clang-tidy/readability/ConditionaltostdminmaxCheck.h
@@ -13,9 +13,7 @@
 
 namespace clang::tidy::readability {
 
-/// FIXME: replaces certain conditional statements with equivalent std::min or
-/// std::max expressions, improving readability and promoting the use of
-/// standard library functions."
+/// FIXME: replaces certain conditional statements with equivalent std::min or std::max expressions, improving readability and promoting the use of standard library functions."
 ///
 /// For the user-facing documentation see:
 /// http://clang.llvm.org/extra/clang-tidy/checks/readability/ConditionalToStdMinMax.html

>From 9aad658ef0e6175cdc0388c914a444a5bcd9ba1c Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Fri, 12 Jan 2024 15:43:52 +0530
Subject: [PATCH 06/46] Revert "Add readability check to suggest replacement of
 conditional statement with std::min/std::max"

This reverts commit 1883d987b2f83adaef05fdb47ae25c7b06582a64.
---
 .../clang-tidy/readability/CMakeLists.txt     |  1 -
 .../ConditionaltostdminmaxCheck.cpp           | 86 -------------------
 .../readability/ConditionaltostdminmaxCheck.h | 30 -------
 .../readability/ReadabilityTidyModule.cpp     |  3 -
 clang-tools-extra/docs/ReleaseNotes.rst       |  6 --
 .../docs/clang-tidy/checks/list.rst           |  1 -
 .../readability/ConditionalToStdMinMax.rst    | 29 -------
 .../readability/ConditionalToStdMinMax.cpp    | 27 ------
 8 files changed, 183 deletions(-)
 delete mode 100644 clang-tools-extra/clang-tidy/readability/ConditionaltostdminmaxCheck.cpp
 delete mode 100644 clang-tools-extra/clang-tidy/readability/ConditionaltostdminmaxCheck.h
 delete mode 100644 clang-tools-extra/docs/clang-tidy/checks/readability/ConditionalToStdMinMax.rst
 delete mode 100644 clang-tools-extra/test/clang-tidy/checkers/readability/ConditionalToStdMinMax.cpp

diff --git a/clang-tools-extra/clang-tidy/readability/CMakeLists.txt b/clang-tools-extra/clang-tidy/readability/CMakeLists.txt
index 4bc373bb69bb8..408c822b861c5 100644
--- a/clang-tools-extra/clang-tidy/readability/CMakeLists.txt
+++ b/clang-tools-extra/clang-tidy/readability/CMakeLists.txt
@@ -8,7 +8,6 @@ add_clang_library(clangTidyReadabilityModule
   AvoidReturnWithVoidValueCheck.cpp
   AvoidUnconditionalPreprocessorIfCheck.cpp
   BracesAroundStatementsCheck.cpp
-  ConditionaltostdminmaxCheck.cpp
   ConstReturnTypeCheck.cpp
   ContainerContainsCheck.cpp
   ContainerDataPointerCheck.cpp
diff --git a/clang-tools-extra/clang-tidy/readability/ConditionaltostdminmaxCheck.cpp b/clang-tools-extra/clang-tidy/readability/ConditionaltostdminmaxCheck.cpp
deleted file mode 100644
index fba8c68f73745..0000000000000
--- a/clang-tools-extra/clang-tidy/readability/ConditionaltostdminmaxCheck.cpp
+++ /dev/null
@@ -1,86 +0,0 @@
-//===--- ConditionaltostdminmaxCheck.cpp - clang-tidy ---------------------===//
-//
-// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
-// See https://llvm.org/LICENSE.txt for license information.
-// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
-//
-//===----------------------------------------------------------------------===//
-
-#include "ConditionaltostdminmaxCheck.h"
-#include "clang/AST/ASTContext.h"
-#include "clang/ASTMatchers/ASTMatchFinder.h"
-
-using namespace clang::ast_matchers;
-
-namespace clang::tidy::readability {
-
-void ConditionaltostdminmaxCheck::registerMatchers(MatchFinder *Finder) {
-  Finder->addMatcher(
-    ifStmt(
-      has(
-        binaryOperator(
-          anyOf(hasOperatorName("<"),hasOperatorName(">")),
-          hasLHS(ignoringImpCasts(declRefExpr().bind("lhsVar1"))),
-          hasRHS(ignoringImpCasts(declRefExpr().bind("rhsVar1")))
-          )
-          )
-        ,
-        hasThen(
-          stmt(
-            binaryOperator(
-              hasOperatorName("="),
-              hasLHS(ignoringImpCasts(declRefExpr().bind("lhsVar2"))),
-              hasRHS(ignoringImpCasts(declRefExpr().bind("rhsVar2")))
-              )
-            )
-          ) 
-    ).bind("ifStmt"),this);
-
-
-
-}
-
-void ConditionaltostdminmaxCheck::check(const MatchFinder::MatchResult &Result) {
-  const DeclRefExpr *lhsVar1 = Result.Nodes.getNodeAs<DeclRefExpr>("lhsVar1");
-  const DeclRefExpr *rhsVar1 = Result.Nodes.getNodeAs<DeclRefExpr>("rhsVar1");
-  const DeclRefExpr *lhsVar2 = Result.Nodes.getNodeAs<DeclRefExpr>("lhsVar2");
-  const DeclRefExpr *rhsVar2 = Result.Nodes.getNodeAs<DeclRefExpr>("rhsVar2");  
-  const IfStmt *ifStmt = Result.Nodes.getNodeAs<IfStmt>("ifStmt");
-
-  if (!lhsVar1 || !rhsVar1 || !lhsVar2 || !rhsVar2 || !ifStmt)
-        return;
-
-  const BinaryOperator *binaryOp = dyn_cast<BinaryOperator>(ifStmt->getCond());
-  if (!binaryOp)
-      return;
-
-  SourceLocation ifLocation = ifStmt->getIfLoc();
-  SourceLocation thenLocation = ifStmt->getEndLoc();
-
-  if(binaryOp->getOpcode() == BO_LT){
-    if(lhsVar1->getDecl() == lhsVar2->getDecl() && rhsVar1->getDecl() == rhsVar2->getDecl()){
-      diag(ifStmt->getIfLoc(), "use std::max instead of <")<<FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
-                                      lhsVar2->getNameInfo().getAsString() + " = std::max(" + lhsVar1->getNameInfo().getAsString() + ", " +
-                                      rhsVar1->getNameInfo().getAsString() + ")");
-    }
-    else if(lhsVar1->getDecl() == rhsVar2->getDecl() && rhsVar1->getDecl() == lhsVar2->getDecl()){
-      diag(ifStmt->getIfLoc(), "use std::min instead of <")<<FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
-                                      lhsVar2->getNameInfo().getAsString() + " = std::min(" + lhsVar1->getNameInfo().getAsString() + ", " +
-                                      rhsVar1->getNameInfo().getAsString() + ")");
-    }
-  }
-  else if(binaryOp->getOpcode() == BO_GT){
-    if(lhsVar1->getDecl() == lhsVar2->getDecl() && rhsVar1->getDecl() == rhsVar2->getDecl()){
-      diag(ifStmt->getIfLoc(), "use std::min instead of >")<<FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
-                                      lhsVar2->getNameInfo().getAsString() + " = std::min(" + lhsVar1->getNameInfo().getAsString() + ", " +
-                                      rhsVar1->getNameInfo().getAsString() + ")");
-    }
-    else if(lhsVar1->getDecl() == rhsVar2->getDecl() && rhsVar1->getDecl() == lhsVar2->getDecl()){
-      diag(ifStmt->getIfLoc(), "use std::max instead of >")<<FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
-                                      lhsVar2->getNameInfo().getAsString() + " = std::max(" + lhsVar1->getNameInfo().getAsString() + ", " +
-                                      rhsVar1->getNameInfo().getAsString() + ")");
-    }
-  }
-}
-
-} // namespace clang::tidy::readability
diff --git a/clang-tools-extra/clang-tidy/readability/ConditionaltostdminmaxCheck.h b/clang-tools-extra/clang-tidy/readability/ConditionaltostdminmaxCheck.h
deleted file mode 100644
index b7eabcc7d16d4..0000000000000
--- a/clang-tools-extra/clang-tidy/readability/ConditionaltostdminmaxCheck.h
+++ /dev/null
@@ -1,30 +0,0 @@
-//===--- ConditionaltostdminmaxCheck.h - clang-tidy -------------*- C++ -*-===//
-//
-// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
-// See https://llvm.org/LICENSE.txt for license information.
-// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
-//
-//===----------------------------------------------------------------------===//
-
-#ifndef LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_READABILITY_CONDITIONALTOSTDMINMAXCHECK_H
-#define LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_READABILITY_CONDITIONALTOSTDMINMAXCHECK_H
-
-#include "../ClangTidyCheck.h"
-
-namespace clang::tidy::readability {
-
-/// FIXME: replaces certain conditional statements with equivalent std::min or std::max expressions, improving readability and promoting the use of standard library functions."
-///
-/// For the user-facing documentation see:
-/// http://clang.llvm.org/extra/clang-tidy/checks/readability/ConditionalToStdMinMax.html
-class ConditionaltostdminmaxCheck : public ClangTidyCheck {
-public:
-  ConditionaltostdminmaxCheck(StringRef Name, ClangTidyContext *Context)
-      : ClangTidyCheck(Name, Context) {}
-  void registerMatchers(ast_matchers::MatchFinder *Finder) override;
-  void check(const ast_matchers::MatchFinder::MatchResult &Result) override;
-};
-
-} // namespace clang::tidy::readability
-
-#endif // LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_READABILITY_CONDITIONALTOSTDMINMAXCHECK_H
diff --git a/clang-tools-extra/clang-tidy/readability/ReadabilityTidyModule.cpp b/clang-tools-extra/clang-tidy/readability/ReadabilityTidyModule.cpp
index 63f8f03be6bb9..0b0aad7c0dcb3 100644
--- a/clang-tools-extra/clang-tidy/readability/ReadabilityTidyModule.cpp
+++ b/clang-tools-extra/clang-tidy/readability/ReadabilityTidyModule.cpp
@@ -13,7 +13,6 @@
 #include "AvoidReturnWithVoidValueCheck.h"
 #include "AvoidUnconditionalPreprocessorIfCheck.h"
 #include "BracesAroundStatementsCheck.h"
-#include "ConditionaltostdminmaxCheck.h"
 #include "ConstReturnTypeCheck.h"
 #include "ContainerContainsCheck.h"
 #include "ContainerDataPointerCheck.h"
@@ -63,8 +62,6 @@ namespace readability {
 class ReadabilityModule : public ClangTidyModule {
 public:
   void addCheckFactories(ClangTidyCheckFactories &CheckFactories) override {
-    CheckFactories.registerCheck<ConditionaltostdminmaxCheck>(
-        "readability-ConditionalToStdMinMax");
     CheckFactories.registerCheck<AvoidConstParamsInDecls>(
         "readability-avoid-const-params-in-decls");
     CheckFactories.registerCheck<AvoidReturnWithVoidValueCheck>(
diff --git a/clang-tools-extra/docs/ReleaseNotes.rst b/clang-tools-extra/docs/ReleaseNotes.rst
index c3fb990ad6a73..b4d87e0ed2a67 100644
--- a/clang-tools-extra/docs/ReleaseNotes.rst
+++ b/clang-tools-extra/docs/ReleaseNotes.rst
@@ -224,12 +224,6 @@ New checks
   Recommends the smallest possible underlying type for an ``enum`` or ``enum``
   class based on the range of its enumerators.
 
-- New :doc:`readability-ConditionalToStdMinMax
-  <clang-tidy/checks/readability/ConditionalToStdMinMax>` check.
-
-  Replaces certain conditional statements with equivalent std::min or std::max expressions, 
-  improving readability and promoting the use of standard library functions.
-
 - New :doc:`readability-reference-to-constructed-temporary
   <clang-tidy/checks/readability/reference-to-constructed-temporary>` check.
 
diff --git a/clang-tools-extra/docs/clang-tidy/checks/list.rst b/clang-tools-extra/docs/clang-tidy/checks/list.rst
index c2eac55425c69..2f86121ad8729 100644
--- a/clang-tools-extra/docs/clang-tidy/checks/list.rst
+++ b/clang-tools-extra/docs/clang-tidy/checks/list.rst
@@ -336,7 +336,6 @@ Clang-Tidy Checks
    :doc:`portability-restrict-system-includes <portability/restrict-system-includes>`, "Yes"
    :doc:`portability-simd-intrinsics <portability/simd-intrinsics>`,
    :doc:`portability-std-allocator-const <portability/std-allocator-const>`,
-   :doc:`readability-ConditionalToStdMinMax <readability/ConditionalToStdMinMax>`, "Yes"
    :doc:`readability-avoid-const-params-in-decls <readability/avoid-const-params-in-decls>`, "Yes"
    :doc:`readability-avoid-return-with-void-value <readability/avoid-return-with-void-value>`,
    :doc:`readability-avoid-unconditional-preprocessor-if <readability/avoid-unconditional-preprocessor-if>`,
diff --git a/clang-tools-extra/docs/clang-tidy/checks/readability/ConditionalToStdMinMax.rst b/clang-tools-extra/docs/clang-tidy/checks/readability/ConditionalToStdMinMax.rst
deleted file mode 100644
index e95858999b277..0000000000000
--- a/clang-tools-extra/docs/clang-tidy/checks/readability/ConditionalToStdMinMax.rst
+++ /dev/null
@@ -1,29 +0,0 @@
-.. title:: clang-tidy - readability-ConditionalToStdMinMax
-
-readability-ConditionalToStdMinMax
-==================================
-
-Replaces certain conditional statements with equivalent std::min or std::max expressions, 
-improving readability and promoting the use of standard library functions.
-
-Examples:
-
-Before:
-
-.. code-block:: c++
-
-  void foo(){
-    int a,b;
-    if(a < b)
-        a = b;
-    }
-
-
-After:
-
-.. code-block:: c++
-
-  int main(){
-    a = std::max(a, b);
-
-  }
\ No newline at end of file
diff --git a/clang-tools-extra/test/clang-tidy/checkers/readability/ConditionalToStdMinMax.cpp b/clang-tools-extra/test/clang-tidy/checkers/readability/ConditionalToStdMinMax.cpp
deleted file mode 100644
index d29e9aa9fec70..0000000000000
--- a/clang-tools-extra/test/clang-tidy/checkers/readability/ConditionalToStdMinMax.cpp
+++ /dev/null
@@ -1,27 +0,0 @@
-// RUN: %check_clang_tidy %s readability-ConditionalToStdMinMax %t
-
-void foo() {
-  int value1,value2;
-
-  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use std::max instead of < [readability-ConditionalToStdMinMax]
-  if (value1 < value2)
-    value1 = value2; // CHECK-FIXES: value1 = std::max(value1, value2);
-
-  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use std::min instead of < [readability-ConditionalToStdMinMax]
-  if (value1 < value2)
-    value2 = value1; // CHECK-FIXES: value2 = std::min(value1, value2);
-
-  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use std::min instead of > [readability-ConditionalToStdMinMax]
-  if (value2 > value1)
-    value2 = value1; // CHECK-FIXES: value2 = std::min(value2, value1);
-
-  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use std::max instead of > [readability-ConditionalToStdMinMax]
-  if (value2 > value1)
-    value1 = value2; // CHECK-FIXES: value1 = std::max(value2, value1);
-
-  // No suggestion needed here
-  if (value1 == value2)
-    value1 = value2;
-
-  
-}
\ No newline at end of file

>From 2fc0938430a25ca6672c2d408e55f5b1a3188d60 Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Fri, 12 Jan 2024 17:24:08 +0530
Subject: [PATCH 07/46] Added Suggested Changes

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../clang-tidy/readability/CMakeLists.txt     |   1 +
 .../readability/ReadabilityTidyModule.cpp     |   3 +
 .../readability/UseStdMinMaxCheck.cpp         | 103 ++++++++++++++++++
 .../readability/UseStdMinMaxCheck.h           |  38 +++++++
 clang-tools-extra/docs/ReleaseNotes.rst       |   5 +
 .../docs/clang-tidy/checks/list.rst           |   1 +
 .../checks/readability/UseStdMinMax.rst       |  33 ++++++
 .../checkers/readability/use-std-min-max.cpp  |  35 ++++++
 8 files changed, 219 insertions(+)
 create mode 100644 clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
 create mode 100644 clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.h
 create mode 100644 clang-tools-extra/docs/clang-tidy/checks/readability/UseStdMinMax.rst
 create mode 100644 clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp

diff --git a/clang-tools-extra/clang-tidy/readability/CMakeLists.txt b/clang-tools-extra/clang-tidy/readability/CMakeLists.txt
index 408c822b861c5..3670a43995434 100644
--- a/clang-tools-extra/clang-tidy/readability/CMakeLists.txt
+++ b/clang-tools-extra/clang-tidy/readability/CMakeLists.txt
@@ -52,6 +52,7 @@ add_clang_library(clangTidyReadabilityModule
   UniqueptrDeleteReleaseCheck.cpp
   UppercaseLiteralSuffixCheck.cpp
   UseAnyOfAllOfCheck.cpp
+  UseStdMinMaxCheck.cpp
 
   LINK_LIBS
   clangTidy
diff --git a/clang-tools-extra/clang-tidy/readability/ReadabilityTidyModule.cpp b/clang-tools-extra/clang-tidy/readability/ReadabilityTidyModule.cpp
index 0b0aad7c0dcb3..cba32ea24cec7 100644
--- a/clang-tools-extra/clang-tidy/readability/ReadabilityTidyModule.cpp
+++ b/clang-tools-extra/clang-tidy/readability/ReadabilityTidyModule.cpp
@@ -55,6 +55,7 @@
 #include "UniqueptrDeleteReleaseCheck.h"
 #include "UppercaseLiteralSuffixCheck.h"
 #include "UseAnyOfAllOfCheck.h"
+#include "UseStdMinMaxCheck.h"
 
 namespace clang::tidy {
 namespace readability {
@@ -62,6 +63,8 @@ namespace readability {
 class ReadabilityModule : public ClangTidyModule {
 public:
   void addCheckFactories(ClangTidyCheckFactories &CheckFactories) override {
+    CheckFactories.registerCheck<UseStdMinMaxCheck>(
+        "readability-use-std-min-max");
     CheckFactories.registerCheck<AvoidConstParamsInDecls>(
         "readability-avoid-const-params-in-decls");
     CheckFactories.registerCheck<AvoidReturnWithVoidValueCheck>(
diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
new file mode 100644
index 0000000000000..984792322ce5d
--- /dev/null
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
@@ -0,0 +1,103 @@
+//===--- UseStdMinMaxCheck.cpp - clang-tidy -------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "UseStdMinMaxCheck.h"
+#include "clang/AST/ASTContext.h"
+#include "clang/ASTMatchers/ASTMatchFinder.h"
+#include "clang/Lex/Preprocessor.h"
+#include <optional>
+
+using namespace clang::ast_matchers;
+
+namespace clang::tidy::readability {
+
+void UseStdMinMaxCheck::registerMatchers(MatchFinder *Finder) {
+   Finder->addMatcher(
+      ifStmt(has(binaryOperator(
+                 anyOf(hasOperatorName("<"), hasOperatorName(">"),hasOperatorName("<="), hasOperatorName(">=")),
+                 hasLHS(expr().bind("lhsVar1")),
+                 hasRHS(expr().bind("rhsVar1")))),
+             hasThen(stmt(binaryOperator(
+                 hasOperatorName("="),
+                 hasLHS(expr().bind("lhsVar2")),
+                 hasRHS(expr().bind("rhsVar2"))))))
+          .bind("ifStmt"),
+      this);
+
+}
+
+void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
+  const auto *lhsVar1 = Result.Nodes.getNodeAs<Expr>("lhsVar1");
+  const auto *rhsVar1 = Result.Nodes.getNodeAs<Expr>("rhsVar1");
+  const auto *lhsVar2 = Result.Nodes.getNodeAs<Expr>("lhsVar2");
+  const auto *rhsVar2 = Result.Nodes.getNodeAs<Expr>("rhsVar2");
+  const auto *ifStmt = Result.Nodes.getNodeAs<IfStmt>("ifStmt");
+  auto &Context = *Result.Context;
+
+  if (!lhsVar1 || !rhsVar1 || !lhsVar2 || !rhsVar2 || !ifStmt)
+    return;
+
+  const BinaryOperator *binaryOp = dyn_cast<BinaryOperator>(ifStmt->getCond());
+  if (!binaryOp)
+    return;
+
+  SourceLocation ifLocation = ifStmt->getIfLoc();
+  SourceLocation thenLocation = ifStmt->getEndLoc();
+  auto lhsVar1Str = Lexer::getSourceText(CharSourceRange::getTokenRange(lhsVar1->getSourceRange()),
+                                       Context.getSourceManager(), Context.getLangOpts());
+
+  auto lhsVar2Str = Lexer::getSourceText(CharSourceRange::getTokenRange(lhsVar2->getSourceRange()),
+                                       Context.getSourceManager(), Context.getLangOpts());
+
+  auto rhsVar1Str = Lexer::getSourceText(CharSourceRange::getTokenRange(rhsVar1->getSourceRange()),
+                                       Context.getSourceManager(), Context.getLangOpts());
+
+  auto rhsVar2Str = Lexer::getSourceText(CharSourceRange::getTokenRange(rhsVar2->getSourceRange()),
+                                       Context.getSourceManager(), Context.getLangOpts());
+
+  if (binaryOp->getOpcode() == BO_LT) {
+    if (lhsVar1Str == lhsVar2Str &&
+        rhsVar1Str == rhsVar2Str) {
+      diag(ifStmt->getIfLoc(), "use `std::max` instead of `<`")
+          << FixItHint::CreateReplacement(
+                 SourceRange(ifLocation, thenLocation),
+                 lhsVar2Str.str() + " = std::max(" +
+                     lhsVar1Str.str() + ", " +
+                     rhsVar1Str.str() + ")");
+    } else if (lhsVar1Str == rhsVar2Str &&
+               rhsVar1Str == lhsVar2Str) {
+      diag(ifStmt->getIfLoc(), "use `std::min` instead of `<`")
+          << FixItHint::CreateReplacement(
+                 SourceRange(ifLocation, thenLocation),
+                 lhsVar2Str.str() + " = std::min(" +
+                     lhsVar1Str.str() + ", " +
+                     rhsVar1Str.str() + ")");
+    }
+  } else if (binaryOp->getOpcode() == BO_GT) {
+    if (lhsVar1Str == lhsVar2Str &&
+        rhsVar1Str == rhsVar2Str) {
+      diag(ifStmt->getIfLoc(), "use `std::min` instead of `>`")
+          << FixItHint::CreateReplacement(
+                 SourceRange(ifLocation, thenLocation),
+                 lhsVar2Str.str() + " = std::min(" +
+                     lhsVar1Str.str() + ", " +
+                     rhsVar1Str.str() + ")");
+    } else if (lhsVar1Str == rhsVar2Str &&
+               rhsVar1Str == lhsVar2Str) {
+      diag(ifStmt->getIfLoc(), "use `std::max` instead of `>`")
+          << FixItHint::CreateReplacement(
+                 SourceRange(ifLocation, thenLocation),
+                 lhsVar2Str.str() + " = std::max(" +
+                     lhsVar1Str.str() + ", " +
+                     rhsVar1Str.str() + ")");
+    }
+  }
+  
+}
+
+} // namespace clang::tidy::readability
diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.h b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.h
new file mode 100644
index 0000000000000..476b19ba5c9cf
--- /dev/null
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.h
@@ -0,0 +1,38 @@
+//===--- UseStdMinMaxCheck.h - clang-tidy -----------------------*- C++ -*-===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_READABILITY_USESTDMINMAXCHECK_H
+#define LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_READABILITY_USESTDMINMAXCHECK_H
+
+#include "../ClangTidyCheck.h"
+
+namespace clang::tidy::readability {
+
+/// replaces certain conditional statements with equivalent ``std::min`` or
+/// ``std::max`` expressions, improving readability and promoting the use of
+/// standard library functions.
+///
+/// For the user-facing documentation see:
+/// http://clang.llvm.org/extra/clang-tidy/checks/readability/UseStdMinMax.html
+class UseStdMinMaxCheck : public ClangTidyCheck {
+public:
+  UseStdMinMaxCheck(StringRef Name, ClangTidyContext *Context)
+      : ClangTidyCheck(Name, Context) {}
+  bool isLanguageVersionSupported(const LangOptions &LangOpts) const override {
+    return LangOpts.CPlusPlus;
+  }
+  void registerMatchers(ast_matchers::MatchFinder *Finder) override;
+  void check(const ast_matchers::MatchFinder::MatchResult &Result) override;
+  std::optional<TraversalKind> getCheckTraversalKind() const override {
+    return TK_IgnoreUnlessSpelledInSource;
+  }
+};
+
+} // namespace clang::tidy::readability
+
+#endif // LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_READABILITY_USESTDMINMAXCHECK_H
diff --git a/clang-tools-extra/docs/ReleaseNotes.rst b/clang-tools-extra/docs/ReleaseNotes.rst
index b4d87e0ed2a67..2d3a2c2981e6c 100644
--- a/clang-tools-extra/docs/ReleaseNotes.rst
+++ b/clang-tools-extra/docs/ReleaseNotes.rst
@@ -224,6 +224,11 @@ New checks
   Recommends the smallest possible underlying type for an ``enum`` or ``enum``
   class based on the range of its enumerators.
 
+- New :doc:`readability-use-std-min-max
+  <clang-tidy/checks/readability/use-std-min-max>` check.
+
+  FIXME: add release notes.
+
 - New :doc:`readability-reference-to-constructed-temporary
   <clang-tidy/checks/readability/reference-to-constructed-temporary>` check.
 
diff --git a/clang-tools-extra/docs/clang-tidy/checks/list.rst b/clang-tools-extra/docs/clang-tidy/checks/list.rst
index 2f86121ad8729..25b3550a77e46 100644
--- a/clang-tools-extra/docs/clang-tidy/checks/list.rst
+++ b/clang-tools-extra/docs/clang-tidy/checks/list.rst
@@ -336,6 +336,7 @@ Clang-Tidy Checks
    :doc:`portability-restrict-system-includes <portability/restrict-system-includes>`, "Yes"
    :doc:`portability-simd-intrinsics <portability/simd-intrinsics>`,
    :doc:`portability-std-allocator-const <portability/std-allocator-const>`,
+   :doc:`readability-use-std-min-max <readability/use-std-min-max>`, "Yes"
    :doc:`readability-avoid-const-params-in-decls <readability/avoid-const-params-in-decls>`, "Yes"
    :doc:`readability-avoid-return-with-void-value <readability/avoid-return-with-void-value>`,
    :doc:`readability-avoid-unconditional-preprocessor-if <readability/avoid-unconditional-preprocessor-if>`,
diff --git a/clang-tools-extra/docs/clang-tidy/checks/readability/UseStdMinMax.rst b/clang-tools-extra/docs/clang-tidy/checks/readability/UseStdMinMax.rst
new file mode 100644
index 0000000000000..c8b9bdc7c5ea3
--- /dev/null
+++ b/clang-tools-extra/docs/clang-tidy/checks/readability/UseStdMinMax.rst
@@ -0,0 +1,33 @@
+.. title:: clang-tidy - readability-use-std-min-max
+
+readability-use-std-min-max
+========================
+
+Replaces certain conditional statements with equivalent ``std::min`` or ``std::max`` expressions, 
+improving readability and promoting the use of standard library functions.
+Note: While this transformation improves code clarity, it may not be
+suitable for performance-critical code. Using ``std::min`` or ``std::max`` can
+introduce additional stores, potentially impacting performance compared to
+the original if statement that only assigns when the value needs to change.
+
+Examples:
+
+Before:
+
+.. code-block:: c++
+
+  void foo(){
+    int a,b;
+    if(a < b)
+        a = b;
+    }
+
+
+After:
+
+.. code-block:: c++
+
+  void foo(){
+    a = std::max(a, b);
+
+  }
diff --git a/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp b/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
new file mode 100644
index 0000000000000..37ee1fd65fb91
--- /dev/null
+++ b/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
@@ -0,0 +1,35 @@
+// RUN: %check_clang_tidy %s readability-use-std-min-max %t
+
+void foo() {
+  int value1,value2,value3;
+  short value4;
+
+  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
+  if (value1 < value2)
+    value1 = value2; // CHECK-FIXES: value1 = std::max(value1, value2);
+
+  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::min` instead of `<` [readability-use-std-min-max]
+  if (value1 < value2)
+    value2 = value1; // CHECK-FIXES: value2 = std::min(value1, value2);
+
+  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::min` instead of `>` [readability-use-std-min-max]
+  if (value2 > value1)
+    value2 = value1; // CHECK-FIXES: value2 = std::min(value2, value1);
+
+  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::max` instead of `>` [readability-use-std-min-max
+  if (value2 > value1)
+    value1 = value2; // CHECK-FIXES: value1 = std::max(value2, value1);
+
+  // No suggestion needed here
+  if (value1 == value2)
+    value1 = value2;
+  
+  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
+  if(value1<value4)
+    value1=value4; // CHECK-FIXES: value1 = std::max(value1, value4);
+  
+  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::min` instead of `<` [readability-use-std-min-max]
+  if(value1+value2<value3)
+    value3 = value1+value2; // CHECK-FIXES: value3 = std::min(value1+value2, value3);
+  
+}
\ No newline at end of file

>From 1139ac49be8023011bd57a2462781ac8b219c161 Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Fri, 12 Jan 2024 17:24:47 +0530
Subject: [PATCH 08/46] Formatted the Code

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../readability/UseStdMinMaxCheck.cpp         | 88 +++++++++----------
 1 file changed, 41 insertions(+), 47 deletions(-)

diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
index 984792322ce5d..f203ec1e89b35 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
@@ -17,18 +17,17 @@ using namespace clang::ast_matchers;
 namespace clang::tidy::readability {
 
 void UseStdMinMaxCheck::registerMatchers(MatchFinder *Finder) {
-   Finder->addMatcher(
-      ifStmt(has(binaryOperator(
-                 anyOf(hasOperatorName("<"), hasOperatorName(">"),hasOperatorName("<="), hasOperatorName(">=")),
-                 hasLHS(expr().bind("lhsVar1")),
-                 hasRHS(expr().bind("rhsVar1")))),
-             hasThen(stmt(binaryOperator(
-                 hasOperatorName("="),
-                 hasLHS(expr().bind("lhsVar2")),
-                 hasRHS(expr().bind("rhsVar2"))))))
+  Finder->addMatcher(
+      ifStmt(
+          has(binaryOperator(
+              anyOf(hasOperatorName("<"), hasOperatorName(">"),
+                    hasOperatorName("<="), hasOperatorName(">=")),
+              hasLHS(expr().bind("lhsVar1")), hasRHS(expr().bind("rhsVar1")))),
+          hasThen(stmt(binaryOperator(hasOperatorName("="),
+                                      hasLHS(expr().bind("lhsVar2")),
+                                      hasRHS(expr().bind("rhsVar2"))))))
           .bind("ifStmt"),
       this);
-
 }
 
 void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
@@ -48,56 +47,51 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
 
   SourceLocation ifLocation = ifStmt->getIfLoc();
   SourceLocation thenLocation = ifStmt->getEndLoc();
-  auto lhsVar1Str = Lexer::getSourceText(CharSourceRange::getTokenRange(lhsVar1->getSourceRange()),
-                                       Context.getSourceManager(), Context.getLangOpts());
+  auto lhsVar1Str = Lexer::getSourceText(
+      CharSourceRange::getTokenRange(lhsVar1->getSourceRange()),
+      Context.getSourceManager(), Context.getLangOpts());
 
-  auto lhsVar2Str = Lexer::getSourceText(CharSourceRange::getTokenRange(lhsVar2->getSourceRange()),
-                                       Context.getSourceManager(), Context.getLangOpts());
+  auto lhsVar2Str = Lexer::getSourceText(
+      CharSourceRange::getTokenRange(lhsVar2->getSourceRange()),
+      Context.getSourceManager(), Context.getLangOpts());
 
-  auto rhsVar1Str = Lexer::getSourceText(CharSourceRange::getTokenRange(rhsVar1->getSourceRange()),
-                                       Context.getSourceManager(), Context.getLangOpts());
+  auto rhsVar1Str = Lexer::getSourceText(
+      CharSourceRange::getTokenRange(rhsVar1->getSourceRange()),
+      Context.getSourceManager(), Context.getLangOpts());
 
-  auto rhsVar2Str = Lexer::getSourceText(CharSourceRange::getTokenRange(rhsVar2->getSourceRange()),
-                                       Context.getSourceManager(), Context.getLangOpts());
+  auto rhsVar2Str = Lexer::getSourceText(
+      CharSourceRange::getTokenRange(rhsVar2->getSourceRange()),
+      Context.getSourceManager(), Context.getLangOpts());
 
   if (binaryOp->getOpcode() == BO_LT) {
-    if (lhsVar1Str == lhsVar2Str &&
-        rhsVar1Str == rhsVar2Str) {
+    if (lhsVar1Str == lhsVar2Str && rhsVar1Str == rhsVar2Str) {
       diag(ifStmt->getIfLoc(), "use `std::max` instead of `<`")
-          << FixItHint::CreateReplacement(
-                 SourceRange(ifLocation, thenLocation),
-                 lhsVar2Str.str() + " = std::max(" +
-                     lhsVar1Str.str() + ", " +
-                     rhsVar1Str.str() + ")");
-    } else if (lhsVar1Str == rhsVar2Str &&
-               rhsVar1Str == lhsVar2Str) {
+          << FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
+                                          lhsVar2Str.str() + " = std::max(" +
+                                              lhsVar1Str.str() + ", " +
+                                              rhsVar1Str.str() + ")");
+    } else if (lhsVar1Str == rhsVar2Str && rhsVar1Str == lhsVar2Str) {
       diag(ifStmt->getIfLoc(), "use `std::min` instead of `<`")
-          << FixItHint::CreateReplacement(
-                 SourceRange(ifLocation, thenLocation),
-                 lhsVar2Str.str() + " = std::min(" +
-                     lhsVar1Str.str() + ", " +
-                     rhsVar1Str.str() + ")");
+          << FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
+                                          lhsVar2Str.str() + " = std::min(" +
+                                              lhsVar1Str.str() + ", " +
+                                              rhsVar1Str.str() + ")");
     }
   } else if (binaryOp->getOpcode() == BO_GT) {
-    if (lhsVar1Str == lhsVar2Str &&
-        rhsVar1Str == rhsVar2Str) {
+    if (lhsVar1Str == lhsVar2Str && rhsVar1Str == rhsVar2Str) {
       diag(ifStmt->getIfLoc(), "use `std::min` instead of `>`")
-          << FixItHint::CreateReplacement(
-                 SourceRange(ifLocation, thenLocation),
-                 lhsVar2Str.str() + " = std::min(" +
-                     lhsVar1Str.str() + ", " +
-                     rhsVar1Str.str() + ")");
-    } else if (lhsVar1Str == rhsVar2Str &&
-               rhsVar1Str == lhsVar2Str) {
+          << FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
+                                          lhsVar2Str.str() + " = std::min(" +
+                                              lhsVar1Str.str() + ", " +
+                                              rhsVar1Str.str() + ")");
+    } else if (lhsVar1Str == rhsVar2Str && rhsVar1Str == lhsVar2Str) {
       diag(ifStmt->getIfLoc(), "use `std::max` instead of `>`")
-          << FixItHint::CreateReplacement(
-                 SourceRange(ifLocation, thenLocation),
-                 lhsVar2Str.str() + " = std::max(" +
-                     lhsVar1Str.str() + ", " +
-                     rhsVar1Str.str() + ")");
+          << FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
+                                          lhsVar2Str.str() + " = std::max(" +
+                                              lhsVar1Str.str() + ", " +
+                                              rhsVar1Str.str() + ")");
     }
   }
-  
 }
 
 } // namespace clang::tidy::readability

>From f73e9f019a03f5f864e952ddbad288d9a11b801e Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Fri, 12 Jan 2024 17:27:10 +0530
Subject: [PATCH 09/46] Added Release Notes

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 clang-tools-extra/docs/ReleaseNotes.rst | 4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)

diff --git a/clang-tools-extra/docs/ReleaseNotes.rst b/clang-tools-extra/docs/ReleaseNotes.rst
index 2d3a2c2981e6c..314e0eb69f793 100644
--- a/clang-tools-extra/docs/ReleaseNotes.rst
+++ b/clang-tools-extra/docs/ReleaseNotes.rst
@@ -227,7 +227,9 @@ New checks
 - New :doc:`readability-use-std-min-max
   <clang-tidy/checks/readability/use-std-min-max>` check.
 
-  FIXME: add release notes.
+  Replaces certain conditional statements with equivalent ``std::min`` or
+  ``std::max`` expressions, improving readability and promoting the use of
+  standard library functions.
 
 - New :doc:`readability-reference-to-constructed-temporary
   <clang-tidy/checks/readability/reference-to-constructed-temporary>` check.

>From faf3312b6d6713cb9af43ae09ca66f3ac05878bf Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Fri, 12 Jan 2024 17:31:38 +0530
Subject: [PATCH 10/46] corrected file name

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../checks/readability/{UseStdMinMax.rst => use-std-min-max.rst}  | 0
 1 file changed, 0 insertions(+), 0 deletions(-)
 rename clang-tools-extra/docs/clang-tidy/checks/readability/{UseStdMinMax.rst => use-std-min-max.rst} (100%)

diff --git a/clang-tools-extra/docs/clang-tidy/checks/readability/UseStdMinMax.rst b/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst
similarity index 100%
rename from clang-tools-extra/docs/clang-tidy/checks/readability/UseStdMinMax.rst
rename to clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst

>From 5ed9896cffdbf057b4e8088a37c98a50e0e4d946 Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Fri, 12 Jan 2024 17:35:44 +0530
Subject: [PATCH 11/46] corrected title length in docs

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../docs/clang-tidy/checks/readability/use-std-min-max.rst      | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst b/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst
index c8b9bdc7c5ea3..573beeeb2a842 100644
--- a/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst
+++ b/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst
@@ -1,7 +1,7 @@
 .. title:: clang-tidy - readability-use-std-min-max
 
 readability-use-std-min-max
-========================
+===========================
 
 Replaces certain conditional statements with equivalent ``std::min`` or ``std::max`` expressions, 
 improving readability and promoting the use of standard library functions.

>From 19c4b63da4a183f661a6e06fabc78aaf4e2868e4 Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Fri, 12 Jan 2024 21:54:46 +0530
Subject: [PATCH 12/46] Suggested Changes

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../readability/UseStdMinMaxCheck.cpp         |  2 +-
 .../checks/readability/use-std-min-max.rst    | 22 +++++++++----------
 .../checkers/readability/use-std-min-max.cpp  |  1 -
 3 files changed, 11 insertions(+), 14 deletions(-)

diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
index f203ec1e89b35..1a4392523cf18 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
@@ -41,7 +41,7 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
   if (!lhsVar1 || !rhsVar1 || !lhsVar2 || !rhsVar2 || !ifStmt)
     return;
 
-  const BinaryOperator *binaryOp = dyn_cast<BinaryOperator>(ifStmt->getCond());
+  const auto *binaryOp = dyn_cast<BinaryOperator>(ifStmt->getCond());
   if (!binaryOp)
     return;
 
diff --git a/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst b/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst
index 573beeeb2a842..2364acacbaffd 100644
--- a/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst
+++ b/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst
@@ -5,10 +5,8 @@ readability-use-std-min-max
 
 Replaces certain conditional statements with equivalent ``std::min`` or ``std::max`` expressions, 
 improving readability and promoting the use of standard library functions.
-Note: While this transformation improves code clarity, it may not be
-suitable for performance-critical code. Using ``std::min`` or ``std::max`` can
-introduce additional stores, potentially impacting performance compared to
-the original if statement that only assigns when the value needs to change.
+Note: this transformation may impact performance in performance-critical code due to potential 
+additional stores compared to the original if statement.
 
 Examples:
 
@@ -16,18 +14,18 @@ Before:
 
 .. code-block:: c++
 
-  void foo(){
-    int a,b;
-    if(a < b)
-        a = b;
-    }
+  void foo() {
+  int a, b;
+  if (a < b)
+    a = b;
+  }
 
 
 After:
 
 .. code-block:: c++
 
-  void foo(){
-    a = std::max(a, b);
-
+  void foo() {
+  int a, b;
+  a = std::max(a, b);
   }
diff --git a/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp b/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
index 37ee1fd65fb91..b65e3a9b27cc2 100644
--- a/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
+++ b/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
@@ -31,5 +31,4 @@ void foo() {
   // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::min` instead of `<` [readability-use-std-min-max]
   if(value1+value2<value3)
     value3 = value1+value2; // CHECK-FIXES: value3 = std::min(value1+value2, value3);
-  
 }
\ No newline at end of file

>From 8167787453886874b8e458f040c878ad7e711016 Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Fri, 12 Jan 2024 22:35:17 +0530
Subject: [PATCH 13/46] body indentation

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../clang-tidy/checks/readability/use-std-min-max.rst  | 10 +++++-----
 1 file changed, 5 insertions(+), 5 deletions(-)

diff --git a/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst b/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst
index 2364acacbaffd..de22f069d2192 100644
--- a/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst
+++ b/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst
@@ -15,9 +15,9 @@ Before:
 .. code-block:: c++
 
   void foo() {
-  int a, b;
-  if (a < b)
-    a = b;
+    int a, b;
+    if (a < b)
+      a = b;
   }
 
 
@@ -26,6 +26,6 @@ After:
 .. code-block:: c++
 
   void foo() {
-  int a, b;
-  a = std::max(a, b);
+    int a, b;
+    a = std::max(a, b);
   }

>From 3a28399a08b4625abe7d08dee82fbee850de534e Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Sat, 13 Jan 2024 21:17:23 +0530
Subject: [PATCH 14/46] added intialisation,constexpr tests

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../checks/readability/use-std-min-max.rst    |  4 ++--
 .../checkers/readability/use-std-min-max.cpp  | 23 +++++++++++++++++++
 2 files changed, 25 insertions(+), 2 deletions(-)

diff --git a/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst b/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst
index de22f069d2192..0d621d4d4477f 100644
--- a/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst
+++ b/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst
@@ -15,7 +15,7 @@ Before:
 .. code-block:: c++
 
   void foo() {
-    int a, b;
+    int a = 2, b = 3;
     if (a < b)
       a = b;
   }
@@ -26,6 +26,6 @@ After:
 .. code-block:: c++
 
   void foo() {
-    int a, b;
+    int a = 2, b = 3;
     a = std::max(a, b);
   }
diff --git a/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp b/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
index b65e3a9b27cc2..1dc48ffc63cfb 100644
--- a/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
+++ b/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
@@ -1,5 +1,16 @@
 // RUN: %check_clang_tidy %s readability-use-std-min-max %t
 
+constexpr int myConstexprMin(int a, int b) {
+  return a < b ? a : b;
+}
+
+constexpr int myConstexprMax(int a, int b) {
+  return a > b ? a : b;
+}
+
+int bar(int x, int y) {
+  return x < y ? x : y;
+}
 void foo() {
   int value1,value2,value3;
   short value4;
@@ -31,4 +42,16 @@ void foo() {
   // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::min` instead of `<` [readability-use-std-min-max]
   if(value1+value2<value3)
     value3 = value1+value2; // CHECK-FIXES: value3 = std::min(value1+value2, value3);
+  
+  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
+  if (value1 < myConstexprMin(value2, value3))
+    value1 = myConstexprMin(value2, value3); // CHECK-FIXES: value1 = std::max(value1, myConstexprMin(value2, value3));
+  
+  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::min` instead of `>` [readability-use-std-min-max]
+  if (value1 > myConstexprMax(value2, value3))
+    value1 = myConstexprMax(value2, value3); // CHECK-FIXES: value1 = std::min(value1, myConstexprMax(value2, value3));
+  
+  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
+  if (value1 < bar(value2, value3))
+    value1 = bar(value2, value3); // CHECK-FIXES: value1 = std::max(value1, bar(value2, value3));
 }
\ No newline at end of file

>From 2ecd08a149d60b9dfdc54d777bf10b34758054a8 Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Sat, 13 Jan 2024 21:32:22 +0530
Subject: [PATCH 15/46] small fixes

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../clang-tidy/checks/readability/use-std-min-max.rst    | 9 +++++----
 .../clang-tidy/checkers/readability/use-std-min-max.cpp  | 1 +
 2 files changed, 6 insertions(+), 4 deletions(-)

diff --git a/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst b/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst
index 0d621d4d4477f..7e64a05ccd8b8 100644
--- a/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst
+++ b/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst
@@ -3,10 +3,11 @@
 readability-use-std-min-max
 ===========================
 
-Replaces certain conditional statements with equivalent ``std::min`` or ``std::max`` expressions, 
-improving readability and promoting the use of standard library functions.
-Note: this transformation may impact performance in performance-critical code due to potential 
-additional stores compared to the original if statement.
+Replaces certain conditionals with ``std::min`` or ``std::max`` for readability,
+promoting use of standard library functions. Note: This may impact
+performance in critical code due to potential additional stores compared
+to the original if statement.
+
 
 Examples:
 
diff --git a/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp b/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
index 1dc48ffc63cfb..9525d5e1f2489 100644
--- a/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
+++ b/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
@@ -11,6 +11,7 @@ constexpr int myConstexprMax(int a, int b) {
 int bar(int x, int y) {
   return x < y ? x : y;
 }
+
 void foo() {
   int value1,value2,value3;
   short value4;

>From 00d4080a6a1f4af2b79b748ff60527aae10c9f97 Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Mon, 15 Jan 2024 21:12:17 +0530
Subject: [PATCH 16/46] Addded Suggested Changes

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../readability/UseStdMinMaxCheck.cpp         | 50 +++++++--------
 .../readability/UseStdMinMaxCheck.h           |  2 +-
 .../checkers/readability/use-std-min-max.cpp  | 63 +++++++++++++++++++
 3 files changed, 88 insertions(+), 27 deletions(-)

diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
index 1a4392523cf18..833d27d4957b3 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
@@ -8,6 +8,7 @@
 
 #include "UseStdMinMaxCheck.h"
 #include "clang/AST/ASTContext.h"
+#include "../utils/ASTUtils.h"
 #include "clang/ASTMatchers/ASTMatchFinder.h"
 #include "clang/Lex/Preprocessor.h"
 #include <optional>
@@ -47,6 +48,7 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
 
   SourceLocation ifLocation = ifStmt->getIfLoc();
   SourceLocation thenLocation = ifStmt->getEndLoc();
+
   auto lhsVar1Str = Lexer::getSourceText(
       CharSourceRange::getTokenRange(lhsVar1->getSourceRange()),
       Context.getSourceManager(), Context.getLangOpts());
@@ -58,38 +60,34 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
   auto rhsVar1Str = Lexer::getSourceText(
       CharSourceRange::getTokenRange(rhsVar1->getSourceRange()),
       Context.getSourceManager(), Context.getLangOpts());
+  
+  auto replacementMax = lhsVar2Str.str() + " = std::max(" + lhsVar1Str.str() + ", " + rhsVar1Str.str() + ")";
+  auto replacementMin = lhsVar2Str.str() + " = std::min(" + lhsVar1Str.str() + ", " + rhsVar1Str.str() + ")";
+  auto *operatorStr = binaryOp->getOpcodeStr().data();
 
-  auto rhsVar2Str = Lexer::getSourceText(
-      CharSourceRange::getTokenRange(rhsVar2->getSourceRange()),
-      Context.getSourceManager(), Context.getLangOpts());
-
-  if (binaryOp->getOpcode() == BO_LT) {
-    if (lhsVar1Str == lhsVar2Str && rhsVar1Str == rhsVar2Str) {
-      diag(ifStmt->getIfLoc(), "use `std::max` instead of `<`")
+  if (binaryOp->getOpcode() == BO_LT || binaryOp->getOpcode() == BO_LE) {
+    if (tidy::utils::areStatementsIdentical(lhsVar1, lhsVar2,Context) &&
+        tidy::utils::areStatementsIdentical(rhsVar1, rhsVar2,Context)) {
+      diag(ifStmt->getIfLoc(), "use `std::max` instead of `%0`")<< operatorStr
           << FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
-                                          lhsVar2Str.str() + " = std::max(" +
-                                              lhsVar1Str.str() + ", " +
-                                              rhsVar1Str.str() + ")");
-    } else if (lhsVar1Str == rhsVar2Str && rhsVar1Str == lhsVar2Str) {
-      diag(ifStmt->getIfLoc(), "use `std::min` instead of `<`")
+                                    std::move(replacementMax));
+    } else if (tidy::utils::areStatementsIdentical(lhsVar1, rhsVar2,Context) &&
+               tidy::utils::areStatementsIdentical(rhsVar1, lhsVar2,Context)) {
+      diag(ifStmt->getIfLoc(), "use `std::min` instead of `%0`")<< operatorStr
           << FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
-                                          lhsVar2Str.str() + " = std::min(" +
-                                              lhsVar1Str.str() + ", " +
-                                              rhsVar1Str.str() + ")");
+                                    std::move(replacementMin));
     }
-  } else if (binaryOp->getOpcode() == BO_GT) {
-    if (lhsVar1Str == lhsVar2Str && rhsVar1Str == rhsVar2Str) {
-      diag(ifStmt->getIfLoc(), "use `std::min` instead of `>`")
+  } else if (binaryOp->getOpcode() == BO_GT || binaryOp->getOpcode() == BO_GE) {
+    if (tidy::utils::areStatementsIdentical(lhsVar1, lhsVar2,Context) &&
+        tidy::utils::areStatementsIdentical(rhsVar1, rhsVar2,Context)) {
+      diag(ifStmt->getIfLoc(), "use `std::min` instead of `%0`")<< operatorStr
           << FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
-                                          lhsVar2Str.str() + " = std::min(" +
-                                              lhsVar1Str.str() + ", " +
-                                              rhsVar1Str.str() + ")");
-    } else if (lhsVar1Str == rhsVar2Str && rhsVar1Str == lhsVar2Str) {
-      diag(ifStmt->getIfLoc(), "use `std::max` instead of `>`")
+                                    std::move(replacementMin));
+    } else if (tidy::utils::areStatementsIdentical(lhsVar1, rhsVar2,Context) &&
+               tidy::utils::areStatementsIdentical(rhsVar1, lhsVar2,Context)) {
+      diag(ifStmt->getIfLoc(), "use `std::max` instead of `%0`")<< operatorStr
           << FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
-                                          lhsVar2Str.str() + " = std::max(" +
-                                              lhsVar1Str.str() + ", " +
-                                              rhsVar1Str.str() + ")");
+                                    std::move(replacementMax));
     }
   }
 }
diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.h b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.h
index 476b19ba5c9cf..d6f4fdf40ea30 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.h
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.h
@@ -13,7 +13,7 @@
 
 namespace clang::tidy::readability {
 
-/// replaces certain conditional statements with equivalent ``std::min`` or
+/// Replaces certain conditional statements with equivalent ``std::min`` or
 /// ``std::max`` expressions, improving readability and promoting the use of
 /// standard library functions.
 ///
diff --git a/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp b/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
index 9525d5e1f2489..99be29fb163bb 100644
--- a/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
+++ b/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
@@ -12,9 +12,16 @@ int bar(int x, int y) {
   return x < y ? x : y;
 }
 
+class MyClass {
+public:
+  int member1;
+  int member2;
+};
+
 void foo() {
   int value1,value2,value3;
   short value4;
+  MyClass obj;
 
   // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
   if (value1 < value2)
@@ -55,4 +62,60 @@ void foo() {
   // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
   if (value1 < bar(value2, value3))
     value1 = bar(value2, value3); // CHECK-FIXES: value1 = std::max(value1, bar(value2, value3));
+  
+  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::min` instead of `<=` [readability-use-std-min-max]
+  if (value1 <= value2)
+    value2 = value1; // CHECK-FIXES: value2 = std::min(value1, value2);
+
+  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::max` instead of `<=` [readability-use-std-min-max]
+  if (value1 <= value2)
+    value1 = value2; // CHECK-FIXES: value1 = std::max(value1, value2);
+
+  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::max` instead of `>=` [readability-use-std-min-max]
+  if (value2 >= value1)
+    value1 = value2; // CHECK-FIXES: value1 = std::max(value2, value1);
+
+  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::min` instead of `>=` [readability-use-std-min-max]
+  if (value2 >= value1)
+    value2 = value1; // CHECK-FIXES: value2 = std::min(value2, value1);
+  
+  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
+  if (obj.member1 < obj.member2)
+    obj.member1 = obj.member2; // CHECK-FIXES: obj.member1 = std::max(obj.member1, obj.member2);
+
+  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::min` instead of `<` [readability-use-std-min-max]
+  if (obj.member1 < obj.member2)
+    obj.member2 = obj.member1; // CHECK-FIXES: obj.member2 = std::min(obj.member1, obj.member2);
+
+  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::min` instead of `>` [readability-use-std-min-max]
+  if (obj.member2 > obj.member1)
+    obj.member2 = obj.member1; // CHECK-FIXES: obj.member2 = std::min(obj.member2, obj.member1);
+
+  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::max` instead of `>` [readability-use-std-min-max]
+  if (obj.member2 > obj.member1)
+    obj.member1 = obj.member2; // CHECK-FIXES: obj.member1 = std::max(obj.member2, obj.member1);
+  
+  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
+  if (obj.member1 < value4)
+    obj.member1 = value4; // CHECK-FIXES: obj.member1 = std::max(obj.member1, value4);
+  
+  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::min` instead of `<` [readability-use-std-min-max]
+  if (obj.member1 + value2 < value3)
+    value3 = obj.member1 + value2; // CHECK-FIXES: value3 = std::min(obj.member1 + value2, value3);
+  
+  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::min` instead of `<=` [readability-use-std-min-max]
+  if (value1 <= obj.member2)
+    obj.member2 = value1; // CHECK-FIXES: obj.member2 = std::min(value1, obj.member2);
+
+  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::max` instead of `<=` [readability-use-std-min-max]
+  if (value1 <= obj.member2)
+    value1 = obj.member2; // CHECK-FIXES: value1 = std::max(value1, obj.member2);
+
+  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::max` instead of `>=` [readability-use-std-min-max]
+  if (obj.member2 >= value1)
+    value1 = obj.member2; // CHECK-FIXES: value1 = std::max(obj.member2, value1);
+
+  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::min` instead of `>=` [readability-use-std-min-max]
+  if (obj.member2 >= value1)
+    obj.member2 = value1; // CHECK-FIXES: obj.member2 = std::min(obj.member2, value1);
 }
\ No newline at end of file

>From 6db08204966b52862ecdcf5ff829fe06e266b882 Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Mon, 15 Jan 2024 21:12:41 +0530
Subject: [PATCH 17/46] formatted the code

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../readability/UseStdMinMaxCheck.cpp         | 46 +++++++++++--------
 1 file changed, 26 insertions(+), 20 deletions(-)

diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
index 833d27d4957b3..2f7a8d944a504 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
@@ -7,8 +7,8 @@
 //===----------------------------------------------------------------------===//
 
 #include "UseStdMinMaxCheck.h"
-#include "clang/AST/ASTContext.h"
 #include "../utils/ASTUtils.h"
+#include "clang/AST/ASTContext.h"
 #include "clang/ASTMatchers/ASTMatchFinder.h"
 #include "clang/Lex/Preprocessor.h"
 #include <optional>
@@ -60,34 +60,40 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
   auto rhsVar1Str = Lexer::getSourceText(
       CharSourceRange::getTokenRange(rhsVar1->getSourceRange()),
       Context.getSourceManager(), Context.getLangOpts());
-  
-  auto replacementMax = lhsVar2Str.str() + " = std::max(" + lhsVar1Str.str() + ", " + rhsVar1Str.str() + ")";
-  auto replacementMin = lhsVar2Str.str() + " = std::min(" + lhsVar1Str.str() + ", " + rhsVar1Str.str() + ")";
+
+  auto replacementMax = lhsVar2Str.str() + " = std::max(" + lhsVar1Str.str() +
+                        ", " + rhsVar1Str.str() + ")";
+  auto replacementMin = lhsVar2Str.str() + " = std::min(" + lhsVar1Str.str() +
+                        ", " + rhsVar1Str.str() + ")";
   auto *operatorStr = binaryOp->getOpcodeStr().data();
 
   if (binaryOp->getOpcode() == BO_LT || binaryOp->getOpcode() == BO_LE) {
-    if (tidy::utils::areStatementsIdentical(lhsVar1, lhsVar2,Context) &&
-        tidy::utils::areStatementsIdentical(rhsVar1, rhsVar2,Context)) {
-      diag(ifStmt->getIfLoc(), "use `std::max` instead of `%0`")<< operatorStr
+    if (tidy::utils::areStatementsIdentical(lhsVar1, lhsVar2, Context) &&
+        tidy::utils::areStatementsIdentical(rhsVar1, rhsVar2, Context)) {
+      diag(ifStmt->getIfLoc(), "use `std::max` instead of `%0`")
+          << operatorStr
           << FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
-                                    std::move(replacementMax));
-    } else if (tidy::utils::areStatementsIdentical(lhsVar1, rhsVar2,Context) &&
-               tidy::utils::areStatementsIdentical(rhsVar1, lhsVar2,Context)) {
-      diag(ifStmt->getIfLoc(), "use `std::min` instead of `%0`")<< operatorStr
+                                          std::move(replacementMax));
+    } else if (tidy::utils::areStatementsIdentical(lhsVar1, rhsVar2, Context) &&
+               tidy::utils::areStatementsIdentical(rhsVar1, lhsVar2, Context)) {
+      diag(ifStmt->getIfLoc(), "use `std::min` instead of `%0`")
+          << operatorStr
           << FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
-                                    std::move(replacementMin));
+                                          std::move(replacementMin));
     }
   } else if (binaryOp->getOpcode() == BO_GT || binaryOp->getOpcode() == BO_GE) {
-    if (tidy::utils::areStatementsIdentical(lhsVar1, lhsVar2,Context) &&
-        tidy::utils::areStatementsIdentical(rhsVar1, rhsVar2,Context)) {
-      diag(ifStmt->getIfLoc(), "use `std::min` instead of `%0`")<< operatorStr
+    if (tidy::utils::areStatementsIdentical(lhsVar1, lhsVar2, Context) &&
+        tidy::utils::areStatementsIdentical(rhsVar1, rhsVar2, Context)) {
+      diag(ifStmt->getIfLoc(), "use `std::min` instead of `%0`")
+          << operatorStr
           << FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
-                                    std::move(replacementMin));
-    } else if (tidy::utils::areStatementsIdentical(lhsVar1, rhsVar2,Context) &&
-               tidy::utils::areStatementsIdentical(rhsVar1, lhsVar2,Context)) {
-      diag(ifStmt->getIfLoc(), "use `std::max` instead of `%0`")<< operatorStr
+                                          std::move(replacementMin));
+    } else if (tidy::utils::areStatementsIdentical(lhsVar1, rhsVar2, Context) &&
+               tidy::utils::areStatementsIdentical(rhsVar1, lhsVar2, Context)) {
+      diag(ifStmt->getIfLoc(), "use `std::max` instead of `%0`")
+          << operatorStr
           << FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
-                                    std::move(replacementMax));
+                                          std::move(replacementMax));
     }
   }
 }

>From 5073650de12a6588cd171bccfc67f6298065f82e Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Tue, 16 Jan 2024 03:38:20 +0530
Subject: [PATCH 18/46] Added Include Check

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../readability/UseStdMinMaxCheck.cpp         | 26 ++++++++++++++++---
 .../readability/UseStdMinMaxCheck.h           | 11 +++++---
 2 files changed, 30 insertions(+), 7 deletions(-)

diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
index 2f7a8d944a504..b7f9f65c71ad6 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
@@ -17,6 +17,16 @@ using namespace clang::ast_matchers;
 
 namespace clang::tidy::readability {
 
+UseStdMinMaxCheck::UseStdMinMaxCheck(StringRef Name, ClangTidyContext *Context)
+    : ClangTidyCheck(Name, Context),
+      IncludeInserter(Options.getLocalOrGlobal("IncludeStyle",
+                                               utils::IncludeSorter::IS_LLVM),
+                      areDiagsSelfContained()),AlgotithmHeader(Options.get("AlgorithmHeader","<algorithm>")) {}
+
+void UseStdMinMaxCheck::storeOptions(ClangTidyOptions::OptionMap &Opts) {
+  Options.store(Opts, "IncludeStyle", IncludeInserter.getStyle());
+}
+
 void UseStdMinMaxCheck::registerMatchers(MatchFinder *Finder) {
   Finder->addMatcher(
       ifStmt(
@@ -31,6 +41,12 @@ void UseStdMinMaxCheck::registerMatchers(MatchFinder *Finder) {
       this);
 }
 
+void UseStdMinMaxCheck::registerPPCallbacks(const SourceManager &SM,
+                                            Preprocessor *PP,
+                                            Preprocessor *ModuleExpanderPP) {
+  IncludeInserter.registerPreprocessor(PP);
+}
+
 void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
   const auto *lhsVar1 = Result.Nodes.getNodeAs<Expr>("lhsVar1");
   const auto *rhsVar1 = Result.Nodes.getNodeAs<Expr>("rhsVar1");
@@ -38,6 +54,7 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
   const auto *rhsVar2 = Result.Nodes.getNodeAs<Expr>("rhsVar2");
   const auto *ifStmt = Result.Nodes.getNodeAs<IfStmt>("ifStmt");
   auto &Context = *Result.Context;
+  const SourceManager &Source = Context.getSourceManager();
 
   if (!lhsVar1 || !rhsVar1 || !lhsVar2 || !rhsVar2 || !ifStmt)
     return;
@@ -70,16 +87,17 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
   if (binaryOp->getOpcode() == BO_LT || binaryOp->getOpcode() == BO_LE) {
     if (tidy::utils::areStatementsIdentical(lhsVar1, lhsVar2, Context) &&
         tidy::utils::areStatementsIdentical(rhsVar1, rhsVar2, Context)) {
+          
       diag(ifStmt->getIfLoc(), "use `std::max` instead of `%0`")
           << operatorStr
           << FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
-                                          std::move(replacementMax));
+                                          std::move(replacementMax))<<IncludeInserter.createIncludeInsertion(Source.getFileID(ifStmt->getBeginLoc()), AlgotithmHeader);
     } else if (tidy::utils::areStatementsIdentical(lhsVar1, rhsVar2, Context) &&
                tidy::utils::areStatementsIdentical(rhsVar1, lhsVar2, Context)) {
       diag(ifStmt->getIfLoc(), "use `std::min` instead of `%0`")
           << operatorStr
           << FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
-                                          std::move(replacementMin));
+                                          std::move(replacementMin))<<IncludeInserter.createIncludeInsertion(Source.getFileID(ifStmt->getBeginLoc()), AlgotithmHeader);
     }
   } else if (binaryOp->getOpcode() == BO_GT || binaryOp->getOpcode() == BO_GE) {
     if (tidy::utils::areStatementsIdentical(lhsVar1, lhsVar2, Context) &&
@@ -87,13 +105,13 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
       diag(ifStmt->getIfLoc(), "use `std::min` instead of `%0`")
           << operatorStr
           << FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
-                                          std::move(replacementMin));
+                                          std::move(replacementMin))<<IncludeInserter.createIncludeInsertion(Source.getFileID(ifStmt->getBeginLoc()), AlgotithmHeader);
     } else if (tidy::utils::areStatementsIdentical(lhsVar1, rhsVar2, Context) &&
                tidy::utils::areStatementsIdentical(rhsVar1, lhsVar2, Context)) {
       diag(ifStmt->getIfLoc(), "use `std::max` instead of `%0`")
           << operatorStr
           << FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
-                                          std::move(replacementMax));
+                                          std::move(replacementMax))<<IncludeInserter.createIncludeInsertion(Source.getFileID(ifStmt->getBeginLoc()), AlgotithmHeader);
     }
   }
 }
diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.h b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.h
index d6f4fdf40ea30..c92e80a351e1b 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.h
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.h
@@ -10,7 +10,7 @@
 #define LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_READABILITY_USESTDMINMAXCHECK_H
 
 #include "../ClangTidyCheck.h"
-
+#include "../utils/IncludeInserter.h"
 namespace clang::tidy::readability {
 
 /// Replaces certain conditional statements with equivalent ``std::min`` or
@@ -21,16 +21,21 @@ namespace clang::tidy::readability {
 /// http://clang.llvm.org/extra/clang-tidy/checks/readability/UseStdMinMax.html
 class UseStdMinMaxCheck : public ClangTidyCheck {
 public:
-  UseStdMinMaxCheck(StringRef Name, ClangTidyContext *Context)
-      : ClangTidyCheck(Name, Context) {}
+  UseStdMinMaxCheck(StringRef Name, ClangTidyContext *Context);
   bool isLanguageVersionSupported(const LangOptions &LangOpts) const override {
     return LangOpts.CPlusPlus;
   }
+  void registerPPCallbacks(const SourceManager &SM, Preprocessor *PP,
+                           Preprocessor *ModuleExpanderPP) override;
+  void storeOptions(ClangTidyOptions::OptionMap &Opts) override;
   void registerMatchers(ast_matchers::MatchFinder *Finder) override;
   void check(const ast_matchers::MatchFinder::MatchResult &Result) override;
   std::optional<TraversalKind> getCheckTraversalKind() const override {
     return TK_IgnoreUnlessSpelledInSource;
   }
+  private:
+  utils::IncludeInserter IncludeInserter;
+  StringRef AlgotithmHeader;
 };
 
 } // namespace clang::tidy::readability

>From c728a39c8a11fc17130a49c6d472fff2133ce6dc Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Tue, 16 Jan 2024 03:38:52 +0530
Subject: [PATCH 19/46] Formatted the code

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../readability/UseStdMinMaxCheck.cpp         | 21 +++++++++++++------
 .../readability/UseStdMinMaxCheck.h           |  3 ++-
 2 files changed, 17 insertions(+), 7 deletions(-)

diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
index b7f9f65c71ad6..15e26f9baf68b 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
@@ -21,7 +21,8 @@ UseStdMinMaxCheck::UseStdMinMaxCheck(StringRef Name, ClangTidyContext *Context)
     : ClangTidyCheck(Name, Context),
       IncludeInserter(Options.getLocalOrGlobal("IncludeStyle",
                                                utils::IncludeSorter::IS_LLVM),
-                      areDiagsSelfContained()),AlgotithmHeader(Options.get("AlgorithmHeader","<algorithm>")) {}
+                      areDiagsSelfContained()),
+      AlgotithmHeader(Options.get("AlgorithmHeader", "<algorithm>")) {}
 
 void UseStdMinMaxCheck::storeOptions(ClangTidyOptions::OptionMap &Opts) {
   Options.store(Opts, "IncludeStyle", IncludeInserter.getStyle());
@@ -87,17 +88,21 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
   if (binaryOp->getOpcode() == BO_LT || binaryOp->getOpcode() == BO_LE) {
     if (tidy::utils::areStatementsIdentical(lhsVar1, lhsVar2, Context) &&
         tidy::utils::areStatementsIdentical(rhsVar1, rhsVar2, Context)) {
-          
+
       diag(ifStmt->getIfLoc(), "use `std::max` instead of `%0`")
           << operatorStr
           << FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
-                                          std::move(replacementMax))<<IncludeInserter.createIncludeInsertion(Source.getFileID(ifStmt->getBeginLoc()), AlgotithmHeader);
+                                          std::move(replacementMax))
+          << IncludeInserter.createIncludeInsertion(
+                 Source.getFileID(ifStmt->getBeginLoc()), AlgotithmHeader);
     } else if (tidy::utils::areStatementsIdentical(lhsVar1, rhsVar2, Context) &&
                tidy::utils::areStatementsIdentical(rhsVar1, lhsVar2, Context)) {
       diag(ifStmt->getIfLoc(), "use `std::min` instead of `%0`")
           << operatorStr
           << FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
-                                          std::move(replacementMin))<<IncludeInserter.createIncludeInsertion(Source.getFileID(ifStmt->getBeginLoc()), AlgotithmHeader);
+                                          std::move(replacementMin))
+          << IncludeInserter.createIncludeInsertion(
+                 Source.getFileID(ifStmt->getBeginLoc()), AlgotithmHeader);
     }
   } else if (binaryOp->getOpcode() == BO_GT || binaryOp->getOpcode() == BO_GE) {
     if (tidy::utils::areStatementsIdentical(lhsVar1, lhsVar2, Context) &&
@@ -105,13 +110,17 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
       diag(ifStmt->getIfLoc(), "use `std::min` instead of `%0`")
           << operatorStr
           << FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
-                                          std::move(replacementMin))<<IncludeInserter.createIncludeInsertion(Source.getFileID(ifStmt->getBeginLoc()), AlgotithmHeader);
+                                          std::move(replacementMin))
+          << IncludeInserter.createIncludeInsertion(
+                 Source.getFileID(ifStmt->getBeginLoc()), AlgotithmHeader);
     } else if (tidy::utils::areStatementsIdentical(lhsVar1, rhsVar2, Context) &&
                tidy::utils::areStatementsIdentical(rhsVar1, lhsVar2, Context)) {
       diag(ifStmt->getIfLoc(), "use `std::max` instead of `%0`")
           << operatorStr
           << FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
-                                          std::move(replacementMax))<<IncludeInserter.createIncludeInsertion(Source.getFileID(ifStmt->getBeginLoc()), AlgotithmHeader);
+                                          std::move(replacementMax))
+          << IncludeInserter.createIncludeInsertion(
+                 Source.getFileID(ifStmt->getBeginLoc()), AlgotithmHeader);
     }
   }
 }
diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.h b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.h
index c92e80a351e1b..4146d9455bcd1 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.h
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.h
@@ -33,7 +33,8 @@ class UseStdMinMaxCheck : public ClangTidyCheck {
   std::optional<TraversalKind> getCheckTraversalKind() const override {
     return TK_IgnoreUnlessSpelledInSource;
   }
-  private:
+
+private:
   utils::IncludeInserter IncludeInserter;
   StringRef AlgotithmHeader;
 };

>From b8202aefe3e5cb07f59b7fc0d7647820987bde4b Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Wed, 17 Jan 2024 16:44:02 +0530
Subject: [PATCH 20/46] Added tests for macro & if with brackets

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../readability/UseStdMinMaxCheck.cpp         |  42 +++---
 .../readability/UseStdMinMaxCheck.h           |   2 +-
 .../checkers/readability/use-std-min-max.cpp  | 132 +++++++++++-------
 3 files changed, 104 insertions(+), 72 deletions(-)

diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
index 15e26f9baf68b..1b0adc2ac6876 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
@@ -22,7 +22,7 @@ UseStdMinMaxCheck::UseStdMinMaxCheck(StringRef Name, ClangTidyContext *Context)
       IncludeInserter(Options.getLocalOrGlobal("IncludeStyle",
                                                utils::IncludeSorter::IS_LLVM),
                       areDiagsSelfContained()),
-      AlgotithmHeader(Options.get("AlgorithmHeader", "<algorithm>")) {}
+      AlgorithmHeader(Options.get("AlgorithmHeader", "<algorithm>")) {}
 
 void UseStdMinMaxCheck::storeOptions(ClangTidyOptions::OptionMap &Opts) {
   Options.store(Opts, "IncludeStyle", IncludeInserter.getStyle());
@@ -35,9 +35,13 @@ void UseStdMinMaxCheck::registerMatchers(MatchFinder *Finder) {
               anyOf(hasOperatorName("<"), hasOperatorName(">"),
                     hasOperatorName("<="), hasOperatorName(">=")),
               hasLHS(expr().bind("lhsVar1")), hasRHS(expr().bind("rhsVar1")))),
-          hasThen(stmt(binaryOperator(hasOperatorName("="),
-                                      hasLHS(expr().bind("lhsVar2")),
-                                      hasRHS(expr().bind("rhsVar2"))))))
+          hasThen(
+              anyOf(stmt(binaryOperator(hasOperatorName("="),
+                                        hasLHS(expr().bind("lhsVar2")),
+                                        hasRHS(expr().bind("rhsVar2")))),
+                    compoundStmt(has(binaryOperator(
+                        hasOperatorName("="), hasLHS(expr().bind("lhsVar2")),
+                        hasRHS(expr().bind("rhsVar2"))))))))
           .bind("ifStmt"),
       this);
 }
@@ -67,22 +71,22 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
   SourceLocation ifLocation = ifStmt->getIfLoc();
   SourceLocation thenLocation = ifStmt->getEndLoc();
 
-  auto lhsVar1Str = Lexer::getSourceText(
-      CharSourceRange::getTokenRange(lhsVar1->getSourceRange()),
-      Context.getSourceManager(), Context.getLangOpts());
+  auto lhsVar1Str =
+      Lexer::getSourceText(Source.getExpansionRange(lhsVar1->getSourceRange()),
+                           Context.getSourceManager(), Context.getLangOpts());
 
-  auto lhsVar2Str = Lexer::getSourceText(
-      CharSourceRange::getTokenRange(lhsVar2->getSourceRange()),
-      Context.getSourceManager(), Context.getLangOpts());
+  auto lhsVar2Str =
+      Lexer::getSourceText(Source.getExpansionRange(lhsVar2->getSourceRange()),
+                           Context.getSourceManager(), Context.getLangOpts());
 
-  auto rhsVar1Str = Lexer::getSourceText(
-      CharSourceRange::getTokenRange(rhsVar1->getSourceRange()),
-      Context.getSourceManager(), Context.getLangOpts());
+  auto rhsVar1Str =
+      Lexer::getSourceText(Source.getExpansionRange(rhsVar1->getSourceRange()),
+                           Context.getSourceManager(), Context.getLangOpts());
 
   auto replacementMax = lhsVar2Str.str() + " = std::max(" + lhsVar1Str.str() +
-                        ", " + rhsVar1Str.str() + ")";
+                        ", " + rhsVar1Str.str() + ");";
   auto replacementMin = lhsVar2Str.str() + " = std::min(" + lhsVar1Str.str() +
-                        ", " + rhsVar1Str.str() + ")";
+                        ", " + rhsVar1Str.str() + ");";
   auto *operatorStr = binaryOp->getOpcodeStr().data();
 
   if (binaryOp->getOpcode() == BO_LT || binaryOp->getOpcode() == BO_LE) {
@@ -94,7 +98,7 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
           << FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
                                           std::move(replacementMax))
           << IncludeInserter.createIncludeInsertion(
-                 Source.getFileID(ifStmt->getBeginLoc()), AlgotithmHeader);
+                 Source.getFileID(ifStmt->getBeginLoc()), AlgorithmHeader);
     } else if (tidy::utils::areStatementsIdentical(lhsVar1, rhsVar2, Context) &&
                tidy::utils::areStatementsIdentical(rhsVar1, lhsVar2, Context)) {
       diag(ifStmt->getIfLoc(), "use `std::min` instead of `%0`")
@@ -102,7 +106,7 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
           << FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
                                           std::move(replacementMin))
           << IncludeInserter.createIncludeInsertion(
-                 Source.getFileID(ifStmt->getBeginLoc()), AlgotithmHeader);
+                 Source.getFileID(ifStmt->getBeginLoc()), AlgorithmHeader);
     }
   } else if (binaryOp->getOpcode() == BO_GT || binaryOp->getOpcode() == BO_GE) {
     if (tidy::utils::areStatementsIdentical(lhsVar1, lhsVar2, Context) &&
@@ -112,7 +116,7 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
           << FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
                                           std::move(replacementMin))
           << IncludeInserter.createIncludeInsertion(
-                 Source.getFileID(ifStmt->getBeginLoc()), AlgotithmHeader);
+                 Source.getFileID(ifStmt->getBeginLoc()), AlgorithmHeader);
     } else if (tidy::utils::areStatementsIdentical(lhsVar1, rhsVar2, Context) &&
                tidy::utils::areStatementsIdentical(rhsVar1, lhsVar2, Context)) {
       diag(ifStmt->getIfLoc(), "use `std::max` instead of `%0`")
@@ -120,7 +124,7 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
           << FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
                                           std::move(replacementMax))
           << IncludeInserter.createIncludeInsertion(
-                 Source.getFileID(ifStmt->getBeginLoc()), AlgotithmHeader);
+                 Source.getFileID(ifStmt->getBeginLoc()), AlgorithmHeader);
     }
   }
 }
diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.h b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.h
index 4146d9455bcd1..52b34fdbe2627 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.h
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.h
@@ -36,7 +36,7 @@ class UseStdMinMaxCheck : public ClangTidyCheck {
 
 private:
   utils::IncludeInserter IncludeInserter;
-  StringRef AlgotithmHeader;
+  StringRef AlgorithmHeader;
 };
 
 } // namespace clang::tidy::readability
diff --git a/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp b/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
index 99be29fb163bb..4a43d8f3926d4 100644
--- a/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
+++ b/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
@@ -1,5 +1,7 @@
 // RUN: %check_clang_tidy %s readability-use-std-min-max %t
 
+#define MY_MACRO_MIN(a, b) ((a) < (b) ? (a) : (b))
+
 constexpr int myConstexprMin(int a, int b) {
   return a < b ? a : b;
 }
@@ -8,10 +10,6 @@ constexpr int myConstexprMax(int a, int b) {
   return a > b ? a : b;
 }
 
-int bar(int x, int y) {
-  return x < y ? x : y;
-}
-
 class MyClass {
 public:
   int member1;
@@ -23,99 +21,129 @@ void foo() {
   short value4;
   MyClass obj;
 
-  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
+  // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
+  // CHECK-FIXES: value1 = std::max(value1, value2);
   if (value1 < value2)
-    value1 = value2; // CHECK-FIXES: value1 = std::max(value1, value2);
+    value1 = value2; 
 
-  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::min` instead of `<` [readability-use-std-min-max]
+  // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `<` [readability-use-std-min-max]
+  // CHECK-FIXES: value2 = std::min(value1, value2);
   if (value1 < value2)
-    value2 = value1; // CHECK-FIXES: value2 = std::min(value1, value2);
+    value2 = value1; 
 
-  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::min` instead of `>` [readability-use-std-min-max]
+  // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `>` [readability-use-std-min-max]
+  // CHECK-FIXES: value2 = std::min(value2, value1);
   if (value2 > value1)
-    value2 = value1; // CHECK-FIXES: value2 = std::min(value2, value1);
+    value2 = value1; 
 
-  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::max` instead of `>` [readability-use-std-min-max
+  // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `>` [readability-use-std-min-max
+  // CHECK-FIXES: value1 = std::max(value2, value1);
   if (value2 > value1)
-    value1 = value2; // CHECK-FIXES: value1 = std::max(value2, value1);
+    value1 = value2; 
 
   // No suggestion needed here
   if (value1 == value2)
     value1 = value2;
   
-  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
+  // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
+  // CHECK-FIXES: value1 = std::max(value1, value4);
   if(value1<value4)
-    value1=value4; // CHECK-FIXES: value1 = std::max(value1, value4);
+    value1=value4; 
   
-  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::min` instead of `<` [readability-use-std-min-max]
+  // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `<` [readability-use-std-min-max]
+  // CHECK-FIXES: value3 = std::min(value1+value2, value3);
   if(value1+value2<value3)
-    value3 = value1+value2; // CHECK-FIXES: value3 = std::min(value1+value2, value3);
+    value3 = value1+value2; 
   
-  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
+  // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
+  // CHECK-FIXES: value1 = std::max(value1, myConstexprMin(value2, value3));
   if (value1 < myConstexprMin(value2, value3))
-    value1 = myConstexprMin(value2, value3); // CHECK-FIXES: value1 = std::max(value1, myConstexprMin(value2, value3));
+    value1 = myConstexprMin(value2, value3); 
   
-  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::min` instead of `>` [readability-use-std-min-max]
+  // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `>` [readability-use-std-min-max]
+  // CHECK-FIXES: value1 = std::min(value1, myConstexprMax(value2, value3));
   if (value1 > myConstexprMax(value2, value3))
-    value1 = myConstexprMax(value2, value3); // CHECK-FIXES: value1 = std::min(value1, myConstexprMax(value2, value3));
-  
-  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
-  if (value1 < bar(value2, value3))
-    value1 = bar(value2, value3); // CHECK-FIXES: value1 = std::max(value1, bar(value2, value3));
+    value1 = myConstexprMax(value2, value3); 
   
-  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::min` instead of `<=` [readability-use-std-min-max]
+  // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `<=` [readability-use-std-min-max]
+  // CHECK-FIXES: value2 = std::min(value1, value2);
   if (value1 <= value2)
-    value2 = value1; // CHECK-FIXES: value2 = std::min(value1, value2);
+    value2 = value1; 
 
-  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::max` instead of `<=` [readability-use-std-min-max]
+  // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `<=` [readability-use-std-min-max]
+  // CHECK-FIXES: value1 = std::max(value1, value2);
   if (value1 <= value2)
-    value1 = value2; // CHECK-FIXES: value1 = std::max(value1, value2);
+    value1 = value2; 
 
-  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::max` instead of `>=` [readability-use-std-min-max]
+  // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `>=` [readability-use-std-min-max]
+  // CHECK-FIXES: value1 = std::max(value2, value1);
   if (value2 >= value1)
-    value1 = value2; // CHECK-FIXES: value1 = std::max(value2, value1);
+    value1 = value2; 
 
-  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::min` instead of `>=` [readability-use-std-min-max]
+  // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `>=` [readability-use-std-min-max]
+  // CHECK-FIXES: value2 = std::min(value2, value1);
   if (value2 >= value1)
-    value2 = value1; // CHECK-FIXES: value2 = std::min(value2, value1);
+    value2 = value1; 
   
-  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
+  // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
+  // CHECK-FIXES: obj.member1 = std::max(obj.member1, obj.member2);
   if (obj.member1 < obj.member2)
-    obj.member1 = obj.member2; // CHECK-FIXES: obj.member1 = std::max(obj.member1, obj.member2);
+    obj.member1 = obj.member2; 
 
-  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::min` instead of `<` [readability-use-std-min-max]
+  // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `<` [readability-use-std-min-max]
+  // CHECK-FIXES: obj.member2 = std::min(obj.member1, obj.member2);
   if (obj.member1 < obj.member2)
-    obj.member2 = obj.member1; // CHECK-FIXES: obj.member2 = std::min(obj.member1, obj.member2);
+    obj.member2 = obj.member1; 
 
-  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::min` instead of `>` [readability-use-std-min-max]
+  // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `>` [readability-use-std-min-max]
+  // CHECK-FIXES: obj.member2 = std::min(obj.member2, obj.member1);
   if (obj.member2 > obj.member1)
-    obj.member2 = obj.member1; // CHECK-FIXES: obj.member2 = std::min(obj.member2, obj.member1);
+    obj.member2 = obj.member1; 
 
-  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::max` instead of `>` [readability-use-std-min-max]
+  // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `>` [readability-use-std-min-max]
+  // CHECK-FIXES: obj.member1 = std::max(obj.member2, obj.member1);
   if (obj.member2 > obj.member1)
-    obj.member1 = obj.member2; // CHECK-FIXES: obj.member1 = std::max(obj.member2, obj.member1);
+    obj.member1 = obj.member2; 
   
-  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
+  // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
+  // CHECK-FIXES: obj.member1 = std::max(obj.member1, value4);
   if (obj.member1 < value4)
-    obj.member1 = value4; // CHECK-FIXES: obj.member1 = std::max(obj.member1, value4);
+    obj.member1 = value4; 
   
-  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::min` instead of `<` [readability-use-std-min-max]
+  // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `<` [readability-use-std-min-max]
+  // CHECK-FIXES: value3 = std::min(obj.member1 + value2, value3);
   if (obj.member1 + value2 < value3)
-    value3 = obj.member1 + value2; // CHECK-FIXES: value3 = std::min(obj.member1 + value2, value3);
+    value3 = obj.member1 + value2; 
   
-  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::min` instead of `<=` [readability-use-std-min-max]
+  // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `<=` [readability-use-std-min-max]
+  // CHECK-FIXES: obj.member2 = std::min(value1, obj.member2);
   if (value1 <= obj.member2)
-    obj.member2 = value1; // CHECK-FIXES: obj.member2 = std::min(value1, obj.member2);
+    obj.member2 = value1; 
 
-  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::max` instead of `<=` [readability-use-std-min-max]
+  // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `<=` [readability-use-std-min-max]
+  // CHECK-FIXES: value1 = std::max(value1, obj.member2);
   if (value1 <= obj.member2)
-    value1 = obj.member2; // CHECK-FIXES: value1 = std::max(value1, obj.member2);
+    value1 = obj.member2; 
 
-  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::max` instead of `>=` [readability-use-std-min-max]
+  // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `>=` [readability-use-std-min-max]
+  // CHECK-FIXES: value1 = std::max(obj.member2, value1);
   if (obj.member2 >= value1)
-    value1 = obj.member2; // CHECK-FIXES: value1 = std::max(obj.member2, value1);
+    value1 = obj.member2; 
 
-  // CHECK-MESSAGES: :[[@LINE+1]]:3: warning: use `std::min` instead of `>=` [readability-use-std-min-max]
+  // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `>=` [readability-use-std-min-max]
+  // CHECK-FIXES: obj.member2 = std::min(obj.member2, value1);
   if (obj.member2 >= value1)
-    obj.member2 = value1; // CHECK-FIXES: obj.member2 = std::min(obj.member2, value1);
+    obj.member2 = value1; 
+  
+  // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `<` [readability-use-std-min-max]
+  // CHECK-FIXES: value3 = std::min(MY_MACRO_MIN(value1, value2), value3);
+  if (MY_MACRO_MIN(value1, value2) < value3)
+    value3 = MY_MACRO_MIN(value1, value2); 
+  
+  // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `<` [readability-use-std-min-max]
+  // CHECK-FIXES: value2 = std::min(value1, value2);
+  if (value1 < value2){
+    value2 = value1; 
+  }
+
 }
\ No newline at end of file

>From 5e31665d0c449ae09d21b409bbf8b1e035f553b7 Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Fri, 19 Jan 2024 13:06:27 +0530
Subject: [PATCH 21/46] Added suggested changes

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../readability/UseStdMinMaxCheck.cpp         | 136 +++++++++---------
 clang-tools-extra/docs/ReleaseNotes.rst       |   3 +-
 .../checkers/readability/use-std-min-max.cpp  |  30 +++-
 3 files changed, 96 insertions(+), 73 deletions(-)

diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
index 1b0adc2ac6876..88bd2e1a941b8 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
@@ -21,28 +21,27 @@ UseStdMinMaxCheck::UseStdMinMaxCheck(StringRef Name, ClangTidyContext *Context)
     : ClangTidyCheck(Name, Context),
       IncludeInserter(Options.getLocalOrGlobal("IncludeStyle",
                                                utils::IncludeSorter::IS_LLVM),
-                      areDiagsSelfContained()),
-      AlgorithmHeader(Options.get("AlgorithmHeader", "<algorithm>")) {}
+                      areDiagsSelfContained()) {}
 
 void UseStdMinMaxCheck::storeOptions(ClangTidyOptions::OptionMap &Opts) {
   Options.store(Opts, "IncludeStyle", IncludeInserter.getStyle());
+  Options.store(Opts, "AlgorithmHeader", Options.get("AlgorithmHeader", "<algorithm>"));
 }
 
 void UseStdMinMaxCheck::registerMatchers(MatchFinder *Finder) {
   Finder->addMatcher(
       ifStmt(
-          has(binaryOperator(
-              anyOf(hasOperatorName("<"), hasOperatorName(">"),
-                    hasOperatorName("<="), hasOperatorName(">=")),
-              hasLHS(expr().bind("lhsVar1")), hasRHS(expr().bind("rhsVar1")))),
+          hasCondition(binaryOperator(
+              hasAnyOperatorName("<",">","<=",">="),
+              hasLHS(expr().bind("CondLhs")), hasRHS(expr().bind("CondRhs")))),
           hasThen(
               anyOf(stmt(binaryOperator(hasOperatorName("="),
-                                        hasLHS(expr().bind("lhsVar2")),
-                                        hasRHS(expr().bind("rhsVar2")))),
+                                        hasLHS(expr().bind("AssignLhs")),
+                                        hasRHS(expr().bind("AssignRhs")))),
                     compoundStmt(has(binaryOperator(
-                        hasOperatorName("="), hasLHS(expr().bind("lhsVar2")),
-                        hasRHS(expr().bind("rhsVar2"))))))))
-          .bind("ifStmt"),
+                        hasOperatorName("="), hasLHS(expr().bind("AssignLhs")),
+                        hasRHS(expr().bind("AssignRhs"))))).bind("compound"))))
+          .bind("if"),
       this);
 }
 
@@ -53,79 +52,78 @@ void UseStdMinMaxCheck::registerPPCallbacks(const SourceManager &SM,
 }
 
 void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
-  const auto *lhsVar1 = Result.Nodes.getNodeAs<Expr>("lhsVar1");
-  const auto *rhsVar1 = Result.Nodes.getNodeAs<Expr>("rhsVar1");
-  const auto *lhsVar2 = Result.Nodes.getNodeAs<Expr>("lhsVar2");
-  const auto *rhsVar2 = Result.Nodes.getNodeAs<Expr>("rhsVar2");
-  const auto *ifStmt = Result.Nodes.getNodeAs<IfStmt>("ifStmt");
+  const auto *CondLhs = Result.Nodes.getNodeAs<Expr>("CondLhs");
+  const auto *CondRhs = Result.Nodes.getNodeAs<Expr>("CondRhs");
+  const auto *AssignLhs = Result.Nodes.getNodeAs<Expr>("AssignLhs");
+  const auto *AssignRhs = Result.Nodes.getNodeAs<Expr>("AssignRhs");
+  const auto *If = Result.Nodes.getNodeAs<IfStmt>("if");
+  const auto *Compound = Result.Nodes.getNodeAs<CompoundStmt>("compound");
   auto &Context = *Result.Context;
   const SourceManager &Source = Context.getSourceManager();
 
-  if (!lhsVar1 || !rhsVar1 || !lhsVar2 || !rhsVar2 || !ifStmt)
+  const auto *BinaryOp = dyn_cast<BinaryOperator>(If->getCond());
+  if (!BinaryOp || If->hasElseStorage())
     return;
+  
+  if(Compound){
+    int count = 0;
+    clang::Stmt::const_child_iterator I = Compound->child_begin();
+    clang::Stmt::const_child_iterator E = Compound->child_end();
+    for(; I != E; ++I){count++;}
+    if(count>1)
+      return;
 
-  const auto *binaryOp = dyn_cast<BinaryOperator>(ifStmt->getCond());
-  if (!binaryOp)
-    return;
+  }
 
-  SourceLocation ifLocation = ifStmt->getIfLoc();
-  SourceLocation thenLocation = ifStmt->getEndLoc();
+  SourceLocation IfLocation = If->getIfLoc();
+  SourceLocation ThenLocation = If->getEndLoc();
 
-  auto lhsVar1Str =
-      Lexer::getSourceText(Source.getExpansionRange(lhsVar1->getSourceRange()),
-                           Context.getSourceManager(), Context.getLangOpts());
+  if(IfLocation.isMacroID() || ThenLocation.isMacroID())
+    return;
 
-  auto lhsVar2Str =
-      Lexer::getSourceText(Source.getExpansionRange(lhsVar2->getSourceRange()),
+  const auto CondLhsStr =
+      Lexer::getSourceText(Source.getExpansionRange(CondLhs->getSourceRange()),
                            Context.getSourceManager(), Context.getLangOpts());
 
-  auto rhsVar1Str =
-      Lexer::getSourceText(Source.getExpansionRange(rhsVar1->getSourceRange()),
+  const auto AssignLhsStr =
+      Lexer::getSourceText(Source.getExpansionRange(AssignLhs->getSourceRange()),
                            Context.getSourceManager(), Context.getLangOpts());
 
-  auto replacementMax = lhsVar2Str.str() + " = std::max(" + lhsVar1Str.str() +
-                        ", " + rhsVar1Str.str() + ");";
-  auto replacementMin = lhsVar2Str.str() + " = std::min(" + lhsVar1Str.str() +
-                        ", " + rhsVar1Str.str() + ");";
-  auto *operatorStr = binaryOp->getOpcodeStr().data();
-
-  if (binaryOp->getOpcode() == BO_LT || binaryOp->getOpcode() == BO_LE) {
-    if (tidy::utils::areStatementsIdentical(lhsVar1, lhsVar2, Context) &&
-        tidy::utils::areStatementsIdentical(rhsVar1, rhsVar2, Context)) {
+  const auto CondRhsStr =
+      Lexer::getSourceText(Source.getExpansionRange(CondRhs->getSourceRange()),
+                           Context.getSourceManager(), Context.getLangOpts());
 
-      diag(ifStmt->getIfLoc(), "use `std::max` instead of `%0`")
-          << operatorStr
-          << FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
-                                          std::move(replacementMax))
+  auto CreateMaxReplacement = [&]() {
+    return AssignLhsStr.str() + " = std::max(" + CondLhsStr.str() +
+           ", " + CondRhsStr.str() + ");";
+  };
+
+  auto CreateMinReplacement = [&]() {
+    return AssignLhsStr.str() + " = std::min(" + CondLhsStr.str() +
+           ", " + CondRhsStr.str() + ");";
+  };
+  const auto OperatorStr = BinaryOp->getOpcodeStr();
+  if(((BinaryOp->getOpcode() == BO_LT || BinaryOp->getOpcode() == BO_LE) && (tidy::utils::areStatementsIdentical(CondLhs, AssignRhs, Context) &&
+               tidy::utils::areStatementsIdentical(CondRhs, AssignLhs, Context))) || ((BinaryOp->getOpcode() == BO_GT || BinaryOp->getOpcode() == BO_GE) && (tidy::utils::areStatementsIdentical(CondLhs, AssignLhs, Context) &&
+        tidy::utils::areStatementsIdentical(CondRhs, AssignRhs, Context)))){
+          diag(IfLocation, "use `std::min` instead of `%0`")
+          << OperatorStr
+          << FixItHint::CreateReplacement(SourceRange(IfLocation, ThenLocation),
+                                          std::move(CreateMinReplacement()))
           << IncludeInserter.createIncludeInsertion(
-                 Source.getFileID(ifStmt->getBeginLoc()), AlgorithmHeader);
-    } else if (tidy::utils::areStatementsIdentical(lhsVar1, rhsVar2, Context) &&
-               tidy::utils::areStatementsIdentical(rhsVar1, lhsVar2, Context)) {
-      diag(ifStmt->getIfLoc(), "use `std::min` instead of `%0`")
-          << operatorStr
-          << FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
-                                          std::move(replacementMin))
-          << IncludeInserter.createIncludeInsertion(
-                 Source.getFileID(ifStmt->getBeginLoc()), AlgorithmHeader);
-    }
-  } else if (binaryOp->getOpcode() == BO_GT || binaryOp->getOpcode() == BO_GE) {
-    if (tidy::utils::areStatementsIdentical(lhsVar1, lhsVar2, Context) &&
-        tidy::utils::areStatementsIdentical(rhsVar1, rhsVar2, Context)) {
-      diag(ifStmt->getIfLoc(), "use `std::min` instead of `%0`")
-          << operatorStr
-          << FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
-                                          std::move(replacementMin))
-          << IncludeInserter.createIncludeInsertion(
-                 Source.getFileID(ifStmt->getBeginLoc()), AlgorithmHeader);
-    } else if (tidy::utils::areStatementsIdentical(lhsVar1, rhsVar2, Context) &&
-               tidy::utils::areStatementsIdentical(rhsVar1, lhsVar2, Context)) {
-      diag(ifStmt->getIfLoc(), "use `std::max` instead of `%0`")
-          << operatorStr
-          << FixItHint::CreateReplacement(SourceRange(ifLocation, thenLocation),
-                                          std::move(replacementMax))
+                 Source.getFileID(If->getBeginLoc()), AlgorithmHeader);
+
+  }
+  else if(((BinaryOp->getOpcode() == BO_LT || BinaryOp->getOpcode() == BO_LE) && (tidy::utils::areStatementsIdentical(CondLhs, AssignLhs, Context) &&
+        tidy::utils::areStatementsIdentical(CondRhs, AssignRhs, Context))) || ((BinaryOp->getOpcode() == BO_GT || BinaryOp->getOpcode() == BO_GE) && (tidy::utils::areStatementsIdentical(CondLhs, AssignRhs, Context) &&
+               tidy::utils::areStatementsIdentical(CondRhs, AssignLhs, Context)))){
+          diag(IfLocation, "use `std::max` instead of `%0`")
+          << OperatorStr
+          << FixItHint::CreateReplacement(SourceRange(IfLocation, ThenLocation),
+                                          std::move(CreateMaxReplacement()))
           << IncludeInserter.createIncludeInsertion(
-                 Source.getFileID(ifStmt->getBeginLoc()), AlgorithmHeader);
-    }
+                 Source.getFileID(If->getBeginLoc()), AlgorithmHeader);
+
   }
 }
 
diff --git a/clang-tools-extra/docs/ReleaseNotes.rst b/clang-tools-extra/docs/ReleaseNotes.rst
index 9f96001514ac3..3592411084e6a 100644
--- a/clang-tools-extra/docs/ReleaseNotes.rst
+++ b/clang-tools-extra/docs/ReleaseNotes.rst
@@ -228,8 +228,7 @@ New checks
   <clang-tidy/checks/readability/use-std-min-max>` check.
 
   Replaces certain conditional statements with equivalent ``std::min`` or
-  ``std::max`` expressions, improving readability and promoting the use of
-  standard library functions.
+  ``std::max`` expressions.
 
 - New :doc:`readability-avoid-nested-conditional-operator
   <clang-tidy/checks/readability/avoid-nested-conditional-operator>` check.
diff --git a/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp b/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
index 4a43d8f3926d4..03971fc4c56cd 100644
--- a/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
+++ b/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
@@ -10,6 +10,11 @@ constexpr int myConstexprMax(int a, int b) {
   return a > b ? a : b;
 }
 
+#define MY_IF_MACRO(condition, statement) \
+  if (condition) {                        \
+    statement                             \
+  }
+
 class MyClass {
 public:
   int member1;
@@ -135,8 +140,7 @@ void foo() {
   if (obj.member2 >= value1)
     obj.member2 = value1; 
   
-  // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `<` [readability-use-std-min-max]
-  // CHECK-FIXES: value3 = std::min(MY_MACRO_MIN(value1, value2), value3);
+  // No suggestion needed here
   if (MY_MACRO_MIN(value1, value2) < value3)
     value3 = MY_MACRO_MIN(value1, value2); 
   
@@ -146,4 +150,26 @@ void foo() {
     value2 = value1; 
   }
 
+  // No suggestion needed here
+  if(value1 < value2)
+    value2 = value1;
+  else
+    value2 = value3;
+  
+  // No suggestion needed here
+  if(value1<value2){
+    value2 = value1; 
+  }
+  else{
+    value2 = value3;  
+  }
+
+  // No suggestion needed here
+  if(value1<value2){
+    value2 = value1; 
+    int res = value1 + value2;
+  }
+
+  // No suggestion needed here
+  MY_IF_MACRO(value1 < value2, value1 = value2;)
 }
\ No newline at end of file

>From a2cfcdcdcc14a95f89aa40378487a2812e6b04a8 Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Fri, 19 Jan 2024 13:07:48 +0530
Subject: [PATCH 22/46] Formatted the code

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../readability/UseStdMinMaxCheck.cpp         | 103 ++++++++++--------
 1 file changed, 58 insertions(+), 45 deletions(-)

diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
index 88bd2e1a941b8..4f684f5bcc16f 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
@@ -25,22 +25,24 @@ UseStdMinMaxCheck::UseStdMinMaxCheck(StringRef Name, ClangTidyContext *Context)
 
 void UseStdMinMaxCheck::storeOptions(ClangTidyOptions::OptionMap &Opts) {
   Options.store(Opts, "IncludeStyle", IncludeInserter.getStyle());
-  Options.store(Opts, "AlgorithmHeader", Options.get("AlgorithmHeader", "<algorithm>"));
+  Options.store(Opts, "AlgorithmHeader",
+                Options.get("AlgorithmHeader", "<algorithm>"));
 }
 
 void UseStdMinMaxCheck::registerMatchers(MatchFinder *Finder) {
   Finder->addMatcher(
       ifStmt(
-          hasCondition(binaryOperator(
-              hasAnyOperatorName("<",">","<=",">="),
-              hasLHS(expr().bind("CondLhs")), hasRHS(expr().bind("CondRhs")))),
-          hasThen(
-              anyOf(stmt(binaryOperator(hasOperatorName("="),
-                                        hasLHS(expr().bind("AssignLhs")),
-                                        hasRHS(expr().bind("AssignRhs")))),
-                    compoundStmt(has(binaryOperator(
-                        hasOperatorName("="), hasLHS(expr().bind("AssignLhs")),
-                        hasRHS(expr().bind("AssignRhs"))))).bind("compound"))))
+          hasCondition(binaryOperator(hasAnyOperatorName("<", ">", "<=", ">="),
+                                      hasLHS(expr().bind("CondLhs")),
+                                      hasRHS(expr().bind("CondRhs")))),
+          hasThen(anyOf(stmt(binaryOperator(hasOperatorName("="),
+                                            hasLHS(expr().bind("AssignLhs")),
+                                            hasRHS(expr().bind("AssignRhs")))),
+                        compoundStmt(has(binaryOperator(
+                                         hasOperatorName("="),
+                                         hasLHS(expr().bind("AssignLhs")),
+                                         hasRHS(expr().bind("AssignRhs")))))
+                            .bind("compound"))))
           .bind("if"),
       this);
 }
@@ -64,66 +66,77 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
   const auto *BinaryOp = dyn_cast<BinaryOperator>(If->getCond());
   if (!BinaryOp || If->hasElseStorage())
     return;
-  
-  if(Compound){
+
+  if (Compound) {
     int count = 0;
     clang::Stmt::const_child_iterator I = Compound->child_begin();
     clang::Stmt::const_child_iterator E = Compound->child_end();
-    for(; I != E; ++I){count++;}
-    if(count>1)
+    for (; I != E; ++I) {
+      count++;
+    }
+    if (count > 1)
       return;
-
   }
 
   SourceLocation IfLocation = If->getIfLoc();
   SourceLocation ThenLocation = If->getEndLoc();
 
-  if(IfLocation.isMacroID() || ThenLocation.isMacroID())
+  if (IfLocation.isMacroID() || ThenLocation.isMacroID())
     return;
 
   const auto CondLhsStr =
       Lexer::getSourceText(Source.getExpansionRange(CondLhs->getSourceRange()),
                            Context.getSourceManager(), Context.getLangOpts());
 
-  const auto AssignLhsStr =
-      Lexer::getSourceText(Source.getExpansionRange(AssignLhs->getSourceRange()),
-                           Context.getSourceManager(), Context.getLangOpts());
+  const auto AssignLhsStr = Lexer::getSourceText(
+      Source.getExpansionRange(AssignLhs->getSourceRange()),
+      Context.getSourceManager(), Context.getLangOpts());
 
   const auto CondRhsStr =
       Lexer::getSourceText(Source.getExpansionRange(CondRhs->getSourceRange()),
                            Context.getSourceManager(), Context.getLangOpts());
 
   auto CreateMaxReplacement = [&]() {
-    return AssignLhsStr.str() + " = std::max(" + CondLhsStr.str() +
-           ", " + CondRhsStr.str() + ");";
+    return AssignLhsStr.str() + " = std::max(" + CondLhsStr.str() + ", " +
+           CondRhsStr.str() + ");";
   };
 
   auto CreateMinReplacement = [&]() {
-    return AssignLhsStr.str() + " = std::min(" + CondLhsStr.str() +
-           ", " + CondRhsStr.str() + ");";
+    return AssignLhsStr.str() + " = std::min(" + CondLhsStr.str() + ", " +
+           CondRhsStr.str() + ");";
   };
   const auto OperatorStr = BinaryOp->getOpcodeStr();
-  if(((BinaryOp->getOpcode() == BO_LT || BinaryOp->getOpcode() == BO_LE) && (tidy::utils::areStatementsIdentical(CondLhs, AssignRhs, Context) &&
-               tidy::utils::areStatementsIdentical(CondRhs, AssignLhs, Context))) || ((BinaryOp->getOpcode() == BO_GT || BinaryOp->getOpcode() == BO_GE) && (tidy::utils::areStatementsIdentical(CondLhs, AssignLhs, Context) &&
-        tidy::utils::areStatementsIdentical(CondRhs, AssignRhs, Context)))){
-          diag(IfLocation, "use `std::min` instead of `%0`")
-          << OperatorStr
-          << FixItHint::CreateReplacement(SourceRange(IfLocation, ThenLocation),
-                                          std::move(CreateMinReplacement()))
-          << IncludeInserter.createIncludeInsertion(
-                 Source.getFileID(If->getBeginLoc()), AlgorithmHeader);
-
-  }
-  else if(((BinaryOp->getOpcode() == BO_LT || BinaryOp->getOpcode() == BO_LE) && (tidy::utils::areStatementsIdentical(CondLhs, AssignLhs, Context) &&
-        tidy::utils::areStatementsIdentical(CondRhs, AssignRhs, Context))) || ((BinaryOp->getOpcode() == BO_GT || BinaryOp->getOpcode() == BO_GE) && (tidy::utils::areStatementsIdentical(CondLhs, AssignRhs, Context) &&
-               tidy::utils::areStatementsIdentical(CondRhs, AssignLhs, Context)))){
-          diag(IfLocation, "use `std::max` instead of `%0`")
-          << OperatorStr
-          << FixItHint::CreateReplacement(SourceRange(IfLocation, ThenLocation),
-                                          std::move(CreateMaxReplacement()))
-          << IncludeInserter.createIncludeInsertion(
-                 Source.getFileID(If->getBeginLoc()), AlgorithmHeader);
-
+  if (((BinaryOp->getOpcode() == BO_LT || BinaryOp->getOpcode() == BO_LE) &&
+       (tidy::utils::areStatementsIdentical(CondLhs, AssignRhs, Context) &&
+        tidy::utils::areStatementsIdentical(CondRhs, AssignLhs, Context))) ||
+      ((BinaryOp->getOpcode() == BO_GT || BinaryOp->getOpcode() == BO_GE) &&
+       (tidy::utils::areStatementsIdentical(CondLhs, AssignLhs, Context) &&
+        tidy::utils::areStatementsIdentical(CondRhs, AssignRhs, Context)))) {
+    diag(IfLocation, "use `std::min` instead of `%0`")
+        << OperatorStr
+        << FixItHint::CreateReplacement(SourceRange(IfLocation, ThenLocation),
+                                        std::move(CreateMinReplacement()))
+        << IncludeInserter.createIncludeInsertion(
+               Source.getFileID(If->getBeginLoc()), AlgorithmHeader);
+
+  } else if (((BinaryOp->getOpcode() == BO_LT ||
+               BinaryOp->getOpcode() == BO_LE) &&
+              (tidy::utils::areStatementsIdentical(CondLhs, AssignLhs,
+                                                   Context) &&
+               tidy::utils::areStatementsIdentical(CondRhs, AssignRhs,
+                                                   Context))) ||
+             ((BinaryOp->getOpcode() == BO_GT ||
+               BinaryOp->getOpcode() == BO_GE) &&
+              (tidy::utils::areStatementsIdentical(CondLhs, AssignRhs,
+                                                   Context) &&
+               tidy::utils::areStatementsIdentical(CondRhs, AssignLhs,
+                                                   Context)))) {
+    diag(IfLocation, "use `std::max` instead of `%0`")
+        << OperatorStr
+        << FixItHint::CreateReplacement(SourceRange(IfLocation, ThenLocation),
+                                        std::move(CreateMaxReplacement()))
+        << IncludeInserter.createIncludeInsertion(
+               Source.getFileID(If->getBeginLoc()), AlgorithmHeader);
   }
 }
 

>From f5a0f12bbf59e141b4a0832a73d76a9be402ff14 Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Sat, 20 Jan 2024 01:55:16 +0530
Subject: [PATCH 23/46] Converted to Lambdas,placed at sorted location

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../readability/ReadabilityTidyModule.cpp     |  4 +-
 .../readability/UseStdMinMaxCheck.cpp         | 56 +++++++++----------
 clang-tools-extra/docs/ReleaseNotes.rst       | 12 ++--
 .../docs/clang-tidy/checks/list.rst           |  2 +-
 4 files changed, 35 insertions(+), 39 deletions(-)

diff --git a/clang-tools-extra/clang-tidy/readability/ReadabilityTidyModule.cpp b/clang-tools-extra/clang-tidy/readability/ReadabilityTidyModule.cpp
index 89999e2794d2b..1cc520b0c005a 100644
--- a/clang-tools-extra/clang-tidy/readability/ReadabilityTidyModule.cpp
+++ b/clang-tools-extra/clang-tidy/readability/ReadabilityTidyModule.cpp
@@ -64,8 +64,6 @@ namespace readability {
 class ReadabilityModule : public ClangTidyModule {
 public:
   void addCheckFactories(ClangTidyCheckFactories &CheckFactories) override {
-    CheckFactories.registerCheck<UseStdMinMaxCheck>(
-        "readability-use-std-min-max");
     CheckFactories.registerCheck<AvoidConstParamsInDecls>(
         "readability-avoid-const-params-in-decls");
     CheckFactories.registerCheck<AvoidNestedConditionalOperatorCheck>(
@@ -160,6 +158,8 @@ class ReadabilityModule : public ClangTidyModule {
         "readability-uppercase-literal-suffix");
     CheckFactories.registerCheck<UseAnyOfAllOfCheck>(
         "readability-use-anyofallof");
+    CheckFactories.registerCheck<UseStdMinMaxCheck>(
+        "readability-use-std-min-max");
   }
 };
 
diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
index 4f684f5bcc16f..44173515842e4 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
@@ -60,7 +60,8 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
   const auto *AssignRhs = Result.Nodes.getNodeAs<Expr>("AssignRhs");
   const auto *If = Result.Nodes.getNodeAs<IfStmt>("if");
   const auto *Compound = Result.Nodes.getNodeAs<CompoundStmt>("compound");
-  auto &Context = *Result.Context;
+  const auto &Context = *Result.Context;
+  const auto &LO = Context.getLangOpts();
   const SourceManager &Source = Context.getSourceManager();
 
   const auto *BinaryOp = dyn_cast<BinaryOperator>(If->getCond());
@@ -68,42 +69,37 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
     return;
 
   if (Compound) {
-    int count = 0;
-    clang::Stmt::const_child_iterator I = Compound->child_begin();
-    clang::Stmt::const_child_iterator E = Compound->child_end();
-    for (; I != E; ++I) {
-      count++;
-    }
-    if (count > 1)
+    if (Compound->size() > 1)
       return;
   }
 
-  SourceLocation IfLocation = If->getIfLoc();
-  SourceLocation ThenLocation = If->getEndLoc();
+  const SourceLocation IfLocation = If->getIfLoc();
+  const SourceLocation ThenLocation = If->getEndLoc();
 
   if (IfLocation.isMacroID() || ThenLocation.isMacroID())
     return;
 
-  const auto CondLhsStr =
-      Lexer::getSourceText(Source.getExpansionRange(CondLhs->getSourceRange()),
-                           Context.getSourceManager(), Context.getLangOpts());
-
-  const auto AssignLhsStr = Lexer::getSourceText(
-      Source.getExpansionRange(AssignLhs->getSourceRange()),
-      Context.getSourceManager(), Context.getLangOpts());
-
-  const auto CondRhsStr =
-      Lexer::getSourceText(Source.getExpansionRange(CondRhs->getSourceRange()),
-                           Context.getSourceManager(), Context.getLangOpts());
-
-  auto CreateMaxReplacement = [&]() {
-    return AssignLhsStr.str() + " = std::max(" + CondLhsStr.str() + ", " +
-           CondRhsStr.str() + ");";
+  const auto CreateString = [&](int index) -> llvm::StringRef {
+    switch (index) {
+    case 1:
+      return Lexer::getSourceText(
+          Source.getExpansionRange(CondLhs->getSourceRange()), Source, LO);
+    case 2:
+      return Lexer::getSourceText(
+          Source.getExpansionRange(CondRhs->getSourceRange()), Source, LO);
+    case 3:
+      return Lexer::getSourceText(
+          Source.getExpansionRange(AssignLhs->getSourceRange()), Source, LO);
+    default:
+      return "Invalid index";
+    }
   };
 
-  auto CreateMinReplacement = [&]() {
-    return AssignLhsStr.str() + " = std::min(" + CondLhsStr.str() + ", " +
-           CondRhsStr.str() + ");";
+  const auto CreateReplacement = [&](bool useMax) {
+    std::string functionName = useMax ? "std::max" : "std::min";
+    return CreateString(/* AssignLhs */ 3).str() + " = " + functionName + "(" +
+           CreateString(/* CondLhs */ 1).str() + ", " +
+           CreateString(/* CondRhs */ 2).str() + ");";
   };
   const auto OperatorStr = BinaryOp->getOpcodeStr();
   if (((BinaryOp->getOpcode() == BO_LT || BinaryOp->getOpcode() == BO_LE) &&
@@ -115,7 +111,7 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
     diag(IfLocation, "use `std::min` instead of `%0`")
         << OperatorStr
         << FixItHint::CreateReplacement(SourceRange(IfLocation, ThenLocation),
-                                        std::move(CreateMinReplacement()))
+                                        CreateReplacement(/*useMax = false*/ 0))
         << IncludeInserter.createIncludeInsertion(
                Source.getFileID(If->getBeginLoc()), AlgorithmHeader);
 
@@ -134,7 +130,7 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
     diag(IfLocation, "use `std::max` instead of `%0`")
         << OperatorStr
         << FixItHint::CreateReplacement(SourceRange(IfLocation, ThenLocation),
-                                        std::move(CreateMaxReplacement()))
+                                        CreateReplacement(/*useMax = true*/ 1))
         << IncludeInserter.createIncludeInsertion(
                Source.getFileID(If->getBeginLoc()), AlgorithmHeader);
   }
diff --git a/clang-tools-extra/docs/ReleaseNotes.rst b/clang-tools-extra/docs/ReleaseNotes.rst
index 3592411084e6a..e258f4978c45f 100644
--- a/clang-tools-extra/docs/ReleaseNotes.rst
+++ b/clang-tools-extra/docs/ReleaseNotes.rst
@@ -224,12 +224,6 @@ New checks
   Recommends the smallest possible underlying type for an ``enum`` or ``enum``
   class based on the range of its enumerators.
 
-- New :doc:`readability-use-std-min-max
-  <clang-tidy/checks/readability/use-std-min-max>` check.
-
-  Replaces certain conditional statements with equivalent ``std::min`` or
-  ``std::max`` expressions.
-
 - New :doc:`readability-avoid-nested-conditional-operator
   <clang-tidy/checks/readability/avoid-nested-conditional-operator>` check.
 
@@ -247,6 +241,12 @@ New checks
   Detects C++ code where a reference variable is used to extend the lifetime
   of a temporary object that has just been constructed.
 
+- New :doc:`readability-use-std-min-max
+  <clang-tidy/checks/readability/use-std-min-max>` check.
+
+  Replaces certain conditional statements with equivalent ``std::min`` or
+  ``std::max`` expressions.
+
 New check aliases
 ^^^^^^^^^^^^^^^^^
 
diff --git a/clang-tools-extra/docs/clang-tidy/checks/list.rst b/clang-tools-extra/docs/clang-tidy/checks/list.rst
index 3bd414f0eed89..68360eb67ac55 100644
--- a/clang-tools-extra/docs/clang-tidy/checks/list.rst
+++ b/clang-tools-extra/docs/clang-tidy/checks/list.rst
@@ -336,7 +336,6 @@ Clang-Tidy Checks
    :doc:`portability-restrict-system-includes <portability/restrict-system-includes>`, "Yes"
    :doc:`portability-simd-intrinsics <portability/simd-intrinsics>`,
    :doc:`portability-std-allocator-const <portability/std-allocator-const>`,
-   :doc:`readability-use-std-min-max <readability/use-std-min-max>`, "Yes"
    :doc:`readability-avoid-const-params-in-decls <readability/avoid-const-params-in-decls>`, "Yes"
    :doc:`readability-avoid-nested-conditional-operator <readability/avoid-nested-conditional-operator>`,
    :doc:`readability-avoid-return-with-void-value <readability/avoid-return-with-void-value>`,
@@ -384,6 +383,7 @@ Clang-Tidy Checks
    :doc:`readability-uniqueptr-delete-release <readability/uniqueptr-delete-release>`, "Yes"
    :doc:`readability-uppercase-literal-suffix <readability/uppercase-literal-suffix>`, "Yes"
    :doc:`readability-use-anyofallof <readability/use-anyofallof>`,
+   :doc:`readability-use-std-min-max <readability/use-std-min-max>`, "Yes"
    :doc:`zircon-temporary-objects <zircon/temporary-objects>`,
 
 

>From e239576831f3592fd35ed4628da1809026b621f8 Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Sat, 20 Jan 2024 22:54:37 +0530
Subject: [PATCH 24/46] Single Lambda

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../readability/UseStdMinMaxCheck.cpp         | 32 +++++++------------
 .../checks/readability/use-std-min-max.rst    |  4 +--
 2 files changed, 13 insertions(+), 23 deletions(-)

diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
index 44173515842e4..9d740db05001e 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
@@ -79,27 +79,17 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
   if (IfLocation.isMacroID() || ThenLocation.isMacroID())
     return;
 
-  const auto CreateString = [&](int index) -> llvm::StringRef {
-    switch (index) {
-    case 1:
-      return Lexer::getSourceText(
-          Source.getExpansionRange(CondLhs->getSourceRange()), Source, LO);
-    case 2:
-      return Lexer::getSourceText(
-          Source.getExpansionRange(CondRhs->getSourceRange()), Source, LO);
-    case 3:
-      return Lexer::getSourceText(
-          Source.getExpansionRange(AssignLhs->getSourceRange()), Source, LO);
-    default:
-      return "Invalid index";
-    }
-  };
-
   const auto CreateReplacement = [&](bool useMax) {
     std::string functionName = useMax ? "std::max" : "std::min";
-    return CreateString(/* AssignLhs */ 3).str() + " = " + functionName + "(" +
-           CreateString(/* CondLhs */ 1).str() + ", " +
-           CreateString(/* CondRhs */ 2).str() + ");";
+    const auto CondLhsStr = Lexer::getSourceText(
+        Source.getExpansionRange(CondLhs->getSourceRange()), Source, LO);
+    const auto CondRhsStr = Lexer::getSourceText(
+        Source.getExpansionRange(CondRhs->getSourceRange()), Source, LO);
+    const auto AssignLhsStr = Lexer::getSourceText(
+        Source.getExpansionRange(AssignLhs->getSourceRange()), Source, LO);
+    return (AssignLhsStr + " = " + functionName + "(" + CondLhsStr + ", " +
+            CondRhsStr + ");")
+        .str();
   };
   const auto OperatorStr = BinaryOp->getOpcodeStr();
   if (((BinaryOp->getOpcode() == BO_LT || BinaryOp->getOpcode() == BO_LE) &&
@@ -111,7 +101,7 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
     diag(IfLocation, "use `std::min` instead of `%0`")
         << OperatorStr
         << FixItHint::CreateReplacement(SourceRange(IfLocation, ThenLocation),
-                                        CreateReplacement(/*useMax = false*/ 0))
+                                        CreateReplacement(/*useMax=*/false))
         << IncludeInserter.createIncludeInsertion(
                Source.getFileID(If->getBeginLoc()), AlgorithmHeader);
 
@@ -130,7 +120,7 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
     diag(IfLocation, "use `std::max` instead of `%0`")
         << OperatorStr
         << FixItHint::CreateReplacement(SourceRange(IfLocation, ThenLocation),
-                                        CreateReplacement(/*useMax = true*/ 1))
+                                        CreateReplacement(/*useMax=*/true))
         << IncludeInserter.createIncludeInsertion(
                Source.getFileID(If->getBeginLoc()), AlgorithmHeader);
   }
diff --git a/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst b/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst
index 7e64a05ccd8b8..2cf6a58552cde 100644
--- a/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst
+++ b/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst
@@ -3,8 +3,8 @@
 readability-use-std-min-max
 ===========================
 
-Replaces certain conditionals with ``std::min`` or ``std::max`` for readability,
-promoting use of standard library functions. Note: This may impact
+Replaces certain conditional statements with equivalent ``std::min`` or
+``std::max`` expressions. Note: This may impact
 performance in critical code due to potential additional stores compared
 to the original if statement.
 

>From b868d5b5c3c5057eaec066ad6efa86e39aaf63e2 Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Sun, 21 Jan 2024 00:20:19 +0530
Subject: [PATCH 25/46] CamelCase,const auto*

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../clang-tidy/readability/UseStdMinMaxCheck.cpp       | 10 +++++-----
 .../clang-tidy/readability/UseStdMinMaxCheck.h         |  4 +---
 2 files changed, 6 insertions(+), 8 deletions(-)

diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
index 9d740db05001e..aa8a43631eb6f 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
@@ -79,15 +79,15 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
   if (IfLocation.isMacroID() || ThenLocation.isMacroID())
     return;
 
-  const auto CreateReplacement = [&](bool useMax) {
-    std::string functionName = useMax ? "std::max" : "std::min";
+  const auto CreateReplacement = [&](bool UseMax) {
+    const auto *FunctionName = UseMax ? "std::max" : "std::min";
     const auto CondLhsStr = Lexer::getSourceText(
         Source.getExpansionRange(CondLhs->getSourceRange()), Source, LO);
     const auto CondRhsStr = Lexer::getSourceText(
         Source.getExpansionRange(CondRhs->getSourceRange()), Source, LO);
     const auto AssignLhsStr = Lexer::getSourceText(
         Source.getExpansionRange(AssignLhs->getSourceRange()), Source, LO);
-    return (AssignLhsStr + " = " + functionName + "(" + CondLhsStr + ", " +
+    return (AssignLhsStr + " = " + FunctionName + "(" + CondLhsStr + ", " +
             CondRhsStr + ");")
         .str();
   };
@@ -101,7 +101,7 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
     diag(IfLocation, "use `std::min` instead of `%0`")
         << OperatorStr
         << FixItHint::CreateReplacement(SourceRange(IfLocation, ThenLocation),
-                                        CreateReplacement(/*useMax=*/false))
+                                        CreateReplacement(/*UseMax=*/false))
         << IncludeInserter.createIncludeInsertion(
                Source.getFileID(If->getBeginLoc()), AlgorithmHeader);
 
@@ -120,7 +120,7 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
     diag(IfLocation, "use `std::max` instead of `%0`")
         << OperatorStr
         << FixItHint::CreateReplacement(SourceRange(IfLocation, ThenLocation),
-                                        CreateReplacement(/*useMax=*/true))
+                                        CreateReplacement(/*UseMax=*/true))
         << IncludeInserter.createIncludeInsertion(
                Source.getFileID(If->getBeginLoc()), AlgorithmHeader);
   }
diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.h b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.h
index 52b34fdbe2627..b4afe35696823 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.h
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.h
@@ -14,9 +14,7 @@
 namespace clang::tidy::readability {
 
 /// Replaces certain conditional statements with equivalent ``std::min`` or
-/// ``std::max`` expressions, improving readability and promoting the use of
-/// standard library functions.
-///
+/// ``std::max`` expressions.
 /// For the user-facing documentation see:
 /// http://clang.llvm.org/extra/clang-tidy/checks/readability/UseStdMinMax.html
 class UseStdMinMaxCheck : public ClangTidyCheck {

>From 0797e0c0f7a078de137e7e3e719afa9d70c061dd Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Sun, 21 Jan 2024 01:19:46 +0530
Subject: [PATCH 26/46] fixes

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../readability/UseStdMinMaxCheck.cpp         | 22 +++++---
 .../readability/UseStdMinMaxCheck.h           |  1 -
 .../checkers/readability/use-std-min-max.cpp  | 52 +++++++++----------
 3 files changed, 40 insertions(+), 35 deletions(-)

diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
index aa8a43631eb6f..a870235207fdd 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
@@ -17,6 +17,8 @@ using namespace clang::ast_matchers;
 
 namespace clang::tidy::readability {
 
+static const llvm::StringRef AlgorithmHeader("<algorithm>");
+
 UseStdMinMaxCheck::UseStdMinMaxCheck(StringRef Name, ClangTidyContext *Context)
     : ClangTidyCheck(Name, Context),
       IncludeInserter(Options.getLocalOrGlobal("IncludeStyle",
@@ -25,8 +27,6 @@ UseStdMinMaxCheck::UseStdMinMaxCheck(StringRef Name, ClangTidyContext *Context)
 
 void UseStdMinMaxCheck::storeOptions(ClangTidyOptions::OptionMap &Opts) {
   Options.store(Opts, "IncludeStyle", IncludeInserter.getStyle());
-  Options.store(Opts, "AlgorithmHeader",
-                Options.get("AlgorithmHeader", "<algorithm>"));
 }
 
 void UseStdMinMaxCheck::registerMatchers(MatchFinder *Finder) {
@@ -87,8 +87,10 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
         Source.getExpansionRange(CondRhs->getSourceRange()), Source, LO);
     const auto AssignLhsStr = Lexer::getSourceText(
         Source.getExpansionRange(AssignLhs->getSourceRange()), Source, LO);
-    return (AssignLhsStr + " = " + FunctionName + "(" + CondLhsStr + ", " +
-            CondRhsStr + ");")
+    const auto AssignLhsType =
+        AssignLhs->getType().getCanonicalType().getAsString();
+    return (AssignLhsStr + " = " + FunctionName + "<" + AssignLhsType + ">(" +
+            CondLhsStr + ", " + CondRhsStr + ");")
         .str();
   };
   const auto OperatorStr = BinaryOp->getOpcodeStr();
@@ -100,8 +102,10 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
         tidy::utils::areStatementsIdentical(CondRhs, AssignRhs, Context)))) {
     diag(IfLocation, "use `std::min` instead of `%0`")
         << OperatorStr
-        << FixItHint::CreateReplacement(SourceRange(IfLocation, ThenLocation),
-                                        CreateReplacement(/*UseMax=*/false))
+        << FixItHint::CreateReplacement(
+               SourceRange(IfLocation, Lexer::getLocForEndOfToken(
+                                           ThenLocation, 0, Source, LO)),
+               CreateReplacement(/*UseMax=*/false))
         << IncludeInserter.createIncludeInsertion(
                Source.getFileID(If->getBeginLoc()), AlgorithmHeader);
 
@@ -119,8 +123,10 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
                                                    Context)))) {
     diag(IfLocation, "use `std::max` instead of `%0`")
         << OperatorStr
-        << FixItHint::CreateReplacement(SourceRange(IfLocation, ThenLocation),
-                                        CreateReplacement(/*UseMax=*/true))
+        << FixItHint::CreateReplacement(
+               SourceRange(IfLocation, Lexer::getLocForEndOfToken(
+                                           ThenLocation, 0, Source, LO)),
+               CreateReplacement(/*UseMax=*/true))
         << IncludeInserter.createIncludeInsertion(
                Source.getFileID(If->getBeginLoc()), AlgorithmHeader);
   }
diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.h b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.h
index b4afe35696823..860e47794a99c 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.h
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.h
@@ -34,7 +34,6 @@ class UseStdMinMaxCheck : public ClangTidyCheck {
 
 private:
   utils::IncludeInserter IncludeInserter;
-  StringRef AlgorithmHeader;
 };
 
 } // namespace clang::tidy::readability
diff --git a/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp b/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
index 03971fc4c56cd..6249957e3076c 100644
--- a/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
+++ b/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
@@ -27,22 +27,22 @@ void foo() {
   MyClass obj;
 
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
-  // CHECK-FIXES: value1 = std::max(value1, value2);
+  // CHECK-FIXES: value1 = std::max<int>(value1, value2);
   if (value1 < value2)
     value1 = value2; 
 
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `<` [readability-use-std-min-max]
-  // CHECK-FIXES: value2 = std::min(value1, value2);
+  // CHECK-FIXES: value2 = std::min<int>(value1, value2);
   if (value1 < value2)
     value2 = value1; 
 
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `>` [readability-use-std-min-max]
-  // CHECK-FIXES: value2 = std::min(value2, value1);
+  // CHECK-FIXES: value2 = std::min<int>(value2, value1);
   if (value2 > value1)
     value2 = value1; 
 
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `>` [readability-use-std-min-max
-  // CHECK-FIXES: value1 = std::max(value2, value1);
+  // CHECK-FIXES: value1 = std::max<int>(value2, value1);
   if (value2 > value1)
     value1 = value2; 
 
@@ -51,92 +51,92 @@ void foo() {
     value1 = value2;
   
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
-  // CHECK-FIXES: value1 = std::max(value1, value4);
+  // CHECK-FIXES: value1 = std::max<int>(value1, value4);
   if(value1<value4)
     value1=value4; 
   
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `<` [readability-use-std-min-max]
-  // CHECK-FIXES: value3 = std::min(value1+value2, value3);
+  // CHECK-FIXES: value3 = std::min<int>(value1+value2, value3);
   if(value1+value2<value3)
     value3 = value1+value2; 
   
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
-  // CHECK-FIXES: value1 = std::max(value1, myConstexprMin(value2, value3));
+  // CHECK-FIXES: value1 = std::max<int>(value1, myConstexprMin(value2, value3));
   if (value1 < myConstexprMin(value2, value3))
     value1 = myConstexprMin(value2, value3); 
   
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `>` [readability-use-std-min-max]
-  // CHECK-FIXES: value1 = std::min(value1, myConstexprMax(value2, value3));
+  // CHECK-FIXES: value1 = std::min<int>(value1, myConstexprMax(value2, value3));
   if (value1 > myConstexprMax(value2, value3))
     value1 = myConstexprMax(value2, value3); 
   
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `<=` [readability-use-std-min-max]
-  // CHECK-FIXES: value2 = std::min(value1, value2);
+  // CHECK-FIXES: value2 = std::min<int>(value1, value2);
   if (value1 <= value2)
     value2 = value1; 
 
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `<=` [readability-use-std-min-max]
-  // CHECK-FIXES: value1 = std::max(value1, value2);
+  // CHECK-FIXES: value1 = std::max<int>(value1, value2);
   if (value1 <= value2)
     value1 = value2; 
 
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `>=` [readability-use-std-min-max]
-  // CHECK-FIXES: value1 = std::max(value2, value1);
+  // CHECK-FIXES: value1 = std::max<int>(value2, value1);
   if (value2 >= value1)
     value1 = value2; 
 
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `>=` [readability-use-std-min-max]
-  // CHECK-FIXES: value2 = std::min(value2, value1);
+  // CHECK-FIXES: value2 = std::min<int>(value2, value1);
   if (value2 >= value1)
     value2 = value1; 
   
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
-  // CHECK-FIXES: obj.member1 = std::max(obj.member1, obj.member2);
+  // CHECK-FIXES: obj.member1 = std::max<int>(obj.member1, obj.member2);
   if (obj.member1 < obj.member2)
     obj.member1 = obj.member2; 
 
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `<` [readability-use-std-min-max]
-  // CHECK-FIXES: obj.member2 = std::min(obj.member1, obj.member2);
+  // CHECK-FIXES: obj.member2 = std::min<int>(obj.member1, obj.member2);
   if (obj.member1 < obj.member2)
     obj.member2 = obj.member1; 
 
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `>` [readability-use-std-min-max]
-  // CHECK-FIXES: obj.member2 = std::min(obj.member2, obj.member1);
+  // CHECK-FIXES: obj.member2 = std::min<int>(obj.member2, obj.member1);
   if (obj.member2 > obj.member1)
     obj.member2 = obj.member1; 
 
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `>` [readability-use-std-min-max]
-  // CHECK-FIXES: obj.member1 = std::max(obj.member2, obj.member1);
+  // CHECK-FIXES: obj.member1 = std::max<int>(obj.member2, obj.member1);
   if (obj.member2 > obj.member1)
     obj.member1 = obj.member2; 
   
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
-  // CHECK-FIXES: obj.member1 = std::max(obj.member1, value4);
+  // CHECK-FIXES: obj.member1 = std::max<int>(obj.member1, value4);
   if (obj.member1 < value4)
     obj.member1 = value4; 
   
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `<` [readability-use-std-min-max]
-  // CHECK-FIXES: value3 = std::min(obj.member1 + value2, value3);
+  // CHECK-FIXES: value3 = std::min<int>(obj.member1 + value2, value3);
   if (obj.member1 + value2 < value3)
     value3 = obj.member1 + value2; 
   
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `<=` [readability-use-std-min-max]
-  // CHECK-FIXES: obj.member2 = std::min(value1, obj.member2);
+  // CHECK-FIXES: obj.member2 = std::min<int>(value1, obj.member2);
   if (value1 <= obj.member2)
     obj.member2 = value1; 
 
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `<=` [readability-use-std-min-max]
-  // CHECK-FIXES: value1 = std::max(value1, obj.member2);
+  // CHECK-FIXES: value1 = std::max<int>(value1, obj.member2);
   if (value1 <= obj.member2)
     value1 = obj.member2; 
 
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `>=` [readability-use-std-min-max]
-  // CHECK-FIXES: value1 = std::max(obj.member2, value1);
+  // CHECK-FIXES: value1 = std::max<int>(obj.member2, value1);
   if (obj.member2 >= value1)
     value1 = obj.member2; 
 
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `>=` [readability-use-std-min-max]
-  // CHECK-FIXES: obj.member2 = std::min(obj.member2, value1);
+  // CHECK-FIXES: obj.member2 = std::min<int>(obj.member2, value1);
   if (obj.member2 >= value1)
     obj.member2 = value1; 
   
@@ -144,10 +144,10 @@ void foo() {
   if (MY_MACRO_MIN(value1, value2) < value3)
     value3 = MY_MACRO_MIN(value1, value2); 
   
-  // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `<` [readability-use-std-min-max]
-  // CHECK-FIXES: value2 = std::min(value1, value2);
-  if (value1 < value2){
-    value2 = value1; 
+  // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
+  // CHECK-FIXES: value4 = std::max<short>(value4, value2);
+  if (value4 < value2){
+    value4 = value2; 
   }
 
   // No suggestion needed here

>From c6028b0ddd8ce1ace6e6c3f14244e889250a8e34 Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Sun, 21 Jan 2024 21:26:25 +0530
Subject: [PATCH 27/46] few nits

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../readability/UseStdMinMaxCheck.cpp         | 29 +++++++-------
 .../checkers/readability/use-std-min-max.cpp  | 40 +++++++++----------
 2 files changed, 34 insertions(+), 35 deletions(-)

diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
index a870235207fdd..6e39ebeda2b2c 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
@@ -11,7 +11,6 @@
 #include "clang/AST/ASTContext.h"
 #include "clang/ASTMatchers/ASTMatchFinder.h"
 #include "clang/Lex/Preprocessor.h"
-#include <optional>
 
 using namespace clang::ast_matchers;
 
@@ -38,11 +37,11 @@ void UseStdMinMaxCheck::registerMatchers(MatchFinder *Finder) {
           hasThen(anyOf(stmt(binaryOperator(hasOperatorName("="),
                                             hasLHS(expr().bind("AssignLhs")),
                                             hasRHS(expr().bind("AssignRhs")))),
-                        compoundStmt(has(binaryOperator(
+                        compoundStmt(statementCountIs(1),
+                                     has(binaryOperator(
                                          hasOperatorName("="),
                                          hasLHS(expr().bind("AssignLhs")),
-                                         hasRHS(expr().bind("AssignRhs")))))
-                            .bind("compound"))))
+                                         hasRHS(expr().bind("AssignRhs"))))))))
           .bind("if"),
       this);
 }
@@ -59,7 +58,6 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
   const auto *AssignLhs = Result.Nodes.getNodeAs<Expr>("AssignLhs");
   const auto *AssignRhs = Result.Nodes.getNodeAs<Expr>("AssignRhs");
   const auto *If = Result.Nodes.getNodeAs<IfStmt>("if");
-  const auto *Compound = Result.Nodes.getNodeAs<CompoundStmt>("compound");
   const auto &Context = *Result.Context;
   const auto &LO = Context.getLangOpts();
   const SourceManager &Source = Context.getSourceManager();
@@ -68,11 +66,6 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
   if (!BinaryOp || If->hasElseStorage())
     return;
 
-  if (Compound) {
-    if (Compound->size() > 1)
-      return;
-  }
-
   const SourceLocation IfLocation = If->getIfLoc();
   const SourceLocation ThenLocation = If->getEndLoc();
 
@@ -87,11 +80,17 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
         Source.getExpansionRange(CondRhs->getSourceRange()), Source, LO);
     const auto AssignLhsStr = Lexer::getSourceText(
         Source.getExpansionRange(AssignLhs->getSourceRange()), Source, LO);
-    const auto AssignLhsType =
-        AssignLhs->getType().getCanonicalType().getAsString();
-    return (AssignLhsStr + " = " + FunctionName + "<" + AssignLhsType + ">(" +
-            CondLhsStr + ", " + CondRhsStr + ");")
-        .str();
+    if (CondLhs->getType() != CondRhs->getType()) {
+      return (AssignLhsStr + " = " + FunctionName + "<" +
+              AssignLhs->getType().getAsString() + ">(" + CondLhsStr + ", " +
+              CondRhsStr + ");")
+          .str();
+    } else {
+      return (AssignLhsStr + " = " + FunctionName + "(" + CondLhsStr + ", " +
+              CondRhsStr + ");")
+          .str();
+    }
+    
   };
   const auto OperatorStr = BinaryOp->getOpcodeStr();
   if (((BinaryOp->getOpcode() == BO_LT || BinaryOp->getOpcode() == BO_LE) &&
diff --git a/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp b/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
index 6249957e3076c..cdb169fd42c6f 100644
--- a/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
+++ b/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
@@ -27,22 +27,22 @@ void foo() {
   MyClass obj;
 
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
-  // CHECK-FIXES: value1 = std::max<int>(value1, value2);
+  // CHECK-FIXES: value1 = std::max(value1, value2);
   if (value1 < value2)
     value1 = value2; 
 
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `<` [readability-use-std-min-max]
-  // CHECK-FIXES: value2 = std::min<int>(value1, value2);
+  // CHECK-FIXES: value2 = std::min(value1, value2);
   if (value1 < value2)
     value2 = value1; 
 
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `>` [readability-use-std-min-max]
-  // CHECK-FIXES: value2 = std::min<int>(value2, value1);
+  // CHECK-FIXES: value2 = std::min(value2, value1);
   if (value2 > value1)
     value2 = value1; 
 
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `>` [readability-use-std-min-max
-  // CHECK-FIXES: value1 = std::max<int>(value2, value1);
+  // CHECK-FIXES: value1 = std::max(value2, value1);
   if (value2 > value1)
     value1 = value2; 
 
@@ -56,57 +56,57 @@ void foo() {
     value1=value4; 
   
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `<` [readability-use-std-min-max]
-  // CHECK-FIXES: value3 = std::min<int>(value1+value2, value3);
+  // CHECK-FIXES: value3 = std::min(value1+value2, value3);
   if(value1+value2<value3)
     value3 = value1+value2; 
   
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
-  // CHECK-FIXES: value1 = std::max<int>(value1, myConstexprMin(value2, value3));
+  // CHECK-FIXES: value1 = std::max(value1, myConstexprMin(value2, value3));
   if (value1 < myConstexprMin(value2, value3))
     value1 = myConstexprMin(value2, value3); 
   
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `>` [readability-use-std-min-max]
-  // CHECK-FIXES: value1 = std::min<int>(value1, myConstexprMax(value2, value3));
+  // CHECK-FIXES: value1 = std::min(value1, myConstexprMax(value2, value3));
   if (value1 > myConstexprMax(value2, value3))
     value1 = myConstexprMax(value2, value3); 
   
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `<=` [readability-use-std-min-max]
-  // CHECK-FIXES: value2 = std::min<int>(value1, value2);
+  // CHECK-FIXES: value2 = std::min(value1, value2);
   if (value1 <= value2)
     value2 = value1; 
 
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `<=` [readability-use-std-min-max]
-  // CHECK-FIXES: value1 = std::max<int>(value1, value2);
+  // CHECK-FIXES: value1 = std::max(value1, value2);
   if (value1 <= value2)
     value1 = value2; 
 
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `>=` [readability-use-std-min-max]
-  // CHECK-FIXES: value1 = std::max<int>(value2, value1);
+  // CHECK-FIXES: value1 = std::max(value2, value1);
   if (value2 >= value1)
     value1 = value2; 
 
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `>=` [readability-use-std-min-max]
-  // CHECK-FIXES: value2 = std::min<int>(value2, value1);
+  // CHECK-FIXES: value2 = std::min(value2, value1);
   if (value2 >= value1)
     value2 = value1; 
   
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
-  // CHECK-FIXES: obj.member1 = std::max<int>(obj.member1, obj.member2);
+  // CHECK-FIXES: obj.member1 = std::max(obj.member1, obj.member2);
   if (obj.member1 < obj.member2)
     obj.member1 = obj.member2; 
 
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `<` [readability-use-std-min-max]
-  // CHECK-FIXES: obj.member2 = std::min<int>(obj.member1, obj.member2);
+  // CHECK-FIXES: obj.member2 = std::min(obj.member1, obj.member2);
   if (obj.member1 < obj.member2)
     obj.member2 = obj.member1; 
 
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `>` [readability-use-std-min-max]
-  // CHECK-FIXES: obj.member2 = std::min<int>(obj.member2, obj.member1);
+  // CHECK-FIXES: obj.member2 = std::min(obj.member2, obj.member1);
   if (obj.member2 > obj.member1)
     obj.member2 = obj.member1; 
 
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `>` [readability-use-std-min-max]
-  // CHECK-FIXES: obj.member1 = std::max<int>(obj.member2, obj.member1);
+  // CHECK-FIXES: obj.member1 = std::max(obj.member2, obj.member1);
   if (obj.member2 > obj.member1)
     obj.member1 = obj.member2; 
   
@@ -116,27 +116,27 @@ void foo() {
     obj.member1 = value4; 
   
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `<` [readability-use-std-min-max]
-  // CHECK-FIXES: value3 = std::min<int>(obj.member1 + value2, value3);
+  // CHECK-FIXES: value3 = std::min(obj.member1 + value2, value3);
   if (obj.member1 + value2 < value3)
     value3 = obj.member1 + value2; 
   
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `<=` [readability-use-std-min-max]
-  // CHECK-FIXES: obj.member2 = std::min<int>(value1, obj.member2);
+  // CHECK-FIXES: obj.member2 = std::min(value1, obj.member2);
   if (value1 <= obj.member2)
     obj.member2 = value1; 
 
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `<=` [readability-use-std-min-max]
-  // CHECK-FIXES: value1 = std::max<int>(value1, obj.member2);
+  // CHECK-FIXES: value1 = std::max(value1, obj.member2);
   if (value1 <= obj.member2)
     value1 = obj.member2; 
 
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `>=` [readability-use-std-min-max]
-  // CHECK-FIXES: value1 = std::max<int>(obj.member2, value1);
+  // CHECK-FIXES: value1 = std::max(obj.member2, value1);
   if (obj.member2 >= value1)
     value1 = obj.member2; 
 
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `>=` [readability-use-std-min-max]
-  // CHECK-FIXES: obj.member2 = std::min<int>(obj.member2, value1);
+  // CHECK-FIXES: obj.member2 = std::min(obj.member2, value1);
   if (obj.member2 >= value1)
     obj.member2 = value1; 
   

>From 6acf645970379656373f997a37583cce1ae5e254 Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Sun, 21 Jan 2024 21:32:46 +0530
Subject: [PATCH 28/46] formatted the code

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp | 1 -
 1 file changed, 1 deletion(-)

diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
index 6e39ebeda2b2c..4cd7898efb82a 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
@@ -90,7 +90,6 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
               CondRhsStr + ");")
           .str();
     }
-    
   };
   const auto OperatorStr = BinaryOp->getOpcodeStr();
   if (((BinaryOp->getOpcode() == BO_LT || BinaryOp->getOpcode() == BO_LE) &&

>From 0eb4aca8023104d228427205e762680737d7b412 Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Mon, 22 Jan 2024 03:23:27 +0530
Subject: [PATCH 29/46] extra checks

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../clang-tidy/readability/UseStdMinMaxCheck.cpp   |  2 +-
 .../checkers/readability/use-std-min-max.cpp       | 14 ++++++++++++++
 2 files changed, 15 insertions(+), 1 deletion(-)

diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
index 4cd7898efb82a..142425f90e234 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
@@ -30,7 +30,7 @@ void UseStdMinMaxCheck::storeOptions(ClangTidyOptions::OptionMap &Opts) {
 
 void UseStdMinMaxCheck::registerMatchers(MatchFinder *Finder) {
   Finder->addMatcher(
-      ifStmt(
+      ifStmt(unless(hasAncestor(ifStmt())),
           hasCondition(binaryOperator(hasAnyOperatorName("<", ">", "<=", ">="),
                                       hasLHS(expr().bind("CondLhs")),
                                       hasRHS(expr().bind("CondRhs")))),
diff --git a/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp b/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
index cdb169fd42c6f..97b9b9924700b 100644
--- a/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
+++ b/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
@@ -172,4 +172,18 @@ void foo() {
 
   // No suggestion needed here
   MY_IF_MACRO(value1 < value2, value1 = value2;)
+
+  // No suggestion needed here
+  if(value1<value2){
+    value1 = value2;
+  }
+  else if(value1>value2){
+    value2 = value1;
+  }
+
+  // No suggestions needed here
+  if(value1 == value2){
+    if(value1<value3)
+      value1 = value3;
+  }
 }
\ No newline at end of file

>From d5b8dc25598b516d81f6ab49c916f2fd41ade6ca Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Mon, 22 Jan 2024 16:13:59 +0530
Subject: [PATCH 30/46] ensure if has no else if

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../readability/UseStdMinMaxCheck.cpp           | 12 ++++++++----
 .../checkers/readability/use-std-min-max.cpp    | 17 ++++++++++++++++-
 2 files changed, 24 insertions(+), 5 deletions(-)

diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
index 142425f90e234..1bc09d8563602 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
@@ -30,7 +30,8 @@ void UseStdMinMaxCheck::storeOptions(ClangTidyOptions::OptionMap &Opts) {
 
 void UseStdMinMaxCheck::registerMatchers(MatchFinder *Finder) {
   Finder->addMatcher(
-      ifStmt(unless(hasAncestor(ifStmt())),
+      ifStmt(
+          stmt().bind("if"),
           hasCondition(binaryOperator(hasAnyOperatorName("<", ">", "<=", ">="),
                                       hasLHS(expr().bind("CondLhs")),
                                       hasRHS(expr().bind("CondRhs")))),
@@ -41,8 +42,9 @@ void UseStdMinMaxCheck::registerMatchers(MatchFinder *Finder) {
                                      has(binaryOperator(
                                          hasOperatorName("="),
                                          hasLHS(expr().bind("AssignLhs")),
-                                         hasRHS(expr().bind("AssignRhs"))))))))
-          .bind("if"),
+                                         hasRHS(expr().bind("AssignRhs"))))))),
+          hasParent(stmt(unless(ifStmt(hasElse(
+              equalsBoundNode("if"))))))), // Ensure `if` has no `else if`
       this);
 }
 
@@ -63,12 +65,14 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
   const SourceManager &Source = Context.getSourceManager();
 
   const auto *BinaryOp = dyn_cast<BinaryOperator>(If->getCond());
-  if (!BinaryOp || If->hasElseStorage())
+  // Ignore `if` statements with `else`
+  if (If->hasElseStorage())
     return;
 
   const SourceLocation IfLocation = If->getIfLoc();
   const SourceLocation ThenLocation = If->getEndLoc();
 
+  // Ignore Macros
   if (IfLocation.isMacroID() || ThenLocation.isMacroID())
     return;
 
diff --git a/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp b/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
index 97b9b9924700b..4f36b1dedcbd4 100644
--- a/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
+++ b/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
@@ -181,9 +181,24 @@ void foo() {
     value2 = value1;
   }
 
-  // No suggestions needed here
+  // CHECK-MESSAGES: :[[@LINE+3]]:5: warning: use `std::max` instead of `<` [readability-use-std-min-max]
+  // CHECK-FIXES: value1 = std::max(value1, value3);
   if(value1 == value2){
     if(value1<value3)
       value1 = value3;
   }
+
+  // CHECK-MESSAGES: :[[@LINE+5]]:7: warning: use `std::max` instead of `<` [readability-use-std-min-max]
+  // CHECK-FIXES: value1 = std::max<int>(value1, value4);
+  if(value1 == value2){
+    if(value2 == value3){
+      value3+=1;
+      if(value1<value4){
+        value1 = value4;
+      }
+    }
+    else if(value3>value2){
+      value2 = value3;
+    }
+  }
 }
\ No newline at end of file

>From a92160ca6cb61f384609c7dd894bd78821c99921 Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Mon, 22 Jan 2024 23:51:27 +0530
Subject: [PATCH 31/46] correct style issue

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../readability/UseStdMinMaxCheck.cpp         | 61 ++++++++--------
 .../checks/readability/use-std-min-max.rst    | 69 ++++++++++---------
 2 files changed, 64 insertions(+), 66 deletions(-)

diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
index 1bc09d8563602..a220ad36df271 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
@@ -29,20 +29,21 @@ void UseStdMinMaxCheck::storeOptions(ClangTidyOptions::OptionMap &Opts) {
 }
 
 void UseStdMinMaxCheck::registerMatchers(MatchFinder *Finder) {
+  auto AssignOperator =
+      binaryOperator(hasOperatorName("="), hasLHS(expr().bind("AssignLhs")),
+                     hasRHS(expr().bind("AssignRhs")));
+
   Finder->addMatcher(
       ifStmt(
           stmt().bind("if"),
+          unless(hasElse(stmt())), // Ensure `if` has no `else`
           hasCondition(binaryOperator(hasAnyOperatorName("<", ">", "<=", ">="),
                                       hasLHS(expr().bind("CondLhs")),
-                                      hasRHS(expr().bind("CondRhs")))),
-          hasThen(anyOf(stmt(binaryOperator(hasOperatorName("="),
-                                            hasLHS(expr().bind("AssignLhs")),
-                                            hasRHS(expr().bind("AssignRhs")))),
-                        compoundStmt(statementCountIs(1),
-                                     has(binaryOperator(
-                                         hasOperatorName("="),
-                                         hasLHS(expr().bind("AssignLhs")),
-                                         hasRHS(expr().bind("AssignRhs"))))))),
+                                      hasRHS(expr().bind("CondRhs")))
+                           .bind("binaryOp")),
+          hasThen(
+              anyOf(stmt(AssignOperator),
+                    compoundStmt(statementCountIs(1), has(AssignOperator)))),
           hasParent(stmt(unless(ifStmt(hasElse(
               equalsBoundNode("if"))))))), // Ensure `if` has no `else if`
       this);
@@ -55,20 +56,11 @@ void UseStdMinMaxCheck::registerPPCallbacks(const SourceManager &SM,
 }
 
 void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
-  const auto *CondLhs = Result.Nodes.getNodeAs<Expr>("CondLhs");
-  const auto *CondRhs = Result.Nodes.getNodeAs<Expr>("CondRhs");
-  const auto *AssignLhs = Result.Nodes.getNodeAs<Expr>("AssignLhs");
-  const auto *AssignRhs = Result.Nodes.getNodeAs<Expr>("AssignRhs");
   const auto *If = Result.Nodes.getNodeAs<IfStmt>("if");
   const auto &Context = *Result.Context;
   const auto &LO = Context.getLangOpts();
   const SourceManager &Source = Context.getSourceManager();
 
-  const auto *BinaryOp = dyn_cast<BinaryOperator>(If->getCond());
-  // Ignore `if` statements with `else`
-  if (If->hasElseStorage())
-    return;
-
   const SourceLocation IfLocation = If->getIfLoc();
   const SourceLocation ThenLocation = If->getEndLoc();
 
@@ -76,6 +68,11 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
   if (IfLocation.isMacroID() || ThenLocation.isMacroID())
     return;
 
+  const auto *CondLhs = Result.Nodes.getNodeAs<Expr>("CondLhs");
+  const auto *CondRhs = Result.Nodes.getNodeAs<Expr>("CondRhs");
+  const auto *AssignLhs = Result.Nodes.getNodeAs<Expr>("AssignLhs");
+  const auto *AssignRhs = Result.Nodes.getNodeAs<Expr>("AssignRhs");
+
   const auto CreateReplacement = [&](bool UseMax) {
     const auto *FunctionName = UseMax ? "std::max" : "std::min";
     const auto CondLhsStr = Lexer::getSourceText(
@@ -84,22 +81,20 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
         Source.getExpansionRange(CondRhs->getSourceRange()), Source, LO);
     const auto AssignLhsStr = Lexer::getSourceText(
         Source.getExpansionRange(AssignLhs->getSourceRange()), Source, LO);
-    if (CondLhs->getType() != CondRhs->getType()) {
-      return (AssignLhsStr + " = " + FunctionName + "<" +
-              AssignLhs->getType().getAsString() + ">(" + CondLhsStr + ", " +
-              CondRhsStr + ");")
-          .str();
-    } else {
-      return (AssignLhsStr + " = " + FunctionName + "(" + CondLhsStr + ", " +
-              CondRhsStr + ");")
-          .str();
-    }
+    return (AssignLhsStr + " = " + FunctionName +
+            ((CondLhs->getType() != CondRhs->getType())
+                 ? "<" + AssignLhs->getType().getAsString() + ">("
+                 : "(") +
+            CondLhsStr + ", " + CondRhsStr + ");")
+        .str();
   };
+  const auto *BinaryOp = Result.Nodes.getNodeAs<BinaryOperator>("binaryOp");
+  const auto BinaryOpcode = BinaryOp->getOpcode();
   const auto OperatorStr = BinaryOp->getOpcodeStr();
-  if (((BinaryOp->getOpcode() == BO_LT || BinaryOp->getOpcode() == BO_LE) &&
+  if (((BinaryOpcode == BO_LT || BinaryOpcode == BO_LE) &&
        (tidy::utils::areStatementsIdentical(CondLhs, AssignRhs, Context) &&
         tidy::utils::areStatementsIdentical(CondRhs, AssignLhs, Context))) ||
-      ((BinaryOp->getOpcode() == BO_GT || BinaryOp->getOpcode() == BO_GE) &&
+      ((BinaryOpcode == BO_GT || BinaryOpcode == BO_GE) &&
        (tidy::utils::areStatementsIdentical(CondLhs, AssignLhs, Context) &&
         tidy::utils::areStatementsIdentical(CondRhs, AssignRhs, Context)))) {
     diag(IfLocation, "use `std::min` instead of `%0`")
@@ -111,14 +106,12 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
         << IncludeInserter.createIncludeInsertion(
                Source.getFileID(If->getBeginLoc()), AlgorithmHeader);
 
-  } else if (((BinaryOp->getOpcode() == BO_LT ||
-               BinaryOp->getOpcode() == BO_LE) &&
+  } else if (((BinaryOpcode == BO_LT || BinaryOpcode == BO_LE) &&
               (tidy::utils::areStatementsIdentical(CondLhs, AssignLhs,
                                                    Context) &&
                tidy::utils::areStatementsIdentical(CondRhs, AssignRhs,
                                                    Context))) ||
-             ((BinaryOp->getOpcode() == BO_GT ||
-               BinaryOp->getOpcode() == BO_GE) &&
+             ((BinaryOpcode == BO_GT || BinaryOpcode == BO_GE) &&
               (tidy::utils::areStatementsIdentical(CondLhs, AssignRhs,
                                                    Context) &&
                tidy::utils::areStatementsIdentical(CondRhs, AssignLhs,
diff --git a/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst b/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst
index 2cf6a58552cde..5b4ea9fbcbce2 100644
--- a/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst
+++ b/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst
@@ -1,32 +1,37 @@
-.. title:: clang-tidy - readability-use-std-min-max
-
-readability-use-std-min-max
-===========================
-
-Replaces certain conditional statements with equivalent ``std::min`` or
-``std::max`` expressions. Note: This may impact
-performance in critical code due to potential additional stores compared
-to the original if statement.
-
-
-Examples:
-
-Before:
-
-.. code-block:: c++
-
-  void foo() {
-    int a = 2, b = 3;
-    if (a < b)
-      a = b;
-  }
-
-
-After:
-
-.. code-block:: c++
-
-  void foo() {
-    int a = 2, b = 3;
-    a = std::max(a, b);
-  }
+..title::clang - tidy - readability - use - std - min -
+        max
+
+            readability -
+        use - std - min - max ==
+    == == == == == == == == == == == ==
+    =
+
+        Replaces certain conditional statements with equivalent ``std::min`` or
+``std::max`` expressions
+                .Note
+    : This may impact performance in critical code due to potential additional stores compared to the
+          original if statement
+                .
+
+      Before :
+
+                ..code -
+            block::c++
+
+            void
+            foo() {
+  int a = 2, b = 3;
+  if (a < b)
+    a = b;
+}
+
+After :
+
+        ..code -
+    block::c++
+
+    void
+    foo() {
+  int a = 2, b = 3;
+  a = std::max(a, b);
+}

>From 5eafb596916d8673761101a846f7d22e5c6b2b63 Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Tue, 23 Jan 2024 00:00:34 +0530
Subject: [PATCH 32/46] correct docs

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../checks/readability/use-std-min-max.rst    | 66 ++++++++-----------
 1 file changed, 29 insertions(+), 37 deletions(-)

diff --git a/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst b/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst
index 5b4ea9fbcbce2..ee8f3c6f0629c 100644
--- a/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst
+++ b/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst
@@ -1,37 +1,29 @@
-..title::clang - tidy - readability - use - std - min -
-        max
-
-            readability -
-        use - std - min - max ==
-    == == == == == == == == == == == ==
-    =
-
-        Replaces certain conditional statements with equivalent ``std::min`` or
-``std::max`` expressions
-                .Note
-    : This may impact performance in critical code due to potential additional stores compared to the
-          original if statement
-                .
-
-      Before :
-
-                ..code -
-            block::c++
-
-            void
-            foo() {
-  int a = 2, b = 3;
-  if (a < b)
-    a = b;
-}
-
-After :
-
-        ..code -
-    block::c++
-
-    void
-    foo() {
-  int a = 2, b = 3;
-  a = std::max(a, b);
-}
+.. title:: clang-tidy - readability-use-std-min-max
+
+readability-use-std-min-max
+===========================
+
+Replaces certain conditional statements with equivalent ``std::min`` or
+``std::max`` expressions. Note: This may impact
+performance in critical code due to potential additional stores compared
+to the original if statement.
+
+Before:
+
+.. code-block:: c++
+
+  void foo() {
+    int a = 2, b = 3;
+    if (a < b)
+      a = b;
+  }
+
+
+After:
+
+.. code-block:: c++
+
+  void foo() {
+    int a = 2, b = 3;
+    a = std::max(a, b);
+  }

>From 26bfbdc2928516d448085022122cfbac13f71c5d Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Tue, 23 Jan 2024 00:12:09 +0530
Subject: [PATCH 33/46] correct docs

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../clang-tidy/checks/readability/use-std-min-max.rst     | 8 ++++----
 1 file changed, 4 insertions(+), 4 deletions(-)

diff --git a/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst b/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst
index ee8f3c6f0629c..73712bdba83b7 100644
--- a/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst
+++ b/clang-tools-extra/docs/clang-tidy/checks/readability/use-std-min-max.rst
@@ -3,10 +3,10 @@
 readability-use-std-min-max
 ===========================
 
-Replaces certain conditional statements with equivalent ``std::min`` or
-``std::max`` expressions. Note: This may impact
-performance in critical code due to potential additional stores compared
-to the original if statement.
+Replaces certain conditional statements with equivalent calls to
+``std::min`` or ``std::max``.
+Note: This may impact performance in critical code due to potential
+additional stores compared to the original if statement.
 
 Before:
 

>From 57bccd6ed654550698bb22100f0919362b1dd7ac Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Tue, 23 Jan 2024 01:01:17 +0530
Subject: [PATCH 34/46] static functions

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../readability/UseStdMinMaxCheck.cpp         | 116 +++++++++---------
 .../readability/UseStdMinMaxCheck.h           |   4 +-
 clang-tools-extra/docs/ReleaseNotes.rst       |   4 +-
 3 files changed, 65 insertions(+), 59 deletions(-)

diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
index a220ad36df271..3d115268704c6 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
@@ -18,6 +18,45 @@ namespace clang::tidy::readability {
 
 static const llvm::StringRef AlgorithmHeader("<algorithm>");
 
+static bool MinCondition(const BinaryOperator::Opcode &Op,const Expr *CondLhs,const Expr *CondRhs,const Expr *AssignLhs,const Expr *AssignRhs,const ASTContext &Context){
+  return ((Op == BO_LT || Op == BO_LE) &&
+       (tidy::utils::areStatementsIdentical(CondLhs, AssignRhs, Context) &&
+        tidy::utils::areStatementsIdentical(CondRhs, AssignLhs, Context))) || 
+        ((Op == BO_GT || Op == BO_GE) && 
+        (tidy::utils::areStatementsIdentical(CondLhs, AssignLhs, Context) &&
+        tidy::utils::areStatementsIdentical(CondRhs, AssignRhs, Context)));
+}
+
+static bool MaxCondition(const BinaryOperator::Opcode &Op,const Expr *CondLhs,const Expr *CondRhs,const Expr *AssignLhs,const Expr *AssignRhs,const ASTContext &Context){
+  return ((Op == BO_LT || Op == BO_LE) &&
+              (tidy::utils::areStatementsIdentical(CondLhs, AssignLhs,
+                                                   Context) &&
+               tidy::utils::areStatementsIdentical(CondRhs, AssignRhs,
+                                                   Context))) ||
+             ((Op == BO_GT || Op == BO_GE) &&
+              (tidy::utils::areStatementsIdentical(CondLhs, AssignRhs,
+                                                   Context) &&
+               tidy::utils::areStatementsIdentical(CondRhs, AssignLhs,
+                                                   Context)));
+}
+
+static std::string CreateReplacement(const bool UseMax,const BinaryOperator::Opcode &Op,const Expr *CondLhs,const Expr *CondRhs,const Expr *AssignLhs,const ASTContext &Context,const SourceManager &Source,const LangOptions &LO){
+  const auto *FunctionName = UseMax ? "std::max" : "std::min";
+  const auto CondLhsStr = Lexer::getSourceText(
+      Source.getExpansionRange(CondLhs->getSourceRange()), Source, LO);
+  const auto CondRhsStr = Lexer::getSourceText(
+      Source.getExpansionRange(CondRhs->getSourceRange()), Source, LO);
+  const auto AssignLhsStr = Lexer::getSourceText(
+      Source.getExpansionRange(AssignLhs->getSourceRange()), Source, LO);
+  return (AssignLhsStr + " = " + FunctionName +
+          ((CondLhs->getType() != CondRhs->getType())
+               ? "<" + AssignLhs->getType().getAsString() + ">("
+               : "(") +
+          CondLhsStr + ", " + CondRhsStr + ");")
+      .str();
+}
+
+
 UseStdMinMaxCheck::UseStdMinMaxCheck(StringRef Name, ClangTidyContext *Context)
     : ClangTidyCheck(Name, Context),
       IncludeInserter(Options.getLocalOrGlobal("IncludeStyle",
@@ -59,71 +98,38 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
   const auto *If = Result.Nodes.getNodeAs<IfStmt>("if");
   const auto &Context = *Result.Context;
   const auto &LO = Context.getLangOpts();
-  const SourceManager &Source = Context.getSourceManager();
-
-  const SourceLocation IfLocation = If->getIfLoc();
-  const SourceLocation ThenLocation = If->getEndLoc();
-
-  // Ignore Macros
-  if (IfLocation.isMacroID() || ThenLocation.isMacroID())
-    return;
-
   const auto *CondLhs = Result.Nodes.getNodeAs<Expr>("CondLhs");
   const auto *CondRhs = Result.Nodes.getNodeAs<Expr>("CondRhs");
   const auto *AssignLhs = Result.Nodes.getNodeAs<Expr>("AssignLhs");
   const auto *AssignRhs = Result.Nodes.getNodeAs<Expr>("AssignRhs");
-
-  const auto CreateReplacement = [&](bool UseMax) {
-    const auto *FunctionName = UseMax ? "std::max" : "std::min";
-    const auto CondLhsStr = Lexer::getSourceText(
-        Source.getExpansionRange(CondLhs->getSourceRange()), Source, LO);
-    const auto CondRhsStr = Lexer::getSourceText(
-        Source.getExpansionRange(CondRhs->getSourceRange()), Source, LO);
-    const auto AssignLhsStr = Lexer::getSourceText(
-        Source.getExpansionRange(AssignLhs->getSourceRange()), Source, LO);
-    return (AssignLhsStr + " = " + FunctionName +
-            ((CondLhs->getType() != CondRhs->getType())
-                 ? "<" + AssignLhs->getType().getAsString() + ">("
-                 : "(") +
-            CondLhsStr + ", " + CondRhsStr + ");")
-        .str();
-  };
   const auto *BinaryOp = Result.Nodes.getNodeAs<BinaryOperator>("binaryOp");
   const auto BinaryOpcode = BinaryOp->getOpcode();
   const auto OperatorStr = BinaryOp->getOpcodeStr();
-  if (((BinaryOpcode == BO_LT || BinaryOpcode == BO_LE) &&
-       (tidy::utils::areStatementsIdentical(CondLhs, AssignRhs, Context) &&
-        tidy::utils::areStatementsIdentical(CondRhs, AssignLhs, Context))) ||
-      ((BinaryOpcode == BO_GT || BinaryOpcode == BO_GE) &&
-       (tidy::utils::areStatementsIdentical(CondLhs, AssignLhs, Context) &&
-        tidy::utils::areStatementsIdentical(CondRhs, AssignRhs, Context)))) {
-    diag(IfLocation, "use `std::min` instead of `%0`")
-        << OperatorStr
-        << FixItHint::CreateReplacement(
-               SourceRange(IfLocation, Lexer::getLocForEndOfToken(
-                                           ThenLocation, 0, Source, LO)),
-               CreateReplacement(/*UseMax=*/false))
-        << IncludeInserter.createIncludeInsertion(
-               Source.getFileID(If->getBeginLoc()), AlgorithmHeader);
+  const SourceManager &Source = Context.getSourceManager();
+  const SourceLocation IfLocation = If->getIfLoc();
+  const SourceLocation ThenLocation = If->getEndLoc();
 
-  } else if (((BinaryOpcode == BO_LT || BinaryOpcode == BO_LE) &&
-              (tidy::utils::areStatementsIdentical(CondLhs, AssignLhs,
-                                                   Context) &&
-               tidy::utils::areStatementsIdentical(CondRhs, AssignRhs,
-                                                   Context))) ||
-             ((BinaryOpcode == BO_GT || BinaryOpcode == BO_GE) &&
-              (tidy::utils::areStatementsIdentical(CondLhs, AssignRhs,
-                                                   Context) &&
-               tidy::utils::areStatementsIdentical(CondRhs, AssignLhs,
-                                                   Context)))) {
-    diag(IfLocation, "use `std::max` instead of `%0`")
+  // Ignore Macros
+  if (IfLocation.isMacroID() || ThenLocation.isMacroID())
+    return;
+  
+  auto ReplaceAndDiagnose = [&](bool UseMax) {
+    diag(IfLocation, "use `std::%0` instead of `%1`")
+        << (UseMax ? "max" : "min")
         << OperatorStr
         << FixItHint::CreateReplacement(
-               SourceRange(IfLocation, Lexer::getLocForEndOfToken(
-                                           ThenLocation, 0, Source, LO)),
-               CreateReplacement(/*UseMax=*/true))
-        << IncludeInserter.createIncludeInsertion(
-               Source.getFileID(If->getBeginLoc()), AlgorithmHeader);
+               SourceRange(IfLocation, Lexer::getLocForEndOfToken(ThenLocation, 0, Source, LO)),
+               CreateReplacement(UseMax, BinaryOpcode, CondLhs, CondRhs,
+                                 AssignLhs, Context, Source, LO))
+        << IncludeInserter.createIncludeInsertion(Source.getFileID(If->getBeginLoc()), AlgorithmHeader);
+  };
+
+  
+  if (MinCondition(BinaryOpcode,CondLhs,CondRhs,AssignLhs,AssignRhs,Context)) {
+    ReplaceAndDiagnose(/*UseMax=*/false);
+  } 
+  else if (MaxCondition(BinaryOpcode,CondLhs,CondRhs,AssignLhs,AssignRhs,Context)) {
+    ReplaceAndDiagnose(/*UseMax=*/true);
   }
 }
 
diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.h b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.h
index 860e47794a99c..d5c8da21b3017 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.h
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.h
@@ -13,8 +13,8 @@
 #include "../utils/IncludeInserter.h"
 namespace clang::tidy::readability {
 
-/// Replaces certain conditional statements with equivalent ``std::min`` or
-/// ``std::max`` expressions.
+/// Replaces certain conditional statements with equivalent calls to
+/// ``std::min`` or ``std::max``.
 /// For the user-facing documentation see:
 /// http://clang.llvm.org/extra/clang-tidy/checks/readability/UseStdMinMax.html
 class UseStdMinMaxCheck : public ClangTidyCheck {
diff --git a/clang-tools-extra/docs/ReleaseNotes.rst b/clang-tools-extra/docs/ReleaseNotes.rst
index e258f4978c45f..89a75cde3e60e 100644
--- a/clang-tools-extra/docs/ReleaseNotes.rst
+++ b/clang-tools-extra/docs/ReleaseNotes.rst
@@ -244,8 +244,8 @@ New checks
 - New :doc:`readability-use-std-min-max
   <clang-tidy/checks/readability/use-std-min-max>` check.
 
-  Replaces certain conditional statements with equivalent ``std::min`` or
-  ``std::max`` expressions.
+  Replaces certain conditional statements with equivalent calls to
+  ``std::min`` or ``std::max``.
 
 New check aliases
 ^^^^^^^^^^^^^^^^^

>From 61fd66a1c53d66b6087ff4df082e0eeb35e4a162 Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Tue, 23 Jan 2024 01:14:48 +0530
Subject: [PATCH 35/46] small fix

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../readability/UseStdMinMaxCheck.cpp         | 77 +++++++++++--------
 1 file changed, 46 insertions(+), 31 deletions(-)

diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
index 3d115268704c6..e45dcd4ef78c2 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
@@ -18,30 +18,44 @@ namespace clang::tidy::readability {
 
 static const llvm::StringRef AlgorithmHeader("<algorithm>");
 
-static bool MinCondition(const BinaryOperator::Opcode &Op,const Expr *CondLhs,const Expr *CondRhs,const Expr *AssignLhs,const Expr *AssignRhs,const ASTContext &Context){
-  return ((Op == BO_LT || Op == BO_LE) &&
-       (tidy::utils::areStatementsIdentical(CondLhs, AssignRhs, Context) &&
-        tidy::utils::areStatementsIdentical(CondRhs, AssignLhs, Context))) || 
-        ((Op == BO_GT || Op == BO_GE) && 
-        (tidy::utils::areStatementsIdentical(CondLhs, AssignLhs, Context) &&
-        tidy::utils::areStatementsIdentical(CondRhs, AssignRhs, Context)));
+static bool MinCondition(const BinaryOperator::Opcode &Op, const Expr *CondLhs,
+                         const Expr *CondRhs, const Expr *AssignLhs,
+                         const Expr *AssignRhs, const ASTContext &Context) {
+  if ((Op == BO_LT || Op == BO_LE) &&
+      (tidy::utils::areStatementsIdentical(CondLhs, AssignRhs, Context) &&
+       tidy::utils::areStatementsIdentical(CondRhs, AssignLhs, Context)))
+    return true;
+
+  if ((Op == BO_GT || Op == BO_GE) &&
+      (tidy::utils::areStatementsIdentical(CondLhs, AssignLhs, Context) &&
+       tidy::utils::areStatementsIdentical(CondRhs, AssignRhs, Context)))
+    return true;
+
+  return false;
 }
 
-static bool MaxCondition(const BinaryOperator::Opcode &Op,const Expr *CondLhs,const Expr *CondRhs,const Expr *AssignLhs,const Expr *AssignRhs,const ASTContext &Context){
-  return ((Op == BO_LT || Op == BO_LE) &&
-              (tidy::utils::areStatementsIdentical(CondLhs, AssignLhs,
-                                                   Context) &&
-               tidy::utils::areStatementsIdentical(CondRhs, AssignRhs,
-                                                   Context))) ||
-             ((Op == BO_GT || Op == BO_GE) &&
-              (tidy::utils::areStatementsIdentical(CondLhs, AssignRhs,
-                                                   Context) &&
-               tidy::utils::areStatementsIdentical(CondRhs, AssignLhs,
-                                                   Context)));
+static bool MaxCondition(const BinaryOperator::Opcode &Op, const Expr *CondLhs,
+                         const Expr *CondRhs, const Expr *AssignLhs,
+                         const Expr *AssignRhs, const ASTContext &Context) {
+  if ((Op == BO_LT || Op == BO_LE) &&
+      (tidy::utils::areStatementsIdentical(CondLhs, AssignLhs, Context) &&
+       tidy::utils::areStatementsIdentical(CondRhs, AssignRhs, Context)))
+    return true;
+
+  if ((Op == BO_GT || Op == BO_GE) &&
+      (tidy::utils::areStatementsIdentical(CondLhs, AssignRhs, Context) &&
+       tidy::utils::areStatementsIdentical(CondRhs, AssignLhs, Context)))
+    return true;
+
+  return false;
 }
 
-static std::string CreateReplacement(const bool UseMax,const BinaryOperator::Opcode &Op,const Expr *CondLhs,const Expr *CondRhs,const Expr *AssignLhs,const ASTContext &Context,const SourceManager &Source,const LangOptions &LO){
-  const auto *FunctionName = UseMax ? "std::max" : "std::min";
+static std::string
+CreateReplacement(const bool UseMax, const BinaryOperator::Opcode &Op,
+                  const Expr *CondLhs, const Expr *CondRhs,
+                  const Expr *AssignLhs, const ASTContext &Context,
+                  const SourceManager &Source, const LangOptions &LO,
+                  const StringRef &FunctionName) {
   const auto CondLhsStr = Lexer::getSourceText(
       Source.getExpansionRange(CondLhs->getSourceRange()), Source, LO);
   const auto CondRhsStr = Lexer::getSourceText(
@@ -56,7 +70,6 @@ static std::string CreateReplacement(const bool UseMax,const BinaryOperator::Opc
       .str();
 }
 
-
 UseStdMinMaxCheck::UseStdMinMaxCheck(StringRef Name, ClangTidyContext *Context)
     : ClangTidyCheck(Name, Context),
       IncludeInserter(Options.getLocalOrGlobal("IncludeStyle",
@@ -112,23 +125,25 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
   // Ignore Macros
   if (IfLocation.isMacroID() || ThenLocation.isMacroID())
     return;
-  
+
   auto ReplaceAndDiagnose = [&](bool UseMax) {
+    const llvm::StringRef FunctionName = UseMax ? "std::max" : "std::min";
     diag(IfLocation, "use `std::%0` instead of `%1`")
-        << (UseMax ? "max" : "min")
-        << OperatorStr
+        << (UseMax ? "max" : "min") << OperatorStr
         << FixItHint::CreateReplacement(
-               SourceRange(IfLocation, Lexer::getLocForEndOfToken(ThenLocation, 0, Source, LO)),
+               SourceRange(IfLocation, Lexer::getLocForEndOfToken(
+                                           ThenLocation, 0, Source, LO)),
                CreateReplacement(UseMax, BinaryOpcode, CondLhs, CondRhs,
-                                 AssignLhs, Context, Source, LO))
-        << IncludeInserter.createIncludeInsertion(Source.getFileID(If->getBeginLoc()), AlgorithmHeader);
+                                 AssignLhs, Context, Source, LO, FunctionName))
+        << IncludeInserter.createIncludeInsertion(
+               Source.getFileID(If->getBeginLoc()), AlgorithmHeader);
   };
 
-  
-  if (MinCondition(BinaryOpcode,CondLhs,CondRhs,AssignLhs,AssignRhs,Context)) {
+  if (MinCondition(BinaryOpcode, CondLhs, CondRhs, AssignLhs, AssignRhs,
+                   Context)) {
     ReplaceAndDiagnose(/*UseMax=*/false);
-  } 
-  else if (MaxCondition(BinaryOpcode,CondLhs,CondRhs,AssignLhs,AssignRhs,Context)) {
+  } else if (MaxCondition(BinaryOpcode, CondLhs, CondRhs, AssignLhs, AssignRhs,
+                          Context)) {
     ReplaceAndDiagnose(/*UseMax=*/true);
   }
 }

>From a841ebccf3401506cfe4c1b0553c4e94b762b804 Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Tue, 23 Jan 2024 19:27:24 +0530
Subject: [PATCH 36/46] style issues

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../readability/UseStdMinMaxCheck.cpp         | 38 +++++++++----------
 1 file changed, 18 insertions(+), 20 deletions(-)

diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
index e45dcd4ef78c2..50f4a6f297f86 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
@@ -18,7 +18,7 @@ namespace clang::tidy::readability {
 
 static const llvm::StringRef AlgorithmHeader("<algorithm>");
 
-static bool MinCondition(const BinaryOperator::Opcode &Op, const Expr *CondLhs,
+static bool minCondition(const BinaryOperator::Opcode Op, const Expr *CondLhs,
                          const Expr *CondRhs, const Expr *AssignLhs,
                          const Expr *AssignRhs, const ASTContext &Context) {
   if ((Op == BO_LT || Op == BO_LE) &&
@@ -34,7 +34,7 @@ static bool MinCondition(const BinaryOperator::Opcode &Op, const Expr *CondLhs,
   return false;
 }
 
-static bool MaxCondition(const BinaryOperator::Opcode &Op, const Expr *CondLhs,
+static bool maxCondition(const BinaryOperator::Opcode Op, const Expr *CondLhs,
                          const Expr *CondRhs, const Expr *AssignLhs,
                          const Expr *AssignRhs, const ASTContext &Context) {
   if ((Op == BO_LT || Op == BO_LE) &&
@@ -51,16 +51,15 @@ static bool MaxCondition(const BinaryOperator::Opcode &Op, const Expr *CondLhs,
 }
 
 static std::string
-CreateReplacement(const bool UseMax, const BinaryOperator::Opcode &Op,
-                  const Expr *CondLhs, const Expr *CondRhs,
-                  const Expr *AssignLhs, const ASTContext &Context,
-                  const SourceManager &Source, const LangOptions &LO,
-                  const StringRef &FunctionName) {
-  const auto CondLhsStr = Lexer::getSourceText(
+createReplacement(const BinaryOperator::Opcode Op, const Expr *CondLhs,
+                  const Expr *CondRhs, const Expr *AssignLhs,
+                  const ASTContext &Context, const SourceManager &Source,
+                  const LangOptions &LO, StringRef FunctionName) {
+  const llvm::StringRef CondLhsStr = Lexer::getSourceText(
       Source.getExpansionRange(CondLhs->getSourceRange()), Source, LO);
-  const auto CondRhsStr = Lexer::getSourceText(
+  const llvm::StringRef CondRhsStr = Lexer::getSourceText(
       Source.getExpansionRange(CondRhs->getSourceRange()), Source, LO);
-  const auto AssignLhsStr = Lexer::getSourceText(
+  const llvm::StringRef AssignLhsStr = Lexer::getSourceText(
       Source.getExpansionRange(AssignLhs->getSourceRange()), Source, LO);
   return (AssignLhsStr + " = " + FunctionName +
           ((CondLhs->getType() != CondRhs->getType())
@@ -126,25 +125,24 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
   if (IfLocation.isMacroID() || ThenLocation.isMacroID())
     return;
 
-  auto ReplaceAndDiagnose = [&](bool UseMax) {
-    const llvm::StringRef FunctionName = UseMax ? "std::max" : "std::min";
-    diag(IfLocation, "use `std::%0` instead of `%1`")
-        << (UseMax ? "max" : "min") << OperatorStr
+  auto ReplaceAndDiagnose = [&](const llvm::StringRef FunctionName) {
+    diag(IfLocation, "use `%0` instead of `%1`")
+        << FunctionName << OperatorStr
         << FixItHint::CreateReplacement(
                SourceRange(IfLocation, Lexer::getLocForEndOfToken(
                                            ThenLocation, 0, Source, LO)),
-               CreateReplacement(UseMax, BinaryOpcode, CondLhs, CondRhs,
-                                 AssignLhs, Context, Source, LO, FunctionName))
+               createReplacement(BinaryOpcode, CondLhs, CondRhs, AssignLhs,
+                                 Context, Source, LO, FunctionName))
         << IncludeInserter.createIncludeInsertion(
                Source.getFileID(If->getBeginLoc()), AlgorithmHeader);
   };
 
-  if (MinCondition(BinaryOpcode, CondLhs, CondRhs, AssignLhs, AssignRhs,
+  if (minCondition(BinaryOpcode, CondLhs, CondRhs, AssignLhs, AssignRhs,
                    Context)) {
-    ReplaceAndDiagnose(/*UseMax=*/false);
-  } else if (MaxCondition(BinaryOpcode, CondLhs, CondRhs, AssignLhs, AssignRhs,
+    ReplaceAndDiagnose("std::min");
+  } else if (maxCondition(BinaryOpcode, CondLhs, CondRhs, AssignLhs, AssignRhs,
                           Context)) {
-    ReplaceAndDiagnose(/*UseMax=*/true);
+    ReplaceAndDiagnose("std::max");
   }
 }
 

>From 7d2c085cbfc0008b56a04b076917e8b500ab3058 Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Tue, 23 Jan 2024 19:27:24 +0530
Subject: [PATCH 37/46] corrrect style issue

---
 .../readability/UseStdMinMaxCheck.cpp         | 38 +++++++++----------
 1 file changed, 18 insertions(+), 20 deletions(-)

diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
index e45dcd4ef78c2..50f4a6f297f86 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
@@ -18,7 +18,7 @@ namespace clang::tidy::readability {
 
 static const llvm::StringRef AlgorithmHeader("<algorithm>");
 
-static bool MinCondition(const BinaryOperator::Opcode &Op, const Expr *CondLhs,
+static bool minCondition(const BinaryOperator::Opcode Op, const Expr *CondLhs,
                          const Expr *CondRhs, const Expr *AssignLhs,
                          const Expr *AssignRhs, const ASTContext &Context) {
   if ((Op == BO_LT || Op == BO_LE) &&
@@ -34,7 +34,7 @@ static bool MinCondition(const BinaryOperator::Opcode &Op, const Expr *CondLhs,
   return false;
 }
 
-static bool MaxCondition(const BinaryOperator::Opcode &Op, const Expr *CondLhs,
+static bool maxCondition(const BinaryOperator::Opcode Op, const Expr *CondLhs,
                          const Expr *CondRhs, const Expr *AssignLhs,
                          const Expr *AssignRhs, const ASTContext &Context) {
   if ((Op == BO_LT || Op == BO_LE) &&
@@ -51,16 +51,15 @@ static bool MaxCondition(const BinaryOperator::Opcode &Op, const Expr *CondLhs,
 }
 
 static std::string
-CreateReplacement(const bool UseMax, const BinaryOperator::Opcode &Op,
-                  const Expr *CondLhs, const Expr *CondRhs,
-                  const Expr *AssignLhs, const ASTContext &Context,
-                  const SourceManager &Source, const LangOptions &LO,
-                  const StringRef &FunctionName) {
-  const auto CondLhsStr = Lexer::getSourceText(
+createReplacement(const BinaryOperator::Opcode Op, const Expr *CondLhs,
+                  const Expr *CondRhs, const Expr *AssignLhs,
+                  const ASTContext &Context, const SourceManager &Source,
+                  const LangOptions &LO, StringRef FunctionName) {
+  const llvm::StringRef CondLhsStr = Lexer::getSourceText(
       Source.getExpansionRange(CondLhs->getSourceRange()), Source, LO);
-  const auto CondRhsStr = Lexer::getSourceText(
+  const llvm::StringRef CondRhsStr = Lexer::getSourceText(
       Source.getExpansionRange(CondRhs->getSourceRange()), Source, LO);
-  const auto AssignLhsStr = Lexer::getSourceText(
+  const llvm::StringRef AssignLhsStr = Lexer::getSourceText(
       Source.getExpansionRange(AssignLhs->getSourceRange()), Source, LO);
   return (AssignLhsStr + " = " + FunctionName +
           ((CondLhs->getType() != CondRhs->getType())
@@ -126,25 +125,24 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
   if (IfLocation.isMacroID() || ThenLocation.isMacroID())
     return;
 
-  auto ReplaceAndDiagnose = [&](bool UseMax) {
-    const llvm::StringRef FunctionName = UseMax ? "std::max" : "std::min";
-    diag(IfLocation, "use `std::%0` instead of `%1`")
-        << (UseMax ? "max" : "min") << OperatorStr
+  auto ReplaceAndDiagnose = [&](const llvm::StringRef FunctionName) {
+    diag(IfLocation, "use `%0` instead of `%1`")
+        << FunctionName << OperatorStr
         << FixItHint::CreateReplacement(
                SourceRange(IfLocation, Lexer::getLocForEndOfToken(
                                            ThenLocation, 0, Source, LO)),
-               CreateReplacement(UseMax, BinaryOpcode, CondLhs, CondRhs,
-                                 AssignLhs, Context, Source, LO, FunctionName))
+               createReplacement(BinaryOpcode, CondLhs, CondRhs, AssignLhs,
+                                 Context, Source, LO, FunctionName))
         << IncludeInserter.createIncludeInsertion(
                Source.getFileID(If->getBeginLoc()), AlgorithmHeader);
   };
 
-  if (MinCondition(BinaryOpcode, CondLhs, CondRhs, AssignLhs, AssignRhs,
+  if (minCondition(BinaryOpcode, CondLhs, CondRhs, AssignLhs, AssignRhs,
                    Context)) {
-    ReplaceAndDiagnose(/*UseMax=*/false);
-  } else if (MaxCondition(BinaryOpcode, CondLhs, CondRhs, AssignLhs, AssignRhs,
+    ReplaceAndDiagnose("std::min");
+  } else if (maxCondition(BinaryOpcode, CondLhs, CondRhs, AssignLhs, AssignRhs,
                           Context)) {
-    ReplaceAndDiagnose(/*UseMax=*/true);
+    ReplaceAndDiagnose("std::max");
   }
 }
 

>From abec9b5fa5febad1d169450d74f44dc5b82d9fc5 Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Fri, 26 Jan 2024 06:41:25 +0530
Subject: [PATCH 38/46] correct functional bugs

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../readability/UseStdMinMaxCheck.cpp         | 46 +++++++++++++++++--
 .../checkers/readability/use-std-min-max.cpp  | 12 ++++-
 2 files changed, 53 insertions(+), 5 deletions(-)

diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
index 50f4a6f297f86..4f9cef7127b70 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
@@ -9,13 +9,44 @@
 #include "UseStdMinMaxCheck.h"
 #include "../utils/ASTUtils.h"
 #include "clang/AST/ASTContext.h"
+#include "clang/AST/RecursiveASTVisitor.h"
 #include "clang/ASTMatchers/ASTMatchFinder.h"
 #include "clang/Lex/Preprocessor.h"
+#include <iostream>
+using namespace std;
 
 using namespace clang::ast_matchers;
 
 namespace clang::tidy::readability {
 
+class ExprVisitor : public clang::RecursiveASTVisitor<ExprVisitor> {
+public:
+  explicit ExprVisitor(clang::ASTContext *Context) : Context(Context) {}
+  bool visitStmt(const clang::Stmt *S, bool &found,
+                 clang::QualType &GlobalImplicitCastType) {
+
+    if (isa<clang::ImplicitCastExpr>(S) && !found) {
+      found = true;
+      const clang::ImplicitCastExpr *ImplicitCast =
+          cast<clang::ImplicitCastExpr>(S);
+      GlobalImplicitCastType = ImplicitCast->getType();
+      // Stop visiting children.
+      return false;
+    }
+    // Continue visiting children.
+    for (const clang::Stmt *Child : S->children()) {
+      if (Child) {
+        this->visitStmt(Child, found, GlobalImplicitCastType);
+      }
+    }
+
+    return true; // Continue visiting other nodes.
+  }
+
+private:
+  clang::ASTContext *Context;
+};
+
 static const llvm::StringRef AlgorithmHeader("<algorithm>");
 
 static bool minCondition(const BinaryOperator::Opcode Op, const Expr *CondLhs,
@@ -54,16 +85,19 @@ static std::string
 createReplacement(const BinaryOperator::Opcode Op, const Expr *CondLhs,
                   const Expr *CondRhs, const Expr *AssignLhs,
                   const ASTContext &Context, const SourceManager &Source,
-                  const LangOptions &LO, StringRef FunctionName) {
+                  const LangOptions &LO, StringRef FunctionName,
+                  QualType GlobalImplicitCastType) {
   const llvm::StringRef CondLhsStr = Lexer::getSourceText(
       Source.getExpansionRange(CondLhs->getSourceRange()), Source, LO);
   const llvm::StringRef CondRhsStr = Lexer::getSourceText(
       Source.getExpansionRange(CondRhs->getSourceRange()), Source, LO);
   const llvm::StringRef AssignLhsStr = Lexer::getSourceText(
       Source.getExpansionRange(AssignLhs->getSourceRange()), Source, LO);
+
   return (AssignLhsStr + " = " + FunctionName +
           ((CondLhs->getType() != CondRhs->getType())
-               ? "<" + AssignLhs->getType().getAsString() + ">("
+               ? "<" + GlobalImplicitCastType.getCanonicalType().getAsString() +
+                     ">("
                : "(") +
           CondLhsStr + ", " + CondRhsStr + ");")
       .str();
@@ -120,6 +154,11 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
   const SourceManager &Source = Context.getSourceManager();
   const SourceLocation IfLocation = If->getIfLoc();
   const SourceLocation ThenLocation = If->getEndLoc();
+  bool found = false;
+  clang::QualType GlobalImplicitCastType;
+
+  ExprVisitor Visitor(Result.Context);
+  Visitor.visitStmt(If, found, GlobalImplicitCastType);
 
   // Ignore Macros
   if (IfLocation.isMacroID() || ThenLocation.isMacroID())
@@ -132,7 +171,8 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
                SourceRange(IfLocation, Lexer::getLocForEndOfToken(
                                            ThenLocation, 0, Source, LO)),
                createReplacement(BinaryOpcode, CondLhs, CondRhs, AssignLhs,
-                                 Context, Source, LO, FunctionName))
+                                 Context, Source, LO, FunctionName,
+                                 GlobalImplicitCastType))
         << IncludeInserter.createIncludeInsertion(
                Source.getFileID(If->getBeginLoc()), AlgorithmHeader);
   };
diff --git a/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp b/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
index 4f36b1dedcbd4..ebf3a072c9269 100644
--- a/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
+++ b/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
@@ -1,5 +1,4 @@
 // RUN: %check_clang_tidy %s readability-use-std-min-max %t
-
 #define MY_MACRO_MIN(a, b) ((a) < (b) ? (a) : (b))
 
 constexpr int myConstexprMin(int a, int b) {
@@ -24,8 +23,11 @@ class MyClass {
 void foo() {
   int value1,value2,value3;
   short value4;
+  unsigned int value5;
+  unsigned char value6;
   MyClass obj;
 
+
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
   // CHECK-FIXES: value1 = std::max(value1, value2);
   if (value1 < value2)
@@ -145,7 +147,7 @@ void foo() {
     value3 = MY_MACRO_MIN(value1, value2); 
   
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
-  // CHECK-FIXES: value4 = std::max<short>(value4, value2);
+  // CHECK-FIXES: value4 = std::max<int>(value4, value2);
   if (value4 < value2){
     value4 = value2; 
   }
@@ -201,4 +203,10 @@ void foo() {
       value2 = value3;
     }
   }
+
+  // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `<` [readability-use-std-min-max]
+  // CHECK-FIXES: value6 = std::min<unsigned int>(value5, value6);
+  if(value5<value6){
+    value6 = value5;
+  }
 }
\ No newline at end of file

>From 6a0e495888c6d81061146ded25bd4d3978fd1086 Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Fri, 26 Jan 2024 13:57:20 +0530
Subject: [PATCH 39/46] pass dependent types

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../readability/UseStdMinMaxCheck.cpp         | 12 +++++++---
 .../checkers/readability/use-std-min-max.cpp  | 23 +++++++++++++++++--
 2 files changed, 30 insertions(+), 5 deletions(-)

diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
index 4f9cef7127b70..879d39a6f3061 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
@@ -95,7 +95,8 @@ createReplacement(const BinaryOperator::Opcode Op, const Expr *CondLhs,
       Source.getExpansionRange(AssignLhs->getSourceRange()), Source, LO);
 
   return (AssignLhsStr + " = " + FunctionName +
-          ((CondLhs->getType() != CondRhs->getType())
+          ((CondLhs->getType()->getUnqualifiedDesugaredType() !=
+            CondRhs->getType()->getUnqualifiedDesugaredType())
                ? "<" + GlobalImplicitCastType.getCanonicalType().getAsString() +
                      ">("
                : "(") +
@@ -154,16 +155,21 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
   const SourceManager &Source = Context.getSourceManager();
   const SourceLocation IfLocation = If->getIfLoc();
   const SourceLocation ThenLocation = If->getEndLoc();
-  bool found = false;
+  bool Found = false;
   clang::QualType GlobalImplicitCastType;
 
   ExprVisitor Visitor(Result.Context);
-  Visitor.visitStmt(If, found, GlobalImplicitCastType);
+  Visitor.visitStmt(If, Found, GlobalImplicitCastType);
 
   // Ignore Macros
   if (IfLocation.isMacroID() || ThenLocation.isMacroID())
     return;
 
+  // Ignore Dependent types
+  if (CondLhs->getType()->isDependentType() ||
+      CondRhs->getType()->isDependentType())
+    return;
+
   auto ReplaceAndDiagnose = [&](const llvm::StringRef FunctionName) {
     diag(IfLocation, "use `%0` instead of `%1`")
         << FunctionName << OperatorStr
diff --git a/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp b/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
index ebf3a072c9269..638e26ef8c25f 100644
--- a/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
+++ b/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
@@ -20,11 +20,15 @@ class MyClass {
   int member2;
 };
 
-void foo() {
+template<typename T>
+
+void foo(T value7) {
   int value1,value2,value3;
   short value4;
   unsigned int value5;
   unsigned char value6;
+  const int value8 = 5;
+  volatile int value9 = 6;
   MyClass obj;
 
 
@@ -209,4 +213,19 @@ void foo() {
   if(value5<value6){
     value6 = value5;
   }
-}
\ No newline at end of file
+
+  //No suggestion needed here
+  if(value7<value6){
+    value6 = value7;
+  }
+
+  //CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `<` [readability-use-std-min-max]
+  //CHECK-FIXES: value1 = std::min(value8, value1);
+  if(value8<value1)
+    value1 = value8;
+  
+  //CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `<` [readability-use-std-min-max]
+  //CHECK-FIXES: value1 = std::min(value9, value1);
+  if(value9<value1)
+    value1 = value9;
+}

>From 274b55fdfd464afef20befa3feed55869a087221 Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Fri, 26 Jan 2024 21:52:32 +0530
Subject: [PATCH 40/46] filter implicit cast expr

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../readability/UseStdMinMaxCheck.cpp         | 59 ++++++++++++++++---
 1 file changed, 51 insertions(+), 8 deletions(-)

diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
index 879d39a6f3061..a904097dd5144 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
@@ -12,13 +12,53 @@
 #include "clang/AST/RecursiveASTVisitor.h"
 #include "clang/ASTMatchers/ASTMatchFinder.h"
 #include "clang/Lex/Preprocessor.h"
-#include <iostream>
-using namespace std;
 
 using namespace clang::ast_matchers;
 
 namespace clang::tidy::readability {
 
+static bool isImplicitCastType(const clang::CastKind castKind) {
+  switch (castKind) {
+  case clang::CK_CPointerToObjCPointerCast:
+  case clang::CK_BlockPointerToObjCPointerCast:
+  case clang::CK_BitCast:
+  case clang::CK_AnyPointerToBlockPointerCast:
+  case clang::CK_NullToMemberPointer:
+  case clang::CK_NullToPointer:
+  case clang::CK_IntegralToPointer:
+  case clang::CK_PointerToIntegral:
+  case clang::CK_IntegralCast:
+  case clang::CK_BooleanToSignedIntegral:
+  case clang::CK_IntegralToFloating:
+  case clang::CK_FloatingToIntegral:
+  case clang::CK_FloatingCast:
+  case clang::CK_ObjCObjectLValueCast:
+  case clang::CK_FloatingRealToComplex:
+  case clang::CK_FloatingComplexToReal:
+  case clang::CK_FloatingComplexCast:
+  case clang::CK_FloatingComplexToIntegralComplex:
+  case clang::CK_IntegralRealToComplex:
+  case clang::CK_IntegralComplexToReal:
+  case clang::CK_IntegralComplexCast:
+  case clang::CK_IntegralComplexToFloatingComplex:
+  case clang::CK_FloatingToFixedPoint:
+  case clang::CK_FixedPointToFloating:
+  case clang::CK_FixedPointCast:
+  case clang::CK_FixedPointToIntegral:
+  case clang::CK_IntegralToFixedPoint:
+  case clang::CK_MatrixCast:
+  case clang::CK_PointerToBoolean:
+  case clang::CK_IntegralToBoolean:
+  case clang::CK_FloatingToBoolean:
+  case clang::CK_MemberPointerToBoolean:
+  case clang::CK_FloatingComplexToBoolean:
+  case clang::CK_IntegralComplexToBoolean:
+    return true;
+  default:
+    return false;
+  }
+}
+
 class ExprVisitor : public clang::RecursiveASTVisitor<ExprVisitor> {
 public:
   explicit ExprVisitor(clang::ASTContext *Context) : Context(Context) {}
@@ -26,12 +66,15 @@ class ExprVisitor : public clang::RecursiveASTVisitor<ExprVisitor> {
                  clang::QualType &GlobalImplicitCastType) {
 
     if (isa<clang::ImplicitCastExpr>(S) && !found) {
-      found = true;
-      const clang::ImplicitCastExpr *ImplicitCast =
-          cast<clang::ImplicitCastExpr>(S);
-      GlobalImplicitCastType = ImplicitCast->getType();
-      // Stop visiting children.
-      return false;
+      const auto CastKind = cast<clang::ImplicitCastExpr>(S)->getCastKind();
+      if (isImplicitCastType(CastKind)) {
+        found = true;
+        const clang::ImplicitCastExpr *ImplicitCast =
+            cast<clang::ImplicitCastExpr>(S);
+        GlobalImplicitCastType = ImplicitCast->getType();
+        // Stop visiting children.
+        return false;
+      }
     }
     // Continue visiting children.
     for (const clang::Stmt *Child : S->children()) {

>From 8bf8235b7e7ef90649c4ae815019565fcc1726f2 Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Sat, 27 Jan 2024 23:52:03 +0530
Subject: [PATCH 41/46] Add mising type, optimise

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../readability/UseStdMinMaxCheck.cpp         | 32 +++++++++++++------
 1 file changed, 22 insertions(+), 10 deletions(-)

diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
index a904097dd5144..11cacade5623c 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
@@ -53,6 +53,7 @@ static bool isImplicitCastType(const clang::CastKind castKind) {
   case clang::CK_MemberPointerToBoolean:
   case clang::CK_FloatingComplexToBoolean:
   case clang::CK_IntegralComplexToBoolean:
+  case clang::CK_UserDefinedConversion:
     return true;
   default:
     return false;
@@ -124,12 +125,13 @@ static bool maxCondition(const BinaryOperator::Opcode Op, const Expr *CondLhs,
   return false;
 }
 
-static std::string
-createReplacement(const BinaryOperator::Opcode Op, const Expr *CondLhs,
-                  const Expr *CondRhs, const Expr *AssignLhs,
-                  const ASTContext &Context, const SourceManager &Source,
-                  const LangOptions &LO, StringRef FunctionName,
-                  QualType GlobalImplicitCastType) {
+static std::string createReplacement(const BinaryOperator::Opcode Op,
+                                     const Expr *CondLhs, const Expr *CondRhs,
+                                     const Expr *AssignLhs,
+                                     const ASTContext *Context,
+                                     const SourceManager &Source,
+                                     const LangOptions &LO,
+                                     StringRef FunctionName, const IfStmt *If) {
   const llvm::StringRef CondLhsStr = Lexer::getSourceText(
       Source.getExpansionRange(CondLhs->getSourceRange()), Source, LO);
   const llvm::StringRef CondRhsStr = Lexer::getSourceText(
@@ -137,9 +139,20 @@ createReplacement(const BinaryOperator::Opcode Op, const Expr *CondLhs,
   const llvm::StringRef AssignLhsStr = Lexer::getSourceText(
       Source.getExpansionRange(AssignLhs->getSourceRange()), Source, LO);
 
+  bool IsImplicitCastTypeNeeded = false;
+  clang::QualType GlobalImplicitCastType;
+  if ((CondLhs->getType()->getUnqualifiedDesugaredType() !=
+       CondRhs->getType()->getUnqualifiedDesugaredType()) &&
+      (CondLhs->getType().getCanonicalType() !=
+       (CondRhs->getType().getCanonicalType()))) {
+    IsImplicitCastTypeNeeded = true;
+    bool Found = false;
+    ExprVisitor Visitor(const_cast<ASTContext *>(Context));
+    Visitor.visitStmt(If, Found, GlobalImplicitCastType);
+  }
+
   return (AssignLhsStr + " = " + FunctionName +
-          ((CondLhs->getType()->getUnqualifiedDesugaredType() !=
-            CondRhs->getType()->getUnqualifiedDesugaredType())
+          (IsImplicitCastTypeNeeded
                ? "<" + GlobalImplicitCastType.getCanonicalType().getAsString() +
                      ">("
                : "(") +
@@ -220,8 +233,7 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
                SourceRange(IfLocation, Lexer::getLocForEndOfToken(
                                            ThenLocation, 0, Source, LO)),
                createReplacement(BinaryOpcode, CondLhs, CondRhs, AssignLhs,
-                                 Context, Source, LO, FunctionName,
-                                 GlobalImplicitCastType))
+                                 Result.Context, Source, LO, FunctionName, If))
         << IncludeInserter.createIncludeInsertion(
                Source.getFileID(If->getBeginLoc()), AlgorithmHeader);
   };

>From d8df8c8202d7c29d9a14eff4a96ef1ab43d088f3 Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Sun, 28 Jan 2024 00:09:27 +0530
Subject: [PATCH 42/46] removed whitespace

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../test/clang-tidy/checkers/readability/use-std-min-max.cpp     | 1 -
 1 file changed, 1 deletion(-)

diff --git a/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp b/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
index 638e26ef8c25f..b8a1dbd0c7661 100644
--- a/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
+++ b/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
@@ -31,7 +31,6 @@ void foo(T value7) {
   volatile int value9 = 6;
   MyClass obj;
 
-
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
   // CHECK-FIXES: value1 = std::max(value1, value2);
   if (value1 < value2)

>From 8a5d58515096b6131d8c174f8744c17e87567522 Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Sun, 28 Jan 2024 01:23:08 +0530
Subject: [PATCH 43/46] remove unsed initialisation

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../clang-tidy/readability/UseStdMinMaxCheck.cpp   | 14 ++------------
 1 file changed, 2 insertions(+), 12 deletions(-)

diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
index 11cacade5623c..ea9dd0309dceb 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
@@ -62,7 +62,6 @@ static bool isImplicitCastType(const clang::CastKind castKind) {
 
 class ExprVisitor : public clang::RecursiveASTVisitor<ExprVisitor> {
 public:
-  explicit ExprVisitor(clang::ASTContext *Context) : Context(Context) {}
   bool visitStmt(const clang::Stmt *S, bool &found,
                  clang::QualType &GlobalImplicitCastType) {
 
@@ -86,9 +85,6 @@ class ExprVisitor : public clang::RecursiveASTVisitor<ExprVisitor> {
 
     return true; // Continue visiting other nodes.
   }
-
-private:
-  clang::ASTContext *Context;
 };
 
 static const llvm::StringRef AlgorithmHeader("<algorithm>");
@@ -128,7 +124,6 @@ static bool maxCondition(const BinaryOperator::Opcode Op, const Expr *CondLhs,
 static std::string createReplacement(const BinaryOperator::Opcode Op,
                                      const Expr *CondLhs, const Expr *CondRhs,
                                      const Expr *AssignLhs,
-                                     const ASTContext *Context,
                                      const SourceManager &Source,
                                      const LangOptions &LO,
                                      StringRef FunctionName, const IfStmt *If) {
@@ -147,7 +142,7 @@ static std::string createReplacement(const BinaryOperator::Opcode Op,
        (CondRhs->getType().getCanonicalType()))) {
     IsImplicitCastTypeNeeded = true;
     bool Found = false;
-    ExprVisitor Visitor(const_cast<ASTContext *>(Context));
+    ExprVisitor Visitor;
     Visitor.visitStmt(If, Found, GlobalImplicitCastType);
   }
 
@@ -211,11 +206,6 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
   const SourceManager &Source = Context.getSourceManager();
   const SourceLocation IfLocation = If->getIfLoc();
   const SourceLocation ThenLocation = If->getEndLoc();
-  bool Found = false;
-  clang::QualType GlobalImplicitCastType;
-
-  ExprVisitor Visitor(Result.Context);
-  Visitor.visitStmt(If, Found, GlobalImplicitCastType);
 
   // Ignore Macros
   if (IfLocation.isMacroID() || ThenLocation.isMacroID())
@@ -233,7 +223,7 @@ void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
                SourceRange(IfLocation, Lexer::getLocForEndOfToken(
                                            ThenLocation, 0, Source, LO)),
                createReplacement(BinaryOpcode, CondLhs, CondRhs, AssignLhs,
-                                 Result.Context, Source, LO, FunctionName, If))
+                                 Source, LO, FunctionName, If))
         << IncludeInserter.createIncludeInsertion(
                Source.getFileID(If->getBeginLoc()), AlgorithmHeader);
   };

>From 85fb67d6d673602b0cdcc78dabd2db7f9b9bee6c Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Sun, 28 Jan 2024 02:31:59 +0530
Subject: [PATCH 44/46] small change

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../test/clang-tidy/checkers/readability/use-std-min-max.cpp  | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp b/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
index b8a1dbd0c7661..a9633b087d42f 100644
--- a/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
+++ b/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
@@ -12,7 +12,7 @@ constexpr int myConstexprMax(int a, int b) {
 #define MY_IF_MACRO(condition, statement) \
   if (condition) {                        \
     statement                             \
-  }
+  }                                       \
 
 class MyClass {
 public:
@@ -46,7 +46,7 @@ void foo(T value7) {
   if (value2 > value1)
     value2 = value1; 
 
-  // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `>` [readability-use-std-min-max
+  // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `>` [readability-use-std-min-max]
   // CHECK-FIXES: value1 = std::max(value2, value1);
   if (value2 > value1)
     value1 = value2; 

>From 1214547f9980714cfdc6f8e9565f3b3cc17cc3fb Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Mon, 29 Jan 2024 06:16:35 +0530
Subject: [PATCH 45/46] simplify

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../readability/UseStdMinMaxCheck.cpp         | 158 +++++-------------
 .../checkers/readability/use-std-min-max.cpp  |  30 ++--
 2 files changed, 58 insertions(+), 130 deletions(-)

diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
index ea9dd0309dceb..78886665c1134 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
@@ -9,7 +9,6 @@
 #include "UseStdMinMaxCheck.h"
 #include "../utils/ASTUtils.h"
 #include "clang/AST/ASTContext.h"
-#include "clang/AST/RecursiveASTVisitor.h"
 #include "clang/ASTMatchers/ASTMatchFinder.h"
 #include "clang/Lex/Preprocessor.h"
 
@@ -17,76 +16,6 @@ using namespace clang::ast_matchers;
 
 namespace clang::tidy::readability {
 
-static bool isImplicitCastType(const clang::CastKind castKind) {
-  switch (castKind) {
-  case clang::CK_CPointerToObjCPointerCast:
-  case clang::CK_BlockPointerToObjCPointerCast:
-  case clang::CK_BitCast:
-  case clang::CK_AnyPointerToBlockPointerCast:
-  case clang::CK_NullToMemberPointer:
-  case clang::CK_NullToPointer:
-  case clang::CK_IntegralToPointer:
-  case clang::CK_PointerToIntegral:
-  case clang::CK_IntegralCast:
-  case clang::CK_BooleanToSignedIntegral:
-  case clang::CK_IntegralToFloating:
-  case clang::CK_FloatingToIntegral:
-  case clang::CK_FloatingCast:
-  case clang::CK_ObjCObjectLValueCast:
-  case clang::CK_FloatingRealToComplex:
-  case clang::CK_FloatingComplexToReal:
-  case clang::CK_FloatingComplexCast:
-  case clang::CK_FloatingComplexToIntegralComplex:
-  case clang::CK_IntegralRealToComplex:
-  case clang::CK_IntegralComplexToReal:
-  case clang::CK_IntegralComplexCast:
-  case clang::CK_IntegralComplexToFloatingComplex:
-  case clang::CK_FloatingToFixedPoint:
-  case clang::CK_FixedPointToFloating:
-  case clang::CK_FixedPointCast:
-  case clang::CK_FixedPointToIntegral:
-  case clang::CK_IntegralToFixedPoint:
-  case clang::CK_MatrixCast:
-  case clang::CK_PointerToBoolean:
-  case clang::CK_IntegralToBoolean:
-  case clang::CK_FloatingToBoolean:
-  case clang::CK_MemberPointerToBoolean:
-  case clang::CK_FloatingComplexToBoolean:
-  case clang::CK_IntegralComplexToBoolean:
-  case clang::CK_UserDefinedConversion:
-    return true;
-  default:
-    return false;
-  }
-}
-
-class ExprVisitor : public clang::RecursiveASTVisitor<ExprVisitor> {
-public:
-  bool visitStmt(const clang::Stmt *S, bool &found,
-                 clang::QualType &GlobalImplicitCastType) {
-
-    if (isa<clang::ImplicitCastExpr>(S) && !found) {
-      const auto CastKind = cast<clang::ImplicitCastExpr>(S)->getCastKind();
-      if (isImplicitCastType(CastKind)) {
-        found = true;
-        const clang::ImplicitCastExpr *ImplicitCast =
-            cast<clang::ImplicitCastExpr>(S);
-        GlobalImplicitCastType = ImplicitCast->getType();
-        // Stop visiting children.
-        return false;
-      }
-    }
-    // Continue visiting children.
-    for (const clang::Stmt *Child : S->children()) {
-      if (Child) {
-        this->visitStmt(Child, found, GlobalImplicitCastType);
-      }
-    }
-
-    return true; // Continue visiting other nodes.
-  }
-};
-
 static const llvm::StringRef AlgorithmHeader("<algorithm>");
 
 static bool minCondition(const BinaryOperator::Opcode Op, const Expr *CondLhs,
@@ -121,12 +50,12 @@ static bool maxCondition(const BinaryOperator::Opcode Op, const Expr *CondLhs,
   return false;
 }
 
-static std::string createReplacement(const BinaryOperator::Opcode Op,
-                                     const Expr *CondLhs, const Expr *CondRhs,
+static std::string createReplacement(const Expr *CondLhs, const Expr *CondRhs,
                                      const Expr *AssignLhs,
                                      const SourceManager &Source,
                                      const LangOptions &LO,
-                                     StringRef FunctionName, const IfStmt *If) {
+                                     StringRef FunctionName,
+                                     const BinaryOperator *BO) {
   const llvm::StringRef CondLhsStr = Lexer::getSourceText(
       Source.getExpansionRange(CondLhs->getSourceRange()), Source, LO);
   const llvm::StringRef CondRhsStr = Lexer::getSourceText(
@@ -134,20 +63,19 @@ static std::string createReplacement(const BinaryOperator::Opcode Op,
   const llvm::StringRef AssignLhsStr = Lexer::getSourceText(
       Source.getExpansionRange(AssignLhs->getSourceRange()), Source, LO);
 
-  bool IsImplicitCastTypeNeeded = false;
   clang::QualType GlobalImplicitCastType;
-  if ((CondLhs->getType()->getUnqualifiedDesugaredType() !=
-       CondRhs->getType()->getUnqualifiedDesugaredType()) &&
-      (CondLhs->getType().getCanonicalType() !=
-       (CondRhs->getType().getCanonicalType()))) {
-    IsImplicitCastTypeNeeded = true;
-    bool Found = false;
-    ExprVisitor Visitor;
-    Visitor.visitStmt(If, Found, GlobalImplicitCastType);
+  if (CondLhs->getType()
+          .getCanonicalType()
+          .getNonReferenceType()
+          .getUnqualifiedType() != CondRhs->getType()
+                                       .getCanonicalType()
+                                       .getNonReferenceType()
+                                       .getUnqualifiedType()) {
+    GlobalImplicitCastType = BO->getLHS()->getType();
   }
 
   return (AssignLhsStr + " = " + FunctionName +
-          (IsImplicitCastTypeNeeded
+          (!GlobalImplicitCastType.isNull()
                ? "<" + GlobalImplicitCastType.getCanonicalType().getAsString() +
                      ">("
                : "(") +
@@ -165,24 +93,35 @@ void UseStdMinMaxCheck::storeOptions(ClangTidyOptions::OptionMap &Opts) {
   Options.store(Opts, "IncludeStyle", IncludeInserter.getStyle());
 }
 
+// Ignore if statements that are inside macros.
+AST_MATCHER(IfStmt, isIfInMacro) {
+  return Node.getIfLoc().isMacroID() || Node.getEndLoc().isMacroID();
+}
+
+// Ignore expressions that are of dependent types.
+AST_MATCHER(Expr, isExprDependentType) {
+  return Node.getType()->isDependentType();
+}
+
 void UseStdMinMaxCheck::registerMatchers(MatchFinder *Finder) {
   auto AssignOperator =
       binaryOperator(hasOperatorName("="), hasLHS(expr().bind("AssignLhs")),
                      hasRHS(expr().bind("AssignRhs")));
-
+  auto BinaryOperator =
+      binaryOperator(
+          hasAnyOperatorName("<", ">", "<=", ">="),
+          hasLHS(expr(unless(isExprDependentType())).bind("CondLhs")),
+          hasRHS(expr(unless(isExprDependentType())).bind("CondRhs")))
+          .bind("binaryOp");
   Finder->addMatcher(
-      ifStmt(
-          stmt().bind("if"),
-          unless(hasElse(stmt())), // Ensure `if` has no `else`
-          hasCondition(binaryOperator(hasAnyOperatorName("<", ">", "<=", ">="),
-                                      hasLHS(expr().bind("CondLhs")),
-                                      hasRHS(expr().bind("CondRhs")))
-                           .bind("binaryOp")),
-          hasThen(
-              anyOf(stmt(AssignOperator),
-                    compoundStmt(statementCountIs(1), has(AssignOperator)))),
-          hasParent(stmt(unless(ifStmt(hasElse(
-              equalsBoundNode("if"))))))), // Ensure `if` has no `else if`
+      ifStmt(stmt().bind("if"), unless(isIfInMacro()),
+             unless(hasElse(stmt())), // Ensure `if` has no `else`
+             hasCondition(BinaryOperator),
+             hasThen(
+                 anyOf(stmt(AssignOperator),
+                       compoundStmt(statementCountIs(1), has(AssignOperator)))),
+             hasParent(stmt(unless(ifStmt(hasElse(
+                 equalsBoundNode("if"))))))), // Ensure `if` has no `else if`
       this);
 }
 
@@ -194,45 +133,34 @@ void UseStdMinMaxCheck::registerPPCallbacks(const SourceManager &SM,
 
 void UseStdMinMaxCheck::check(const MatchFinder::MatchResult &Result) {
   const auto *If = Result.Nodes.getNodeAs<IfStmt>("if");
-  const auto &Context = *Result.Context;
-  const auto &LO = Context.getLangOpts();
+  const auto &LO = (*Result.Context).getLangOpts();
   const auto *CondLhs = Result.Nodes.getNodeAs<Expr>("CondLhs");
   const auto *CondRhs = Result.Nodes.getNodeAs<Expr>("CondRhs");
   const auto *AssignLhs = Result.Nodes.getNodeAs<Expr>("AssignLhs");
   const auto *AssignRhs = Result.Nodes.getNodeAs<Expr>("AssignRhs");
   const auto *BinaryOp = Result.Nodes.getNodeAs<BinaryOperator>("binaryOp");
   const auto BinaryOpcode = BinaryOp->getOpcode();
-  const auto OperatorStr = BinaryOp->getOpcodeStr();
-  const SourceManager &Source = Context.getSourceManager();
   const SourceLocation IfLocation = If->getIfLoc();
   const SourceLocation ThenLocation = If->getEndLoc();
 
-  // Ignore Macros
-  if (IfLocation.isMacroID() || ThenLocation.isMacroID())
-    return;
-
-  // Ignore Dependent types
-  if (CondLhs->getType()->isDependentType() ||
-      CondRhs->getType()->isDependentType())
-    return;
-
   auto ReplaceAndDiagnose = [&](const llvm::StringRef FunctionName) {
+    const SourceManager &Source = (*Result.Context).getSourceManager();
     diag(IfLocation, "use `%0` instead of `%1`")
-        << FunctionName << OperatorStr
+        << FunctionName << BinaryOp->getOpcodeStr()
         << FixItHint::CreateReplacement(
                SourceRange(IfLocation, Lexer::getLocForEndOfToken(
                                            ThenLocation, 0, Source, LO)),
-               createReplacement(BinaryOpcode, CondLhs, CondRhs, AssignLhs,
-                                 Source, LO, FunctionName, If))
+               createReplacement(CondLhs, CondRhs, AssignLhs, Source, LO,
+                                 FunctionName, BinaryOp))
         << IncludeInserter.createIncludeInsertion(
                Source.getFileID(If->getBeginLoc()), AlgorithmHeader);
   };
 
   if (minCondition(BinaryOpcode, CondLhs, CondRhs, AssignLhs, AssignRhs,
-                   Context)) {
+                   (*Result.Context))) {
     ReplaceAndDiagnose("std::min");
   } else if (maxCondition(BinaryOpcode, CondLhs, CondRhs, AssignLhs, AssignRhs,
-                          Context)) {
+                          (*Result.Context))) {
     ReplaceAndDiagnose("std::max");
   }
 }
diff --git a/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp b/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
index a9633b087d42f..1029f0b109476 100644
--- a/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
+++ b/clang-tools-extra/test/clang-tidy/checkers/readability/use-std-min-max.cpp
@@ -1,4 +1,4 @@
-// RUN: %check_clang_tidy %s readability-use-std-min-max %t
+// RUN: %check_clang_tidy -std=c++11-or-later %s readability-use-std-min-max %t -- -- -fno-delayed-template-parsing
 #define MY_MACRO_MIN(a, b) ((a) < (b) ? (a) : (b))
 
 constexpr int myConstexprMin(int a, int b) {
@@ -12,7 +12,7 @@ constexpr int myConstexprMax(int a, int b) {
 #define MY_IF_MACRO(condition, statement) \
   if (condition) {                        \
     statement                             \
-  }                                       \
+  }                                       
 
 class MyClass {
 public:
@@ -24,12 +24,6 @@ template<typename T>
 
 void foo(T value7) {
   int value1,value2,value3;
-  short value4;
-  unsigned int value5;
-  unsigned char value6;
-  const int value8 = 5;
-  volatile int value9 = 6;
-  MyClass obj;
 
   // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
   // CHECK-FIXES: value1 = std::max(value1, value2);
@@ -54,9 +48,10 @@ void foo(T value7) {
   // No suggestion needed here
   if (value1 == value2)
     value1 = value2;
-  
-  // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
+
+  // CHECK-MESSAGES: :[[@LINE+3]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
   // CHECK-FIXES: value1 = std::max<int>(value1, value4);
+  short value4;
   if(value1<value4)
     value1=value4; 
   
@@ -95,8 +90,9 @@ void foo(T value7) {
   if (value2 >= value1)
     value2 = value1; 
   
-  // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
+  // CHECK-MESSAGES: :[[@LINE+3]]:3: warning: use `std::max` instead of `<` [readability-use-std-min-max]
   // CHECK-FIXES: obj.member1 = std::max(obj.member1, obj.member2);
+  MyClass obj;
   if (obj.member1 < obj.member2)
     obj.member1 = obj.member2; 
 
@@ -206,9 +202,11 @@ void foo(T value7) {
       value2 = value3;
     }
   }
-
-  // CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `<` [readability-use-std-min-max]
+  
+  // CHECK-MESSAGES: :[[@LINE+4]]:3: warning: use `std::min` instead of `<` [readability-use-std-min-max]
   // CHECK-FIXES: value6 = std::min<unsigned int>(value5, value6);
+  unsigned int value5;
+  unsigned char value6;
   if(value5<value6){
     value6 = value5;
   }
@@ -218,13 +216,15 @@ void foo(T value7) {
     value6 = value7;
   }
 
-  //CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `<` [readability-use-std-min-max]
+  //CHECK-MESSAGES: :[[@LINE+3]]:3: warning: use `std::min` instead of `<` [readability-use-std-min-max]
   //CHECK-FIXES: value1 = std::min(value8, value1);
+  const int value8 = 5;
   if(value8<value1)
     value1 = value8;
   
-  //CHECK-MESSAGES: :[[@LINE+2]]:3: warning: use `std::min` instead of `<` [readability-use-std-min-max]
+  //CHECK-MESSAGES: :[[@LINE+3]]:3: warning: use `std::min` instead of `<` [readability-use-std-min-max]
   //CHECK-FIXES: value1 = std::min(value9, value1);
+  volatile int value9 = 6;
   if(value9<value1)
     value1 = value9;
 }

>From 6aef7137a8cdc58efaceb296730b71c12c7be46f Mon Sep 17 00:00:00 2001
From: 11happy <soni5happy at gmail.com>
Date: Tue, 30 Jan 2024 14:44:45 +0530
Subject: [PATCH 46/46] small fix

Signed-off-by: 11happy <soni5happy at gmail.com>
---
 .../readability/UseStdMinMaxCheck.cpp         | 47 ++++++++++---------
 1 file changed, 24 insertions(+), 23 deletions(-)

diff --git a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
index 78886665c1134..1ff2863643d68 100644
--- a/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
+++ b/clang-tools-extra/clang-tidy/readability/UseStdMinMaxCheck.cpp
@@ -16,6 +16,15 @@ using namespace clang::ast_matchers;
 
 namespace clang::tidy::readability {
 
+namespace {
+
+// Ignore if statements that are inside macros.
+AST_MATCHER(IfStmt, isIfInMacro) {
+  return Node.getIfLoc().isMacroID() || Node.getEndLoc().isMacroID();
+}
+
+} // namespace
+
 static const llvm::StringRef AlgorithmHeader("<algorithm>");
 
 static bool minCondition(const BinaryOperator::Opcode Op, const Expr *CondLhs,
@@ -64,13 +73,15 @@ static std::string createReplacement(const Expr *CondLhs, const Expr *CondRhs,
       Source.getExpansionRange(AssignLhs->getSourceRange()), Source, LO);
 
   clang::QualType GlobalImplicitCastType;
-  if (CondLhs->getType()
-          .getCanonicalType()
-          .getNonReferenceType()
-          .getUnqualifiedType() != CondRhs->getType()
-                                       .getCanonicalType()
-                                       .getNonReferenceType()
-                                       .getUnqualifiedType()) {
+  clang::QualType LhsType = CondLhs->getType()
+                                .getCanonicalType()
+                                .getNonReferenceType()
+                                .getUnqualifiedType();
+  clang::QualType RhsType = CondRhs->getType()
+                                .getCanonicalType()
+                                .getNonReferenceType()
+                                .getUnqualifiedType();
+  if (LhsType != RhsType) {
     GlobalImplicitCastType = BO->getLHS()->getType();
   }
 
@@ -93,25 +104,15 @@ void UseStdMinMaxCheck::storeOptions(ClangTidyOptions::OptionMap &Opts) {
   Options.store(Opts, "IncludeStyle", IncludeInserter.getStyle());
 }
 
-// Ignore if statements that are inside macros.
-AST_MATCHER(IfStmt, isIfInMacro) {
-  return Node.getIfLoc().isMacroID() || Node.getEndLoc().isMacroID();
-}
-
-// Ignore expressions that are of dependent types.
-AST_MATCHER(Expr, isExprDependentType) {
-  return Node.getType()->isDependentType();
-}
-
 void UseStdMinMaxCheck::registerMatchers(MatchFinder *Finder) {
   auto AssignOperator =
-      binaryOperator(hasOperatorName("="), hasLHS(expr().bind("AssignLhs")),
-                     hasRHS(expr().bind("AssignRhs")));
+      binaryOperator(hasOperatorName("="),
+                     hasLHS(expr(unless(isTypeDependent())).bind("AssignLhs")),
+                     hasRHS(expr(unless(isTypeDependent())).bind("AssignRhs")));
   auto BinaryOperator =
-      binaryOperator(
-          hasAnyOperatorName("<", ">", "<=", ">="),
-          hasLHS(expr(unless(isExprDependentType())).bind("CondLhs")),
-          hasRHS(expr(unless(isExprDependentType())).bind("CondRhs")))
+      binaryOperator(hasAnyOperatorName("<", ">", "<=", ">="),
+                     hasLHS(expr(unless(isTypeDependent())).bind("CondLhs")),
+                     hasRHS(expr(unless(isTypeDependent())).bind("CondRhs")))
           .bind("binaryOp");
   Finder->addMatcher(
       ifStmt(stmt().bind("if"), unless(isIfInMacro()),



More information about the cfe-commits mailing list