[PATCH] D110727: [clang] don't instantiate templates with injected arguments
Matheus Izvekov via Phabricator via cfe-commits
cfe-commits at lists.llvm.org
Wed Sep 29 14:19:25 PDT 2021
This revision was landed with ongoing or failed builds.
This revision was automatically updated to reflect the committed changes.
Closed by commit rGaf10d6f350ff: [clang] don't instantiate templates with injected arguments (authored by mizvekov).
Repository:
rG LLVM Github Monorepo
CHANGES SINCE LAST ACTION
https://reviews.llvm.org/D110727/new/
https://reviews.llvm.org/D110727
Files:
clang/lib/Sema/SemaTemplateInstantiate.cpp
clang/test/SemaTemplate/generic-lambda.cpp
Index: clang/test/SemaTemplate/generic-lambda.cpp
===================================================================
--- /dev/null
+++ clang/test/SemaTemplate/generic-lambda.cpp
@@ -0,0 +1,62 @@
+// RUN: %clang_cc1 -std=c++20 -fsyntax-only -verify %s
+
+// expected-no-diagnostics
+
+template <class T, class U> constexpr bool is_same_v = false;
+template <class T> constexpr bool is_same_v<T, T> = true;
+template <class T, class U>
+concept is_same = is_same_v<T, U>;
+
+template <class T> struct X {};
+template <class T, class U>
+concept C1 = is_same<T, X<U>>;
+
+template <class T1> X<X<X<T1>>> t1() {
+ return []<class T2>(T2) -> X<X<T2>> {
+ struct S {
+ static X<X<T2>> f() {
+ return []<class T3>(T3) -> X<T3> {
+ static_assert(is_same<T2, X<T1>>);
+ static_assert(is_same<T3, X<T2>>);
+ return X<T3>();
+ }(X<T2>());
+ }
+ };
+ return S::f();
+ }(X<T1>());
+};
+template X<X<X<int>>> t1<int>();
+
+#if 0 // FIXME: crashes
+template<class T1> auto t2() {
+ return []<class T2>(T2) {
+ struct S {
+ static auto f() {
+ return []<class T3>(T3) {
+ static_assert(is_same<T2, X<T1>>);
+ static_assert(is_same<T3, X<T2>>);
+ return X<T3>();
+ }(X<T2>());
+ }
+ };
+ return S::f();
+ }(X<T1>());
+};
+template auto t2<int>();
+static_assert(is_same<decltype(t2<int>()), X<X<X<int>>>>);
+
+template<class T1> C1<X<X<T1>>> auto t3() {
+ return []<C1<T1> T2>(T2) -> C1<X<T2>> auto {
+ struct S {
+ static auto f() {
+ return []<C1<T2> T3>(T3) -> C1<T3> auto {
+ return X<T3>();
+ }(X<T2>());
+ }
+ };
+ return S::f();
+ }(X<T1>());
+};
+template C1<X<X<int>>> auto t3<int>();
+static_assert(is_same<decltype(t3<int>()), X<X<X<int>>>>);
+#endif
Index: clang/lib/Sema/SemaTemplateInstantiate.cpp
===================================================================
--- clang/lib/Sema/SemaTemplateInstantiate.cpp
+++ clang/lib/Sema/SemaTemplateInstantiate.cpp
@@ -161,10 +161,9 @@
if (isGenericLambdaCallOperatorOrStaticInvokerSpecialization(Function))
break;
- } else if (FunctionTemplateDecl *FunTmpl
- = Function->getDescribedFunctionTemplate()) {
- // Add the "injected" template arguments.
- Result.addOuterTemplateArguments(FunTmpl->getInjectedTemplateArgs());
+ } else if (Function->getDescribedFunctionTemplate()) {
+ assert(Result.getNumSubstitutedLevels() == 0 &&
+ "Outer template not instantiated?");
}
// If this is a friend declaration and it declares an entity at
@@ -180,11 +179,8 @@
}
} else if (CXXRecordDecl *Rec = dyn_cast<CXXRecordDecl>(Ctx)) {
if (ClassTemplateDecl *ClassTemplate = Rec->getDescribedClassTemplate()) {
- QualType T = ClassTemplate->getInjectedClassNameSpecialization();
- const TemplateSpecializationType *TST =
- cast<TemplateSpecializationType>(Context.getCanonicalType(T));
- Result.addOuterTemplateArguments(
- llvm::makeArrayRef(TST->getArgs(), TST->getNumArgs()));
+ assert(Result.getNumSubstitutedLevels() == 0 &&
+ "Outer template not instantiated?");
if (ClassTemplate->isMemberSpecialization())
break;
}
-------------- next part --------------
A non-text attachment was scrubbed...
Name: D110727.376033.patch
Type: text/x-patch
Size: 3346 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/cfe-commits/attachments/20210929/a098d5d2/attachment.bin>
More information about the cfe-commits
mailing list