blob: 45f6da0d0591f776e4ba44aea2fa69e5cbae539e [file] [log] [blame]
Alexey Bataeva769e072013-03-22 06:34:35 +00001//===--- ParseOpenMP.cpp - OpenMP directives parsing ----------------------===//
2//
3// The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9/// \file
10/// \brief This file implements parsing of all OpenMP directives and clauses.
11///
12//===----------------------------------------------------------------------===//
13
Chandler Carruth5553d0d2014-01-07 11:51:46 +000014#include "RAIIObjectsForParser.h"
Alexey Bataev9959db52014-05-06 10:08:46 +000015#include "clang/AST/ASTConsumer.h"
16#include "clang/AST/ASTContext.h"
Alexey Bataev5ec3eb12013-07-19 03:13:43 +000017#include "clang/AST/StmtOpenMP.h"
Alexey Bataeva769e072013-03-22 06:34:35 +000018#include "clang/Parse/ParseDiagnostic.h"
Alexey Bataev6f6f3b42013-05-13 04:18:18 +000019#include "clang/Parse/Parser.h"
20#include "clang/Sema/Scope.h"
21#include "llvm/ADT/PointerIntPair.h"
Alexey Bataeva769e072013-03-22 06:34:35 +000022using namespace clang;
23
24//===----------------------------------------------------------------------===//
25// OpenMP declarative directives.
26//===----------------------------------------------------------------------===//
27
Alexey Bataev4acb8592014-07-07 13:01:15 +000028static OpenMPDirectiveKind ParseOpenMPDirectiveKind(Parser &P) {
Alexander Musmanf82886e2014-09-18 05:12:34 +000029 // Array of foldings: F[i][0] F[i][1] ===> F[i][2].
30 // E.g.: OMPD_for OMPD_simd ===> OMPD_for_simd
31 // TODO: add other combined directives in topological order.
32 const OpenMPDirectiveKind F[][3] = {
33 { OMPD_for, OMPD_simd, OMPD_for_simd },
34 { OMPD_parallel, OMPD_for, OMPD_parallel_for },
35 { OMPD_parallel, OMPD_sections, OMPD_parallel_sections }
36 };
Alexey Bataev4acb8592014-07-07 13:01:15 +000037 auto Tok = P.getCurToken();
38 auto DKind =
39 Tok.isAnnotation()
40 ? OMPD_unknown
41 : getOpenMPDirectiveKind(P.getPreprocessor().getSpelling(Tok));
Alexander Musmanf82886e2014-09-18 05:12:34 +000042 for (unsigned i = 0; i < llvm::array_lengthof(F); ++i) {
43 if (DKind == F[i][0]) {
44 Tok = P.getPreprocessor().LookAhead(0);
45 auto SDKind =
46 Tok.isAnnotation()
47 ? OMPD_unknown
48 : getOpenMPDirectiveKind(P.getPreprocessor().getSpelling(Tok));
49 if (SDKind == F[i][1]) {
50 P.ConsumeToken();
51 DKind = F[i][2];
52 }
Alexey Bataev4acb8592014-07-07 13:01:15 +000053 }
54 }
55 return DKind;
56}
57
Alexey Bataev6f6f3b42013-05-13 04:18:18 +000058/// \brief Parsing of declarative OpenMP directives.
59///
60/// threadprivate-directive:
61/// annot_pragma_openmp 'threadprivate' simple-variable-list
Alexey Bataeva769e072013-03-22 06:34:35 +000062///
63Parser::DeclGroupPtrTy Parser::ParseOpenMPDeclarativeDirective() {
64 assert(Tok.is(tok::annot_pragma_openmp) && "Not an OpenMP directive!");
Alexey Bataevee6507d2013-11-18 08:17:37 +000065 ParenBraceBracketBalancer BalancerRAIIObj(*this);
Alexey Bataeva769e072013-03-22 06:34:35 +000066
67 SourceLocation Loc = ConsumeToken();
Alexey Bataev6f6f3b42013-05-13 04:18:18 +000068 SmallVector<Expr *, 5> Identifiers;
Alexey Bataev4acb8592014-07-07 13:01:15 +000069 auto DKind = ParseOpenMPDirectiveKind(*this);
Alexey Bataev6f6f3b42013-05-13 04:18:18 +000070
71 switch (DKind) {
Alexey Bataeva769e072013-03-22 06:34:35 +000072 case OMPD_threadprivate:
73 ConsumeToken();
Alexey Bataev6f6f3b42013-05-13 04:18:18 +000074 if (!ParseOpenMPSimpleVarList(OMPD_threadprivate, Identifiers, true)) {
Alexey Bataeva769e072013-03-22 06:34:35 +000075 // The last seen token is annot_pragma_openmp_end - need to check for
76 // extra tokens.
77 if (Tok.isNot(tok::annot_pragma_openmp_end)) {
78 Diag(Tok, diag::warn_omp_extra_tokens_at_eol)
Alexey Bataeva55ed262014-05-28 06:15:33 +000079 << getOpenMPDirectiveName(OMPD_threadprivate);
Alp Tokerd751fa72013-12-18 19:10:49 +000080 SkipUntil(tok::annot_pragma_openmp_end, StopBeforeMatch);
Alexey Bataeva769e072013-03-22 06:34:35 +000081 }
Alexey Bataev6f6f3b42013-05-13 04:18:18 +000082 // Skip the last annot_pragma_openmp_end.
Alexey Bataeva769e072013-03-22 06:34:35 +000083 ConsumeToken();
Alexey Bataeva55ed262014-05-28 06:15:33 +000084 return Actions.ActOnOpenMPThreadprivateDirective(Loc, Identifiers);
Alexey Bataeva769e072013-03-22 06:34:35 +000085 }
86 break;
87 case OMPD_unknown:
88 Diag(Tok, diag::err_omp_unknown_directive);
89 break;
Alexey Bataev5ec3eb12013-07-19 03:13:43 +000090 case OMPD_parallel:
Alexey Bataev1b59ab52014-02-27 08:29:12 +000091 case OMPD_simd:
Alexey Bataev5ec3eb12013-07-19 03:13:43 +000092 case OMPD_task:
Alexey Bataev68446b72014-07-18 07:47:19 +000093 case OMPD_taskyield:
Alexey Bataev4d1dfea2014-07-18 09:11:51 +000094 case OMPD_barrier:
Alexey Bataev2df347a2014-07-18 10:17:07 +000095 case OMPD_taskwait:
Alexey Bataev6125da92014-07-21 11:26:11 +000096 case OMPD_flush:
Alexey Bataevf29276e2014-06-18 04:14:57 +000097 case OMPD_for:
Alexander Musmanf82886e2014-09-18 05:12:34 +000098 case OMPD_for_simd:
Alexey Bataevd3f8dd22014-06-25 11:44:49 +000099 case OMPD_sections:
Alexey Bataev1e0498a2014-06-26 08:21:58 +0000100 case OMPD_section:
Alexey Bataevd1e40fb2014-06-26 12:05:45 +0000101 case OMPD_single:
Alexander Musman80c22892014-07-17 08:54:58 +0000102 case OMPD_master:
Alexey Bataev9fb6e642014-07-22 06:45:04 +0000103 case OMPD_ordered:
Alexander Musmand9ed09f2014-07-21 09:42:05 +0000104 case OMPD_critical:
Alexey Bataev4acb8592014-07-07 13:01:15 +0000105 case OMPD_parallel_for:
Alexey Bataev84d0b3e2014-07-08 08:12:03 +0000106 case OMPD_parallel_sections:
Alexey Bataev0162e452014-07-22 10:10:35 +0000107 case OMPD_atomic:
Alexey Bataev0bd520b2014-09-19 08:19:49 +0000108 case OMPD_target:
Alexey Bataeva769e072013-03-22 06:34:35 +0000109 Diag(Tok, diag::err_omp_unexpected_directive)
Alexey Bataeva55ed262014-05-28 06:15:33 +0000110 << getOpenMPDirectiveName(DKind);
Alexey Bataeva769e072013-03-22 06:34:35 +0000111 break;
112 }
Alp Tokerd751fa72013-12-18 19:10:49 +0000113 SkipUntil(tok::annot_pragma_openmp_end);
Alexey Bataeva769e072013-03-22 06:34:35 +0000114 return DeclGroupPtrTy();
115}
116
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000117/// \brief Parsing of declarative or executable OpenMP directives.
118///
119/// threadprivate-directive:
120/// annot_pragma_openmp 'threadprivate' simple-variable-list
121/// annot_pragma_openmp_end
122///
Alexey Bataevd3f8dd22014-06-25 11:44:49 +0000123/// executable-directive:
Alexey Bataevd1e40fb2014-06-26 12:05:45 +0000124/// annot_pragma_openmp 'parallel' | 'simd' | 'for' | 'sections' |
Alexander Musmand9ed09f2014-07-21 09:42:05 +0000125/// 'section' | 'single' | 'master' | 'critical' [ '(' <name> ')' ] |
126/// 'parallel for' | 'parallel sections' | 'task' | 'taskyield' |
Alexander Musmanf82886e2014-09-18 05:12:34 +0000127/// 'barrier' | 'taskwait' | 'flush' | 'ordered' | 'atomic' |
Alexey Bataev0bd520b2014-09-19 08:19:49 +0000128/// 'for simd' | 'target' {clause}
Alexey Bataev9fb6e642014-07-22 06:45:04 +0000129/// annot_pragma_openmp_end
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000130///
Alexey Bataev68446b72014-07-18 07:47:19 +0000131StmtResult
132Parser::ParseOpenMPDeclarativeOrExecutableDirective(bool StandAloneAllowed) {
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000133 assert(Tok.is(tok::annot_pragma_openmp) && "Not an OpenMP directive!");
Alexey Bataevee6507d2013-11-18 08:17:37 +0000134 ParenBraceBracketBalancer BalancerRAIIObj(*this);
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000135 SmallVector<Expr *, 5> Identifiers;
136 SmallVector<OMPClause *, 5> Clauses;
Alexey Bataev4ca40ed2014-05-12 04:23:46 +0000137 SmallVector<llvm::PointerIntPair<OMPClause *, 1, bool>, OMPC_unknown + 1>
Alexey Bataeva55ed262014-05-28 06:15:33 +0000138 FirstClauses(OMPC_unknown + 1);
Alexander Musmana8e9d2e2014-06-03 10:16:47 +0000139 unsigned ScopeFlags =
Alexey Bataeva55ed262014-05-28 06:15:33 +0000140 Scope::FnScope | Scope::DeclScope | Scope::OpenMPDirectiveScope;
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000141 SourceLocation Loc = ConsumeToken(), EndLoc;
Alexey Bataev4acb8592014-07-07 13:01:15 +0000142 auto DKind = ParseOpenMPDirectiveKind(*this);
Alexey Bataev758e55e2013-09-06 18:03:48 +0000143 // Name of critical directive.
144 DeclarationNameInfo DirName;
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000145 StmtResult Directive = StmtError();
Alexey Bataev68446b72014-07-18 07:47:19 +0000146 bool HasAssociatedStatement = true;
Alexey Bataev6125da92014-07-21 11:26:11 +0000147 bool FlushHasClause = false;
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000148
149 switch (DKind) {
150 case OMPD_threadprivate:
151 ConsumeToken();
152 if (!ParseOpenMPSimpleVarList(OMPD_threadprivate, Identifiers, false)) {
153 // The last seen token is annot_pragma_openmp_end - need to check for
154 // extra tokens.
155 if (Tok.isNot(tok::annot_pragma_openmp_end)) {
156 Diag(Tok, diag::warn_omp_extra_tokens_at_eol)
Alexey Bataeva55ed262014-05-28 06:15:33 +0000157 << getOpenMPDirectiveName(OMPD_threadprivate);
Alp Tokerd751fa72013-12-18 19:10:49 +0000158 SkipUntil(tok::annot_pragma_openmp_end, StopBeforeMatch);
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000159 }
160 DeclGroupPtrTy Res =
Alexey Bataeva55ed262014-05-28 06:15:33 +0000161 Actions.ActOnOpenMPThreadprivateDirective(Loc, Identifiers);
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000162 Directive = Actions.ActOnDeclStmt(Res, Loc, Tok.getLocation());
163 }
Alp Tokerd751fa72013-12-18 19:10:49 +0000164 SkipUntil(tok::annot_pragma_openmp_end);
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000165 break;
Alexey Bataev6125da92014-07-21 11:26:11 +0000166 case OMPD_flush:
167 if (PP.LookAhead(0).is(tok::l_paren)) {
168 FlushHasClause = true;
169 // Push copy of the current token back to stream to properly parse
170 // pseudo-clause OMPFlushClause.
171 PP.EnterToken(Tok);
172 }
Alexey Bataev68446b72014-07-18 07:47:19 +0000173 case OMPD_taskyield:
Alexey Bataev4d1dfea2014-07-18 09:11:51 +0000174 case OMPD_barrier:
Alexey Bataev2df347a2014-07-18 10:17:07 +0000175 case OMPD_taskwait:
Alexey Bataev68446b72014-07-18 07:47:19 +0000176 if (!StandAloneAllowed) {
177 Diag(Tok, diag::err_omp_immediate_directive)
178 << getOpenMPDirectiveName(DKind);
179 }
180 HasAssociatedStatement = false;
Alexey Bataev6125da92014-07-21 11:26:11 +0000181 // Fall through for further analysis.
Alexey Bataev1b59ab52014-02-27 08:29:12 +0000182 case OMPD_parallel:
Alexey Bataevf29276e2014-06-18 04:14:57 +0000183 case OMPD_simd:
Alexey Bataevd3f8dd22014-06-25 11:44:49 +0000184 case OMPD_for:
Alexander Musmanf82886e2014-09-18 05:12:34 +0000185 case OMPD_for_simd:
Alexey Bataev1e0498a2014-06-26 08:21:58 +0000186 case OMPD_sections:
Alexey Bataevd1e40fb2014-06-26 12:05:45 +0000187 case OMPD_single:
Alexey Bataev4acb8592014-07-07 13:01:15 +0000188 case OMPD_section:
Alexander Musman80c22892014-07-17 08:54:58 +0000189 case OMPD_master:
Alexander Musmand9ed09f2014-07-21 09:42:05 +0000190 case OMPD_critical:
Alexey Bataev84d0b3e2014-07-08 08:12:03 +0000191 case OMPD_parallel_for:
Alexey Bataev9c2e8ee2014-07-11 11:25:16 +0000192 case OMPD_parallel_sections:
Alexey Bataev9fb6e642014-07-22 06:45:04 +0000193 case OMPD_task:
Alexey Bataev0162e452014-07-22 10:10:35 +0000194 case OMPD_ordered:
Alexey Bataev0bd520b2014-09-19 08:19:49 +0000195 case OMPD_atomic:
196 case OMPD_target: {
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000197 ConsumeToken();
Alexander Musmand9ed09f2014-07-21 09:42:05 +0000198 // Parse directive name of the 'critical' directive if any.
199 if (DKind == OMPD_critical) {
200 BalancedDelimiterTracker T(*this, tok::l_paren,
201 tok::annot_pragma_openmp_end);
202 if (!T.consumeOpen()) {
203 if (Tok.isAnyIdentifier()) {
204 DirName =
205 DeclarationNameInfo(Tok.getIdentifierInfo(), Tok.getLocation());
206 ConsumeAnyToken();
207 } else {
208 Diag(Tok, diag::err_omp_expected_identifier_for_critical);
209 }
210 T.consumeClose();
211 }
212 }
Alexey Bataev758e55e2013-09-06 18:03:48 +0000213
Alexey Bataevf29276e2014-06-18 04:14:57 +0000214 if (isOpenMPLoopDirective(DKind))
215 ScopeFlags |= Scope::OpenMPLoopDirectiveScope;
216 if (isOpenMPSimdDirective(DKind))
217 ScopeFlags |= Scope::OpenMPSimdDirectiveScope;
218 ParseScope OMPDirectiveScope(this, ScopeFlags);
Alexey Bataevbae9a792014-06-27 10:37:06 +0000219 Actions.StartOpenMPDSABlock(DKind, DirName, Actions.getCurScope(), Loc);
Alexey Bataev758e55e2013-09-06 18:03:48 +0000220
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000221 while (Tok.isNot(tok::annot_pragma_openmp_end)) {
Alexey Bataev6125da92014-07-21 11:26:11 +0000222 OpenMPClauseKind CKind =
223 Tok.isAnnotation()
224 ? OMPC_unknown
225 : FlushHasClause ? OMPC_flush
226 : getOpenMPClauseKind(PP.getSpelling(Tok));
227 FlushHasClause = false;
Alexey Bataeva55ed262014-05-28 06:15:33 +0000228 OMPClause *Clause =
229 ParseOpenMPClause(DKind, CKind, !FirstClauses[CKind].getInt());
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000230 FirstClauses[CKind].setInt(true);
231 if (Clause) {
232 FirstClauses[CKind].setPointer(Clause);
233 Clauses.push_back(Clause);
234 }
235
236 // Skip ',' if any.
237 if (Tok.is(tok::comma))
238 ConsumeToken();
239 }
240 // End location of the directive.
241 EndLoc = Tok.getLocation();
242 // Consume final annot_pragma_openmp_end.
243 ConsumeToken();
244
245 StmtResult AssociatedStmt;
246 bool CreateDirective = true;
Alexey Bataev68446b72014-07-18 07:47:19 +0000247 if (HasAssociatedStatement) {
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000248 // The body is a block scope like in Lambdas and Blocks.
249 Sema::CompoundScopeRAII CompoundScope(Actions);
Alexey Bataevbae9a792014-06-27 10:37:06 +0000250 Actions.ActOnOpenMPRegionStart(DKind, getCurScope());
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000251 Actions.ActOnStartOfCompoundStmt();
252 // Parse statement
253 AssociatedStmt = ParseStatement();
254 Actions.ActOnFinishOfCompoundStmt();
255 if (!AssociatedStmt.isUsable()) {
256 Actions.ActOnCapturedRegionError();
257 CreateDirective = false;
258 } else {
Nikola Smiljanic01a75982014-05-29 10:55:11 +0000259 AssociatedStmt = Actions.ActOnCapturedRegionEnd(AssociatedStmt.get());
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000260 CreateDirective = AssociatedStmt.isUsable();
261 }
262 }
263 if (CreateDirective)
Alexey Bataeva55ed262014-05-28 06:15:33 +0000264 Directive = Actions.ActOnOpenMPExecutableDirective(
Alexander Musmand9ed09f2014-07-21 09:42:05 +0000265 DKind, DirName, Clauses, AssociatedStmt.get(), Loc, EndLoc);
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000266
267 // Exit scope.
Alexey Bataev758e55e2013-09-06 18:03:48 +0000268 Actions.EndOpenMPDSABlock(Directive.get());
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000269 OMPDirectiveScope.Exit();
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000270 break;
Alexey Bataeva55ed262014-05-28 06:15:33 +0000271 }
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000272 case OMPD_unknown:
273 Diag(Tok, diag::err_omp_unknown_directive);
Alp Tokerd751fa72013-12-18 19:10:49 +0000274 SkipUntil(tok::annot_pragma_openmp_end);
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000275 break;
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000276 }
277 return Directive;
278}
279
Alexey Bataeva769e072013-03-22 06:34:35 +0000280/// \brief Parses list of simple variables for '#pragma omp threadprivate'
Alexey Bataev6f6f3b42013-05-13 04:18:18 +0000281/// directive.
Alexey Bataeva769e072013-03-22 06:34:35 +0000282///
Alexey Bataev6f6f3b42013-05-13 04:18:18 +0000283/// simple-variable-list:
284/// '(' id-expression {, id-expression} ')'
285///
286bool Parser::ParseOpenMPSimpleVarList(OpenMPDirectiveKind Kind,
287 SmallVectorImpl<Expr *> &VarList,
288 bool AllowScopeSpecifier) {
289 VarList.clear();
Alexey Bataeva769e072013-03-22 06:34:35 +0000290 // Parse '('.
Alp Tokerd751fa72013-12-18 19:10:49 +0000291 BalancedDelimiterTracker T(*this, tok::l_paren, tok::annot_pragma_openmp_end);
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000292 if (T.expectAndConsume(diag::err_expected_lparen_after,
293 getOpenMPDirectiveName(Kind)))
294 return true;
295 bool IsCorrect = true;
Alexey Bataev6f6f3b42013-05-13 04:18:18 +0000296 bool NoIdentIsFound = true;
Alexey Bataeva769e072013-03-22 06:34:35 +0000297
298 // Read tokens while ')' or annot_pragma_openmp_end is not found.
Alexey Bataev6f6f3b42013-05-13 04:18:18 +0000299 while (Tok.isNot(tok::r_paren) && Tok.isNot(tok::annot_pragma_openmp_end)) {
Alexey Bataeva769e072013-03-22 06:34:35 +0000300 CXXScopeSpec SS;
301 SourceLocation TemplateKWLoc;
302 UnqualifiedId Name;
303 // Read var name.
304 Token PrevTok = Tok;
Alexey Bataev6f6f3b42013-05-13 04:18:18 +0000305 NoIdentIsFound = false;
Alexey Bataeva769e072013-03-22 06:34:35 +0000306
Alexey Bataev6f6f3b42013-05-13 04:18:18 +0000307 if (AllowScopeSpecifier && getLangOpts().CPlusPlus &&
308 ParseOptionalCXXScopeSpecifier(SS, ParsedType(), false)) {
Alexey Bataeva769e072013-03-22 06:34:35 +0000309 IsCorrect = false;
310 SkipUntil(tok::comma, tok::r_paren, tok::annot_pragma_openmp_end,
Alp Tokerd751fa72013-12-18 19:10:49 +0000311 StopBeforeMatch);
Alexey Bataev6f6f3b42013-05-13 04:18:18 +0000312 } else if (ParseUnqualifiedId(SS, false, false, false, ParsedType(),
313 TemplateKWLoc, Name)) {
Alexey Bataeva769e072013-03-22 06:34:35 +0000314 IsCorrect = false;
315 SkipUntil(tok::comma, tok::r_paren, tok::annot_pragma_openmp_end,
Alp Tokerd751fa72013-12-18 19:10:49 +0000316 StopBeforeMatch);
Alexey Bataev6f6f3b42013-05-13 04:18:18 +0000317 } else if (Tok.isNot(tok::comma) && Tok.isNot(tok::r_paren) &&
318 Tok.isNot(tok::annot_pragma_openmp_end)) {
319 IsCorrect = false;
320 SkipUntil(tok::comma, tok::r_paren, tok::annot_pragma_openmp_end,
Alp Tokerd751fa72013-12-18 19:10:49 +0000321 StopBeforeMatch);
Alp Tokerec543272013-12-24 09:48:30 +0000322 Diag(PrevTok.getLocation(), diag::err_expected)
323 << tok::identifier
324 << SourceRange(PrevTok.getLocation(), PrevTokLocation);
Alexey Bataeva769e072013-03-22 06:34:35 +0000325 } else {
Alexey Bataev6f6f3b42013-05-13 04:18:18 +0000326 DeclarationNameInfo NameInfo = Actions.GetNameFromUnqualifiedId(Name);
Alexey Bataeva55ed262014-05-28 06:15:33 +0000327 ExprResult Res =
328 Actions.ActOnOpenMPIdExpression(getCurScope(), SS, NameInfo);
Alexey Bataev6f6f3b42013-05-13 04:18:18 +0000329 if (Res.isUsable())
Nikola Smiljanic01a75982014-05-29 10:55:11 +0000330 VarList.push_back(Res.get());
Alexey Bataeva769e072013-03-22 06:34:35 +0000331 }
332 // Consume ','.
333 if (Tok.is(tok::comma)) {
334 ConsumeToken();
335 }
Alexey Bataeva769e072013-03-22 06:34:35 +0000336 }
337
Alexey Bataev6f6f3b42013-05-13 04:18:18 +0000338 if (NoIdentIsFound) {
Alp Tokerec543272013-12-24 09:48:30 +0000339 Diag(Tok, diag::err_expected) << tok::identifier;
Alexey Bataev6f6f3b42013-05-13 04:18:18 +0000340 IsCorrect = false;
341 }
342
343 // Parse ')'.
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000344 IsCorrect = !T.consumeClose() && IsCorrect;
Alexey Bataev6f6f3b42013-05-13 04:18:18 +0000345
346 return !IsCorrect && VarList.empty();
Alexey Bataeva769e072013-03-22 06:34:35 +0000347}
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000348
349/// \brief Parsing of OpenMP clauses.
350///
351/// clause:
Alexey Bataev3778b602014-07-17 07:32:53 +0000352/// if-clause | final-clause | num_threads-clause | safelen-clause |
353/// default-clause | private-clause | firstprivate-clause | shared-clause
354/// | linear-clause | aligned-clause | collapse-clause |
355/// lastprivate-clause | reduction-clause | proc_bind-clause |
Alexey Bataev74ba3a52014-07-17 12:47:03 +0000356/// schedule-clause | copyin-clause | copyprivate-clause | untied-clause |
Alexey Bataev67a4f222014-07-23 10:25:33 +0000357/// mergeable-clause | flush-clause | read-clause | write-clause |
Alexey Bataev82bad8b2014-07-24 08:55:34 +0000358/// update-clause | capture-clause | seq_cst-clause
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000359///
360OMPClause *Parser::ParseOpenMPClause(OpenMPDirectiveKind DKind,
361 OpenMPClauseKind CKind, bool FirstClause) {
Craig Topper161e4db2014-05-21 06:02:52 +0000362 OMPClause *Clause = nullptr;
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000363 bool ErrorFound = false;
364 // Check if clause is allowed for the given directive.
365 if (CKind != OMPC_unknown && !isAllowedClauseForDirective(DKind, CKind)) {
Alexey Bataeva55ed262014-05-28 06:15:33 +0000366 Diag(Tok, diag::err_omp_unexpected_clause) << getOpenMPClauseName(CKind)
367 << getOpenMPDirectiveName(DKind);
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000368 ErrorFound = true;
369 }
370
371 switch (CKind) {
Alexey Bataevaadd52e2014-02-13 05:29:23 +0000372 case OMPC_if:
Alexey Bataev3778b602014-07-17 07:32:53 +0000373 case OMPC_final:
Alexey Bataev568a8332014-03-06 06:15:19 +0000374 case OMPC_num_threads:
Alexey Bataev62c87d22014-03-21 04:51:18 +0000375 case OMPC_safelen:
Alexander Musman8bd31e62014-05-27 15:12:19 +0000376 case OMPC_collapse:
Alexey Bataevaadd52e2014-02-13 05:29:23 +0000377 // OpenMP [2.5, Restrictions]
378 // At most one if clause can appear on the directive.
Alexey Bataev568a8332014-03-06 06:15:19 +0000379 // At most one num_threads clause can appear on the directive.
Alexey Bataev62c87d22014-03-21 04:51:18 +0000380 // OpenMP [2.8.1, simd construct, Restrictions]
Alexander Musman8bd31e62014-05-27 15:12:19 +0000381 // Only one safelen clause can appear on a simd directive.
382 // Only one collapse clause can appear on a simd directive.
Alexey Bataev3778b602014-07-17 07:32:53 +0000383 // OpenMP [2.11.1, task Construct, Restrictions]
384 // At most one if clause can appear on the directive.
385 // At most one final clause can appear on the directive.
Alexey Bataevaadd52e2014-02-13 05:29:23 +0000386 if (!FirstClause) {
Alexey Bataeva55ed262014-05-28 06:15:33 +0000387 Diag(Tok, diag::err_omp_more_one_clause) << getOpenMPDirectiveName(DKind)
388 << getOpenMPClauseName(CKind);
Alexey Bataevdea47612014-07-23 07:46:59 +0000389 ErrorFound = true;
Alexey Bataevaadd52e2014-02-13 05:29:23 +0000390 }
391
392 Clause = ParseOpenMPSingleExprClause(CKind);
393 break;
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000394 case OMPC_default:
Alexey Bataevbcbadb62014-05-06 06:04:14 +0000395 case OMPC_proc_bind:
Alexey Bataevaadd52e2014-02-13 05:29:23 +0000396 // OpenMP [2.14.3.1, Restrictions]
397 // Only a single default clause may be specified on a parallel, task or
398 // teams directive.
Alexey Bataevbcbadb62014-05-06 06:04:14 +0000399 // OpenMP [2.5, parallel Construct, Restrictions]
400 // At most one proc_bind clause can appear on the directive.
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000401 if (!FirstClause) {
Alexey Bataeva55ed262014-05-28 06:15:33 +0000402 Diag(Tok, diag::err_omp_more_one_clause) << getOpenMPDirectiveName(DKind)
403 << getOpenMPClauseName(CKind);
Alexey Bataevdea47612014-07-23 07:46:59 +0000404 ErrorFound = true;
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000405 }
406
407 Clause = ParseOpenMPSimpleClause(CKind);
408 break;
Alexey Bataev56dafe82014-06-20 07:16:17 +0000409 case OMPC_schedule:
410 // OpenMP [2.7.1, Restrictions, p. 3]
411 // Only one schedule clause can appear on a loop directive.
412 if (!FirstClause) {
413 Diag(Tok, diag::err_omp_more_one_clause) << getOpenMPDirectiveName(DKind)
414 << getOpenMPClauseName(CKind);
Alexey Bataevdea47612014-07-23 07:46:59 +0000415 ErrorFound = true;
Alexey Bataev56dafe82014-06-20 07:16:17 +0000416 }
417
418 Clause = ParseOpenMPSingleExprWithArgClause(CKind);
419 break;
Alexey Bataev142e1fc2014-06-20 09:44:06 +0000420 case OMPC_ordered:
Alexey Bataev236070f2014-06-20 11:19:47 +0000421 case OMPC_nowait:
Alexey Bataev7aea99a2014-07-17 12:19:31 +0000422 case OMPC_untied:
Alexey Bataev74ba3a52014-07-17 12:47:03 +0000423 case OMPC_mergeable:
Alexey Bataevf98b00c2014-07-23 02:27:21 +0000424 case OMPC_read:
Alexey Bataevdea47612014-07-23 07:46:59 +0000425 case OMPC_write:
Alexey Bataev67a4f222014-07-23 10:25:33 +0000426 case OMPC_update:
Alexey Bataev459dec02014-07-24 06:46:57 +0000427 case OMPC_capture:
Alexey Bataev82bad8b2014-07-24 08:55:34 +0000428 case OMPC_seq_cst:
Alexey Bataev142e1fc2014-06-20 09:44:06 +0000429 // OpenMP [2.7.1, Restrictions, p. 9]
430 // Only one ordered clause can appear on a loop directive.
Alexey Bataev236070f2014-06-20 11:19:47 +0000431 // OpenMP [2.7.1, Restrictions, C/C++, p. 4]
432 // Only one nowait clause can appear on a for directive.
Alexey Bataev142e1fc2014-06-20 09:44:06 +0000433 if (!FirstClause) {
434 Diag(Tok, diag::err_omp_more_one_clause) << getOpenMPDirectiveName(DKind)
435 << getOpenMPClauseName(CKind);
Alexey Bataevdea47612014-07-23 07:46:59 +0000436 ErrorFound = true;
Alexey Bataev142e1fc2014-06-20 09:44:06 +0000437 }
438
439 Clause = ParseOpenMPClause(CKind);
440 break;
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000441 case OMPC_private:
Alexey Bataevd5af8e42013-10-01 05:32:34 +0000442 case OMPC_firstprivate:
Alexander Musman1bb328c2014-06-04 13:06:39 +0000443 case OMPC_lastprivate:
Alexey Bataev758e55e2013-09-06 18:03:48 +0000444 case OMPC_shared:
Alexey Bataevc5e02582014-06-16 07:08:35 +0000445 case OMPC_reduction:
Alexander Musman8dba6642014-04-22 13:09:42 +0000446 case OMPC_linear:
Alexander Musmanf0d76e72014-05-29 14:36:25 +0000447 case OMPC_aligned:
Alexey Bataevd48bcd82014-03-31 03:36:38 +0000448 case OMPC_copyin:
Alexey Bataevbae9a792014-06-27 10:37:06 +0000449 case OMPC_copyprivate:
Alexey Bataev6125da92014-07-21 11:26:11 +0000450 case OMPC_flush:
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000451 Clause = ParseOpenMPVarListClause(CKind);
452 break;
453 case OMPC_unknown:
454 Diag(Tok, diag::warn_omp_extra_tokens_at_eol)
Alexey Bataeva55ed262014-05-28 06:15:33 +0000455 << getOpenMPDirectiveName(DKind);
Alp Tokerd751fa72013-12-18 19:10:49 +0000456 SkipUntil(tok::annot_pragma_openmp_end, StopBeforeMatch);
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000457 break;
458 case OMPC_threadprivate:
Alexey Bataeva55ed262014-05-28 06:15:33 +0000459 Diag(Tok, diag::err_omp_unexpected_clause) << getOpenMPClauseName(CKind)
460 << getOpenMPDirectiveName(DKind);
Alp Tokerd751fa72013-12-18 19:10:49 +0000461 SkipUntil(tok::comma, tok::annot_pragma_openmp_end, StopBeforeMatch);
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000462 break;
463 }
Craig Topper161e4db2014-05-21 06:02:52 +0000464 return ErrorFound ? nullptr : Clause;
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000465}
466
Alexey Bataevaadd52e2014-02-13 05:29:23 +0000467/// \brief Parsing of OpenMP clauses with single expressions like 'if',
Alexey Bataev3778b602014-07-17 07:32:53 +0000468/// 'final', 'collapse', 'safelen', 'num_threads', 'simdlen', 'num_teams' or
Alexey Bataevaadd52e2014-02-13 05:29:23 +0000469/// 'thread_limit'.
470///
471/// if-clause:
472/// 'if' '(' expression ')'
473///
Alexey Bataev3778b602014-07-17 07:32:53 +0000474/// final-clause:
475/// 'final' '(' expression ')'
476///
Alexey Bataev62c87d22014-03-21 04:51:18 +0000477/// num_threads-clause:
478/// 'num_threads' '(' expression ')'
479///
480/// safelen-clause:
481/// 'safelen' '(' expression ')'
482///
Alexander Musman8bd31e62014-05-27 15:12:19 +0000483/// collapse-clause:
484/// 'collapse' '(' expression ')'
485///
Alexey Bataevaadd52e2014-02-13 05:29:23 +0000486OMPClause *Parser::ParseOpenMPSingleExprClause(OpenMPClauseKind Kind) {
487 SourceLocation Loc = ConsumeToken();
488
489 BalancedDelimiterTracker T(*this, tok::l_paren, tok::annot_pragma_openmp_end);
490 if (T.expectAndConsume(diag::err_expected_lparen_after,
491 getOpenMPClauseName(Kind)))
Craig Topper161e4db2014-05-21 06:02:52 +0000492 return nullptr;
Alexey Bataevaadd52e2014-02-13 05:29:23 +0000493
494 ExprResult LHS(ParseCastExpression(false, false, NotTypeCast));
495 ExprResult Val(ParseRHSOfBinaryExpression(LHS, prec::Conditional));
496
Alexey Bataevaadd52e2014-02-13 05:29:23 +0000497 // Parse ')'.
498 T.consumeClose();
499
500 if (Val.isInvalid())
Craig Topper161e4db2014-05-21 06:02:52 +0000501 return nullptr;
Alexey Bataevaadd52e2014-02-13 05:29:23 +0000502
Alexey Bataeva55ed262014-05-28 06:15:33 +0000503 return Actions.ActOnOpenMPSingleExprClause(
Nikola Smiljanic01a75982014-05-29 10:55:11 +0000504 Kind, Val.get(), Loc, T.getOpenLocation(), T.getCloseLocation());
Alexey Bataevaadd52e2014-02-13 05:29:23 +0000505}
506
Alexey Bataevbcbadb62014-05-06 06:04:14 +0000507/// \brief Parsing of simple OpenMP clauses like 'default' or 'proc_bind'.
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000508///
509/// default-clause:
510/// 'default' '(' 'none' | 'shared' ')
511///
Alexey Bataevbcbadb62014-05-06 06:04:14 +0000512/// proc_bind-clause:
513/// 'proc_bind' '(' 'master' | 'close' | 'spread' ')
514///
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000515OMPClause *Parser::ParseOpenMPSimpleClause(OpenMPClauseKind Kind) {
516 SourceLocation Loc = Tok.getLocation();
517 SourceLocation LOpen = ConsumeToken();
518 // Parse '('.
Alp Tokerd751fa72013-12-18 19:10:49 +0000519 BalancedDelimiterTracker T(*this, tok::l_paren, tok::annot_pragma_openmp_end);
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000520 if (T.expectAndConsume(diag::err_expected_lparen_after,
521 getOpenMPClauseName(Kind)))
Craig Topper161e4db2014-05-21 06:02:52 +0000522 return nullptr;
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000523
Alexey Bataeva55ed262014-05-28 06:15:33 +0000524 unsigned Type = getOpenMPSimpleClauseType(
525 Kind, Tok.isAnnotation() ? "" : PP.getSpelling(Tok));
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000526 SourceLocation TypeLoc = Tok.getLocation();
527 if (Tok.isNot(tok::r_paren) && Tok.isNot(tok::comma) &&
528 Tok.isNot(tok::annot_pragma_openmp_end))
529 ConsumeAnyToken();
530
531 // Parse ')'.
532 T.consumeClose();
533
534 return Actions.ActOnOpenMPSimpleClause(Kind, Type, TypeLoc, LOpen, Loc,
535 Tok.getLocation());
536}
537
Alexey Bataev142e1fc2014-06-20 09:44:06 +0000538/// \brief Parsing of OpenMP clauses like 'ordered'.
539///
540/// ordered-clause:
541/// 'ordered'
542///
Alexey Bataev236070f2014-06-20 11:19:47 +0000543/// nowait-clause:
544/// 'nowait'
545///
Alexey Bataev7aea99a2014-07-17 12:19:31 +0000546/// untied-clause:
547/// 'untied'
548///
Alexey Bataev74ba3a52014-07-17 12:47:03 +0000549/// mergeable-clause:
550/// 'mergeable'
551///
Alexey Bataevf98b00c2014-07-23 02:27:21 +0000552/// read-clause:
553/// 'read'
554///
Alexey Bataev142e1fc2014-06-20 09:44:06 +0000555OMPClause *Parser::ParseOpenMPClause(OpenMPClauseKind Kind) {
556 SourceLocation Loc = Tok.getLocation();
557 ConsumeAnyToken();
558
559 return Actions.ActOnOpenMPClause(Kind, Loc, Tok.getLocation());
560}
561
562
Alexey Bataev56dafe82014-06-20 07:16:17 +0000563/// \brief Parsing of OpenMP clauses with single expressions and some additional
564/// argument like 'schedule' or 'dist_schedule'.
565///
566/// schedule-clause:
567/// 'schedule' '(' kind [',' expression ] ')'
568///
569OMPClause *Parser::ParseOpenMPSingleExprWithArgClause(OpenMPClauseKind Kind) {
570 SourceLocation Loc = ConsumeToken();
571 SourceLocation CommaLoc;
572 // Parse '('.
573 BalancedDelimiterTracker T(*this, tok::l_paren, tok::annot_pragma_openmp_end);
574 if (T.expectAndConsume(diag::err_expected_lparen_after,
575 getOpenMPClauseName(Kind)))
576 return nullptr;
577
578 ExprResult Val;
579 unsigned Type = getOpenMPSimpleClauseType(
580 Kind, Tok.isAnnotation() ? "" : PP.getSpelling(Tok));
581 SourceLocation KLoc = Tok.getLocation();
582 if (Tok.isNot(tok::r_paren) && Tok.isNot(tok::comma) &&
583 Tok.isNot(tok::annot_pragma_openmp_end))
584 ConsumeAnyToken();
585
586 if (Kind == OMPC_schedule &&
587 (Type == OMPC_SCHEDULE_static || Type == OMPC_SCHEDULE_dynamic ||
588 Type == OMPC_SCHEDULE_guided) &&
589 Tok.is(tok::comma)) {
590 CommaLoc = ConsumeAnyToken();
591 ExprResult LHS(ParseCastExpression(false, false, NotTypeCast));
592 Val = ParseRHSOfBinaryExpression(LHS, prec::Conditional);
593 if (Val.isInvalid())
594 return nullptr;
595 }
596
597 // Parse ')'.
598 T.consumeClose();
599
600 return Actions.ActOnOpenMPSingleExprWithArgClause(
601 Kind, Type, Val.get(), Loc, T.getOpenLocation(), KLoc, CommaLoc,
602 T.getCloseLocation());
603}
604
Alexey Bataevc5e02582014-06-16 07:08:35 +0000605static bool ParseReductionId(Parser &P, CXXScopeSpec &ReductionIdScopeSpec,
606 UnqualifiedId &ReductionId) {
607 SourceLocation TemplateKWLoc;
608 if (ReductionIdScopeSpec.isEmpty()) {
609 auto OOK = OO_None;
610 switch (P.getCurToken().getKind()) {
611 case tok::plus:
612 OOK = OO_Plus;
613 break;
614 case tok::minus:
615 OOK = OO_Minus;
616 break;
617 case tok::star:
618 OOK = OO_Star;
619 break;
620 case tok::amp:
621 OOK = OO_Amp;
622 break;
623 case tok::pipe:
624 OOK = OO_Pipe;
625 break;
626 case tok::caret:
627 OOK = OO_Caret;
628 break;
629 case tok::ampamp:
630 OOK = OO_AmpAmp;
631 break;
632 case tok::pipepipe:
633 OOK = OO_PipePipe;
634 break;
635 default:
636 break;
637 }
638 if (OOK != OO_None) {
639 SourceLocation OpLoc = P.ConsumeToken();
Alexey Bataev23b69422014-06-18 07:08:49 +0000640 SourceLocation SymbolLocations[] = {OpLoc, OpLoc, SourceLocation()};
Alexey Bataevc5e02582014-06-16 07:08:35 +0000641 ReductionId.setOperatorFunctionId(OpLoc, OOK, SymbolLocations);
642 return false;
643 }
644 }
645 return P.ParseUnqualifiedId(ReductionIdScopeSpec, /*EnteringContext*/ false,
646 /*AllowDestructorName*/ false,
647 /*AllowConstructorName*/ false, ParsedType(),
648 TemplateKWLoc, ReductionId);
649}
650
Alexander Musman1bb328c2014-06-04 13:06:39 +0000651/// \brief Parsing of OpenMP clause 'private', 'firstprivate', 'lastprivate',
Alexey Bataev6125da92014-07-21 11:26:11 +0000652/// 'shared', 'copyin', 'copyprivate', 'flush' or 'reduction'.
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000653///
654/// private-clause:
655/// 'private' '(' list ')'
Alexey Bataevd5af8e42013-10-01 05:32:34 +0000656/// firstprivate-clause:
657/// 'firstprivate' '(' list ')'
Alexander Musman1bb328c2014-06-04 13:06:39 +0000658/// lastprivate-clause:
659/// 'lastprivate' '(' list ')'
Alexey Bataev758e55e2013-09-06 18:03:48 +0000660/// shared-clause:
661/// 'shared' '(' list ')'
Alexander Musman8dba6642014-04-22 13:09:42 +0000662/// linear-clause:
663/// 'linear' '(' list [ ':' linear-step ] ')'
Alexander Musmanf0d76e72014-05-29 14:36:25 +0000664/// aligned-clause:
665/// 'aligned' '(' list [ ':' alignment ] ')'
Alexey Bataevc5e02582014-06-16 07:08:35 +0000666/// reduction-clause:
667/// 'reduction' '(' reduction-identifier ':' list ')'
Alexey Bataev6125da92014-07-21 11:26:11 +0000668/// copyprivate-clause:
669/// 'copyprivate' '(' list ')'
670/// flush-clause:
671/// 'flush' '(' list ')'
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000672///
673OMPClause *Parser::ParseOpenMPVarListClause(OpenMPClauseKind Kind) {
674 SourceLocation Loc = Tok.getLocation();
675 SourceLocation LOpen = ConsumeToken();
Alexander Musman8dba6642014-04-22 13:09:42 +0000676 SourceLocation ColonLoc = SourceLocation();
Alexey Bataevc5e02582014-06-16 07:08:35 +0000677 // Optional scope specifier and unqualified id for reduction identifier.
678 CXXScopeSpec ReductionIdScopeSpec;
679 UnqualifiedId ReductionId;
680 bool InvalidReductionId = false;
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000681 // Parse '('.
Alp Tokerd751fa72013-12-18 19:10:49 +0000682 BalancedDelimiterTracker T(*this, tok::l_paren, tok::annot_pragma_openmp_end);
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000683 if (T.expectAndConsume(diag::err_expected_lparen_after,
684 getOpenMPClauseName(Kind)))
Craig Topper161e4db2014-05-21 06:02:52 +0000685 return nullptr;
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000686
Alexey Bataevc5e02582014-06-16 07:08:35 +0000687 // Handle reduction-identifier for reduction clause.
688 if (Kind == OMPC_reduction) {
689 ColonProtectionRAIIObject ColonRAII(*this);
690 if (getLangOpts().CPlusPlus) {
691 ParseOptionalCXXScopeSpecifier(ReductionIdScopeSpec, ParsedType(), false);
692 }
693 InvalidReductionId =
694 ParseReductionId(*this, ReductionIdScopeSpec, ReductionId);
695 if (InvalidReductionId) {
696 SkipUntil(tok::colon, tok::r_paren, tok::annot_pragma_openmp_end,
697 StopBeforeMatch);
698 }
699 if (Tok.is(tok::colon)) {
700 ColonLoc = ConsumeToken();
701 } else {
702 Diag(Tok, diag::warn_pragma_expected_colon) << "reduction identifier";
703 }
704 }
705
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000706 SmallVector<Expr *, 5> Vars;
Alexey Bataevc5e02582014-06-16 07:08:35 +0000707 bool IsComma = !InvalidReductionId;
Alexander Musmanf0d76e72014-05-29 14:36:25 +0000708 const bool MayHaveTail = (Kind == OMPC_linear || Kind == OMPC_aligned);
Alexander Musman8dba6642014-04-22 13:09:42 +0000709 while (IsComma || (Tok.isNot(tok::r_paren) && Tok.isNot(tok::colon) &&
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000710 Tok.isNot(tok::annot_pragma_openmp_end))) {
Alexander Musman8dba6642014-04-22 13:09:42 +0000711 ColonProtectionRAIIObject ColonRAII(*this, MayHaveTail);
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000712 // Parse variable
713 ExprResult VarExpr = ParseAssignmentExpression();
714 if (VarExpr.isUsable()) {
Nikola Smiljanic01a75982014-05-29 10:55:11 +0000715 Vars.push_back(VarExpr.get());
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000716 } else {
717 SkipUntil(tok::comma, tok::r_paren, tok::annot_pragma_openmp_end,
Alp Tokerd751fa72013-12-18 19:10:49 +0000718 StopBeforeMatch);
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000719 }
720 // Skip ',' if any
721 IsComma = Tok.is(tok::comma);
Alexander Musman8dba6642014-04-22 13:09:42 +0000722 if (IsComma)
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000723 ConsumeToken();
Alexander Musman8dba6642014-04-22 13:09:42 +0000724 else if (Tok.isNot(tok::r_paren) &&
725 Tok.isNot(tok::annot_pragma_openmp_end) &&
726 (!MayHaveTail || Tok.isNot(tok::colon)))
Alexey Bataev6125da92014-07-21 11:26:11 +0000727 Diag(Tok, diag::err_omp_expected_punc)
728 << ((Kind == OMPC_flush) ? getOpenMPDirectiveName(OMPD_flush)
729 : getOpenMPClauseName(Kind))
730 << (Kind == OMPC_flush);
Alexander Musman8dba6642014-04-22 13:09:42 +0000731 }
732
Alexander Musmanf0d76e72014-05-29 14:36:25 +0000733 // Parse ':' linear-step (or ':' alignment).
Craig Topper161e4db2014-05-21 06:02:52 +0000734 Expr *TailExpr = nullptr;
Alexander Musman8dba6642014-04-22 13:09:42 +0000735 const bool MustHaveTail = MayHaveTail && Tok.is(tok::colon);
736 if (MustHaveTail) {
737 ColonLoc = Tok.getLocation();
738 ConsumeToken();
739 ExprResult Tail = ParseAssignmentExpression();
740 if (Tail.isUsable())
Nikola Smiljanic01a75982014-05-29 10:55:11 +0000741 TailExpr = Tail.get();
Alexander Musman8dba6642014-04-22 13:09:42 +0000742 else
743 SkipUntil(tok::comma, tok::r_paren, tok::annot_pragma_openmp_end,
744 StopBeforeMatch);
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000745 }
746
747 // Parse ')'.
748 T.consumeClose();
Alexey Bataevc5e02582014-06-16 07:08:35 +0000749 if (Vars.empty() || (MustHaveTail && !TailExpr) || InvalidReductionId)
Craig Topper161e4db2014-05-21 06:02:52 +0000750 return nullptr;
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000751
Alexey Bataevc5e02582014-06-16 07:08:35 +0000752 return Actions.ActOnOpenMPVarListClause(
753 Kind, Vars, TailExpr, Loc, LOpen, ColonLoc, Tok.getLocation(),
754 ReductionIdScopeSpec,
755 ReductionId.isValid() ? Actions.GetNameFromUnqualifiedId(ReductionId)
756 : DeclarationNameInfo());
Alexey Bataev5ec3eb12013-07-19 03:13:43 +0000757}
758