Author: Hadong Lee
Date: 2026-08-24T14:44:42Z
New Revision: c7a7180a9f56a8a7150a3a2cf6d1e4a1dcf5972a

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

LOG: [clang-tidy] Fix modernize-use-noexcept crash on unparsed exception specs 
(#218256)

A failed template instantiation can leave a function type with an
`EST_Unparsed` exception specification.
`modernize-use-noexcept` currently calls
`FunctionProtoType::isNothrow()` for that type, which reaches an
unreachable path in `FunctionProtoType::canThrow()`.

This fixes the crash by skipping unparsed exception specifications
before querying whether the function is non-throwing.

Fixes #214291

Added: 
    
clang-tools-extra/test/clang-tidy/checkers/modernize/use-noexcept-unparsed-exception-spec.cpp

Modified: 
    clang-tools-extra/clang-tidy/modernize/UseNoexceptCheck.cpp
    clang-tools-extra/docs/ReleaseNotes.md

Removed: 
    


################################################################################
diff  --git a/clang-tools-extra/clang-tidy/modernize/UseNoexceptCheck.cpp 
b/clang-tools-extra/clang-tidy/modernize/UseNoexceptCheck.cpp
index 6bd5485abbac9..4641d56654e26 100644
--- a/clang-tools-extra/clang-tidy/modernize/UseNoexceptCheck.cpp
+++ b/clang-tools-extra/clang-tidy/modernize/UseNoexceptCheck.cpp
@@ -76,7 +76,8 @@ void UseNoexceptCheck::check(const MatchFinder::MatchResult 
&Result) {
   }
 
   assert(FnTy && "FunctionProtoType is null.");
-  if (isUnresolvedExceptionSpec(FnTy->getExceptionSpecType()))
+  if (FnTy->getExceptionSpecType() == EST_Unparsed ||
+      isUnresolvedExceptionSpec(FnTy->getExceptionSpecType()))
     return;
 
   assert(Range.isValid() && "Exception Source Range is invalid.");

diff  --git a/clang-tools-extra/docs/ReleaseNotes.md 
b/clang-tools-extra/docs/ReleaseNotes.md
index c2e90bc23eb25..6fe497e5f6eaf 100644
--- a/clang-tools-extra/docs/ReleaseNotes.md
+++ b/clang-tools-extra/docs/ReleaseNotes.md
@@ -173,6 +173,10 @@ infrastructure are described first, followed by 
tool-specific sections.
   `std::initializer_list` constructor, as the braced form could select a
   
diff erent constructor.
 
+- Fixed a crash in {doc}`modernize-use-noexcept
+  <clang-tidy/checks/modernize/use-noexcept>` when analyzing malformed template
+  code with an unparsed exception specification.
+
 - Improved {doc}`performance-inefficient-algorithm
   <clang-tidy/checks/performance/inefficient-algorithm>` check to no longer
   produce a fix with the container or the searched-for value missing, such as

diff  --git 
a/clang-tools-extra/test/clang-tidy/checkers/modernize/use-noexcept-unparsed-exception-spec.cpp
 
b/clang-tools-extra/test/clang-tidy/checkers/modernize/use-noexcept-unparsed-exception-spec.cpp
new file mode 100644
index 0000000000000..b7967e8558ac5
--- /dev/null
+++ 
b/clang-tools-extra/test/clang-tidy/checkers/modernize/use-noexcept-unparsed-exception-spec.cpp
@@ -0,0 +1,12 @@
+// RUN: %check_clang_tidy -std=c++11,c++14 -check-suffix=COMMON 
-expect-clang-tidy-error %s modernize-use-noexcept %t
+// RUN: %check_clang_tidy -std=c++17-or-later -check-suffixes=COMMON,CXX17 
-expect-clang-tidy-error %s modernize-use-noexcept %t
+
+struct S {
+  template <typename T>
+  static void f() throw(typename T::X);
+  // CHECK-MESSAGES-CXX17: :[[@LINE-1]]:19: error: ISO C++17 does not allow 
dynamic exception specifications [clang-diagnostic-dynamic-exception-spec]
+  // CHECK-MESSAGES-COMMON: :[[@LINE-2]]:19: warning: dynamic exception 
specification 'throw(typename T::X)' is deprecated; consider using 
'noexcept(false)' instead [modernize-use-noexcept]
+
+  typedef decltype(f<S>()) X;
+  // CHECK-MESSAGES-COMMON: :[[@LINE-1]]:20: error: exception specification is 
not available until end of class definition [clang-diagnostic-error]
+};


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

Reply via email to