llvmorg-github-actions[bot] wrote:
<!--LLVM PR SUMMARY COMMENT-->
@llvm/pr-subscribers-clang
Author: anondeveg
<details>
<summary>Changes</summary>
problem:
when using CUDA extension `>>>` gets lexed as a single
`tok::greatergreatergreater`
to support the kernel-launch syntax. so with code like:
```c++
template <template <template <int>>> struct S;
```
When three `>` instead close nested template parameter lists,
`ParseTemplateParameters` did not split that token the way it already splits
`>>`, so the parser desynced. For:
```c++
template <template <template <int>>> struct S;
```
generating unclear diagnostics.
before fix:
```bash
clang++ -x cuda --cuda-host-only -nocudainc -nocudalib -std=c++17 \
-fsyntax-only ../repro/reprofixme.cpp
../repro/reprofixme.cpp:1:39: error: expected a qualified name after 'typename'
1 | template <template <template <typename>>> struct S;
| ^
../repro/reprofixme.cpp:1:39: error: expected ',' or '>' in
template-parameter-list
../repro/reprofixme.cpp:1:51: error: expected identifier
1 | template <template <template <typename>>> struct S;
| ^
../repro/reprofixme.cpp:1:51: error: expected ',' or '>' in
template-parameter-list
../repro/reprofixme.cpp:1:51: error: expected identifier
../repro/reprofixme.cpp:1:51: error: expected ',' or '>' in
template-parameter-list
../repro/reprofixme.cpp:1:51: error: declaration does not declare anything
7 errors generated when compiling for host.
```
after:
```bash
bin/clang++ -x cuda --cuda-host-only -nocudainc -nocudalib -std=c++17 \
-fsyntax-only ../repro/reprofixme.cpp
../repro/reprofixme.cpp:1:35: error: template template parameter requires
'class' or 'typename' after the parameter list
1 | template <template <template <int>>> struct S;
| ^
| class
../repro/reprofixme.cpp:1:36: error: template template parameter requires
'class' or 'typename' after the parameter list
1 | template <template <template <int>>> struct S;
| ^
| class
2 errors generated when compiling for host.
```
matching what non-CUDA mode output.
---
Full diff: https://github.com/llvm/llvm-project/pull/219638.diff
2 Files Affected:
- (modified) clang/lib/Parse/ParseTemplate.cpp (+8-3)
- (added) clang/test/Parser/cuda-template-angle-brackets.cu (+3)
``````````diff
diff --git a/clang/lib/Parse/ParseTemplate.cpp
b/clang/lib/Parse/ParseTemplate.cpp
index 735a9bd1f9f1c..8d4dbf9db4a56 100644
--- a/clang/lib/Parse/ParseTemplate.cpp
+++ b/clang/lib/Parse/ParseTemplate.cpp
@@ -327,8 +327,8 @@ bool Parser::ParseTemplateParameters(
// Try to parse the template parameter list.
bool Failed = false;
- // FIXME: Missing greatergreatergreater support.
- if (!Tok.is(tok::greater) && !Tok.is(tok::greatergreater)) {
+ if (!Tok.is(tok::greater) && !Tok.is(tok::greatergreater) &&
+ !Tok.is(tok::greatergreatergreater)) {
TemplateScopes.Enter(Scope::TemplateParamScope);
Failed = ParseTemplateParameterList(Depth, TemplateParams);
}
@@ -342,6 +342,10 @@ bool Parser::ParseTemplateParameters(
Tok.setKind(tok::greater);
RAngleLoc = Tok.getLocation();
Tok.setLocation(Tok.getLocation().getLocWithOffset(1));
+ } else if (Tok.is(tok::greatergreatergreater)) {
+ Tok.setKind(tok::greatergreater);
+ RAngleLoc = Tok.getLocation();
+ Tok.setLocation(Tok.getLocation().getLocWithOffset(1));
} else if (!TryConsumeToken(tok::greater, RAngleLoc) && Failed) {
Diag(Tok.getLocation(), diag::err_expected) << tok::greater;
return true;
@@ -367,7 +371,8 @@ Parser::ParseTemplateParameterList(const unsigned Depth,
// Did we find a comma or the end of the template parameter list?
if (Tok.is(tok::comma)) {
ConsumeToken();
- } else if (Tok.isOneOf(tok::greater, tok::greatergreater)) {
+ } else if (Tok.isOneOf(tok::greater, tok::greatergreater,
+ tok::greatergreatergreater)) {
// Don't consume this... that's done by template parser.
break;
} else {
diff --git a/clang/test/Parser/cuda-template-angle-brackets.cu
b/clang/test/Parser/cuda-template-angle-brackets.cu
new file mode 100644
index 0000000000000..38d5a48e6b279
--- /dev/null
+++ b/clang/test/Parser/cuda-template-angle-brackets.cu
@@ -0,0 +1,3 @@
+// RUN: %clang_cc1 -fsyntax-only -verify %s
+
+template <template <template <int>>> struct S; // expected-error 2 {{template
template parameter requires 'class' or 'typename' after the parameter list}}
``````````
</details>
https://github.com/llvm/llvm-project/pull/219638
_______________________________________________
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits