[clang] [clang][Sema] Fix Issue: #166957 - type inconsistency for constrained auto variables(Fixes #166957) (PR #167100)
via cfe-commits
cfe-commits at lists.llvm.org
Fri Nov 7 22:36:55 PST 2025
https://github.com/KaushalMorankar created https://github.com/llvm/llvm-project/pull/167100
```markdown
Fixes #166957
This PR fixes an inconsistency where `getTypeSourceInfo()->getType()` and `getType()` return different `AutoType` instances with different `isDependentType()` values for constrained auto variables in dependent contexts.
Solution
The fix adds logic in ActOnVariableDeclarator (clang/lib/Sema/SemaDecl.cpp:7700-7719) to check if a constrained AutoType is being created, and ensures its dependency status matches the declaration context:
- In dependent contexts (e.g., templates): undeduced constrained autos are marked as dependent
- In non-dependent contexts: they are not marked as dependent
The fix reconstructs the AutoType with the correct dependency flag and updates the TypeSourceInfo to maintain consistency between both type retrieval methods.
Testing
Added comprehensive test coverage in clang/test/SemaCXX/constrained-auto-type-consistency.cpp which includes:
- Constrained auto in abbreviated function templates (dependent context)
- Constrained auto at namespace scope (non-dependent context) etc.
All tests pass with expected-no-diagnostics, confirming the fix resolves the inconsistency without introducing new issues.
Files Changed
- clang/lib/Sema/SemaDecl.cpp: Added logic to ensure AutoType dependency consistency
- clang/test/SemaCXX/constrained-auto-type-consistency.cpp: New test file (92 lines)
>From e413e6242644ce89aad131fed5ca2e120b35e86d Mon Sep 17 00:00:00 2001
From: KaushalMorankar <kaushal.n.morankar at gmail.com>
Date: Sat, 8 Nov 2025 11:44:08 +0530
Subject: [PATCH] [clang][Sema] Fix Issue: #166957 - type inconsistency for
constrained auto variables
---
clang/lib/Sema/SemaDecl.cpp | 20 ++++
.../constrained-auto-type-consistency.cpp | 92 +++++++++++++++++++
2 files changed, 112 insertions(+)
create mode 100644 clang/test/SemaCXX/constrained-auto-type-consistency.cpp
diff --git a/clang/lib/Sema/SemaDecl.cpp b/clang/lib/Sema/SemaDecl.cpp
index 086dd8ba1c670..99877615c50bf 100644
--- a/clang/lib/Sema/SemaDecl.cpp
+++ b/clang/lib/Sema/SemaDecl.cpp
@@ -7697,6 +7697,26 @@ NamedDecl *Sema::ActOnVariableDeclarator(
LookupResult &Previous, MultiTemplateParamsArg TemplateParamLists,
bool &AddToScope, ArrayRef<BindingDecl *> Bindings) {
QualType R = TInfo->getType();
+
+ if (const AutoType *AT = R->getContainedAutoType()) {
+ if (AT->isConstrained()) {
+ bool IsInDependentContext = DC->isDependentContext();
+ bool ShouldBeDependent = IsInDependentContext && !AT->isDeduced();
+
+ if (ShouldBeDependent != AT->isDependentType()) {
+ QualType CanonAuto = Context.getAutoType(
+ AT->isDeduced() ? AT->getDeducedType() : QualType(),
+ AT->getKeyword(),
+ ShouldBeDependent,
+ false,
+ AT->getTypeConstraintConcept(),
+ AT->getTypeConstraintArguments());
+
+ R = Context.getQualifiedType(CanonAuto, R.getQualifiers());
+ TInfo = Context.getTrivialTypeSourceInfo(R, D.getBeginLoc());
+ }
+ }
+ }
DeclarationName Name = GetNameForDeclarator(D).getName();
IdentifierInfo *II = Name.getAsIdentifierInfo();
diff --git a/clang/test/SemaCXX/constrained-auto-type-consistency.cpp b/clang/test/SemaCXX/constrained-auto-type-consistency.cpp
new file mode 100644
index 0000000000000..7f6cec1604151
--- /dev/null
+++ b/clang/test/SemaCXX/constrained-auto-type-consistency.cpp
@@ -0,0 +1,92 @@
+// expected-no-diagnostics
+// RUN: %clang_cc1 -std=c++20 -fsyntax-only -verify %s
+
+namespace std {
+ template<typename T>
+ concept integral = __is_integral(T);
+
+ template<typename T>
+ concept floating_point = __is_floating_point(T);
+}
+
+// Constrained auto in abbreviated function template
+void find(auto value) {
+ std::integral auto var = value;
+}
+
+// Constrained auto at namespace scope (non-dependent context)
+// Should be deduced immediately
+std::integral auto globalVar = 42;
+
+// Multiple constrained autos in template function
+template<typename T>
+void multipleConstrainedAutos(T value) {
+ std::integral auto x = 10;
+ std::floating_point auto y = 3.14;
+ std::integral auto z = value; // dependent on T
+}
+
+// Constrained auto with qualifiers
+void testQualifiers(auto value) {
+ const std::integral auto cv1 = value;
+ std::integral auto const cv2 = value;
+}
+
+// Nested constrained auto
+void testNested(auto outer) {
+ auto lambda = [](auto inner) {
+ std::integral auto nested = inner;
+ return nested;
+ };
+
+ std::integral auto result = lambda(outer);
+}
+
+// Constrained auto with references
+void testReferences(auto value) {
+ std::integral auto& ref = value;
+ const std::integral auto& cref = value;
+}
+
+// Regular unconstrained auto (should not be affected by the fix)
+void testUnconstrainedAuto(auto value) {
+ auto regular = value;
+ decltype(auto) decl_auto = (value);
+}
+
+// Constrained auto in class template member
+template<typename T>
+struct Container {
+ void process(auto item) {
+ std::integral auto local = item;
+ }
+};
+
+// Constrained auto deduction from function call
+std::integral auto getInteger() { return 42; }
+
+void testFunctionReturn(auto param) {
+ std::integral auto fromFunc = getInteger();
+ std::integral auto fromParam = param;
+}
+
+// Ensure the fix doesn't break normal non-template constrained auto
+void normalFunction() {
+ std::integral auto x = 100;
+ // This should be immediately deduced to int, not dependent
+}
+
+// Instantiate templates to verify no crashes
+void instantiateAll() {
+ find(42);
+ multipleConstrainedAutos(5);
+ testQualifiers(7);
+ testNested(8);
+ int val = 10;
+ testReferences(val);
+ testUnconstrainedAuto(11);
+ Container<int> c;
+ c.process(12);
+ testFunctionReturn(13);
+ normalFunction();
+}
More information about the cfe-commits
mailing list