https://github.com/naveen-seth updated 
https://github.com/llvm/llvm-project/pull/166762

>From a774b14ab581542bb599c88faf96d4ac6e970798 Mon Sep 17 00:00:00 2001
From: naveen-seth <[email protected]>
Date: Thu, 6 Nov 2025 12:59:51 +0100
Subject: [PATCH] [clang][AST] Fix crash in constevaluated switch case
 statements

Fixes #166328.

Fixes a crash that occurs when constevaluating a function in a switch
case with a missing non-type template parameter.
This change guards against calling EvaluateKnownConstInt on
value-dependent expressions in switch cases.
---
 clang/lib/AST/ExprConstant.cpp                | 13 +++++---
 .../crash-constexpr-dependent-switch-case.cpp | 31 +++++++++++++++++++
 2 files changed, 40 insertions(+), 4 deletions(-)
 create mode 100644 clang/test/AST/crash-constexpr-dependent-switch-case.cpp

diff --git a/clang/lib/AST/ExprConstant.cpp b/clang/lib/AST/ExprConstant.cpp
index 8fab6efafb983..5320031f585e7 100644
--- a/clang/lib/AST/ExprConstant.cpp
+++ b/clang/lib/AST/ExprConstant.cpp
@@ -5452,10 +5452,15 @@ static EvalStmtResult EvaluateSwitch(StmtResult 
&Result, EvalInfo &Info,
     }
 
     const CaseStmt *CS = cast<CaseStmt>(SC);
-    APSInt LHS = CS->getLHS()->EvaluateKnownConstInt(Info.Ctx);
-    APSInt RHS = CS->getRHS() ? CS->getRHS()->EvaluateKnownConstInt(Info.Ctx)
-                              : LHS;
-    if (LHS <= Value && Value <= RHS) {
+    const Expr *LHSExpr = CS->getLHS();
+    const Expr *RHSExpr = CS->getLHS();
+    if (LHSExpr->isValueDependent() || (RHSExpr && 
RHSExpr->isValueDependent()))
+      return ESR_Failed;
+
+    APSInt LHSValue = LHSExpr->EvaluateKnownConstInt(Info.Ctx);
+    APSInt RHSValue =
+        RHSExpr ? RHSExpr->EvaluateKnownConstInt(Info.Ctx) : LHSValue;
+    if (LHSValue <= Value && Value <= RHSValue) {
       Found = SC;
       break;
     }
diff --git a/clang/test/AST/crash-constexpr-dependent-switch-case.cpp 
b/clang/test/AST/crash-constexpr-dependent-switch-case.cpp
new file mode 100644
index 0000000000000..68a62160a2e78
--- /dev/null
+++ b/clang/test/AST/crash-constexpr-dependent-switch-case.cpp
@@ -0,0 +1,31 @@
+// Fixes #166328
+// RUN: %clang_cc1 -std=c++14 -fsyntax-only -verify= %s
+
+// This function requires a non-type template argument, but we'll
+// intentionally misuse it by omitting the argument.
+// This should trigger an error, but must not crash the compiler when
+// used in a compile-time evaluated switch case statement.
+template<int n>
+constexpr int nonTypeTemplateParamFunc() { // expected-note 5 {{candidate 
template ignored: couldn't infer template argument 'n'}}
+  return n;
+}
+
+constexpr int switchWithErrs(int n) {
+  switch (n) {
+  case int(nonTypeTemplateParamFunc()): // expected-error {{no matching 
function for call to 'nonTypeTemplateParamFunc'}}
+    return n;
+  // GNU Case ranges (Extension)
+  case 0 ... int(nonTypeTemplateParamFunc()): // expected-error {{no matching 
function for call to 'nonTypeTemplateParamFunc'}}
+    return n;
+  case nonTypeTemplateParamFunc() ... 100: // expected-error {{no matching 
function for call to 'nonTypeTemplateParamFunc'}}
+    return n + 1;
+  case nonTypeTemplateParamFunc() ... nonTypeTemplateParamFunc(): // 
expected-error 2 {{no matching function for call to 'nonTypeTemplateParamFunc'}}
+    return n + 2;
+  default:
+    return 0;
+  }
+}
+
+auto main() -> int {
+  constexpr auto num = switchWithErrs(1); // expected-error {{constexpr 
variable 'num' must be initialized by a constant expression}}
+}

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

Reply via email to