This revision was landed with ongoing or failed builds. This revision was automatically updated to reflect the committed changes. Closed by commit rGfbfcfdbf6828: [clang] Fix assert() crash when checking undeduced arg alignment (authored by adamcz).
Repository: rG LLVM Github Monorepo CHANGES SINCE LAST ACTION https://reviews.llvm.org/D100667/new/ https://reviews.llvm.org/D100667 Files: clang/lib/Sema/SemaChecking.cpp clang/lib/Sema/SemaExpr.cpp clang/test/SemaCXX/recovery-expr-type.cpp Index: clang/test/SemaCXX/recovery-expr-type.cpp =================================================================== --- clang/test/SemaCXX/recovery-expr-type.cpp +++ clang/test/SemaCXX/recovery-expr-type.cpp @@ -1,4 +1,4 @@ -// RUN: %clang_cc1 -triple=x86_64-unknown-unknown -frecovery-ast -frecovery-ast-type -o - %s -fsyntax-only -verify +// RUN: %clang_cc1 -triple=x86_64-unknown-unknown -frecovery-ast -frecovery-ast-type -o - %s -std=gnu++17 -fsyntax-only -verify namespace test0 { struct Indestructible { @@ -26,7 +26,7 @@ void foo(); // expected-note 3{{requires 0 arguments}} void func() { // verify that "field has incomplete type" diagnostic is suppressed. - typeof(foo(42)) var; // expected-error {{no matching function}} + typeof(foo(42)) var; // expected-error {{no matching function}} \ // FIXME: suppress the "cannot initialize a variable" diagnostic. int a = foo(1); // expected-error {{no matching function}} \ @@ -116,3 +116,23 @@ template<typename T> const int k = f(T()); // expected-error {{no matching function}} static_assert(k<int> == 1, ""); // expected-note {{instantiation of}} } + +namespace test11 { +// Verify we do not assert()-fail here. +template <class T> void foo(T &t); +template <typename T> +void bar(T t) { + foo(t); +} + +template <typename T = void *> +struct S { // expected-note {{candidate}} + S(T t); // expected-note {{candidate}} + ~S(); +}; +template <typename T> S(T t) -> S<void *>; + +void baz() { + bar(S(123)); // expected-error {{no matching conversion}} +} +} // namespace test11 Index: clang/lib/Sema/SemaExpr.cpp =================================================================== --- clang/lib/Sema/SemaExpr.cpp +++ clang/lib/Sema/SemaExpr.cpp @@ -19662,8 +19662,10 @@ if (isSFINAEContext()) return ExprError(); - if (T.isNull() || !Context.getLangOpts().RecoveryASTType) + if (T.isNull() || T->isUndeducedType() || + !Context.getLangOpts().RecoveryASTType) // We don't know the concrete type, fallback to dependent type. T = Context.DependentTy; + return RecoveryExpr::Create(Context, T, Begin, End, SubExprs); } Index: clang/lib/Sema/SemaChecking.cpp =================================================================== --- clang/lib/Sema/SemaChecking.cpp +++ clang/lib/Sema/SemaChecking.cpp @@ -4540,8 +4540,7 @@ // Find expected alignment, and the actual alignment of the passed object. // getTypeAlignInChars requires complete types - if (ParamTy->isIncompleteType() || ArgTy->isIncompleteType() || - ParamTy->isUndeducedType() || ArgTy->isUndeducedType()) + if (ParamTy->isIncompleteType() || ArgTy->isIncompleteType()) return; CharUnits ParamAlign = Context.getTypeAlignInChars(ParamTy);
Index: clang/test/SemaCXX/recovery-expr-type.cpp =================================================================== --- clang/test/SemaCXX/recovery-expr-type.cpp +++ clang/test/SemaCXX/recovery-expr-type.cpp @@ -1,4 +1,4 @@ -// RUN: %clang_cc1 -triple=x86_64-unknown-unknown -frecovery-ast -frecovery-ast-type -o - %s -fsyntax-only -verify +// RUN: %clang_cc1 -triple=x86_64-unknown-unknown -frecovery-ast -frecovery-ast-type -o - %s -std=gnu++17 -fsyntax-only -verify namespace test0 { struct Indestructible { @@ -26,7 +26,7 @@ void foo(); // expected-note 3{{requires 0 arguments}} void func() { // verify that "field has incomplete type" diagnostic is suppressed. - typeof(foo(42)) var; // expected-error {{no matching function}} + typeof(foo(42)) var; // expected-error {{no matching function}} \ // FIXME: suppress the "cannot initialize a variable" diagnostic. int a = foo(1); // expected-error {{no matching function}} \ @@ -116,3 +116,23 @@ template<typename T> const int k = f(T()); // expected-error {{no matching function}} static_assert(k<int> == 1, ""); // expected-note {{instantiation of}} } + +namespace test11 { +// Verify we do not assert()-fail here. +template <class T> void foo(T &t); +template <typename T> +void bar(T t) { + foo(t); +} + +template <typename T = void *> +struct S { // expected-note {{candidate}} + S(T t); // expected-note {{candidate}} + ~S(); +}; +template <typename T> S(T t) -> S<void *>; + +void baz() { + bar(S(123)); // expected-error {{no matching conversion}} +} +} // namespace test11 Index: clang/lib/Sema/SemaExpr.cpp =================================================================== --- clang/lib/Sema/SemaExpr.cpp +++ clang/lib/Sema/SemaExpr.cpp @@ -19662,8 +19662,10 @@ if (isSFINAEContext()) return ExprError(); - if (T.isNull() || !Context.getLangOpts().RecoveryASTType) + if (T.isNull() || T->isUndeducedType() || + !Context.getLangOpts().RecoveryASTType) // We don't know the concrete type, fallback to dependent type. T = Context.DependentTy; + return RecoveryExpr::Create(Context, T, Begin, End, SubExprs); } Index: clang/lib/Sema/SemaChecking.cpp =================================================================== --- clang/lib/Sema/SemaChecking.cpp +++ clang/lib/Sema/SemaChecking.cpp @@ -4540,8 +4540,7 @@ // Find expected alignment, and the actual alignment of the passed object. // getTypeAlignInChars requires complete types - if (ParamTy->isIncompleteType() || ArgTy->isIncompleteType() || - ParamTy->isUndeducedType() || ArgTy->isUndeducedType()) + if (ParamTy->isIncompleteType() || ArgTy->isIncompleteType()) return; CharUnits ParamAlign = Context.getTypeAlignInChars(ParamTy);
_______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits