[clang] b7ce85a - [Concepts] Fix isDeclarationSpecifier to detect type-constraints correctly
Richard Smith via cfe-commits
cfe-commits at lists.llvm.org
Fri Jan 31 10:21:03 PST 2020
On Fri, 31 Jan 2020, 10:08 Saar Raz via cfe-commits, <
cfe-commits at lists.llvm.org> wrote:
>
> Author: Saar Raz
> Date: 2020-01-31T20:08:13+02:00
> New Revision: b7ce85a130789d23c69156f4b899962458d1f05d
>
> URL:
> https://github.com/llvm/llvm-project/commit/b7ce85a130789d23c69156f4b899962458d1f05d
> DIFF:
> https://github.com/llvm/llvm-project/commit/b7ce85a130789d23c69156f4b899962458d1f05d.diff
>
> LOG: [Concepts] Fix isDeclarationSpecifier to detect type-constraints
> correctly
>
> isDeclarationSpecifiers did not handle some cases of
> placeholder-type-specifiers with
> type-constraints, causing parsing bugs in abbreviated constructor
> templates.
>
> Add comprehensive handling of type-constraints to isDeclarationSpecifier.
>
> Added:
>
>
> Modified:
> clang/lib/Parse/ParseDecl.cpp
> clang/test/Parser/cxx2a-abbreviated-templates.cpp
>
> Removed:
>
>
>
>
> ################################################################################
> diff --git a/clang/lib/Parse/ParseDecl.cpp b/clang/lib/Parse/ParseDecl.cpp
> index 871ca2512598..af6e105ca61f 100644
> --- a/clang/lib/Parse/ParseDecl.cpp
> +++ b/clang/lib/Parse/ParseDecl.cpp
> @@ -5061,6 +5061,8 @@ bool Parser::isDeclarationSpecifier(bool
> DisambiguatingWithExpression) {
> // recurse to handle whatever we get.
> if (TryAnnotateTypeOrScopeToken())
> return true;
> + if (TryAnnotateTypeConstraint())
> + return true;
> if (Tok.is(tok::identifier))
> return false;
>
> @@ -5193,11 +5195,14 @@ bool Parser::isDeclarationSpecifier(bool
> DisambiguatingWithExpression) {
>
> // placeholder-type-specifier
> case tok::annot_template_id: {
> - TemplateIdAnnotation *TemplateId = takeTemplateIdAnnotation(Tok);
> - return TemplateId->Kind == TNK_Concept_template &&
> + return isTypeConstraintAnnotation() &&
> (NextToken().is(tok::kw_auto) ||
> NextToken().is(tok::kw_decltype));
> }
> -
> + case tok::annot_cxxscope:
> + if (NextToken().is(tok::identifier) && TryAnnotateTypeConstraint())
> + return true;
>
Our behaviour here (on invalid code) depends on whether we've already
annotated the type constraint (if not, we don't require the next token to
be auto/decltype). It'd be good to be consistent here.
Incidentally, if we see any kind of (possibly-qualified) identifier or
template-id followed by auto/decltype, I think we should classify it as a
decl-specifier to improve error recovery when there's a typo in a concept
name.
+ return isTypeConstraintAnnotation() &&
> + GetLookAheadToken(2).isOneOf(tok::kw_auto, tok::kw_decltype);
> case tok::kw___declspec:
> case tok::kw___cdecl:
> case tok::kw___stdcall:
>
> diff --git a/clang/test/Parser/cxx2a-abbreviated-templates.cpp
> b/clang/test/Parser/cxx2a-abbreviated-templates.cpp
> index e2b3803c807e..6562389f7676 100644
> --- a/clang/test/Parser/cxx2a-abbreviated-templates.cpp
> +++ b/clang/test/Parser/cxx2a-abbreviated-templates.cpp
> @@ -9,11 +9,36 @@ namespace ns {
> concept D = true;
> }
>
> -void foo(C auto a,
> - C<int> auto b,
> - ns::D auto c,
> - ns::D<int> auto d,
> - const C auto e,
> - const C<int> auto f,
> - const ns::D auto g,
> - const ns::D<int> auto h);
> \ No newline at end of file
> +void foo1(C auto a,
> + C<int> auto b,
> + ns::D auto c,
> + ns::D<int> auto d,
> + const C auto e,
> + const C<int> auto f,
> + const ns::D auto g,
> + const ns::D<int> auto h);
> +void foo2(C auto a);
> +void foo3(C<int> auto b);
> +void foo4(ns::D auto c);
> +void foo5(ns::D<int> auto d);
> +void foo6(const C auto e);
> +void foo7(const C<int> auto f);
> +void foo8(const ns::D auto g);
> +void foo9(const ns::D<int> auto h);
> +
> +struct S1 { S1(C auto a,
> + C<int> auto b,
> + ns::D auto c,
> + ns::D<int> auto d,
> + const C auto e,
> + const C<int> auto f,
> + const ns::D auto g,
> + const ns::D<int> auto h); };
> +struct S2 { S2(C auto a); };
> +struct S3 { S3(C<int> auto b); };
> +struct S4 { S4(ns::D auto c); };
> +struct S5 { S5(ns::D<int> auto d); };
> +struct S6 { S6(const C auto e); };
> +struct S7 { S7(const C<int> auto f); };
> +struct S8 { S8(const ns::D auto g); };
> +struct S9 { S9(const ns::D<int> auto h); };
> \ No newline at end of file
>
>
>
> _______________________________________________
> cfe-commits mailing list
> cfe-commits at lists.llvm.org
> https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.llvm.org/pipermail/cfe-commits/attachments/20200131/4429fc45/attachment.html>
More information about the cfe-commits
mailing list