Author: Victor Chernyakin
Date: 2025-07-09T08:21:40+03:00
New Revision: fbc4255ffcb8412a098926c7fc1ede823d6fb0e5

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

LOG: [clang-tidy] Teach `modernize-type-traits` about more type traits (#147074)

These new traits come from various standard versions:

C++14:

 - `tuple_element_t`

C++17:

- `is_placeholder_v`
- `is_bind_expression_v`
- `ratio_equal_v`
- `ratio_not_equal_v`
- `ratio_less_v`
- `ratio_less_equal_v`
- `ratio_greater_v`
- `ratio_greater_equal_v`
- `is_error_code_enum_v`
- `is_error_condition_enum_v`
- `is_execution_policy_v`
- `tuple_size_v`
- `variant_size_v`
- `uses_allocator_v`
- `variant_alternative_t`

C++20:

  - `compare_three_way_result_t`
  - `common_comparison_category_t`
  - `unwrap_ref_decay_t`
  - `unwrap_reference_t`

C++23:

- `is_implicit_lifetime_v`

C++26:

- `is_nothrow_relocatable_v`
- `is_replaceable_v`
- `is_trivially_relocatable_v`
- `is_virtual_base_of_v`

This doesn't add `treat_as_floating_point_v` or `is_clock_v` because
they require more invasive changes; instead I've opened #147072 to track
them.

Added: 
    

Modified: 
    clang-tools-extra/clang-tidy/modernize/TypeTraitsCheck.cpp
    clang-tools-extra/docs/ReleaseNotes.rst
    clang-tools-extra/docs/clang-tidy/checks/modernize/type-traits.rst
    clang-tools-extra/test/clang-tidy/checkers/modernize/type-traits.cpp

Removed: 
    


################################################################################
diff  --git a/clang-tools-extra/clang-tidy/modernize/TypeTraitsCheck.cpp 
b/clang-tools-extra/clang-tidy/modernize/TypeTraitsCheck.cpp
index c0766395ec5cc..ff0b3213cb58f 100644
--- a/clang-tools-extra/clang-tidy/modernize/TypeTraitsCheck.cpp
+++ b/clang-tools-extra/clang-tidy/modernize/TypeTraitsCheck.cpp
@@ -15,6 +15,9 @@ using namespace clang::ast_matchers;
 
 namespace clang::tidy::modernize {
 
+// FIXME: Add chrono::treat_as_floating_point_v and chrono::is_clock_v.
+// This will require restructuring the code to handle type traits not
+// defined directly in std.
 static const llvm::StringSet<> ValueTraits = {
     "alignment_of",
     "conjunction",
@@ -28,6 +31,7 @@ static const llvm::StringSet<> ValueTraits = {
     "is_array",
     "is_assignable",
     "is_base_of",
+    "is_bind_expression",
     "is_bounded_array",
     "is_class",
     "is_compound",
@@ -40,10 +44,14 @@ static const llvm::StringSet<> ValueTraits = {
     "is_destructible",
     "is_empty",
     "is_enum",
+    "is_error_code_enum",
+    "is_error_condition_enum",
+    "is_execution_policy",
     "is_final",
     "is_floating_point",
     "is_function",
     "is_fundamental",
+    "is_implicit_lifetime",
     "is_integral",
     "is_invocable",
     "is_invocable_r",
@@ -65,14 +73,17 @@ static const llvm::StringSet<> ValueTraits = {
     "is_nothrow_invocable_r",
     "is_nothrow_move_assignable",
     "is_nothrow_move_constructible",
+    "is_nothrow_relocatable",
     "is_nothrow_swappable",
     "is_nothrow_swappable_with",
     "is_null_pointer",
     "is_object",
+    "is_placeholder",
     "is_pointer",
     "is_pointer_interconvertible_base_of",
     "is_polymorphic",
     "is_reference",
+    "is_replaceable",
     "is_rvalue_reference",
     "is_same",
     "is_scalar",
@@ -91,15 +102,26 @@ static const llvm::StringSet<> ValueTraits = {
     "is_trivially_destructible",
     "is_trivially_move_assignable",
     "is_trivially_move_constructible",
+    "is_trivially_relocatable",
     "is_unbounded_array",
     "is_union",
     "is_unsigned",
+    "is_virtual_base_of",
     "is_void",
     "is_volatile",
     "negation",
     "rank",
+    "ratio_equal",
+    "ratio_greater_equal",
+    "ratio_greater",
+    "ratio_less_equal",
+    "ratio_less",
+    "ratio_not_equal",
     "reference_constructs_from_temporary",
     "reference_converts_from_temporary",
+    "tuple_size",
+    "uses_allocator",
+    "variant_size",
 };
 
 static const llvm::StringSet<> TypeTraits = {
@@ -130,6 +152,12 @@ static const llvm::StringSet<> TypeTraits = {
     "result_of",
     "invoke_result",
     "type_identity",
+    "compare_three_way_result",
+    "common_comparison_category",
+    "unwrap_ref_decay",
+    "unwrap_reference",
+    "tuple_element",
+    "variant_alternative",
 };
 
 static DeclarationName getName(const DependentScopeDeclRefExpr &D) {

diff  --git a/clang-tools-extra/docs/ReleaseNotes.rst 
b/clang-tools-extra/docs/ReleaseNotes.rst
index e021d6350694e..6856aa257d670 100644
--- a/clang-tools-extra/docs/ReleaseNotes.rst
+++ b/clang-tools-extra/docs/ReleaseNotes.rst
@@ -281,6 +281,9 @@ Changes in existing checks
   excluding variables with ``thread_local`` storage class specifier from being
   matched.
 
+- Improved :doc:`modernize-type-traits
+  <clang-tidy/checks/modernize/type-traits>` check by detecting more type 
traits.
+
 - Improved :doc:`modernize-use-default-member-init
   <clang-tidy/checks/modernize/use-default-member-init>` check by matching
   arithmetic operations, ``constexpr`` and ``static`` values, and detecting

diff  --git 
a/clang-tools-extra/docs/clang-tidy/checks/modernize/type-traits.rst 
b/clang-tools-extra/docs/clang-tidy/checks/modernize/type-traits.rst
index c2abde856c90f..0716160182cf2 100644
--- a/clang-tools-extra/docs/clang-tidy/checks/modernize/type-traits.rst
+++ b/clang-tools-extra/docs/clang-tidy/checks/modernize/type-traits.rst
@@ -38,3 +38,10 @@ Options
     #define IS_SIGNED(T) std::is_signed<T>::value
 
   Defaults to `false`. 
+
+Limitations
+-----------
+
+Does not currently diagnose uses of type traits with nested name
+specifiers (e.g. ``std::chrono::is_clock``,
+``std::chrono::treat_as_floating_point``).

diff  --git 
a/clang-tools-extra/test/clang-tidy/checkers/modernize/type-traits.cpp 
b/clang-tools-extra/test/clang-tidy/checkers/modernize/type-traits.cpp
index eaec70814d4f1..97ba1fce2a1ec 100644
--- a/clang-tools-extra/test/clang-tidy/checkers/modernize/type-traits.cpp
+++ b/clang-tools-extra/test/clang-tidy/checkers/modernize/type-traits.cpp
@@ -1,7 +1,7 @@
 // RUN: %check_clang_tidy -std=c++14 %s modernize-type-traits %t 
-check-suffixes=',MACRO'
 // RUN: %check_clang_tidy -std=c++14 %s modernize-type-traits %t -- \
 // RUN:   -config='{CheckOptions: {modernize-type-traits.IgnoreMacros: true}}'
-// RUN: %check_clang_tidy -std=c++17 %s modernize-type-traits %t 
-check-suffixes=',CXX17,MACRO,CXX17MACRO'
+// RUN: %check_clang_tidy -std=c++17-or-later %s modernize-type-traits %t 
-check-suffixes=',CXX17,MACRO,CXX17MACRO'
 
 namespace std {
   template <typename>
@@ -19,6 +19,11 @@ namespace std {
     using type = T;
   };
 
+  template <typename...>
+  struct common_type {
+    using type = int;
+  };
+
 inline namespace __std_lib_version1 {
   template<typename T>
   struct add_const {
@@ -66,6 +71,10 @@ using UsingNoTypename = std::enable_if<true>::type;
 // CHECK-MESSAGES: :[[@LINE-1]]:25: warning: use c++14 style type templates
 // CHECK-FIXES: using UsingNoTypename = std::enable_if_t<true>;
 
+using VariadicTrait = std::common_type<int, long, bool>::type;
+// CHECK-MESSAGES: :[[@LINE-1]]:23: warning: use c++14 style type templates
+// CHECK-FIXES: using VariadicTrait = std::common_type_t<int, long, bool>;
+
 using UsingSpace = std::enable_if <true>::type;
 // CHECK-MESSAGES: :[[@LINE-1]]:20: warning: use c++14 style type templates
 // CHECK-FIXES: using UsingSpace = std::enable_if_t <true>;


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

Reply via email to