Author: Fan Mo Date: 2026-07-03T09:25:07+02:00 New Revision: e8b509f10bf34082b6fb35eb35e34f77ea583bef
URL: https://github.com/llvm/llvm-project/commit/e8b509f10bf34082b6fb35eb35e34f77ea583bef DIFF: https://github.com/llvm/llvm-project/commit/e8b509f10bf34082b6fb35eb35e34f77ea583bef.diff LOG: [clang] use decl itself in static assert failed boolean condition printer (#203736) fixes #203701 `getName()` assumes the decl used in the static asserts has a simple identifier name, but in some cases like `operator int` don't — they fails the assertion `Name.isIdentifier() && "Name is not a simple identifier"` when the `static_assert` failure diagnostic tries to print the boolean expression. Switching to getDeclName() handles these special names properly. Reproducer: ```c++ struct S { constexpr S(auto) {} constexpr operator int() const { return 0; } }; constexpr auto a = [](this S) { return 1; }; static_assert((&decltype(a)::operator())(1) == 42); ``` --- One thing I'm not sure about: the print helper that walks the boolean expression lives in `SemaTemplate.cpp` (inside `printTemplateArgumentList` / the DiagRecursiveConstraintEval visitor area). Is there a historical reason for it being there rather than somewhere more general like `SemaOverload.cpp` or a shared diagnostic utility? Happy to move it if that makes more sense. --- AI used for generating & fixing unit test Added: clang/test/SemaCXX/GH203701.cpp Modified: clang/lib/Sema/SemaTemplate.cpp Removed: ################################################################################ diff --git a/clang/lib/Sema/SemaTemplate.cpp b/clang/lib/Sema/SemaTemplate.cpp index 9fe6a2ae209e8..96c3544847849 100644 --- a/clang/lib/Sema/SemaTemplate.cpp +++ b/clang/lib/Sema/SemaTemplate.cpp @@ -3650,7 +3650,7 @@ class FailedBooleanConditionPrinterHelper : public PrinterHelper { DR->getQualifier().print(OS, Policy, true); // Then print the decl itself. const ValueDecl *VD = DR->getDecl(); - OS << VD->getName(); + OS << *VD; if (const auto *IV = dyn_cast<VarTemplateSpecializationDecl>(VD)) { // This is a template variable, print the expanded template arguments. printTemplateArgumentList( diff --git a/clang/test/SemaCXX/GH203701.cpp b/clang/test/SemaCXX/GH203701.cpp new file mode 100644 index 0000000000000..f583865de9ac4 --- /dev/null +++ b/clang/test/SemaCXX/GH203701.cpp @@ -0,0 +1,14 @@ +// RUN: %clang_cc1 -std=c++2b -fsyntax-only -verify %s + +namespace GH203701 { + struct S { + constexpr S(auto) {} + constexpr operator int() const { return 0; } + }; + + constexpr auto a = [](this S) { return 1; }; + + static_assert((&decltype(a)::operator())(1) == 42, ""); // expected-error-re {{static assertion failed due to requirement '(&const GH203701::(lambda at {{.*}})::operator())(1) == 42'{{.*}}}} \ + // expected-note {{expression evaluates to '1 == 42'}} + static_assert((&S::operator int) == nullptr, ""); // expected-error {{static assertion failed due to requirement '(&GH203701::S::operator int) == nullptr'}} +} _______________________________________________ cfe-commits mailing list [email protected] https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
