[clang] [clang][bytecode] Avoid crash in constexpr wcslen on invalid argument… (PR #177891)
Ayush Kumar Gaur via cfe-commits
cfe-commits at lists.llvm.org
Sun Jan 25 19:14:37 PST 2026
https://github.com/Ayush3941 created https://github.com/llvm/llvm-project/pull/177891
### What the problem ?
Fix a clang bytecode constant interpreter crash when evaluating wcslen("x") in a constant-expression path.
Previously we asserted on wchar element size mismatch and crashed in assertion builds.
### Why it happened
The expression is already ill-typed (char[2] → const wchar_t*), clang correctly emits a diagnostic, but later ICE checking tries to fold the expression and reaches the builtin handler. That path must not crash.
### whats the Fix
Replace the assert(ElemSize == wchar_t size) with a graceful failure (return false / emit appropriate diagnostic) when element sizes don’t match, so evaluation stops safely.
### how to Test it
Add a regression test that triggers ICE checking with -fexperimental-new-constant-interpreter and ensures clang does not crash (verifies it reports the type error / static_assert failure instead).
Fixes #177844.
<img width="1366" height="768" alt="Screenshot_2026-01-25_22_07_50" src="https://github.com/user-attachments/assets/488dd0b0-3c17-4f45-b2d0-9339b8fd3409" />
where wclen_crash.c is
`
#include <wchar.h>
static_assert(wcslen("x") == 'x');
int main() {}
`
>From 7679af9795c8a9769e4e2a298ca4ed9db5183ee8 Mon Sep 17 00:00:00 2001
From: Ayush3941 <ayushkgaur1 at gmail.com>
Date: Sun, 25 Jan 2026 22:00:57 -0500
Subject: [PATCH] [clang][bytecode] Avoid crash in constexpr wcslen on invalid
argument type
---
clang/lib/AST/ByteCode/InterpBuiltin.cpp | 12 ++++++++++--
1 file changed, 10 insertions(+), 2 deletions(-)
diff --git a/clang/lib/AST/ByteCode/InterpBuiltin.cpp b/clang/lib/AST/ByteCode/InterpBuiltin.cpp
index d668fa118d3b9..e2517730e81ca 100644
--- a/clang/lib/AST/ByteCode/InterpBuiltin.cpp
+++ b/clang/lib/AST/ByteCode/InterpBuiltin.cpp
@@ -367,10 +367,18 @@ static bool interp__builtin_strlen(InterpState &S, CodePtr OpPC,
unsigned ElemSize = StrPtr.getFieldDesc()->getElemSize();
if (ID == Builtin::BI__builtin_wcslen || ID == Builtin::BIwcslen) {
- [[maybe_unused]] const ASTContext &AC = S.getASTContext();
- assert(ElemSize == AC.getTypeSizeInChars(AC.getWCharType()).getQuantity());
+ const ASTContext &AC = S.getASTContext();
+ unsigned WCharSize = AC.getTypeSizeInChars(AC.getWCharType()).getQuantity();
+ if (ElemSize != WCharSize) {
+ if (S.diagnosing()) {
+ // a dedicated diagnostic
+ diagnoseNonConstexprBuiltin(S, OpPC, ID);
+ }
+ return false;
+ }
}
+
size_t Len = 0;
for (size_t I = StrPtr.getIndex();; ++I, ++Len) {
const Pointer &ElemPtr = StrPtr.atIndex(I);
More information about the cfe-commits
mailing list