]> git.ipfire.org Git - thirdparty/gcc.git/blame - gcc/c/c-parser.c
openmp: Also implicitly mark as declare target to functions mentioned in target regions
[thirdparty/gcc.git] / gcc / c / c-parser.c
CommitLineData
27bf414c 1/* Parser for C and Objective-C.
8d9254fc 2 Copyright (C) 1987-2020 Free Software Foundation, Inc.
27bf414c
JM
3
4 Parser actions based on the old Bison parser; structure somewhat
5 influenced by and fragments based on the C++ parser.
6
7This file is part of GCC.
8
9GCC is free software; you can redistribute it and/or modify it under
10the terms of the GNU General Public License as published by the Free
9dcd6f09 11Software Foundation; either version 3, or (at your option) any later
27bf414c
JM
12version.
13
14GCC is distributed in the hope that it will be useful, but WITHOUT ANY
15WARRANTY; without even the implied warranty of MERCHANTABILITY or
16FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
17for more details.
18
19You should have received a copy of the GNU General Public License
9dcd6f09
NC
20along with GCC; see the file COPYING3. If not see
21<http://www.gnu.org/licenses/>. */
27bf414c
JM
22
23/* TODO:
24
25 Make sure all relevant comments, and all relevant code from all
26 actions, brought over from old parser. Verify exact correspondence
27 of syntax accepted.
28
29 Add testcases covering every input symbol in every state in old and
30 new parsers.
31
32 Include full syntax for GNU C, including erroneous cases accepted
33 with error messages, in syntax productions in comments.
34
35 Make more diagnostics in the front end generally take an explicit
36 location rather than implicitly using input_location. */
37
38#include "config.h"
6c7a259b 39#define INCLUDE_UNIQUE_PTR
27bf414c
JM
40#include "system.h"
41#include "coretypes.h"
2adfab87
AM
42#include "target.h"
43#include "function.h"
2adfab87
AM
44#include "c-tree.h"
45#include "timevar.h"
d8a2d370 46#include "stringpool.h"
2adfab87 47#include "cgraph.h"
d8a2d370
DN
48#include "attribs.h"
49#include "stor-layout.h"
50#include "varasm.h"
51#include "trans-mem.h"
39dabefd 52#include "c-family/c-pragma.h"
acf0174b 53#include "c-lang.h"
61d3ce20 54#include "c-family/c-objc.h"
68a607d8 55#include "plugin.h"
629b3d75
MJ
56#include "omp-general.h"
57#include "omp-offload.h"
9b2b7279 58#include "builtins.h"
41dbbb37 59#include "gomp-constants.h"
992118a1 60#include "c-family/c-indentation.h"
e01d41e5
JJ
61#include "gimple-expr.h"
62#include "context.h"
1a4f11c8 63#include "gcc-rich-location.h"
1ee62b92
PG
64#include "c-parser.h"
65#include "gimple-parser.h"
c2e84327
DM
66#include "read-rtl-function.h"
67#include "run-rtl-passes.h"
324ff1a0 68#include "intl.h"
6c7a259b 69#include "c-family/name-hint.h"
65791f42 70#include "tree-iterator.h"
28567c40 71#include "memmodel.h"
27bf414c 72
d25c7690
PK
73/* We need to walk over decls with incomplete struct/union/enum types
74 after parsing the whole translation unit.
75 In finish_decl(), if the decl is static, has incomplete
76 struct/union/enum type, it is appeneded to incomplete_record_decls.
77 In c_parser_translation_unit(), we iterate over incomplete_record_decls
78 and report error if any of the decls are still incomplete. */
79
7de76362 80vec<tree> incomplete_record_decls;
d25c7690 81
ebedc9a3
DM
82void
83set_c_expr_source_range (c_expr *expr,
84 location_t start, location_t finish)
85{
86 expr->src_range.m_start = start;
87 expr->src_range.m_finish = finish;
bef08b71
DM
88 if (expr->value)
89 set_source_range (expr->value, start, finish);
ebedc9a3
DM
90}
91
92void
93set_c_expr_source_range (c_expr *expr,
94 source_range src_range)
95{
96 expr->src_range = src_range;
bef08b71
DM
97 if (expr->value)
98 set_source_range (expr->value, src_range);
ebedc9a3
DM
99}
100
27bf414c 101\f
27bf414c
JM
102/* Initialization routine for this file. */
103
104void
105c_parse_init (void)
106{
107 /* The only initialization required is of the reserved word
108 identifiers. */
109 unsigned int i;
110 tree id;
eea1139b 111 int mask = 0;
27bf414c 112
36c5e70a
BE
113 /* Make sure RID_MAX hasn't grown past the 8 bits used to hold the keyword in
114 the c_token structure. */
115 gcc_assert (RID_MAX <= 255);
116
eea1139b
ILT
117 mask |= D_CXXONLY;
118 if (!flag_isoc99)
119 mask |= D_C99;
120 if (flag_no_asm)
121 {
122 mask |= D_ASM | D_EXT;
123 if (!flag_isoc99)
124 mask |= D_EXT89;
125 }
27bf414c 126 if (!c_dialect_objc ())
eea1139b 127 mask |= D_OBJC | D_CXX_OBJC;
27bf414c 128
766090c2 129 ridpointers = ggc_cleared_vec_alloc<tree> ((int) RID_MAX);
eea1139b 130 for (i = 0; i < num_c_common_reswords; i++)
27bf414c
JM
131 {
132 /* If a keyword is disabled, do not enter it into the table
133 and so create a canonical spelling that isn't a keyword. */
eea1139b
ILT
134 if (c_common_reswords[i].disable & mask)
135 {
136 if (warn_cxx_compat
137 && (c_common_reswords[i].disable & D_CXXWARN))
138 {
139 id = get_identifier (c_common_reswords[i].word);
140 C_SET_RID_CODE (id, RID_CXX_COMPAT_WARN);
141 C_IS_RESERVED_WORD (id) = 1;
142 }
143 continue;
144 }
27bf414c 145
eea1139b
ILT
146 id = get_identifier (c_common_reswords[i].word);
147 C_SET_RID_CODE (id, c_common_reswords[i].rid);
27bf414c 148 C_IS_RESERVED_WORD (id) = 1;
eea1139b 149 ridpointers [(int) c_common_reswords[i].rid] = id;
27bf414c 150 }
78a7c317
DD
151
152 for (i = 0; i < NUM_INT_N_ENTS; i++)
153 {
154 /* We always create the symbols but they aren't always supported. */
155 char name[50];
156 sprintf (name, "__int%d", int_n_data[i].bitsize);
17958621 157 id = get_identifier (name);
78a7c317
DD
158 C_SET_RID_CODE (id, RID_FIRST_INT_N + i);
159 C_IS_RESERVED_WORD (id) = 1;
5e580306
JL
160
161 sprintf (name, "__int%d__", int_n_data[i].bitsize);
162 id = get_identifier (name);
163 C_SET_RID_CODE (id, RID_FIRST_INT_N + i);
164 C_IS_RESERVED_WORD (id) = 1;
78a7c317 165 }
27bf414c
JM
166}
167\f
27bf414c
JM
168/* A parser structure recording information about the state and
169 context of parsing. Includes lexer information with up to two
170 tokens of look-ahead; more are not needed for C. */
a79683d5 171struct GTY(()) c_parser {
27bf414c 172 /* The look-ahead tokens. */
acf0174b
JJ
173 c_token * GTY((skip)) tokens;
174 /* Buffer for look-ahead tokens. */
de67c4c3
DM
175 c_token tokens_buf[4];
176 /* How many look-ahead tokens are available (0 - 4, or
acf0174b
JJ
177 more if parsing from pre-lexed tokens). */
178 unsigned int tokens_avail;
34b43828
JM
179 /* Raw look-ahead tokens, used only for checking in Objective-C
180 whether '[[' starts attributes. */
181 vec<c_token, va_gc> *raw_tokens;
182 /* The number of raw look-ahead tokens that have since been fully
183 lexed. */
184 unsigned int raw_tokens_used;
27bf414c
JM
185 /* True if a syntax error is being recovered from; false otherwise.
186 c_parser_error sets this flag. It should clear this flag when
187 enough tokens have been consumed to recover from the error. */
188 BOOL_BITFIELD error : 1;
bc4071dd
RH
189 /* True if we're processing a pragma, and shouldn't automatically
190 consume CPP_PRAGMA_EOL. */
191 BOOL_BITFIELD in_pragma : 1;
b4b56033
MLI
192 /* True if we're parsing the outermost block of an if statement. */
193 BOOL_BITFIELD in_if_block : 1;
471c5330
JM
194 /* True if we want to lex a translated, joined string (for an
195 initial #pragma pch_preprocess). Otherwise the parser is
196 responsible for concatenating strings and translating to the
197 execution character set as needed. */
198 BOOL_BITFIELD lex_joined_string : 1;
199 /* True if, when the parser is concatenating string literals, it
200 should translate them to the execution character set (false
201 inside attributes). */
202 BOOL_BITFIELD translate_strings_p : 1;
1973201f 203
0bacb8c7 204 /* Objective-C specific parser/lexer information. */
1973201f
NP
205
206 /* True if we are in a context where the Objective-C "PQ" keywords
207 are considered keywords. */
0bacb8c7 208 BOOL_BITFIELD objc_pq_context : 1;
f05b9d93
NP
209 /* True if we are parsing a (potential) Objective-C foreach
210 statement. This is set to true after we parsed 'for (' and while
211 we wait for 'in' or ';' to decide if it's a standard C for loop or an
212 Objective-C foreach loop. */
213 BOOL_BITFIELD objc_could_be_foreach_context : 1;
0bacb8c7
TT
214 /* The following flag is needed to contextualize Objective-C lexical
215 analysis. In some cases (e.g., 'int NSObject;'), it is
216 undesirable to bind an identifier to an Objective-C class, even
217 if a class with that name exists. */
218 BOOL_BITFIELD objc_need_raw_identifier : 1;
0a35513e
AH
219 /* Nonzero if we're processing a __transaction statement. The value
220 is 1 | TM_STMT_ATTR_*. */
221 unsigned int in_transaction : 4;
668ea4b1
IS
222 /* True if we are in a context where the Objective-C "Property attribute"
223 keywords are valid. */
224 BOOL_BITFIELD objc_property_attr_context : 1;
41958c28 225
8139a48e
DM
226 /* Location of the last consumed token. */
227 location_t last_token_location;
a79683d5 228};
27bf414c 229
1ee62b92
PG
230/* Return a pointer to the Nth token in PARSERs tokens_buf. */
231
232c_token *
233c_parser_tokens_buf (c_parser *parser, unsigned n)
234{
235 return &parser->tokens_buf[n];
236}
237
238/* Return the error state of PARSER. */
239
240bool
241c_parser_error (c_parser *parser)
242{
243 return parser->error;
244}
245
246/* Set the error state of PARSER to ERR. */
247
248void
249c_parser_set_error (c_parser *parser, bool err)
250{
251 parser->error = err;
252}
253
bc4071dd
RH
254
255/* The actual parser and external interface. ??? Does this need to be
256 garbage-collected? */
257
258static GTY (()) c_parser *the_parser;
259
34b43828
JM
260/* Read in and lex a single token, storing it in *TOKEN. If RAW,
261 context-sensitive postprocessing of the token is not done. */
27bf414c
JM
262
263static void
34b43828 264c_lex_one_token (c_parser *parser, c_token *token, bool raw = false)
27bf414c
JM
265{
266 timevar_push (TV_LEX);
bc4071dd 267
34b43828
JM
268 if (raw || vec_safe_length (parser->raw_tokens) == 0)
269 {
270 token->type = c_lex_with_flags (&token->value, &token->location,
271 &token->flags,
272 (parser->lex_joined_string
273 ? 0 : C_LEX_STRING_NO_JOIN));
274 token->id_kind = C_ID_NONE;
275 token->keyword = RID_MAX;
276 token->pragma_kind = PRAGMA_NONE;
277 }
278 else
279 {
280 /* Use a token previously lexed as a raw look-ahead token, and
281 complete the processing on it. */
282 *token = (*parser->raw_tokens)[parser->raw_tokens_used];
283 ++parser->raw_tokens_used;
284 if (parser->raw_tokens_used == vec_safe_length (parser->raw_tokens))
285 {
286 vec_free (parser->raw_tokens);
287 parser->raw_tokens_used = 0;
288 }
289 }
290
291 if (raw)
292 goto out;
bc4071dd 293
27bf414c
JM
294 switch (token->type)
295 {
296 case CPP_NAME:
27bf414c
JM
297 {
298 tree decl;
299
0bacb8c7
TT
300 bool objc_force_identifier = parser->objc_need_raw_identifier;
301 if (c_dialect_objc ())
302 parser->objc_need_raw_identifier = false;
27bf414c
JM
303
304 if (C_IS_RESERVED_WORD (token->value))
305 {
306 enum rid rid_code = C_RID_CODE (token->value);
307
eea1139b
ILT
308 if (rid_code == RID_CXX_COMPAT_WARN)
309 {
3ba09659
AH
310 warning_at (token->location,
311 OPT_Wc___compat,
88388a52
JM
312 "identifier %qE conflicts with C++ keyword",
313 token->value);
eea1139b 314 }
36c5e70a
BE
315 else if (rid_code >= RID_FIRST_ADDR_SPACE
316 && rid_code <= RID_LAST_ADDR_SPACE)
317 {
ffc22840
GJL
318 addr_space_t as;
319 as = (addr_space_t) (rid_code - RID_FIRST_ADDR_SPACE);
320 targetm.addr_space.diagnose_usage (as, token->location);
36c5e70a
BE
321 token->id_kind = C_ID_ADDRSPACE;
322 token->keyword = rid_code;
323 break;
324 }
1973201f 325 else if (c_dialect_objc () && OBJC_IS_PQ_KEYWORD (rid_code))
27bf414c 326 {
1973201f
NP
327 /* We found an Objective-C "pq" keyword (in, out,
328 inout, bycopy, byref, oneway). They need special
329 care because the interpretation depends on the
d853ee42 330 context. */
1973201f 331 if (parser->objc_pq_context)
27bf414c 332 {
27bf414c
JM
333 token->type = CPP_KEYWORD;
334 token->keyword = rid_code;
335 break;
336 }
f05b9d93
NP
337 else if (parser->objc_could_be_foreach_context
338 && rid_code == RID_IN)
339 {
340 /* We are in Objective-C, inside a (potential)
341 foreach context (which means after having
342 parsed 'for (', but before having parsed ';'),
343 and we found 'in'. We consider it the keyword
344 which terminates the declaration at the
345 beginning of a foreach-statement. Note that
346 this means you can't use 'in' for anything else
347 in that context; in particular, in Objective-C
348 you can't use 'in' as the name of the running
349 variable in a C for loop. We could potentially
350 try to add code here to disambiguate, but it
d853ee42 351 seems a reasonable limitation. */
f05b9d93
NP
352 token->type = CPP_KEYWORD;
353 token->keyword = rid_code;
354 break;
355 }
1973201f
NP
356 /* Else, "pq" keywords outside of the "pq" context are
357 not keywords, and we fall through to the code for
d853ee42 358 normal tokens. */
1973201f 359 }
668ea4b1
IS
360 else if (c_dialect_objc () && OBJC_IS_PATTR_KEYWORD (rid_code))
361 {
d853ee42
NP
362 /* We found an Objective-C "property attribute"
363 keyword (getter, setter, readonly, etc). These are
668ea4b1
IS
364 only valid in the property context. */
365 if (parser->objc_property_attr_context)
366 {
367 token->type = CPP_KEYWORD;
368 token->keyword = rid_code;
369 break;
370 }
371 /* Else they are not special keywords.
372 */
373 }
1973201f
NP
374 else if (c_dialect_objc ()
375 && (OBJC_IS_AT_KEYWORD (rid_code)
376 || OBJC_IS_CXX_KEYWORD (rid_code)))
377 {
378 /* We found one of the Objective-C "@" keywords (defs,
379 selector, synchronized, etc) or one of the
380 Objective-C "cxx" keywords (class, private,
381 protected, public, try, catch, throw) without a
382 preceding '@' sign. Do nothing and fall through to
383 the code for normal tokens (in C++ we would still
d853ee42 384 consider the CXX ones keywords, but not in C). */
1973201f 385 ;
27bf414c
JM
386 }
387 else
388 {
27bf414c
JM
389 token->type = CPP_KEYWORD;
390 token->keyword = rid_code;
391 break;
392 }
393 }
394
395 decl = lookup_name (token->value);
396 if (decl)
397 {
398 if (TREE_CODE (decl) == TYPE_DECL)
399 {
400 token->id_kind = C_ID_TYPENAME;
401 break;
402 }
403 }
404 else if (c_dialect_objc ())
405 {
406 tree objc_interface_decl = objc_is_class_name (token->value);
407 /* Objective-C class names are in the same namespace as
408 variables and typedefs, and hence are shadowed by local
409 declarations. */
410 if (objc_interface_decl
0d8a2528 411 && (!objc_force_identifier || global_bindings_p ()))
27bf414c
JM
412 {
413 token->value = objc_interface_decl;
414 token->id_kind = C_ID_CLASSNAME;
415 break;
416 }
417 }
bc4071dd 418 token->id_kind = C_ID_ID;
27bf414c 419 }
27bf414c
JM
420 break;
421 case CPP_AT_NAME:
422 /* This only happens in Objective-C; it must be a keyword. */
423 token->type = CPP_KEYWORD;
49b91f05
NP
424 switch (C_RID_CODE (token->value))
425 {
426 /* Replace 'class' with '@class', 'private' with '@private',
427 etc. This prevents confusion with the C++ keyword
428 'class', and makes the tokens consistent with other
429 Objective-C 'AT' keywords. For example '@class' is
430 reported as RID_AT_CLASS which is consistent with
431 '@synchronized', which is reported as
432 RID_AT_SYNCHRONIZED.
433 */
434 case RID_CLASS: token->keyword = RID_AT_CLASS; break;
435 case RID_PRIVATE: token->keyword = RID_AT_PRIVATE; break;
436 case RID_PROTECTED: token->keyword = RID_AT_PROTECTED; break;
437 case RID_PUBLIC: token->keyword = RID_AT_PUBLIC; break;
438 case RID_THROW: token->keyword = RID_AT_THROW; break;
439 case RID_TRY: token->keyword = RID_AT_TRY; break;
440 case RID_CATCH: token->keyword = RID_AT_CATCH; break;
b8fd7909 441 case RID_SYNCHRONIZED: token->keyword = RID_AT_SYNCHRONIZED; break;
49b91f05
NP
442 default: token->keyword = C_RID_CODE (token->value);
443 }
27bf414c
JM
444 break;
445 case CPP_COLON:
446 case CPP_COMMA:
447 case CPP_CLOSE_PAREN:
448 case CPP_SEMICOLON:
449 /* These tokens may affect the interpretation of any identifiers
450 following, if doing Objective-C. */
0bacb8c7
TT
451 if (c_dialect_objc ())
452 parser->objc_need_raw_identifier = false;
bc4071dd
RH
453 break;
454 case CPP_PRAGMA:
455 /* We smuggled the cpp_token->u.pragma value in an INTEGER_CST. */
d75d71e0 456 token->pragma_kind = (enum pragma_kind) TREE_INT_CST_LOW (token->value);
bc4071dd 457 token->value = NULL;
27bf414c
JM
458 break;
459 default:
27bf414c
JM
460 break;
461 }
34b43828 462 out:
27bf414c
JM
463 timevar_pop (TV_LEX);
464}
465
466/* Return a pointer to the next token from PARSER, reading it in if
467 necessary. */
468
1ee62b92 469c_token *
27bf414c
JM
470c_parser_peek_token (c_parser *parser)
471{
472 if (parser->tokens_avail == 0)
473 {
0bacb8c7 474 c_lex_one_token (parser, &parser->tokens[0]);
27bf414c
JM
475 parser->tokens_avail = 1;
476 }
477 return &parser->tokens[0];
478}
479
29ce73cb
PB
480/* Return a pointer to the next-but-one token from PARSER, reading it
481 in if necessary. The next token is already read in. */
482
1ee62b92 483c_token *
29ce73cb
PB
484c_parser_peek_2nd_token (c_parser *parser)
485{
486 if (parser->tokens_avail >= 2)
487 return &parser->tokens[1];
488 gcc_assert (parser->tokens_avail == 1);
489 gcc_assert (parser->tokens[0].type != CPP_EOF);
490 gcc_assert (parser->tokens[0].type != CPP_PRAGMA_EOL);
491 c_lex_one_token (parser, &parser->tokens[1]);
492 parser->tokens_avail = 2;
493 return &parser->tokens[1];
494}
495
de67c4c3
DM
496/* Return a pointer to the Nth token from PARSER, reading it
497 in if necessary. The N-1th token is already read in. */
498
1ee62b92 499c_token *
de67c4c3
DM
500c_parser_peek_nth_token (c_parser *parser, unsigned int n)
501{
502 /* N is 1-based, not zero-based. */
503 gcc_assert (n > 0);
504
505 if (parser->tokens_avail >= n)
506 return &parser->tokens[n - 1];
507 gcc_assert (parser->tokens_avail == n - 1);
508 c_lex_one_token (parser, &parser->tokens[n - 1]);
509 parser->tokens_avail = n;
510 return &parser->tokens[n - 1];
511}
512
34b43828
JM
513/* Return a pointer to the Nth token from PARSER, reading it in as a
514 raw look-ahead token if necessary. The N-1th token is already read
515 in. Raw look-ahead tokens remain available for when the non-raw
516 functions above are called. */
517
518c_token *
519c_parser_peek_nth_token_raw (c_parser *parser, unsigned int n)
520{
521 /* N is 1-based, not zero-based. */
522 gcc_assert (n > 0);
523
524 if (parser->tokens_avail >= n)
525 return &parser->tokens[n - 1];
526 unsigned int raw_len = vec_safe_length (parser->raw_tokens);
527 unsigned int raw_avail
528 = parser->tokens_avail + raw_len - parser->raw_tokens_used;
529 gcc_assert (raw_avail >= n - 1);
530 if (raw_avail >= n)
531 return &(*parser->raw_tokens)[parser->raw_tokens_used
532 + n - 1 - parser->tokens_avail];
533 vec_safe_reserve (parser->raw_tokens, 1);
534 parser->raw_tokens->quick_grow (raw_len + 1);
535 c_lex_one_token (parser, &(*parser->raw_tokens)[raw_len], true);
536 return &(*parser->raw_tokens)[raw_len];
537}
538
1a4f11c8
DM
539bool
540c_keyword_starts_typename (enum rid keyword)
541{
542 switch (keyword)
543 {
544 case RID_UNSIGNED:
545 case RID_LONG:
546 case RID_SHORT:
547 case RID_SIGNED:
548 case RID_COMPLEX:
549 case RID_INT:
550 case RID_CHAR:
551 case RID_FLOAT:
552 case RID_DOUBLE:
553 case RID_VOID:
554 case RID_DFLOAT32:
555 case RID_DFLOAT64:
556 case RID_DFLOAT128:
c65699ef 557 CASE_RID_FLOATN_NX:
1a4f11c8
DM
558 case RID_BOOL:
559 case RID_ENUM:
560 case RID_STRUCT:
561 case RID_UNION:
562 case RID_TYPEOF:
563 case RID_CONST:
564 case RID_ATOMIC:
565 case RID_VOLATILE:
566 case RID_RESTRICT:
567 case RID_ATTRIBUTE:
568 case RID_FRACT:
569 case RID_ACCUM:
570 case RID_SAT:
571 case RID_AUTO_TYPE:
4b2b493f 572 case RID_ALIGNAS:
1a4f11c8
DM
573 return true;
574 default:
575 if (keyword >= RID_FIRST_INT_N
576 && keyword < RID_FIRST_INT_N + NUM_INT_N_ENTS
577 && int_n_enabled_p[keyword - RID_FIRST_INT_N])
578 return true;
579 return false;
580 }
581}
582
27bf414c
JM
583/* Return true if TOKEN can start a type name,
584 false otherwise. */
1ee62b92 585bool
27bf414c
JM
586c_token_starts_typename (c_token *token)
587{
588 switch (token->type)
589 {
590 case CPP_NAME:
591 switch (token->id_kind)
592 {
593 case C_ID_ID:
594 return false;
36c5e70a
BE
595 case C_ID_ADDRSPACE:
596 return true;
27bf414c
JM
597 case C_ID_TYPENAME:
598 return true;
599 case C_ID_CLASSNAME:
600 gcc_assert (c_dialect_objc ());
601 return true;
602 default:
603 gcc_unreachable ();
604 }
605 case CPP_KEYWORD:
1a4f11c8 606 return c_keyword_starts_typename (token->keyword);
27bf414c
JM
607 case CPP_LESS:
608 if (c_dialect_objc ())
609 return true;
610 return false;
611 default:
612 return false;
613 }
614}
615
616/* Return true if the next token from PARSER can start a type name,
29ce73cb
PB
617 false otherwise. LA specifies how to do lookahead in order to
618 detect unknown type names. If unsure, pick CLA_PREFER_ID. */
619
27bf414c 620static inline bool
29ce73cb 621c_parser_next_tokens_start_typename (c_parser *parser, enum c_lookahead_kind la)
27bf414c
JM
622{
623 c_token *token = c_parser_peek_token (parser);
29ce73cb
PB
624 if (c_token_starts_typename (token))
625 return true;
626
627 /* Try a bit harder to detect an unknown typename. */
628 if (la != cla_prefer_id
629 && token->type == CPP_NAME
630 && token->id_kind == C_ID_ID
631
632 /* Do not try too hard when we could have "object in array". */
633 && !parser->objc_could_be_foreach_context
634
635 && (la == cla_prefer_type
636 || c_parser_peek_2nd_token (parser)->type == CPP_NAME
637 || c_parser_peek_2nd_token (parser)->type == CPP_MULT)
638
639 /* Only unknown identifiers. */
640 && !lookup_name (token->value))
641 return true;
642
643 return false;
27bf414c
JM
644}
645
f725e721
PB
646/* Return true if TOKEN is a type qualifier, false otherwise. */
647static bool
648c_token_is_qualifier (c_token *token)
649{
650 switch (token->type)
651 {
652 case CPP_NAME:
653 switch (token->id_kind)
654 {
655 case C_ID_ADDRSPACE:
656 return true;
657 default:
658 return false;
659 }
660 case CPP_KEYWORD:
661 switch (token->keyword)
662 {
663 case RID_CONST:
664 case RID_VOLATILE:
665 case RID_RESTRICT:
666 case RID_ATTRIBUTE:
267bac10 667 case RID_ATOMIC:
f725e721
PB
668 return true;
669 default:
670 return false;
671 }
672 case CPP_LESS:
673 return false;
674 default:
675 gcc_unreachable ();
676 }
677}
678
679/* Return true if the next token from PARSER is a type qualifier,
680 false otherwise. */
681static inline bool
682c_parser_next_token_is_qualifier (c_parser *parser)
683{
684 c_token *token = c_parser_peek_token (parser);
685 return c_token_is_qualifier (token);
686}
687
4e03c3a7
JM
688/* Return true if TOKEN can start declaration specifiers (not
689 including standard attributes), false otherwise. */
27bf414c
JM
690static bool
691c_token_starts_declspecs (c_token *token)
692{
693 switch (token->type)
694 {
695 case CPP_NAME:
696 switch (token->id_kind)
697 {
698 case C_ID_ID:
699 return false;
36c5e70a
BE
700 case C_ID_ADDRSPACE:
701 return true;
27bf414c
JM
702 case C_ID_TYPENAME:
703 return true;
704 case C_ID_CLASSNAME:
705 gcc_assert (c_dialect_objc ());
706 return true;
707 default:
708 gcc_unreachable ();
709 }
710 case CPP_KEYWORD:
711 switch (token->keyword)
712 {
713 case RID_STATIC:
714 case RID_EXTERN:
715 case RID_REGISTER:
716 case RID_TYPEDEF:
717 case RID_INLINE:
bbceee64 718 case RID_NORETURN:
27bf414c
JM
719 case RID_AUTO:
720 case RID_THREAD:
721 case RID_UNSIGNED:
722 case RID_LONG:
723 case RID_SHORT:
724 case RID_SIGNED:
725 case RID_COMPLEX:
726 case RID_INT:
727 case RID_CHAR:
728 case RID_FLOAT:
729 case RID_DOUBLE:
730 case RID_VOID:
9a8ce21f
JG
731 case RID_DFLOAT32:
732 case RID_DFLOAT64:
733 case RID_DFLOAT128:
c65699ef 734 CASE_RID_FLOATN_NX:
27bf414c
JM
735 case RID_BOOL:
736 case RID_ENUM:
737 case RID_STRUCT:
738 case RID_UNION:
739 case RID_TYPEOF:
740 case RID_CONST:
741 case RID_VOLATILE:
742 case RID_RESTRICT:
743 case RID_ATTRIBUTE:
ab22c1fa
CF
744 case RID_FRACT:
745 case RID_ACCUM:
746 case RID_SAT:
d19fa6b5 747 case RID_ALIGNAS:
267bac10 748 case RID_ATOMIC:
38b7bc7f 749 case RID_AUTO_TYPE:
27bf414c
JM
750 return true;
751 default:
78a7c317
DD
752 if (token->keyword >= RID_FIRST_INT_N
753 && token->keyword < RID_FIRST_INT_N + NUM_INT_N_ENTS
754 && int_n_enabled_p[token->keyword - RID_FIRST_INT_N])
755 return true;
27bf414c
JM
756 return false;
757 }
758 case CPP_LESS:
759 if (c_dialect_objc ())
760 return true;
761 return false;
762 default:
763 return false;
764 }
765}
766
32912286 767
4e03c3a7
JM
768/* Return true if TOKEN can start declaration specifiers (not
769 including standard attributes) or a static assertion, false
770 otherwise. */
32912286
JM
771static bool
772c_token_starts_declaration (c_token *token)
773{
774 if (c_token_starts_declspecs (token)
775 || token->keyword == RID_STATIC_ASSERT)
776 return true;
777 else
778 return false;
779}
780
27bf414c 781/* Return true if the next token from PARSER can start declaration
4e03c3a7
JM
782 specifiers (not including standard attributes), false
783 otherwise. */
1ee62b92 784bool
27bf414c
JM
785c_parser_next_token_starts_declspecs (c_parser *parser)
786{
787 c_token *token = c_parser_peek_token (parser);
bede2adc
NP
788
789 /* In Objective-C, a classname normally starts a declspecs unless it
790 is immediately followed by a dot. In that case, it is the
791 Objective-C 2.0 "dot-syntax" for class objects, ie, calls the
792 setter/getter on the class. c_token_starts_declspecs() can't
793 differentiate between the two cases because it only checks the
794 current token, so we have a special check here. */
795 if (c_dialect_objc ()
796 && token->type == CPP_NAME
797 && token->id_kind == C_ID_CLASSNAME
798 && c_parser_peek_2nd_token (parser)->type == CPP_DOT)
799 return false;
800
27bf414c
JM
801 return c_token_starts_declspecs (token);
802}
803
2f413185 804/* Return true if the next tokens from PARSER can start declaration
4e03c3a7
JM
805 specifiers (not including standard attributes) or a static
806 assertion, false otherwise. */
1ee62b92 807bool
2f413185 808c_parser_next_tokens_start_declaration (c_parser *parser)
32912286
JM
809{
810 c_token *token = c_parser_peek_token (parser);
bede2adc
NP
811
812 /* Same as above. */
813 if (c_dialect_objc ()
814 && token->type == CPP_NAME
815 && token->id_kind == C_ID_CLASSNAME
816 && c_parser_peek_2nd_token (parser)->type == CPP_DOT)
817 return false;
818
2f413185
PB
819 /* Labels do not start declarations. */
820 if (token->type == CPP_NAME
821 && c_parser_peek_2nd_token (parser)->type == CPP_COLON)
822 return false;
823
824 if (c_token_starts_declaration (token))
825 return true;
826
29ce73cb 827 if (c_parser_next_tokens_start_typename (parser, cla_nonabstract_decl))
2f413185
PB
828 return true;
829
830 return false;
32912286
JM
831}
832
27bf414c
JM
833/* Consume the next token from PARSER. */
834
1ee62b92 835void
27bf414c
JM
836c_parser_consume_token (c_parser *parser)
837{
bc4071dd
RH
838 gcc_assert (parser->tokens_avail >= 1);
839 gcc_assert (parser->tokens[0].type != CPP_EOF);
840 gcc_assert (!parser->in_pragma || parser->tokens[0].type != CPP_PRAGMA_EOL);
841 gcc_assert (parser->error || parser->tokens[0].type != CPP_PRAGMA);
8139a48e 842 parser->last_token_location = parser->tokens[0].location;
acf0174b
JJ
843 if (parser->tokens != &parser->tokens_buf[0])
844 parser->tokens++;
4e03c3a7
JM
845 else if (parser->tokens_avail >= 2)
846 {
847 parser->tokens[0] = parser->tokens[1];
848 if (parser->tokens_avail >= 3)
852f0ae8
KK
849 {
850 parser->tokens[1] = parser->tokens[2];
851 if (parser->tokens_avail >= 4)
852 parser->tokens[2] = parser->tokens[3];
853 }
4e03c3a7 854 }
27bf414c
JM
855 parser->tokens_avail--;
856}
857
bc4071dd
RH
858/* Expect the current token to be a #pragma. Consume it and remember
859 that we've begun parsing a pragma. */
860
861static void
862c_parser_consume_pragma (c_parser *parser)
863{
864 gcc_assert (!parser->in_pragma);
865 gcc_assert (parser->tokens_avail >= 1);
866 gcc_assert (parser->tokens[0].type == CPP_PRAGMA);
acf0174b
JJ
867 if (parser->tokens != &parser->tokens_buf[0])
868 parser->tokens++;
4e03c3a7
JM
869 else if (parser->tokens_avail >= 2)
870 {
871 parser->tokens[0] = parser->tokens[1];
872 if (parser->tokens_avail >= 3)
873 parser->tokens[1] = parser->tokens[2];
874 }
bc4071dd
RH
875 parser->tokens_avail--;
876 parser->in_pragma = true;
877}
878
8400e75e 879/* Update the global input_location from TOKEN. */
27bf414c
JM
880static inline void
881c_parser_set_source_position_from_token (c_token *token)
882{
883 if (token->type != CPP_EOF)
884 {
885 input_location = token->location;
27bf414c
JM
886 }
887}
888
de67c4c3
DM
889/* Helper function for c_parser_error.
890 Having peeked a token of kind TOK1_KIND that might signify
891 a conflict marker, peek successor tokens to determine
892 if we actually do have a conflict marker.
893 Specifically, we consider a run of 7 '<', '=' or '>' characters
894 at the start of a line as a conflict marker.
895 These come through the lexer as three pairs and a single,
896 e.g. three CPP_LSHIFT ("<<") and a CPP_LESS ('<').
897 If it returns true, *OUT_LOC is written to with the location/range
898 of the marker. */
899
900static bool
901c_parser_peek_conflict_marker (c_parser *parser, enum cpp_ttype tok1_kind,
902 location_t *out_loc)
903{
904 c_token *token2 = c_parser_peek_2nd_token (parser);
905 if (token2->type != tok1_kind)
906 return false;
907 c_token *token3 = c_parser_peek_nth_token (parser, 3);
908 if (token3->type != tok1_kind)
909 return false;
910 c_token *token4 = c_parser_peek_nth_token (parser, 4);
911 if (token4->type != conflict_marker_get_final_tok_kind (tok1_kind))
912 return false;
913
914 /* It must be at the start of the line. */
915 location_t start_loc = c_parser_peek_token (parser)->location;
916 if (LOCATION_COLUMN (start_loc) != 1)
917 return false;
918
919 /* We have a conflict marker. Construct a location of the form:
920 <<<<<<<
921 ^~~~~~~
922 with start == caret, finishing at the end of the marker. */
923 location_t finish_loc = get_finish (token4->location);
924 *out_loc = make_location (start_loc, start_loc, finish_loc);
925
926 return true;
927}
928
27bf414c
JM
929/* Issue a diagnostic of the form
930 FILE:LINE: MESSAGE before TOKEN
931 where TOKEN is the next token in the input stream of PARSER.
932 MESSAGE (specified by the caller) is usually of the form "expected
933 OTHER-TOKEN".
934
32129a17
DM
935 Use RICHLOC as the location of the diagnostic.
936
27bf414c
JM
937 Do not issue a diagnostic if still recovering from an error.
938
32129a17
DM
939 Return true iff an error was actually emitted.
940
27bf414c
JM
941 ??? This is taken from the C++ parser, but building up messages in
942 this way is not i18n-friendly and some other approach should be
943 used. */
944
32129a17
DM
945static bool
946c_parser_error_richloc (c_parser *parser, const char *gmsgid,
947 rich_location *richloc)
27bf414c
JM
948{
949 c_token *token = c_parser_peek_token (parser);
950 if (parser->error)
32129a17 951 return false;
27bf414c 952 parser->error = true;
4b794eaf 953 if (!gmsgid)
32129a17 954 return false;
de67c4c3
DM
955
956 /* If this is actually a conflict marker, report it as such. */
957 if (token->type == CPP_LSHIFT
958 || token->type == CPP_RSHIFT
959 || token->type == CPP_EQ_EQ)
960 {
961 location_t loc;
962 if (c_parser_peek_conflict_marker (parser, token->type, &loc))
963 {
964 error_at (loc, "version control conflict marker in file");
32129a17 965 return true;
de67c4c3
DM
966 }
967 }
968
4b794eaf 969 c_parse_error (gmsgid,
27bf414c
JM
970 /* Because c_parse_error does not understand
971 CPP_KEYWORD, keywords are treated like
972 identifiers. */
973 (token->type == CPP_KEYWORD ? CPP_NAME : token->type),
cfc93532
MLI
974 /* ??? The C parser does not save the cpp flags of a
975 token, we need to pass 0 here and we will not get
976 the source spelling of some tokens but rather the
977 canonical spelling. */
32129a17
DM
978 token->value, /*flags=*/0, richloc);
979 return true;
980}
981
982/* As c_parser_error_richloc, but issue the message at the
983 location of PARSER's next token, or at input_location
984 if the next token is EOF. */
985
986bool
987c_parser_error (c_parser *parser, const char *gmsgid)
988{
989 c_token *token = c_parser_peek_token (parser);
990 c_parser_set_source_position_from_token (token);
991 rich_location richloc (line_table, input_location);
992 return c_parser_error_richloc (parser, gmsgid, &richloc);
993}
994
995/* Some tokens naturally come in pairs e.g.'(' and ')'.
996 This class is for tracking such a matching pair of symbols.
997 In particular, it tracks the location of the first token,
998 so that if the second token is missing, we can highlight the
999 location of the first token when notifying the user about the
1000 problem. */
1001
1002template <typename traits_t>
1003class token_pair
1004{
1005 public:
1006 /* token_pair's ctor. */
1007 token_pair () : m_open_loc (UNKNOWN_LOCATION) {}
1008
1009 /* If the next token is the opening symbol for this pair, consume it and
1010 return true.
1011 Otherwise, issue an error and return false.
1012 In either case, record the location of the opening token. */
1013
1014 bool require_open (c_parser *parser)
1015 {
1016 c_token *token = c_parser_peek_token (parser);
1017 if (token)
1018 m_open_loc = token->location;
1019
1020 return c_parser_require (parser, traits_t::open_token_type,
1021 traits_t::open_gmsgid);
1022 }
1023
1024 /* Consume the next token from PARSER, recording its location as
1025 that of the opening token within the pair. */
1026
1027 void consume_open (c_parser *parser)
1028 {
1029 c_token *token = c_parser_peek_token (parser);
1030 gcc_assert (token->type == traits_t::open_token_type);
1031 m_open_loc = token->location;
1032 c_parser_consume_token (parser);
1033 }
1034
1035 /* If the next token is the closing symbol for this pair, consume it
1036 and return true.
1037 Otherwise, issue an error, highlighting the location of the
1038 corresponding opening token, and return false. */
1039
1040 bool require_close (c_parser *parser) const
1041 {
1042 return c_parser_require (parser, traits_t::close_token_type,
1043 traits_t::close_gmsgid, m_open_loc);
1044 }
1045
1046 /* Like token_pair::require_close, except that tokens will be skipped
1047 until the desired token is found. An error message is still produced
1048 if the next token is not as expected. */
1049
1050 void skip_until_found_close (c_parser *parser) const
1051 {
1052 c_parser_skip_until_found (parser, traits_t::close_token_type,
1053 traits_t::close_gmsgid, m_open_loc);
1054 }
1055
1056 private:
1057 location_t m_open_loc;
1058};
1059
1060/* Traits for token_pair<T> for tracking matching pairs of parentheses. */
1061
1062struct matching_paren_traits
1063{
1064 static const enum cpp_ttype open_token_type = CPP_OPEN_PAREN;
1065 static const char * const open_gmsgid;
1066 static const enum cpp_ttype close_token_type = CPP_CLOSE_PAREN;
1067 static const char * const close_gmsgid;
1068};
1069
1070const char * const matching_paren_traits::open_gmsgid = "expected %<(%>";
1071const char * const matching_paren_traits::close_gmsgid = "expected %<)%>";
1072
1073/* "matching_parens" is a token_pair<T> class for tracking matching
1074 pairs of parentheses. */
1075
1076typedef token_pair<matching_paren_traits> matching_parens;
1077
1078/* Traits for token_pair<T> for tracking matching pairs of braces. */
1079
1080struct matching_brace_traits
1081{
1082 static const enum cpp_ttype open_token_type = CPP_OPEN_BRACE;
1083 static const char * const open_gmsgid;
1084 static const enum cpp_ttype close_token_type = CPP_CLOSE_BRACE;
1085 static const char * const close_gmsgid;
1086};
1087
1088const char * const matching_brace_traits::open_gmsgid = "expected %<{%>";
1089const char * const matching_brace_traits::close_gmsgid = "expected %<}%>";
1090
1091/* "matching_braces" is a token_pair<T> class for tracking matching
1092 pairs of braces. */
1093
1094typedef token_pair<matching_brace_traits> matching_braces;
1095
1096/* Get a description of the matching symbol to TYPE e.g. "(" for
1097 CPP_CLOSE_PAREN. */
1098
1099static const char *
1100get_matching_symbol (enum cpp_ttype type)
1101{
1102 switch (type)
1103 {
1104 default:
1105 gcc_unreachable ();
1106 return "";
1107 case CPP_CLOSE_PAREN:
1108 return "(";
1109 case CPP_CLOSE_BRACE:
1110 return "{";
1111 }
27bf414c
JM
1112}
1113
1114/* If the next token is of the indicated TYPE, consume it. Otherwise,
1115 issue the error MSGID. If MSGID is NULL then a message has already
1116 been produced and no message will be produced this time. Returns
32129a17
DM
1117 true if found, false otherwise.
1118
1119 If MATCHING_LOCATION is not UNKNOWN_LOCATION, then highlight it
1120 within any error as the location of an "opening" token matching
1121 the close token TYPE (e.g. the location of the '(' when TYPE is
62e1c678
DM
1122 CPP_CLOSE_PAREN).
1123
1124 If TYPE_IS_UNIQUE is true (the default) then msgid describes exactly
1125 one type (e.g. "expected %<)%>") and thus it may be reasonable to
1126 attempt to generate a fix-it hint for the problem.
1127 Otherwise msgid describes multiple token types (e.g.
1128 "expected %<;%>, %<,%> or %<)%>"), and thus we shouldn't attempt to
1129 generate a fix-it hint. */
27bf414c 1130
1ee62b92 1131bool
27bf414c
JM
1132c_parser_require (c_parser *parser,
1133 enum cpp_ttype type,
32129a17 1134 const char *msgid,
62e1c678
DM
1135 location_t matching_location,
1136 bool type_is_unique)
27bf414c
JM
1137{
1138 if (c_parser_next_token_is (parser, type))
1139 {
1140 c_parser_consume_token (parser);
1141 return true;
1142 }
1143 else
1144 {
32129a17
DM
1145 location_t next_token_loc = c_parser_peek_token (parser)->location;
1146 gcc_rich_location richloc (next_token_loc);
1147
62e1c678
DM
1148 /* Potentially supply a fix-it hint, suggesting to add the
1149 missing token immediately after the *previous* token.
1150 This may move the primary location within richloc. */
1151 if (!parser->error && type_is_unique)
1152 maybe_suggest_missing_token_insertion (&richloc, type,
1153 parser->last_token_location);
1154
32129a17
DM
1155 /* If matching_location != UNKNOWN_LOCATION, highlight it.
1156 Attempt to consolidate diagnostics by printing it as a
1157 secondary range within the main diagnostic. */
1158 bool added_matching_location = false;
1159 if (matching_location != UNKNOWN_LOCATION)
1160 added_matching_location
1161 = richloc.add_location_if_nearby (matching_location);
1162
1163 if (c_parser_error_richloc (parser, msgid, &richloc))
1164 /* If we weren't able to consolidate matching_location, then
1165 print it as a secondary diagnostic. */
1166 if (matching_location != UNKNOWN_LOCATION && !added_matching_location)
1167 inform (matching_location, "to match this %qs",
1168 get_matching_symbol (type));
1169
27bf414c
JM
1170 return false;
1171 }
1172}
1173
1174/* If the next token is the indicated keyword, consume it. Otherwise,
1175 issue the error MSGID. Returns true if found, false otherwise. */
1176
1177static bool
1178c_parser_require_keyword (c_parser *parser,
1179 enum rid keyword,
1180 const char *msgid)
1181{
1182 if (c_parser_next_token_is_keyword (parser, keyword))
1183 {
1184 c_parser_consume_token (parser);
1185 return true;
1186 }
1187 else
1188 {
1189 c_parser_error (parser, msgid);
1190 return false;
1191 }
1192}
1193
1194/* Like c_parser_require, except that tokens will be skipped until the
1195 desired token is found. An error message is still produced if the
1196 next token is not as expected. If MSGID is NULL then a message has
1197 already been produced and no message will be produced this
32129a17
DM
1198 time.
1199
1200 If MATCHING_LOCATION is not UNKNOWN_LOCATION, then highlight it
1201 within any error as the location of an "opening" token matching
1202 the close token TYPE (e.g. the location of the '(' when TYPE is
1203 CPP_CLOSE_PAREN). */
27bf414c 1204
1ee62b92 1205void
27bf414c
JM
1206c_parser_skip_until_found (c_parser *parser,
1207 enum cpp_ttype type,
32129a17
DM
1208 const char *msgid,
1209 location_t matching_location)
27bf414c
JM
1210{
1211 unsigned nesting_depth = 0;
1212
32129a17 1213 if (c_parser_require (parser, type, msgid, matching_location))
27bf414c
JM
1214 return;
1215
1216 /* Skip tokens until the desired token is found. */
1217 while (true)
1218 {
1219 /* Peek at the next token. */
1220 c_token *token = c_parser_peek_token (parser);
1221 /* If we've reached the token we want, consume it and stop. */
1222 if (token->type == type && !nesting_depth)
1223 {
1224 c_parser_consume_token (parser);
1225 break;
1226 }
bc4071dd 1227
27bf414c
JM
1228 /* If we've run out of tokens, stop. */
1229 if (token->type == CPP_EOF)
1230 return;
bc4071dd
RH
1231 if (token->type == CPP_PRAGMA_EOL && parser->in_pragma)
1232 return;
27bf414c
JM
1233 if (token->type == CPP_OPEN_BRACE
1234 || token->type == CPP_OPEN_PAREN
1235 || token->type == CPP_OPEN_SQUARE)
1236 ++nesting_depth;
1237 else if (token->type == CPP_CLOSE_BRACE
1238 || token->type == CPP_CLOSE_PAREN
1239 || token->type == CPP_CLOSE_SQUARE)
1240 {
1241 if (nesting_depth-- == 0)
1242 break;
1243 }
1244 /* Consume this token. */
1245 c_parser_consume_token (parser);
1246 }
1247 parser->error = false;
1248}
1249
1250/* Skip tokens until the end of a parameter is found, but do not
1251 consume the comma, semicolon or closing delimiter. */
1252
1253static void
1254c_parser_skip_to_end_of_parameter (c_parser *parser)
1255{
1256 unsigned nesting_depth = 0;
1257
1258 while (true)
1259 {
1260 c_token *token = c_parser_peek_token (parser);
1261 if ((token->type == CPP_COMMA || token->type == CPP_SEMICOLON)
1262 && !nesting_depth)
1263 break;
1264 /* If we've run out of tokens, stop. */
1265 if (token->type == CPP_EOF)
1266 return;
bc4071dd
RH
1267 if (token->type == CPP_PRAGMA_EOL && parser->in_pragma)
1268 return;
27bf414c
JM
1269 if (token->type == CPP_OPEN_BRACE
1270 || token->type == CPP_OPEN_PAREN
1271 || token->type == CPP_OPEN_SQUARE)
1272 ++nesting_depth;
1273 else if (token->type == CPP_CLOSE_BRACE
1274 || token->type == CPP_CLOSE_PAREN
1275 || token->type == CPP_CLOSE_SQUARE)
1276 {
1277 if (nesting_depth-- == 0)
1278 break;
1279 }
1280 /* Consume this token. */
1281 c_parser_consume_token (parser);
1282 }
1283 parser->error = false;
1284}
1285
bc4071dd
RH
1286/* Expect to be at the end of the pragma directive and consume an
1287 end of line marker. */
1288
1289static void
62021f64 1290c_parser_skip_to_pragma_eol (c_parser *parser, bool error_if_not_eol = true)
bc4071dd
RH
1291{
1292 gcc_assert (parser->in_pragma);
1293 parser->in_pragma = false;
1294
62021f64
TB
1295 if (error_if_not_eol && c_parser_peek_token (parser)->type != CPP_PRAGMA_EOL)
1296 c_parser_error (parser, "expected end of line");
1297
1298 cpp_ttype token_type;
1299 do
1300 {
1301 c_token *token = c_parser_peek_token (parser);
1302 token_type = token->type;
1303 if (token_type == CPP_EOF)
1304 break;
1305 c_parser_consume_token (parser);
1306 }
1307 while (token_type != CPP_PRAGMA_EOL);
bc4071dd
RH
1308
1309 parser->error = false;
1310}
27bf414c 1311
2a83cc52
RH
1312/* Skip tokens until we have consumed an entire block, or until we
1313 have consumed a non-nested ';'. */
1314
1315static void
1316c_parser_skip_to_end_of_block_or_statement (c_parser *parser)
1317{
1318 unsigned nesting_depth = 0;
1319 bool save_error = parser->error;
1320
1321 while (true)
1322 {
1323 c_token *token;
1324
1325 /* Peek at the next token. */
1326 token = c_parser_peek_token (parser);
1327
1328 switch (token->type)
1329 {
1330 case CPP_EOF:
1331 return;
1332
1333 case CPP_PRAGMA_EOL:
1334 if (parser->in_pragma)
1335 return;
1336 break;
1337
1338 case CPP_SEMICOLON:
1339 /* If the next token is a ';', we have reached the
1340 end of the statement. */
1341 if (!nesting_depth)
1342 {
1343 /* Consume the ';'. */
1344 c_parser_consume_token (parser);
1345 goto finished;
1346 }
1347 break;
1348
1349 case CPP_CLOSE_BRACE:
1350 /* If the next token is a non-nested '}', then we have
1351 reached the end of the current block. */
1352 if (nesting_depth == 0 || --nesting_depth == 0)
1353 {
1354 c_parser_consume_token (parser);
1355 goto finished;
1356 }
1357 break;
1358
1359 case CPP_OPEN_BRACE:
1360 /* If it the next token is a '{', then we are entering a new
1361 block. Consume the entire block. */
1362 ++nesting_depth;
1363 break;
1364
1365 case CPP_PRAGMA:
1366 /* If we see a pragma, consume the whole thing at once. We
1367 have some safeguards against consuming pragmas willy-nilly.
1368 Normally, we'd expect to be here with parser->error set,
1369 which disables these safeguards. But it's possible to get
1370 here for secondary error recovery, after parser->error has
1371 been cleared. */
1372 c_parser_consume_pragma (parser);
1373 c_parser_skip_to_pragma_eol (parser);
1374 parser->error = save_error;
1375 continue;
9e33de05
RS
1376
1377 default:
1378 break;
2a83cc52
RH
1379 }
1380
1381 c_parser_consume_token (parser);
1382 }
1383
1384 finished:
1385 parser->error = false;
1386}
1387
d2e796ad
MLI
1388/* CPP's options (initialized by c-opts.c). */
1389extern cpp_options *cpp_opts;
1390
27bf414c
JM
1391/* Save the warning flags which are controlled by __extension__. */
1392
1393static inline int
1394disable_extension_diagnostics (void)
1395{
1396 int ret = (pedantic
1397 | (warn_pointer_arith << 1)
1398 | (warn_traditional << 2)
d2e796ad 1399 | (flag_iso << 3)
24b97832 1400 | (warn_long_long << 4)
b3ab9ea2 1401 | (warn_cxx_compat << 5)
f3bede71 1402 | (warn_overlength_strings << 6)
177cce46
MP
1403 /* warn_c90_c99_compat has three states: -1/0/1, so we must
1404 play tricks to properly restore it. */
1405 | ((warn_c90_c99_compat == 1) << 7)
35aff4fb
MP
1406 | ((warn_c90_c99_compat == -1) << 8)
1407 /* Similarly for warn_c99_c11_compat. */
1408 | ((warn_c99_c11_compat == 1) << 9)
1409 | ((warn_c99_c11_compat == -1) << 10)
9f936c86
JM
1410 /* Similarly for warn_c11_c2x_compat. */
1411 | ((warn_c11_c2x_compat == 1) << 11)
1412 | ((warn_c11_c2x_compat == -1) << 12)
35aff4fb 1413 );
e3339d0f 1414 cpp_opts->cpp_pedantic = pedantic = 0;
27bf414c 1415 warn_pointer_arith = 0;
e3339d0f 1416 cpp_opts->cpp_warn_traditional = warn_traditional = 0;
27bf414c 1417 flag_iso = 0;
e3339d0f 1418 cpp_opts->cpp_warn_long_long = warn_long_long = 0;
24b97832 1419 warn_cxx_compat = 0;
b3ab9ea2 1420 warn_overlength_strings = 0;
f3bede71 1421 warn_c90_c99_compat = 0;
35aff4fb 1422 warn_c99_c11_compat = 0;
9f936c86 1423 warn_c11_c2x_compat = 0;
27bf414c
JM
1424 return ret;
1425}
1426
1427/* Restore the warning flags which are controlled by __extension__.
1428 FLAGS is the return value from disable_extension_diagnostics. */
1429
1430static inline void
1431restore_extension_diagnostics (int flags)
1432{
e3339d0f 1433 cpp_opts->cpp_pedantic = pedantic = flags & 1;
27bf414c 1434 warn_pointer_arith = (flags >> 1) & 1;
e3339d0f 1435 cpp_opts->cpp_warn_traditional = warn_traditional = (flags >> 2) & 1;
27bf414c 1436 flag_iso = (flags >> 3) & 1;
e3339d0f 1437 cpp_opts->cpp_warn_long_long = warn_long_long = (flags >> 4) & 1;
24b97832 1438 warn_cxx_compat = (flags >> 5) & 1;
b3ab9ea2 1439 warn_overlength_strings = (flags >> 6) & 1;
177cce46
MP
1440 /* See above for why is this needed. */
1441 warn_c90_c99_compat = (flags >> 7) & 1 ? 1 : ((flags >> 8) & 1 ? -1 : 0);
35aff4fb 1442 warn_c99_c11_compat = (flags >> 9) & 1 ? 1 : ((flags >> 10) & 1 ? -1 : 0);
9f936c86 1443 warn_c11_c2x_compat = (flags >> 11) & 1 ? 1 : ((flags >> 12) & 1 ? -1 : 0);
27bf414c
JM
1444}
1445
0b212d8c
TS
1446/* Helper data structure for parsing #pragma acc routine. */
1447struct oacc_routine_data {
ae9281fc
TS
1448 bool error_seen; /* Set if error has been reported. */
1449 bool fndecl_seen; /* Set if one fn decl/definition has been seen already. */
0b212d8c
TS
1450 tree clauses;
1451 location_t loc;
1452};
1453
4e03c3a7
JM
1454static bool c_parser_nth_token_starts_std_attributes (c_parser *,
1455 unsigned int);
1456static tree c_parser_std_attribute_specifier_sequence (c_parser *);
27bf414c
JM
1457static void c_parser_external_declaration (c_parser *);
1458static void c_parser_asm_definition (c_parser *);
32912286 1459static void c_parser_declaration_or_fndef (c_parser *, bool, bool, bool,
3a40d81d 1460 bool, bool, tree *, vec<c_token>,
4e03c3a7
JM
1461 bool have_attrs = false,
1462 tree attrs = NULL,
81fea426
MP
1463 struct oacc_routine_data * = NULL,
1464 bool * = NULL);
32912286
JM
1465static void c_parser_static_assert_declaration_no_semi (c_parser *);
1466static void c_parser_static_assert_declaration (c_parser *);
27bf414c
JM
1467static struct c_typespec c_parser_enum_specifier (c_parser *);
1468static struct c_typespec c_parser_struct_or_union_specifier (c_parser *);
1469static tree c_parser_struct_declaration (c_parser *);
1470static struct c_typespec c_parser_typeof_specifier (c_parser *);
d19fa6b5 1471static tree c_parser_alignas_specifier (c_parser *);
27bf414c
JM
1472static struct c_declarator *c_parser_direct_declarator (c_parser *, bool,
1473 c_dtr_syn, bool *);
1474static struct c_declarator *c_parser_direct_declarator_inner (c_parser *,
1475 bool,
1476 struct c_declarator *);
4e03c3a7
JM
1477static struct c_arg_info *c_parser_parms_declarator (c_parser *, bool, tree,
1478 bool);
a04a722b 1479static struct c_arg_info *c_parser_parms_list_declarator (c_parser *, tree,
4e03c3a7
JM
1480 tree, bool);
1481static struct c_parm *c_parser_parameter_declaration (c_parser *, tree, bool);
27bf414c 1482static tree c_parser_simple_asm_expr (c_parser *);
783bfe5e 1483static tree c_parser_gnu_attributes (c_parser *);
27bf414c 1484static struct c_expr c_parser_initializer (c_parser *);
16595a1f
BS
1485static struct c_expr c_parser_braced_init (c_parser *, tree, bool,
1486 struct obstack *);
a1e3b3d9
LB
1487static void c_parser_initelt (c_parser *, struct obstack *);
1488static void c_parser_initval (c_parser *, struct c_expr *,
1489 struct obstack *);
9def91e9
JJ
1490static tree c_parser_compound_statement (c_parser *, location_t * = NULL);
1491static location_t c_parser_compound_statement_nostart (c_parser *);
27bf414c 1492static void c_parser_label (c_parser *);
3e2becc4 1493static void c_parser_statement (c_parser *, bool *, location_t * = NULL);
99cd9857
MP
1494static void c_parser_statement_after_labels (c_parser *, bool *,
1495 vec<tree> * = NULL);
3e2becc4
MP
1496static tree c_parser_c99_block_statement (c_parser *, bool *,
1497 location_t * = NULL);
99cd9857 1498static void c_parser_if_statement (c_parser *, bool *, vec<tree> *);
351f85c5 1499static void c_parser_switch_statement (c_parser *, bool *);
170a8bd6
EB
1500static void c_parser_while_statement (c_parser *, bool, unsigned short, bool *);
1501static void c_parser_do_statement (c_parser *, bool, unsigned short);
1502static void c_parser_for_statement (c_parser *, bool, unsigned short, bool *);
27bf414c 1503static tree c_parser_asm_statement (c_parser *);
eadd3d0d 1504static tree c_parser_asm_operands (c_parser *);
1c384bf1 1505static tree c_parser_asm_goto_operands (c_parser *);
27bf414c 1506static tree c_parser_asm_clobbers (c_parser *);
acf0174b
JJ
1507static struct c_expr c_parser_expr_no_commas (c_parser *, struct c_expr *,
1508 tree = NULL_TREE);
27bf414c 1509static struct c_expr c_parser_conditional_expression (c_parser *,
acf0174b 1510 struct c_expr *, tree);
20906c66 1511static struct c_expr c_parser_binary_expression (c_parser *, struct c_expr *,
acf0174b 1512 tree);
27bf414c
JM
1513static struct c_expr c_parser_cast_expression (c_parser *, struct c_expr *);
1514static struct c_expr c_parser_unary_expression (c_parser *);
1515static struct c_expr c_parser_sizeof_expression (c_parser *);
1516static struct c_expr c_parser_alignof_expression (c_parser *);
1517static struct c_expr c_parser_postfix_expression (c_parser *);
1518static struct c_expr c_parser_postfix_expression_after_paren_type (c_parser *,
24b97832
ILT
1519 struct c_type_name *,
1520 location_t);
27bf414c 1521static struct c_expr c_parser_postfix_expression_after_primary (c_parser *,
c2255bc4 1522 location_t loc,
27bf414c 1523 struct c_expr);
0a35513e
AH
1524static tree c_parser_transaction (c_parser *, enum rid);
1525static struct c_expr c_parser_transaction_expression (c_parser *, enum rid);
1526static tree c_parser_transaction_cancel (c_parser *);
27bf414c 1527static struct c_expr c_parser_expression (c_parser *);
46bdb9cf 1528static struct c_expr c_parser_expression_conv (c_parser *);
9771b263
DN
1529static vec<tree, va_gc> *c_parser_expr_list (c_parser *, bool, bool,
1530 vec<tree, va_gc> **, location_t *,
b108f48f
JJ
1531 tree *, vec<location_t> *,
1532 unsigned int * = NULL);
98f08eb8
MS
1533static struct c_expr c_parser_has_attribute_expression (c_parser *);
1534
6e232ba4 1535static void c_parser_oacc_declare (c_parser *);
41dbbb37
TS
1536static void c_parser_oacc_enter_exit_data (c_parser *, bool);
1537static void c_parser_oacc_update (c_parser *);
dda1bf61 1538static void c_parser_omp_construct (c_parser *, bool *);
953ff289
DN
1539static void c_parser_omp_threadprivate (c_parser *);
1540static void c_parser_omp_barrier (c_parser *);
28567c40 1541static void c_parser_omp_depobj (c_parser *);
953ff289 1542static void c_parser_omp_flush (c_parser *);
41dbbb37 1543static tree c_parser_omp_for_loop (location_t, c_parser *, enum tree_code,
dda1bf61 1544 tree, tree *, bool *);
a68ab351 1545static void c_parser_omp_taskwait (c_parser *);
20906c66 1546static void c_parser_omp_taskyield (c_parser *);
acf0174b 1547static void c_parser_omp_cancel (c_parser *);
27bf414c 1548
acf0174b
JJ
1549enum pragma_context { pragma_external, pragma_struct, pragma_param,
1550 pragma_stmt, pragma_compound };
dda1bf61 1551static bool c_parser_pragma (c_parser *, enum pragma_context, bool *);
54d19c3b 1552static void c_parser_omp_cancellation_point (c_parser *, enum pragma_context);
dda1bf61 1553static bool c_parser_omp_target (c_parser *, enum pragma_context, bool *);
acf0174b
JJ
1554static void c_parser_omp_end_declare_target (c_parser *);
1555static void c_parser_omp_declare (c_parser *, enum pragma_context);
28567c40 1556static void c_parser_omp_requires (c_parser *);
dda1bf61 1557static bool c_parser_omp_ordered (c_parser *, enum pragma_context, bool *);
0b212d8c 1558static void c_parser_oacc_routine (c_parser *, enum pragma_context);
bc4071dd 1559
27bf414c
JM
1560/* These Objective-C parser functions are only ever called when
1561 compiling Objective-C. */
c165dca7 1562static void c_parser_objc_class_definition (c_parser *, tree);
27bf414c
JM
1563static void c_parser_objc_class_instance_variables (c_parser *);
1564static void c_parser_objc_class_declaration (c_parser *);
1565static void c_parser_objc_alias_declaration (c_parser *);
c165dca7 1566static void c_parser_objc_protocol_definition (c_parser *, tree);
249a82c4 1567static bool c_parser_objc_method_type (c_parser *);
27bf414c
JM
1568static void c_parser_objc_method_definition (c_parser *);
1569static void c_parser_objc_methodprotolist (c_parser *);
1570static void c_parser_objc_methodproto (c_parser *);
a04a722b 1571static tree c_parser_objc_method_decl (c_parser *, bool, tree *, tree *);
27bf414c
JM
1572static tree c_parser_objc_type_name (c_parser *);
1573static tree c_parser_objc_protocol_refs (c_parser *);
437c2322 1574static void c_parser_objc_try_catch_finally_statement (c_parser *);
27bf414c
JM
1575static void c_parser_objc_synchronized_statement (c_parser *);
1576static tree c_parser_objc_selector (c_parser *);
1577static tree c_parser_objc_selector_arg (c_parser *);
1578static tree c_parser_objc_receiver (c_parser *);
1579static tree c_parser_objc_message_args (c_parser *);
1580static tree c_parser_objc_keywordexpr (c_parser *);
f614132b 1581static void c_parser_objc_at_property_declaration (c_parser *);
da57d1b9
NP
1582static void c_parser_objc_at_synthesize_declaration (c_parser *);
1583static void c_parser_objc_at_dynamic_declaration (c_parser *);
668ea4b1 1584static bool c_parser_objc_diagnose_bad_element_prefix
c165dca7 1585 (c_parser *, struct c_declspecs *);
9def91e9 1586static location_t c_parser_parse_rtl_body (c_parser *, char *);
c2e84327 1587
31dc71a8 1588/* Parse a translation unit (C90 6.7, C99 6.9, C11 6.9).
27bf414c
JM
1589
1590 translation-unit:
1591 external-declarations
1592
1593 external-declarations:
1594 external-declaration
1595 external-declarations external-declaration
1596
1597 GNU extensions:
1598
1599 translation-unit:
1600 empty
1601*/
1602
1603static void
1604c_parser_translation_unit (c_parser *parser)
1605{
1606 if (c_parser_next_token_is (parser, CPP_EOF))
1607 {
c1771a20 1608 pedwarn (c_parser_peek_token (parser)->location, OPT_Wpedantic,
509c9d60 1609 "ISO C forbids an empty translation unit");
27bf414c
JM
1610 }
1611 else
1612 {
1613 void *obstack_position = obstack_alloc (&parser_obstack, 0);
6ec637a4 1614 mark_valid_location_for_stdc_pragma (false);
27bf414c
JM
1615 do
1616 {
1617 ggc_collect ();
1618 c_parser_external_declaration (parser);
1619 obstack_free (&parser_obstack, obstack_position);
1620 }
1621 while (c_parser_next_token_is_not (parser, CPP_EOF));
1622 }
d25c7690 1623
13f92e8d
JJ
1624 unsigned int i;
1625 tree decl;
1626 FOR_EACH_VEC_ELT (incomplete_record_decls, i, decl)
1627 if (DECL_SIZE (decl) == NULL_TREE && TREE_TYPE (decl) != error_mark_node)
686e2237 1628 error ("storage size of %q+D isn%'t known", decl);
7cec9588
JJ
1629
1630 if (current_omp_declare_target_attribute)
1631 {
1632 if (!errorcount)
1633 error ("%<#pragma omp declare target%> without corresponding "
1634 "%<#pragma omp end declare target%>");
1635 current_omp_declare_target_attribute = 0;
1636 }
27bf414c
JM
1637}
1638
31dc71a8 1639/* Parse an external declaration (C90 6.7, C99 6.9, C11 6.9).
27bf414c
JM
1640
1641 external-declaration:
1642 function-definition
1643 declaration
1644
1645 GNU extensions:
1646
1647 external-declaration:
1648 asm-definition
1649 ;
1650 __extension__ external-declaration
1651
1652 Objective-C:
1653
1654 external-declaration:
1655 objc-class-definition
1656 objc-class-declaration
1657 objc-alias-declaration
1658 objc-protocol-definition
1659 objc-method-definition
1660 @end
1661*/
1662
1663static void
1664c_parser_external_declaration (c_parser *parser)
1665{
1666 int ext;
1667 switch (c_parser_peek_token (parser)->type)
1668 {
1669 case CPP_KEYWORD:
1670 switch (c_parser_peek_token (parser)->keyword)
1671 {
1672 case RID_EXTENSION:
1673 ext = disable_extension_diagnostics ();
1674 c_parser_consume_token (parser);
1675 c_parser_external_declaration (parser);
1676 restore_extension_diagnostics (ext);
1677 break;
1678 case RID_ASM:
1679 c_parser_asm_definition (parser);
1680 break;
1681 case RID_AT_INTERFACE:
1682 case RID_AT_IMPLEMENTATION:
1683 gcc_assert (c_dialect_objc ());
c165dca7 1684 c_parser_objc_class_definition (parser, NULL_TREE);
27bf414c 1685 break;
49b91f05 1686 case RID_AT_CLASS:
27bf414c
JM
1687 gcc_assert (c_dialect_objc ());
1688 c_parser_objc_class_declaration (parser);
1689 break;
1690 case RID_AT_ALIAS:
1691 gcc_assert (c_dialect_objc ());
1692 c_parser_objc_alias_declaration (parser);
1693 break;
1694 case RID_AT_PROTOCOL:
1695 gcc_assert (c_dialect_objc ());
c165dca7 1696 c_parser_objc_protocol_definition (parser, NULL_TREE);
27bf414c 1697 break;
668ea4b1
IS
1698 case RID_AT_PROPERTY:
1699 gcc_assert (c_dialect_objc ());
f614132b 1700 c_parser_objc_at_property_declaration (parser);
668ea4b1 1701 break;
da57d1b9
NP
1702 case RID_AT_SYNTHESIZE:
1703 gcc_assert (c_dialect_objc ());
1704 c_parser_objc_at_synthesize_declaration (parser);
1705 break;
1706 case RID_AT_DYNAMIC:
1707 gcc_assert (c_dialect_objc ());
1708 c_parser_objc_at_dynamic_declaration (parser);
1709 break;
27bf414c
JM
1710 case RID_AT_END:
1711 gcc_assert (c_dialect_objc ());
1712 c_parser_consume_token (parser);
1713 objc_finish_implementation ();
1714 break;
1715 default:
1716 goto decl_or_fndef;
1717 }
1718 break;
1719 case CPP_SEMICOLON:
c1771a20 1720 pedwarn (c_parser_peek_token (parser)->location, OPT_Wpedantic,
509c9d60 1721 "ISO C does not allow extra %<;%> outside of a function");
27bf414c
JM
1722 c_parser_consume_token (parser);
1723 break;
bc4071dd 1724 case CPP_PRAGMA:
6ec637a4 1725 mark_valid_location_for_stdc_pragma (true);
dda1bf61 1726 c_parser_pragma (parser, pragma_external, NULL);
6ec637a4 1727 mark_valid_location_for_stdc_pragma (false);
bc4071dd 1728 break;
27bf414c
JM
1729 case CPP_PLUS:
1730 case CPP_MINUS:
1731 if (c_dialect_objc ())
1732 {
1733 c_parser_objc_method_definition (parser);
1734 break;
1735 }
1736 /* Else fall through, and yield a syntax error trying to parse
1737 as a declaration or function definition. */
191816a3 1738 /* FALLTHRU */
27bf414c
JM
1739 default:
1740 decl_or_fndef:
c165dca7
IS
1741 /* A declaration or a function definition (or, in Objective-C,
1742 an @interface or @protocol with prefix attributes). We can
1743 only tell which after parsing the declaration specifiers, if
1744 any, and the first declarator. */
acf0174b
JJ
1745 c_parser_declaration_or_fndef (parser, true, true, true, false, true,
1746 NULL, vNULL);
27bf414c
JM
1747 break;
1748 }
1749}
1750
acf0174b 1751static void c_finish_omp_declare_simd (c_parser *, tree, tree, vec<c_token>);
ae9281fc 1752static void c_finish_oacc_routine (struct oacc_routine_data *, tree, bool);
acf0174b 1753
96a95ac1
AO
1754/* Build and add a DEBUG_BEGIN_STMT statement with location LOC. */
1755
1756static void
1757add_debug_begin_stmt (location_t loc)
1758{
849bbdb9
JJ
1759 /* Don't add DEBUG_BEGIN_STMTs outside of functions, see PR84721. */
1760 if (!MAY_HAVE_DEBUG_MARKER_STMTS || !building_stmt_list_p ())
96a95ac1
AO
1761 return;
1762
1763 tree stmt = build0 (DEBUG_BEGIN_STMT, void_type_node);
1764 SET_EXPR_LOCATION (stmt, loc);
1765 add_stmt (stmt);
1766}
1767
27bf414c 1768/* Parse a declaration or function definition (C90 6.5, 6.7.1, C99
31dc71a8
MP
1769 6.7, 6.9.1, C11 6.7, 6.9.1). If FNDEF_OK is true, a function definition
1770 is accepted; otherwise (old-style parameter declarations) only other
32912286
JM
1771 declarations are accepted. If STATIC_ASSERT_OK is true, a static
1772 assertion is accepted; otherwise (old-style parameter declarations)
1773 it is not. If NESTED is true, we are inside a function or parsing
1774 old-style parameter declarations; any functions encountered are
1775 nested functions and declaration specifiers are required; otherwise
1776 we are at top level and functions are normal functions and
1777 declaration specifiers may be optional. If EMPTY_OK is true, empty
1778 declarations are OK (subject to all other constraints); otherwise
1779 (old-style parameter declarations) they are diagnosed. If
1780 START_ATTR_OK is true, the declaration specifiers may start with
4e03c3a7 1781 attributes (GNU or standard); otherwise they may not.
f05b9d93
NP
1782 OBJC_FOREACH_OBJECT_DECLARATION can be used to get back the parsed
1783 declaration when parsing an Objective-C foreach statement.
81fea426 1784 FALLTHRU_ATTR_P is used to signal whether this function parsed
4e03c3a7
JM
1785 "__attribute__((fallthrough));". ATTRS are any standard attributes
1786 parsed in the caller (in contexts where such attributes had to be
1787 parsed to determine whether what follows is a declaration or a
1788 statement); HAVE_ATTRS says whether there were any such attributes
1789 (even empty).
27bf414c
JM
1790
1791 declaration:
1792 declaration-specifiers init-declarator-list[opt] ;
32912286 1793 static_assert-declaration
27bf414c
JM
1794
1795 function-definition:
1796 declaration-specifiers[opt] declarator declaration-list[opt]
1797 compound-statement
1798
1799 declaration-list:
1800 declaration
1801 declaration-list declaration
1802
1803 init-declarator-list:
1804 init-declarator
1805 init-declarator-list , init-declarator
1806
1807 init-declarator:
783bfe5e
JM
1808 declarator simple-asm-expr[opt] gnu-attributes[opt]
1809 declarator simple-asm-expr[opt] gnu-attributes[opt] = initializer
27bf414c
JM
1810
1811 GNU extensions:
1812
1813 nested-function-definition:
1814 declaration-specifiers declarator declaration-list[opt]
1815 compound-statement
1816
81fea426
MP
1817 attribute ;
1818
c165dca7 1819 Objective-C:
783bfe5e
JM
1820 gnu-attributes objc-class-definition
1821 gnu-attributes objc-category-definition
1822 gnu-attributes objc-protocol-definition
c165dca7 1823
783bfe5e 1824 The simple-asm-expr and gnu-attributes are GNU extensions.
27bf414c
JM
1825
1826 This function does not handle __extension__; that is handled in its
1827 callers. ??? Following the old parser, __extension__ may start
1828 external declarations, declarations in functions and declarations
1829 at the start of "for" loops, but not old-style parameter
1830 declarations.
1831
1832 C99 requires declaration specifiers in a function definition; the
1833 absence is diagnosed through the diagnosis of implicit int. In GNU
1834 C we also allow but diagnose declarations without declaration
1835 specifiers, but only at top level (elsewhere they conflict with
953ff289 1836 other syntax).
b8698a0f 1837
f05b9d93
NP
1838 In Objective-C, declarations of the looping variable in a foreach
1839 statement are exceptionally terminated by 'in' (for example, 'for
1840 (NSObject *object in array) { ... }').
1841
953ff289 1842 OpenMP:
b8698a0f 1843
953ff289 1844 declaration:
1ee62b92
PG
1845 threadprivate-directive
1846
1847 GIMPLE:
1848
1849 gimple-function-definition:
c2e84327
DM
1850 declaration-specifiers[opt] __GIMPLE (gimple-or-rtl-pass-list) declarator
1851 declaration-list[opt] compound-statement
1852
1853 rtl-function-definition:
1854 declaration-specifiers[opt] __RTL (gimple-or-rtl-pass-list) declarator
1ee62b92 1855 declaration-list[opt] compound-statement */
27bf414c
JM
1856
1857static void
32912286
JM
1858c_parser_declaration_or_fndef (c_parser *parser, bool fndef_ok,
1859 bool static_assert_ok, bool empty_ok,
f05b9d93 1860 bool nested, bool start_attr_ok,
acf0174b 1861 tree *objc_foreach_object_declaration,
3a40d81d 1862 vec<c_token> omp_declare_simd_clauses,
4e03c3a7 1863 bool have_attrs, tree attrs,
81fea426
MP
1864 struct oacc_routine_data *oacc_routine_data,
1865 bool *fallthru_attr_p)
27bf414c
JM
1866{
1867 struct c_declspecs *specs;
1868 tree prefix_attrs;
1869 tree all_prefix_attrs;
1870 bool diagnosed_no_specs = false;
c7412148 1871 location_t here = c_parser_peek_token (parser)->location;
bc4071dd 1872
96a95ac1
AO
1873 add_debug_begin_stmt (c_parser_peek_token (parser)->location);
1874
32912286
JM
1875 if (static_assert_ok
1876 && c_parser_next_token_is_keyword (parser, RID_STATIC_ASSERT))
1877 {
1878 c_parser_static_assert_declaration (parser);
1879 return;
1880 }
27bf414c 1881 specs = build_null_declspecs ();
2f413185 1882
4e03c3a7
JM
1883 /* Handle any standard attributes parsed in the caller. */
1884 if (have_attrs)
1885 {
1886 declspecs_add_attrs (here, specs, attrs);
1887 specs->non_std_attrs_seen_p = false;
1888 }
1889
2f413185
PB
1890 /* Try to detect an unknown type name when we have "A B" or "A *B". */
1891 if (c_parser_peek_token (parser)->type == CPP_NAME
1892 && c_parser_peek_token (parser)->id_kind == C_ID_ID
1893 && (c_parser_peek_2nd_token (parser)->type == CPP_NAME
1894 || c_parser_peek_2nd_token (parser)->type == CPP_MULT)
1895 && (!nested || !lookup_name (c_parser_peek_token (parser)->value)))
1896 {
0e36f5c7 1897 tree name = c_parser_peek_token (parser)->value;
1a4f11c8
DM
1898
1899 /* Issue a warning about NAME being an unknown type name, perhaps
1900 with some kind of hint.
1901 If the user forgot a "struct" etc, suggest inserting
1902 it. Otherwise, attempt to look for misspellings. */
1903 gcc_rich_location richloc (here);
0e36f5c7 1904 if (tag_exists_p (RECORD_TYPE, name))
1a4f11c8
DM
1905 {
1906 /* This is not C++ with its implicit typedef. */
254830ba 1907 richloc.add_fixit_insert_before ("struct ");
64a5912c
DM
1908 error_at (&richloc,
1909 "unknown type name %qE;"
1910 " use %<struct%> keyword to refer to the type",
1911 name);
1a4f11c8 1912 }
0e36f5c7 1913 else if (tag_exists_p (UNION_TYPE, name))
1a4f11c8 1914 {
254830ba 1915 richloc.add_fixit_insert_before ("union ");
64a5912c
DM
1916 error_at (&richloc,
1917 "unknown type name %qE;"
1918 " use %<union%> keyword to refer to the type",
1919 name);
1a4f11c8 1920 }
0e36f5c7 1921 else if (tag_exists_p (ENUMERAL_TYPE, name))
1a4f11c8 1922 {
254830ba 1923 richloc.add_fixit_insert_before ("enum ");
64a5912c
DM
1924 error_at (&richloc,
1925 "unknown type name %qE;"
1926 " use %<enum%> keyword to refer to the type",
1927 name);
1a4f11c8
DM
1928 }
1929 else
1930 {
097f82ec 1931 auto_diagnostic_group d;
6c7a259b
DM
1932 name_hint hint = lookup_name_fuzzy (name, FUZZY_LOOKUP_TYPENAME,
1933 here);
7e2de6df 1934 if (const char *suggestion = hint.suggestion ())
1a4f11c8 1935 {
7e2de6df 1936 richloc.add_fixit_replace (suggestion);
64a5912c
DM
1937 error_at (&richloc,
1938 "unknown type name %qE; did you mean %qs?",
7e2de6df 1939 name, suggestion);
1a4f11c8
DM
1940 }
1941 else
1942 error_at (here, "unknown type name %qE", name);
1943 }
2f413185
PB
1944
1945 /* Parse declspecs normally to get a correct pointer type, but avoid
a5812bdc
PB
1946 a further "fails to be a type name" error. Refuse nested functions
1947 since it is not how the user likely wants us to recover. */
2f413185
PB
1948 c_parser_peek_token (parser)->type = CPP_KEYWORD;
1949 c_parser_peek_token (parser)->keyword = RID_VOID;
1950 c_parser_peek_token (parser)->value = error_mark_node;
a5812bdc 1951 fndef_ok = !nested;
2f413185
PB
1952 }
1953
4e03c3a7
JM
1954 /* When there are standard attributes at the start of the
1955 declaration (to apply to the entity being declared), an
1956 init-declarator-list or function definition must be present. */
1957 if (c_parser_nth_token_starts_std_attributes (parser, 1))
1958 have_attrs = true;
1959
568a31f2 1960 c_parser_declspecs (parser, specs, true, true, start_attr_ok,
4e03c3a7 1961 true, true, start_attr_ok, true, cla_nonabstract_decl);
27bf414c
JM
1962 if (parser->error)
1963 {
1964 c_parser_skip_to_end_of_block_or_statement (parser);
1965 return;
1966 }
1967 if (nested && !specs->declspecs_seen_p)
1968 {
1969 c_parser_error (parser, "expected declaration specifiers");
1970 c_parser_skip_to_end_of_block_or_statement (parser);
1971 return;
1972 }
1ee62b92 1973
27bf414c 1974 finish_declspecs (specs);
38b7bc7f 1975 bool auto_type_p = specs->typespec_word == cts_auto_type;
27bf414c
JM
1976 if (c_parser_next_token_is (parser, CPP_SEMICOLON))
1977 {
38b7bc7f
JM
1978 if (auto_type_p)
1979 error_at (here, "%<__auto_type%> in empty declaration");
81fea426
MP
1980 else if (specs->typespec_kind == ctsk_none
1981 && attribute_fallthrough_p (specs->attrs))
1982 {
1983 if (fallthru_attr_p != NULL)
1984 *fallthru_attr_p = true;
f8aea5e3
JM
1985 if (nested)
1986 {
1987 tree fn = build_call_expr_internal_loc (here, IFN_FALLTHROUGH,
1988 void_type_node, 0);
1989 add_stmt (fn);
1990 }
1991 else
1992 pedwarn (here, OPT_Wattributes,
1993 "%<fallthrough%> attribute at top level");
81fea426 1994 }
4e03c3a7
JM
1995 else if (empty_ok && !(have_attrs
1996 && specs->non_std_attrs_seen_p))
27bf414c
JM
1997 shadow_tag (specs);
1998 else
1999 {
2000 shadow_tag_warned (specs, 1);
509c9d60 2001 pedwarn (here, 0, "empty declaration");
27bf414c
JM
2002 }
2003 c_parser_consume_token (parser);
0b212d8c 2004 if (oacc_routine_data)
ae9281fc 2005 c_finish_oacc_routine (oacc_routine_data, NULL_TREE, false);
27bf414c
JM
2006 return;
2007 }
f725e721
PB
2008
2009 /* Provide better error recovery. Note that a type name here is usually
2010 better diagnosed as a redeclaration. */
2011 if (empty_ok
2012 && specs->typespec_kind == ctsk_tagdef
2013 && c_parser_next_token_starts_declspecs (parser)
2014 && !c_parser_next_token_is (parser, CPP_NAME))
2015 {
2016 c_parser_error (parser, "expected %<;%>, identifier or %<(%>");
2017 parser->error = false;
2018 shadow_tag_warned (specs, 1);
2019 return;
2020 }
38b7bc7f 2021 else if (c_dialect_objc () && !auto_type_p)
c165dca7 2022 {
f7e71da5
IS
2023 /* Prefix attributes are an error on method decls. */
2024 switch (c_parser_peek_token (parser)->type)
2025 {
2026 case CPP_PLUS:
2027 case CPP_MINUS:
2028 if (c_parser_objc_diagnose_bad_element_prefix (parser, specs))
2029 return;
2030 if (specs->attrs)
2031 {
2032 warning_at (c_parser_peek_token (parser)->location,
2033 OPT_Wattributes,
2034 "prefix attributes are ignored for methods");
2035 specs->attrs = NULL_TREE;
2036 }
2037 if (fndef_ok)
2038 c_parser_objc_method_definition (parser);
2039 else
2040 c_parser_objc_methodproto (parser);
2041 return;
2042 break;
2043 default:
2044 break;
2045 }
c165dca7
IS
2046 /* This is where we parse 'attributes @interface ...',
2047 'attributes @implementation ...', 'attributes @protocol ...'
2048 (where attributes could be, for example, __attribute__
2049 ((deprecated)).
2050 */
2051 switch (c_parser_peek_token (parser)->keyword)
2052 {
2053 case RID_AT_INTERFACE:
2054 {
2055 if (c_parser_objc_diagnose_bad_element_prefix (parser, specs))
2056 return;
2057 c_parser_objc_class_definition (parser, specs->attrs);
2058 return;
2059 }
2060 break;
2061 case RID_AT_IMPLEMENTATION:
2062 {
2063 if (c_parser_objc_diagnose_bad_element_prefix (parser, specs))
2064 return;
2065 if (specs->attrs)
2066 {
2067 warning_at (c_parser_peek_token (parser)->location,
2068 OPT_Wattributes,
2069 "prefix attributes are ignored for implementations");
2070 specs->attrs = NULL_TREE;
2071 }
2072 c_parser_objc_class_definition (parser, NULL_TREE);
2073 return;
2074 }
2075 break;
2076 case RID_AT_PROTOCOL:
2077 {
2078 if (c_parser_objc_diagnose_bad_element_prefix (parser, specs))
2079 return;
2080 c_parser_objc_protocol_definition (parser, specs->attrs);
2081 return;
2082 }
2083 break;
668ea4b1
IS
2084 case RID_AT_ALIAS:
2085 case RID_AT_CLASS:
2086 case RID_AT_END:
2087 case RID_AT_PROPERTY:
2088 if (specs->attrs)
2089 {
96bbfbac 2090 c_parser_error (parser, "unexpected attribute");
668ea4b1
IS
2091 specs->attrs = NULL;
2092 }
2093 break;
c165dca7
IS
2094 default:
2095 break;
2096 }
2097 }
81fea426
MP
2098 else if (attribute_fallthrough_p (specs->attrs))
2099 warning_at (here, OPT_Wattributes,
2100 "%<fallthrough%> attribute not followed by %<;%>");
2101
27bf414c
JM
2102 pending_xref_error ();
2103 prefix_attrs = specs->attrs;
2104 all_prefix_attrs = prefix_attrs;
2105 specs->attrs = NULL_TREE;
ae9281fc 2106 while (true)
27bf414c
JM
2107 {
2108 struct c_declarator *declarator;
2109 bool dummy = false;
575bfb00 2110 timevar_id_t tv;
1ee62b92 2111 tree fnbody = NULL_TREE;
27bf414c
JM
2112 /* Declaring either one or more declarators (in which case we
2113 should diagnose if there were no declaration specifiers) or a
2114 function definition (in which case the diagnostic for
2115 implicit int suffices). */
9e5b2115
PB
2116 declarator = c_parser_declarator (parser,
2117 specs->typespec_kind != ctsk_none,
27bf414c
JM
2118 C_DTR_NORMAL, &dummy);
2119 if (declarator == NULL)
2120 {
5e9d6aa4 2121 if (omp_declare_simd_clauses.exists ())
acf0174b
JJ
2122 c_finish_omp_declare_simd (parser, NULL_TREE, NULL_TREE,
2123 omp_declare_simd_clauses);
0b212d8c 2124 if (oacc_routine_data)
ae9281fc 2125 c_finish_oacc_routine (oacc_routine_data, NULL_TREE, false);
27bf414c
JM
2126 c_parser_skip_to_end_of_block_or_statement (parser);
2127 return;
2128 }
38b7bc7f
JM
2129 if (auto_type_p && declarator->kind != cdk_id)
2130 {
2131 error_at (here,
2132 "%<__auto_type%> requires a plain identifier"
2133 " as declarator");
2134 c_parser_skip_to_end_of_block_or_statement (parser);
2135 return;
2136 }
27bf414c
JM
2137 if (c_parser_next_token_is (parser, CPP_EQ)
2138 || c_parser_next_token_is (parser, CPP_COMMA)
2139 || c_parser_next_token_is (parser, CPP_SEMICOLON)
2140 || c_parser_next_token_is_keyword (parser, RID_ASM)
f05b9d93
NP
2141 || c_parser_next_token_is_keyword (parser, RID_ATTRIBUTE)
2142 || c_parser_next_token_is_keyword (parser, RID_IN))
27bf414c
JM
2143 {
2144 tree asm_name = NULL_TREE;
2145 tree postfix_attrs = NULL_TREE;
2146 if (!diagnosed_no_specs && !specs->declspecs_seen_p)
2147 {
2148 diagnosed_no_specs = true;
509c9d60 2149 pedwarn (here, 0, "data definition has no type or storage class");
27bf414c
JM
2150 }
2151 /* Having seen a data definition, there cannot now be a
2152 function definition. */
2153 fndef_ok = false;
2154 if (c_parser_next_token_is_keyword (parser, RID_ASM))
2155 asm_name = c_parser_simple_asm_expr (parser);
2156 if (c_parser_next_token_is_keyword (parser, RID_ATTRIBUTE))
ae5ebda4 2157 {
783bfe5e 2158 postfix_attrs = c_parser_gnu_attributes (parser);
ae5ebda4
MP
2159 if (c_parser_next_token_is (parser, CPP_OPEN_BRACE))
2160 {
2161 /* This means there is an attribute specifier after
2162 the declarator in a function definition. Provide
2163 some more information for the user. */
2164 error_at (here, "attributes should be specified before the "
2165 "declarator in a function definition");
2166 c_parser_skip_to_end_of_block_or_statement (parser);
2167 return;
2168 }
2169 }
27bf414c
JM
2170 if (c_parser_next_token_is (parser, CPP_EQ))
2171 {
2172 tree d;
2173 struct c_expr init;
c2255bc4 2174 location_t init_loc;
27bf414c 2175 c_parser_consume_token (parser);
38b7bc7f
JM
2176 if (auto_type_p)
2177 {
38b7bc7f 2178 init_loc = c_parser_peek_token (parser)->location;
5dd9a9d0
DM
2179 rich_location richloc (line_table, init_loc);
2180 start_init (NULL_TREE, asm_name, global_bindings_p (), &richloc);
36618428
MP
2181 /* A parameter is initialized, which is invalid. Don't
2182 attempt to instrument the initializer. */
2183 int flag_sanitize_save = flag_sanitize;
2184 if (nested && !empty_ok)
2185 flag_sanitize = 0;
38b7bc7f 2186 init = c_parser_expr_no_commas (parser, NULL);
36618428 2187 flag_sanitize = flag_sanitize_save;
38b7bc7f
JM
2188 if (TREE_CODE (init.value) == COMPONENT_REF
2189 && DECL_C_BIT_FIELD (TREE_OPERAND (init.value, 1)))
2190 error_at (here,
2191 "%<__auto_type%> used with a bit-field"
2192 " initializer");
2193 init = convert_lvalue_to_rvalue (init_loc, init, true, true);
2194 tree init_type = TREE_TYPE (init.value);
9698b078 2195 /* As with typeof, remove all qualifiers from atomic types. */
38b7bc7f
JM
2196 if (init_type != error_mark_node && TYPE_ATOMIC (init_type))
2197 init_type
9698b078 2198 = c_build_qualified_type (init_type, TYPE_UNQUALIFIED);
38b7bc7f
JM
2199 bool vm_type = variably_modified_type_p (init_type,
2200 NULL_TREE);
2201 if (vm_type)
b2fa0a8b 2202 init.value = save_expr (init.value);
38b7bc7f
JM
2203 finish_init ();
2204 specs->typespec_kind = ctsk_typeof;
2205 specs->locations[cdw_typedef] = init_loc;
2206 specs->typedef_p = true;
2207 specs->type = init_type;
2208 if (vm_type)
2209 {
2210 bool maybe_const = true;
2211 tree type_expr = c_fully_fold (init.value, false,
2212 &maybe_const);
2213 specs->expr_const_operands &= maybe_const;
2214 if (specs->expr)
2215 specs->expr = build2 (COMPOUND_EXPR,
2216 TREE_TYPE (type_expr),
2217 specs->expr, type_expr);
2218 else
2219 specs->expr = type_expr;
2220 }
2221 d = start_decl (declarator, specs, true,
2222 chainon (postfix_attrs, all_prefix_attrs));
2223 if (!d)
2224 d = error_mark_node;
5e9d6aa4 2225 if (omp_declare_simd_clauses.exists ())
38b7bc7f
JM
2226 c_finish_omp_declare_simd (parser, d, NULL_TREE,
2227 omp_declare_simd_clauses);
2228 }
2229 else
2230 {
2231 /* The declaration of the variable is in effect while
2232 its initializer is parsed. */
2233 d = start_decl (declarator, specs, true,
2234 chainon (postfix_attrs, all_prefix_attrs));
2235 if (!d)
2236 d = error_mark_node;
5e9d6aa4 2237 if (omp_declare_simd_clauses.exists ())
38b7bc7f
JM
2238 c_finish_omp_declare_simd (parser, d, NULL_TREE,
2239 omp_declare_simd_clauses);
38b7bc7f 2240 init_loc = c_parser_peek_token (parser)->location;
5dd9a9d0
DM
2241 rich_location richloc (line_table, init_loc);
2242 start_init (d, asm_name, global_bindings_p (), &richloc);
36618428
MP
2243 /* A parameter is initialized, which is invalid. Don't
2244 attempt to instrument the initializer. */
2245 int flag_sanitize_save = flag_sanitize;
2246 if (TREE_CODE (d) == PARM_DECL)
2247 flag_sanitize = 0;
38b7bc7f 2248 init = c_parser_initializer (parser);
36618428 2249 flag_sanitize = flag_sanitize_save;
38b7bc7f
JM
2250 finish_init ();
2251 }
0b212d8c 2252 if (oacc_routine_data)
ae9281fc 2253 c_finish_oacc_routine (oacc_routine_data, d, false);
27bf414c
JM
2254 if (d != error_mark_node)
2255 {
d033409e 2256 maybe_warn_string_init (init_loc, TREE_TYPE (d), init);
c2255bc4 2257 finish_decl (d, init_loc, init.value,
d033409e 2258 init.original_type, asm_name);
27bf414c
JM
2259 }
2260 }
2261 else
2262 {
38b7bc7f
JM
2263 if (auto_type_p)
2264 {
2265 error_at (here,
2266 "%<__auto_type%> requires an initialized "
2267 "data declaration");
2268 c_parser_skip_to_end_of_block_or_statement (parser);
2269 return;
2270 }
27bf414c
JM
2271 tree d = start_decl (declarator, specs, false,
2272 chainon (postfix_attrs,
2273 all_prefix_attrs));
cfc30fd1
JJ
2274 if (d
2275 && TREE_CODE (d) == FUNCTION_DECL
cfc30fd1
JJ
2276 && DECL_ARGUMENTS (d) == NULL_TREE
2277 && DECL_INITIAL (d) == NULL_TREE)
db376f45
EB
2278 {
2279 /* Find the innermost declarator that is neither cdk_id
2280 nor cdk_attrs. */
2281 const struct c_declarator *decl = declarator;
2282 const struct c_declarator *last_non_id_attrs = NULL;
2283
2284 while (decl)
2285 switch (decl->kind)
2286 {
2287 case cdk_array:
2288 case cdk_function:
2289 case cdk_pointer:
2290 last_non_id_attrs = decl;
2291 decl = decl->declarator;
2292 break;
2293
2294 case cdk_attrs:
2295 decl = decl->declarator;
2296 break;
2297
2298 case cdk_id:
2299 decl = 0;
2300 break;
2301
2302 default:
2303 gcc_unreachable ();
2304 }
2305
2306 /* If it exists and is cdk_function, use its parameters. */
2307 if (last_non_id_attrs
2308 && last_non_id_attrs->kind == cdk_function)
2309 DECL_ARGUMENTS (d) = last_non_id_attrs->u.arg_info->parms;
2310 }
5e9d6aa4 2311 if (omp_declare_simd_clauses.exists ())
acf0174b
JJ
2312 {
2313 tree parms = NULL_TREE;
2314 if (d && TREE_CODE (d) == FUNCTION_DECL)
2315 {
2316 struct c_declarator *ce = declarator;
2317 while (ce != NULL)
2318 if (ce->kind == cdk_function)
2319 {
2320 parms = ce->u.arg_info->parms;
2321 break;
2322 }
2323 else
2324 ce = ce->declarator;
2325 }
2326 if (parms)
2327 temp_store_parm_decls (d, parms);
2328 c_finish_omp_declare_simd (parser, d, parms,
2329 omp_declare_simd_clauses);
2330 if (parms)
2331 temp_pop_parm_decls ();
2332 }
0b212d8c 2333 if (oacc_routine_data)
ae9281fc 2334 c_finish_oacc_routine (oacc_routine_data, d, false);
27bf414c 2335 if (d)
c2255bc4 2336 finish_decl (d, UNKNOWN_LOCATION, NULL_TREE,
f05b9d93
NP
2337 NULL_TREE, asm_name);
2338
2339 if (c_parser_next_token_is_keyword (parser, RID_IN))
2340 {
2341 if (d)
2342 *objc_foreach_object_declaration = d;
2343 else
2344 *objc_foreach_object_declaration = error_mark_node;
2345 }
27bf414c
JM
2346 }
2347 if (c_parser_next_token_is (parser, CPP_COMMA))
2348 {
38b7bc7f
JM
2349 if (auto_type_p)
2350 {
2351 error_at (here,
2352 "%<__auto_type%> may only be used with"
2353 " a single declarator");
2354 c_parser_skip_to_end_of_block_or_statement (parser);
2355 return;
2356 }
27bf414c
JM
2357 c_parser_consume_token (parser);
2358 if (c_parser_next_token_is_keyword (parser, RID_ATTRIBUTE))
783bfe5e 2359 all_prefix_attrs = chainon (c_parser_gnu_attributes (parser),
27bf414c
JM
2360 prefix_attrs);
2361 else
2362 all_prefix_attrs = prefix_attrs;
2363 continue;
2364 }
2365 else if (c_parser_next_token_is (parser, CPP_SEMICOLON))
2366 {
2367 c_parser_consume_token (parser);
2368 return;
2369 }
f05b9d93
NP
2370 else if (c_parser_next_token_is_keyword (parser, RID_IN))
2371 {
2372 /* This can only happen in Objective-C: we found the
2373 'in' that terminates the declaration inside an
2374 Objective-C foreach statement. Do not consume the
2375 token, so that the caller can use it to determine
2376 that this indeed is a foreach context. */
2377 return;
2378 }
27bf414c
JM
2379 else
2380 {
2381 c_parser_error (parser, "expected %<,%> or %<;%>");
2382 c_parser_skip_to_end_of_block_or_statement (parser);
2383 return;
2384 }
2385 }
38b7bc7f
JM
2386 else if (auto_type_p)
2387 {
2388 error_at (here,
2389 "%<__auto_type%> requires an initialized data declaration");
2390 c_parser_skip_to_end_of_block_or_statement (parser);
2391 return;
2392 }
27bf414c
JM
2393 else if (!fndef_ok)
2394 {
2395 c_parser_error (parser, "expected %<=%>, %<,%>, %<;%>, "
2396 "%<asm%> or %<__attribute__%>");
2397 c_parser_skip_to_end_of_block_or_statement (parser);
2398 return;
2399 }
2400 /* Function definition (nested or otherwise). */
2401 if (nested)
2402 {
c1771a20 2403 pedwarn (here, OPT_Wpedantic, "ISO C forbids nested functions");
d2784db4 2404 c_push_function_context ();
27bf414c
JM
2405 }
2406 if (!start_function (specs, declarator, all_prefix_attrs))
2407 {
1a59ccf2
DM
2408 /* At this point we've consumed:
2409 declaration-specifiers declarator
2410 and the next token isn't CPP_EQ, CPP_COMMA, CPP_SEMICOLON,
2411 RID_ASM, RID_ATTRIBUTE, or RID_IN,
2412 but the
2413 declaration-specifiers declarator
2414 aren't grokkable as a function definition, so we have
2415 an error. */
2416 gcc_assert (!c_parser_next_token_is (parser, CPP_SEMICOLON));
2417 if (c_parser_next_token_starts_declspecs (parser))
2418 {
2419 /* If we have
2420 declaration-specifiers declarator decl-specs
2421 then assume we have a missing semicolon, which would
2422 give us:
2423 declaration-specifiers declarator decl-specs
2424 ^
2425 ;
2426 <~~~~~~~~~ declaration ~~~~~~~~~~>
2427 Use c_parser_require to get an error with a fix-it hint. */
2428 c_parser_require (parser, CPP_SEMICOLON, "expected %<;%>");
2429 parser->error = false;
2430 }
2431 else
2432 {
2433 /* This can appear in many cases looking nothing like a
2434 function definition, so we don't give a more specific
2435 error suggesting there was one. */
2436 c_parser_error (parser, "expected %<=%>, %<,%>, %<;%>, %<asm%> "
2437 "or %<__attribute__%>");
2438 }
27bf414c 2439 if (nested)
d2784db4 2440 c_pop_function_context ();
27bf414c
JM
2441 break;
2442 }
575bfb00
LC
2443
2444 if (DECL_DECLARED_INLINE_P (current_function_decl))
2445 tv = TV_PARSE_INLINE;
2446 else
2447 tv = TV_PARSE_FUNC;
c2e84327 2448 auto_timevar at (g_timer, tv);
575bfb00 2449
27bf414c
JM
2450 /* Parse old-style parameter declarations. ??? Attributes are
2451 not allowed to start declaration specifiers here because of a
2452 syntax conflict between a function declaration with attribute
2453 suffix and a function definition with an attribute prefix on
2454 first old-style parameter declaration. Following the old
2455 parser, they are not accepted on subsequent old-style
2456 parameter declarations either. However, there is no
2457 ambiguity after the first declaration, nor indeed on the
2458 first as long as we don't allow postfix attributes after a
2459 declarator with a nonempty identifier list in a definition;
2460 and postfix attributes have never been accepted here in
2461 function definitions either. */
2462 while (c_parser_next_token_is_not (parser, CPP_EOF)
2463 && c_parser_next_token_is_not (parser, CPP_OPEN_BRACE))
32912286 2464 c_parser_declaration_or_fndef (parser, false, false, false,
acf0174b 2465 true, false, NULL, vNULL);
27bf414c 2466 store_parm_decls ();
5e9d6aa4 2467 if (omp_declare_simd_clauses.exists ())
acf0174b
JJ
2468 c_finish_omp_declare_simd (parser, current_function_decl, NULL_TREE,
2469 omp_declare_simd_clauses);
0b212d8c 2470 if (oacc_routine_data)
ae9281fc 2471 c_finish_oacc_routine (oacc_routine_data, current_function_decl, true);
5db9e893 2472 location_t startloc = c_parser_peek_token (parser)->location;
1751ecd6 2473 DECL_STRUCT_FUNCTION (current_function_decl)->function_start_locus
5db9e893
JJ
2474 = startloc;
2475 location_t endloc = startloc;
1ee62b92 2476
baa09dc5 2477 /* If the definition was marked with __RTL, use the RTL parser now,
c2e84327 2478 consuming the function body. */
baa09dc5 2479 if (specs->declspec_il == cdil_rtl)
c2e84327 2480 {
9def91e9 2481 endloc = c_parser_parse_rtl_body (parser, specs->gimple_or_rtl_pass);
c2e84327
DM
2482
2483 /* Normally, store_parm_decls sets next_is_function_body,
2484 anticipating a function body. We need a push_scope/pop_scope
2485 pair to flush out this state, or subsequent function parsing
2486 will go wrong. */
2487 push_scope ();
2488 pop_scope ();
2489
9def91e9 2490 finish_function (endloc);
c2e84327
DM
2491 return;
2492 }
baa09dc5
RB
2493 /* If the definition was marked with __GIMPLE then parse the
2494 function body as GIMPLE. */
2495 else if (specs->declspec_il != cdil_none)
2496 {
2497 bool saved = in_late_binary_op;
2498 in_late_binary_op = true;
2499 c_parser_parse_gimple_body (parser, specs->gimple_or_rtl_pass,
d276406a
ML
2500 specs->declspec_il,
2501 specs->entry_bb_count);
baa09dc5
RB
2502 in_late_binary_op = saved;
2503 }
1ee62b92 2504 else
9def91e9 2505 fnbody = c_parser_compound_statement (parser, &endloc);
1ee62b92 2506 tree fndecl = current_function_decl;
27bf414c
JM
2507 if (nested)
2508 {
2509 tree decl = current_function_decl;
9f62cb92
JJ
2510 /* Mark nested functions as needing static-chain initially.
2511 lower_nested_functions will recompute it but the
2512 DECL_STATIC_CHAIN flag is also used before that happens,
2513 by initializer_constant_valid_p. See gcc.dg/nested-fn-2.c. */
2514 DECL_STATIC_CHAIN (decl) = 1;
27bf414c 2515 add_stmt (fnbody);
9def91e9 2516 finish_function (endloc);
d2784db4 2517 c_pop_function_context ();
c2255bc4 2518 add_stmt (build_stmt (DECL_SOURCE_LOCATION (decl), DECL_EXPR, decl));
27bf414c
JM
2519 }
2520 else
2521 {
1ee62b92
PG
2522 if (fnbody)
2523 add_stmt (fnbody);
9def91e9 2524 finish_function (endloc);
27bf414c 2525 }
baa09dc5
RB
2526 /* Get rid of the empty stmt list for GIMPLE/RTL. */
2527 if (specs->declspec_il != cdil_none)
1ee62b92 2528 DECL_SAVED_TREE (fndecl) = NULL_TREE;
575bfb00 2529
27bf414c
JM
2530 break;
2531 }
2532}
2533
2534/* Parse an asm-definition (asm() outside a function body). This is a
2535 GNU extension.
2536
2537 asm-definition:
2538 simple-asm-expr ;
2539*/
2540
2541static void
2542c_parser_asm_definition (c_parser *parser)
2543{
2544 tree asm_str = c_parser_simple_asm_expr (parser);
27bf414c 2545 if (asm_str)
3dafb85c 2546 symtab->finalize_toplevel_asm (asm_str);
27bf414c
JM
2547 c_parser_skip_until_found (parser, CPP_SEMICOLON, "expected %<;%>");
2548}
2549
48b0b196 2550/* Parse a static assertion (C11 6.7.10).
32912286
JM
2551
2552 static_assert-declaration:
2553 static_assert-declaration-no-semi ;
2554*/
2555
2556static void
2557c_parser_static_assert_declaration (c_parser *parser)
2558{
2559 c_parser_static_assert_declaration_no_semi (parser);
2560 if (parser->error
2561 || !c_parser_require (parser, CPP_SEMICOLON, "expected %<;%>"))
2562 c_parser_skip_to_end_of_block_or_statement (parser);
2563}
2564
48b0b196 2565/* Parse a static assertion (C11 6.7.10), without the trailing
32912286
JM
2566 semicolon.
2567
2568 static_assert-declaration-no-semi:
2569 _Static_assert ( constant-expression , string-literal )
9f936c86
JM
2570
2571 C2X:
2572 static_assert-declaration-no-semi:
2573 _Static_assert ( constant-expression )
32912286
JM
2574*/
2575
2576static void
2577c_parser_static_assert_declaration_no_semi (c_parser *parser)
2578{
2579 location_t assert_loc, value_loc;
2580 tree value;
9f936c86 2581 tree string = NULL_TREE;
32912286
JM
2582
2583 gcc_assert (c_parser_next_token_is_keyword (parser, RID_STATIC_ASSERT));
2584 assert_loc = c_parser_peek_token (parser)->location;
35aff4fb
MP
2585 if (flag_isoc99)
2586 pedwarn_c99 (assert_loc, OPT_Wpedantic,
32912286 2587 "ISO C99 does not support %<_Static_assert%>");
35aff4fb
MP
2588 else
2589 pedwarn_c99 (assert_loc, OPT_Wpedantic,
32912286 2590 "ISO C90 does not support %<_Static_assert%>");
32912286 2591 c_parser_consume_token (parser);
32129a17
DM
2592 matching_parens parens;
2593 if (!parens.require_open (parser))
32912286 2594 return;
8062bca6 2595 location_t value_tok_loc = c_parser_peek_token (parser)->location;
32912286 2596 value = c_parser_expr_no_commas (parser, NULL).value;
8062bca6 2597 value_loc = EXPR_LOC_OR_LOC (value, value_tok_loc);
9f936c86 2598 if (c_parser_next_token_is (parser, CPP_COMMA))
32912286 2599 {
32912286 2600 c_parser_consume_token (parser);
9f936c86
JM
2601 switch (c_parser_peek_token (parser)->type)
2602 {
2603 case CPP_STRING:
2604 case CPP_STRING16:
2605 case CPP_STRING32:
2606 case CPP_WSTRING:
2607 case CPP_UTF8STRING:
471c5330 2608 string = c_parser_string_literal (parser, false, true).value;
9f936c86
JM
2609 break;
2610 default:
2611 c_parser_error (parser, "expected string literal");
9f936c86
JM
2612 return;
2613 }
32912286 2614 }
9f936c86
JM
2615 else if (flag_isoc11)
2616 /* If pedantic for pre-C11, the use of _Static_assert itself will
2617 have been diagnosed, so do not also diagnose the use of this
2618 new C2X feature of _Static_assert. */
2619 pedwarn_c11 (assert_loc, OPT_Wpedantic,
2620 "ISO C11 does not support omitting the string in "
2621 "%<_Static_assert%>");
32129a17 2622 parens.require_close (parser);
32912286
JM
2623
2624 if (!INTEGRAL_TYPE_P (TREE_TYPE (value)))
2625 {
2626 error_at (value_loc, "expression in static assertion is not an integer");
2627 return;
2628 }
2629 if (TREE_CODE (value) != INTEGER_CST)
2630 {
2631 value = c_fully_fold (value, false, NULL);
8d95fe25
MP
2632 /* Strip no-op conversions. */
2633 STRIP_TYPE_NOPS (value);
32912286 2634 if (TREE_CODE (value) == INTEGER_CST)
c1771a20 2635 pedwarn (value_loc, OPT_Wpedantic, "expression in static assertion "
32912286
JM
2636 "is not an integer constant expression");
2637 }
2638 if (TREE_CODE (value) != INTEGER_CST)
2639 {
2640 error_at (value_loc, "expression in static assertion is not constant");
2641 return;
2642 }
2643 constant_expression_warning (value);
2644 if (integer_zerop (value))
9f936c86
JM
2645 {
2646 if (string)
2647 error_at (assert_loc, "static assertion failed: %E", string);
2648 else
2649 error_at (assert_loc, "static assertion failed");
2650 }
32912286
JM
2651}
2652
27bf414c 2653/* Parse some declaration specifiers (possibly none) (C90 6.5, C99
31dc71a8 2654 6.7, C11 6.7), adding them to SPECS (which may already include some).
27bf414c 2655 Storage class specifiers are accepted iff SCSPEC_OK; type
568a31f2 2656 specifiers are accepted iff TYPESPEC_OK; alignment specifiers are
783bfe5e 2657 accepted iff ALIGNSPEC_OK; gnu-attributes are accepted at the start
4e03c3a7
JM
2658 iff START_ATTR_OK; __auto_type is accepted iff AUTO_TYPE_OK. In
2659 addition to the syntax shown, standard attributes are accepted at
2660 the start iff START_STD_ATTR_OK and at the end iff END_STD_ATTR_OK;
2661 unlike gnu-attributes, they are not accepted in the middle of the
2662 list. (This combines various different syntax productions in the C
2663 standard, and in some cases gnu-attributes and standard attributes
2664 at the start may already have been parsed before this function is
2665 called.)
27bf414c
JM
2666
2667 declaration-specifiers:
2668 storage-class-specifier declaration-specifiers[opt]
2669 type-specifier declaration-specifiers[opt]
2670 type-qualifier declaration-specifiers[opt]
2671 function-specifier declaration-specifiers[opt]
d19fa6b5 2672 alignment-specifier declaration-specifiers[opt]
27bf414c
JM
2673
2674 Function specifiers (inline) are from C99, and are currently
d19fa6b5 2675 handled as storage class specifiers, as is __thread. Alignment
48b0b196 2676 specifiers are from C11.
27bf414c 2677
31dc71a8 2678 C90 6.5.1, C99 6.7.1, C11 6.7.1:
27bf414c
JM
2679 storage-class-specifier:
2680 typedef
2681 extern
2682 static
2683 auto
2684 register
582d9b50
JM
2685 _Thread_local
2686
2687 (_Thread_local is new in C11.)
27bf414c 2688
31dc71a8 2689 C99 6.7.4, C11 6.7.4:
27bf414c
JM
2690 function-specifier:
2691 inline
c4b3a0a0
JM
2692 _Noreturn
2693
48b0b196 2694 (_Noreturn is new in C11.)
27bf414c 2695
31dc71a8 2696 C90 6.5.2, C99 6.7.2, C11 6.7.2:
27bf414c
JM
2697 type-specifier:
2698 void
2699 char
2700 short
2701 int
2702 long
2703 float
2704 double
2705 signed
2706 unsigned
2707 _Bool
2708 _Complex
2709 [_Imaginary removed in C99 TC2]
2710 struct-or-union-specifier
2711 enum-specifier
2712 typedef-name
267bac10 2713 atomic-type-specifier
27bf414c
JM
2714
2715 (_Bool and _Complex are new in C99.)
267bac10 2716 (atomic-type-specifier is new in C11.)
27bf414c 2717
31dc71a8 2718 C90 6.5.3, C99 6.7.3, C11 6.7.3:
27bf414c
JM
2719
2720 type-qualifier:
2721 const
2722 restrict
2723 volatile
36c5e70a 2724 address-space-qualifier
267bac10 2725 _Atomic
27bf414c
JM
2726
2727 (restrict is new in C99.)
267bac10 2728 (_Atomic is new in C11.)
27bf414c
JM
2729
2730 GNU extensions:
2731
2732 declaration-specifiers:
783bfe5e 2733 gnu-attributes declaration-specifiers[opt]
27bf414c 2734
36c5e70a
BE
2735 type-qualifier:
2736 address-space
2737
2738 address-space:
2739 identifier recognized by the target
2740
27bf414c
JM
2741 storage-class-specifier:
2742 __thread
2743
2744 type-specifier:
2745 typeof-specifier
38b7bc7f 2746 __auto_type
78a7c317 2747 __intN
9a8ce21f
JG
2748 _Decimal32
2749 _Decimal64
2750 _Decimal128
ab22c1fa
CF
2751 _Fract
2752 _Accum
2753 _Sat
2754
2755 (_Fract, _Accum, and _Sat are new from ISO/IEC DTR 18037:
2756 http://www.open-std.org/jtc1/sc22/wg14/www/docs/n1169.pdf)
27bf414c 2757
267bac10
JM
2758 atomic-type-specifier
2759 _Atomic ( type-name )
2760
27bf414c
JM
2761 Objective-C:
2762
2763 type-specifier:
2764 class-name objc-protocol-refs[opt]
2765 typedef-name objc-protocol-refs
2766 objc-protocol-refs
2767*/
2768
1ee62b92 2769void
27bf414c 2770c_parser_declspecs (c_parser *parser, struct c_declspecs *specs,
29ce73cb 2771 bool scspec_ok, bool typespec_ok, bool start_attr_ok,
38b7bc7f 2772 bool alignspec_ok, bool auto_type_ok,
4e03c3a7 2773 bool start_std_attr_ok, bool end_std_attr_ok,
38b7bc7f 2774 enum c_lookahead_kind la)
27bf414c
JM
2775{
2776 bool attrs_ok = start_attr_ok;
9e5b2115 2777 bool seen_type = specs->typespec_kind != ctsk_none;
29ce73cb
PB
2778
2779 if (!typespec_ok)
2780 gcc_assert (la == cla_prefer_id);
2781
4e03c3a7
JM
2782 if (start_std_attr_ok
2783 && c_parser_nth_token_starts_std_attributes (parser, 1))
2784 {
2785 gcc_assert (!specs->non_std_attrs_seen_p);
2786 location_t loc = c_parser_peek_token (parser)->location;
2787 tree attrs = c_parser_std_attribute_specifier_sequence (parser);
2788 declspecs_add_attrs (loc, specs, attrs);
2789 specs->non_std_attrs_seen_p = false;
2790 }
2791
29ce73cb 2792 while (c_parser_next_token_is (parser, CPP_NAME)
27bf414c
JM
2793 || c_parser_next_token_is (parser, CPP_KEYWORD)
2794 || (c_dialect_objc () && c_parser_next_token_is (parser, CPP_LESS)))
2795 {
2796 struct c_typespec t;
2797 tree attrs;
d19fa6b5 2798 tree align;
dc491a25 2799 location_t loc = c_parser_peek_token (parser)->location;
f725e721 2800
29ce73cb
PB
2801 /* If we cannot accept a type, exit if the next token must start
2802 one. Also, if we already have seen a tagged definition,
2803 a typename would be an error anyway and likely the user
2804 has simply forgotten a semicolon, so we exit. */
2805 if ((!typespec_ok || specs->typespec_kind == ctsk_tagdef)
2806 && c_parser_next_tokens_start_typename (parser, la)
4b2b493f
JM
2807 && !c_parser_next_token_is_qualifier (parser)
2808 && !c_parser_next_token_is_keyword (parser, RID_ALIGNAS))
29ce73cb 2809 break;
f725e721 2810
27bf414c
JM
2811 if (c_parser_next_token_is (parser, CPP_NAME))
2812 {
0b2c4be5
DS
2813 c_token *name_token = c_parser_peek_token (parser);
2814 tree value = name_token->value;
2815 c_id_kind kind = name_token->id_kind;
36c5e70a
BE
2816
2817 if (kind == C_ID_ADDRSPACE)
2818 {
2819 addr_space_t as
0b2c4be5
DS
2820 = name_token->keyword - RID_FIRST_ADDR_SPACE;
2821 declspecs_add_addrspace (name_token->location, specs, as);
36c5e70a
BE
2822 c_parser_consume_token (parser);
2823 attrs_ok = true;
2824 continue;
2825 }
2826
29ce73cb
PB
2827 gcc_assert (!c_parser_next_token_is_qualifier (parser));
2828
2829 /* If we cannot accept a type, and the next token must start one,
2830 exit. Do the same if we already have seen a tagged definition,
2831 since it would be an error anyway and likely the user has simply
2832 forgotten a semicolon. */
2833 if (seen_type || !c_parser_next_tokens_start_typename (parser, la))
2834 break;
2835
2836 /* Now at an unknown typename (C_ID_ID), a C_ID_TYPENAME or
2837 a C_ID_CLASSNAME. */
27bf414c
JM
2838 c_parser_consume_token (parser);
2839 seen_type = true;
2840 attrs_ok = true;
29ce73cb
PB
2841 if (kind == C_ID_ID)
2842 {
1c9f5f33 2843 error_at (loc, "unknown type name %qE", value);
29ce73cb
PB
2844 t.kind = ctsk_typedef;
2845 t.spec = error_mark_node;
2846 }
2847 else if (kind == C_ID_TYPENAME
2848 && (!c_dialect_objc ()
2849 || c_parser_next_token_is_not (parser, CPP_LESS)))
27bf414c
JM
2850 {
2851 t.kind = ctsk_typedef;
2852 /* For a typedef name, record the meaning, not the name.
2853 In case of 'foo foo, bar;'. */
2854 t.spec = lookup_name (value);
2855 }
2856 else
2857 {
2858 tree proto = NULL_TREE;
2859 gcc_assert (c_dialect_objc ());
2860 t.kind = ctsk_objc;
2861 if (c_parser_next_token_is (parser, CPP_LESS))
2862 proto = c_parser_objc_protocol_refs (parser);
2863 t.spec = objc_get_protocol_qualified_type (value, proto);
2864 }
29ce73cb
PB
2865 t.expr = NULL_TREE;
2866 t.expr_const_operands = true;
0b2c4be5 2867 declspecs_add_type (name_token->location, specs, t);
27bf414c
JM
2868 continue;
2869 }
2870 if (c_parser_next_token_is (parser, CPP_LESS))
2871 {
2872 /* Make "<SomeProtocol>" equivalent to "id <SomeProtocol>" -
2873 nisse@lysator.liu.se. */
2874 tree proto;
2875 gcc_assert (c_dialect_objc ());
2876 if (!typespec_ok || seen_type)
2877 break;
2878 proto = c_parser_objc_protocol_refs (parser);
2879 t.kind = ctsk_objc;
2880 t.spec = objc_get_protocol_qualified_type (NULL_TREE, proto);
928c19bb
JM
2881 t.expr = NULL_TREE;
2882 t.expr_const_operands = true;
dc491a25 2883 declspecs_add_type (loc, specs, t);
27bf414c
JM
2884 continue;
2885 }
2886 gcc_assert (c_parser_next_token_is (parser, CPP_KEYWORD));
2887 switch (c_parser_peek_token (parser)->keyword)
2888 {
2889 case RID_STATIC:
2890 case RID_EXTERN:
2891 case RID_REGISTER:
2892 case RID_TYPEDEF:
2893 case RID_INLINE:
bbceee64 2894 case RID_NORETURN:
27bf414c
JM
2895 case RID_AUTO:
2896 case RID_THREAD:
2897 if (!scspec_ok)
2898 goto out;
2899 attrs_ok = true;
bbceee64 2900 /* TODO: Distinguish between function specifiers (inline, noreturn)
27bf414c
JM
2901 and storage class specifiers, either here or in
2902 declspecs_add_scspec. */
0b2c4be5
DS
2903 declspecs_add_scspec (loc, specs,
2904 c_parser_peek_token (parser)->value);
27bf414c
JM
2905 c_parser_consume_token (parser);
2906 break;
38b7bc7f
JM
2907 case RID_AUTO_TYPE:
2908 if (!auto_type_ok)
2909 goto out;
2910 /* Fall through. */
27bf414c
JM
2911 case RID_UNSIGNED:
2912 case RID_LONG:
2913 case RID_SHORT:
2914 case RID_SIGNED:
2915 case RID_COMPLEX:
2916 case RID_INT:
2917 case RID_CHAR:
2918 case RID_FLOAT:
2919 case RID_DOUBLE:
2920 case RID_VOID:
9a8ce21f
JG
2921 case RID_DFLOAT32:
2922 case RID_DFLOAT64:
2923 case RID_DFLOAT128:
c65699ef 2924 CASE_RID_FLOATN_NX:
27bf414c 2925 case RID_BOOL:
ab22c1fa
CF
2926 case RID_FRACT:
2927 case RID_ACCUM:
2928 case RID_SAT:
78a7c317
DD
2929 case RID_INT_N_0:
2930 case RID_INT_N_1:
2931 case RID_INT_N_2:
2932 case RID_INT_N_3:
27bf414c
JM
2933 if (!typespec_ok)
2934 goto out;
2935 attrs_ok = true;
2936 seen_type = true;
0bacb8c7
TT
2937 if (c_dialect_objc ())
2938 parser->objc_need_raw_identifier = true;
27bf414c
JM
2939 t.kind = ctsk_resword;
2940 t.spec = c_parser_peek_token (parser)->value;
928c19bb
JM
2941 t.expr = NULL_TREE;
2942 t.expr_const_operands = true;
dc491a25 2943 declspecs_add_type (loc, specs, t);
27bf414c
JM
2944 c_parser_consume_token (parser);
2945 break;
2946 case RID_ENUM:
2947 if (!typespec_ok)
2948 goto out;
2949 attrs_ok = true;
2950 seen_type = true;
2951 t = c_parser_enum_specifier (parser);
a4bb6959 2952 invoke_plugin_callbacks (PLUGIN_FINISH_TYPE, t.spec);
dc491a25 2953 declspecs_add_type (loc, specs, t);
27bf414c
JM
2954 break;
2955 case RID_STRUCT:
2956 case RID_UNION:
2957 if (!typespec_ok)
2958 goto out;
2959 attrs_ok = true;
2960 seen_type = true;
2961 t = c_parser_struct_or_union_specifier (parser);
dab71827 2962 invoke_plugin_callbacks (PLUGIN_FINISH_TYPE, t.spec);
dc491a25 2963 declspecs_add_type (loc, specs, t);
27bf414c
JM
2964 break;
2965 case RID_TYPEOF:
2966 /* ??? The old parser rejected typeof after other type
2967 specifiers, but is a syntax error the best way of
2968 handling this? */
2969 if (!typespec_ok || seen_type)
2970 goto out;
2971 attrs_ok = true;
2972 seen_type = true;
2973 t = c_parser_typeof_specifier (parser);
dc491a25 2974 declspecs_add_type (loc, specs, t);
27bf414c 2975 break;
267bac10
JM
2976 case RID_ATOMIC:
2977 /* C parser handling of Objective-C constructs needs
2978 checking for correct lvalue-to-rvalue conversions, and
2979 the code in build_modify_expr handling various
2980 Objective-C cases, and that in build_unary_op handling
2981 Objective-C cases for increment / decrement, also needs
2982 updating; uses of TYPE_MAIN_VARIANT in objc_compare_types
2983 and objc_types_are_equivalent may also need updates. */
2984 if (c_dialect_objc ())
2985 sorry ("%<_Atomic%> in Objective-C");
35aff4fb
MP
2986 if (flag_isoc99)
2987 pedwarn_c99 (loc, OPT_Wpedantic,
267bac10 2988 "ISO C99 does not support the %<_Atomic%> qualifier");
35aff4fb
MP
2989 else
2990 pedwarn_c99 (loc, OPT_Wpedantic,
267bac10 2991 "ISO C90 does not support the %<_Atomic%> qualifier");
267bac10
JM
2992 attrs_ok = true;
2993 tree value;
2994 value = c_parser_peek_token (parser)->value;
2995 c_parser_consume_token (parser);
2996 if (typespec_ok && c_parser_next_token_is (parser, CPP_OPEN_PAREN))
2997 {
2998 /* _Atomic ( type-name ). */
2999 seen_type = true;
3000 c_parser_consume_token (parser);
3001 struct c_type_name *type = c_parser_type_name (parser);
3002 t.kind = ctsk_typeof;
3003 t.spec = error_mark_node;
3004 t.expr = NULL_TREE;
3005 t.expr_const_operands = true;
3006 if (type != NULL)
3007 t.spec = groktypename (type, &t.expr,
3008 &t.expr_const_operands);
3009 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN,
3010 "expected %<)%>");
3011 if (t.spec != error_mark_node)
3012 {
3013 if (TREE_CODE (t.spec) == ARRAY_TYPE)
3014 error_at (loc, "%<_Atomic%>-qualified array type");
3015 else if (TREE_CODE (t.spec) == FUNCTION_TYPE)
3016 error_at (loc, "%<_Atomic%>-qualified function type");
3017 else if (TYPE_QUALS (t.spec) != TYPE_UNQUALIFIED)
3018 error_at (loc, "%<_Atomic%> applied to a qualified type");
3019 else
3020 t.spec = c_build_qualified_type (t.spec, TYPE_QUAL_ATOMIC);
3021 }
3022 declspecs_add_type (loc, specs, t);
3023 }
3024 else
3025 declspecs_add_qual (loc, specs, value);
3026 break;
27bf414c
JM
3027 case RID_CONST:
3028 case RID_VOLATILE:
3029 case RID_RESTRICT:
3030 attrs_ok = true;
0b2c4be5 3031 declspecs_add_qual (loc, specs, c_parser_peek_token (parser)->value);
27bf414c
JM
3032 c_parser_consume_token (parser);
3033 break;
3034 case RID_ATTRIBUTE:
3035 if (!attrs_ok)
3036 goto out;
783bfe5e 3037 attrs = c_parser_gnu_attributes (parser);
0b2c4be5 3038 declspecs_add_attrs (loc, specs, attrs);
27bf414c 3039 break;
d19fa6b5 3040 case RID_ALIGNAS:
568a31f2
MP
3041 if (!alignspec_ok)
3042 goto out;
d19fa6b5 3043 align = c_parser_alignas_specifier (parser);
0b2c4be5 3044 declspecs_add_alignas (loc, specs, align);
d19fa6b5 3045 break;
1ee62b92
PG
3046 case RID_GIMPLE:
3047 if (! flag_gimple)
a3f9f006 3048 error_at (loc, "%<__GIMPLE%> only valid with %<-fgimple%>");
1ee62b92 3049 c_parser_consume_token (parser);
baa09dc5 3050 specs->declspec_il = cdil_gimple;
1ee62b92 3051 specs->locations[cdw_gimple] = loc;
baa09dc5 3052 c_parser_gimple_or_rtl_pass_list (parser, specs);
c2e84327
DM
3053 break;
3054 case RID_RTL:
3055 c_parser_consume_token (parser);
baa09dc5 3056 specs->declspec_il = cdil_rtl;
c2e84327 3057 specs->locations[cdw_rtl] = loc;
baa09dc5 3058 c_parser_gimple_or_rtl_pass_list (parser, specs);
1ee62b92 3059 break;
27bf414c
JM
3060 default:
3061 goto out;
3062 }
3063 }
4e03c3a7
JM
3064 out:
3065 if (end_std_attr_ok
3066 && c_parser_nth_token_starts_std_attributes (parser, 1))
3067 specs->postfix_attrs = c_parser_std_attribute_specifier_sequence (parser);
27bf414c
JM
3068}
3069
31dc71a8 3070/* Parse an enum specifier (C90 6.5.2.2, C99 6.7.2.2, C11 6.7.2.2).
27bf414c
JM
3071
3072 enum-specifier:
783bfe5e
JM
3073 enum gnu-attributes[opt] identifier[opt] { enumerator-list }
3074 gnu-attributes[opt]
3075 enum gnu-attributes[opt] identifier[opt] { enumerator-list , }
3076 gnu-attributes[opt]
3077 enum gnu-attributes[opt] identifier
27bf414c
JM
3078
3079 The form with trailing comma is new in C99. The forms with
783bfe5e 3080 gnu-attributes are GNU extensions. In GNU C, we accept any expression
27bf414c
JM
3081 without commas in the syntax (assignment expressions, not just
3082 conditional expressions); assignment expressions will be diagnosed
3083 as non-constant.
3084
3085 enumerator-list:
3086 enumerator
3087 enumerator-list , enumerator
3088
3089 enumerator:
4e03c3a7
JM
3090 enumeration-constant attribute-specifier-sequence[opt]
3091 enumeration-constant attribute-specifier-sequence[opt]
3092 = constant-expression
fd5c817a
MP
3093
3094 GNU Extensions:
3095
3096 enumerator:
4e03c3a7
JM
3097 enumeration-constant attribute-specifier-sequence[opt] gnu-attributes[opt]
3098 enumeration-constant attribute-specifier-sequence[opt] gnu-attributes[opt]
3099 = constant-expression
fd5c817a 3100
27bf414c
JM
3101*/
3102
3103static struct c_typespec
3104c_parser_enum_specifier (c_parser *parser)
3105{
3106 struct c_typespec ret;
4e03c3a7
JM
3107 bool have_std_attrs;
3108 tree std_attrs = NULL_TREE;
27bf414c
JM
3109 tree attrs;
3110 tree ident = NULL_TREE;
24b97832 3111 location_t enum_loc;
922f2908 3112 location_t ident_loc = UNKNOWN_LOCATION; /* Quiet warning. */
27bf414c
JM
3113 gcc_assert (c_parser_next_token_is_keyword (parser, RID_ENUM));
3114 c_parser_consume_token (parser);
4e03c3a7
JM
3115 have_std_attrs = c_parser_nth_token_starts_std_attributes (parser, 1);
3116 if (have_std_attrs)
3117 std_attrs = c_parser_std_attribute_specifier_sequence (parser);
783bfe5e 3118 attrs = c_parser_gnu_attributes (parser);
c2255bc4 3119 enum_loc = c_parser_peek_token (parser)->location;
5af28c74
TT
3120 /* Set the location in case we create a decl now. */
3121 c_parser_set_source_position_from_token (c_parser_peek_token (parser));
27bf414c
JM
3122 if (c_parser_next_token_is (parser, CPP_NAME))
3123 {
3124 ident = c_parser_peek_token (parser)->value;
c7412148 3125 ident_loc = c_parser_peek_token (parser)->location;
24b97832 3126 enum_loc = ident_loc;
27bf414c
JM
3127 c_parser_consume_token (parser);
3128 }
3129 if (c_parser_next_token_is (parser, CPP_OPEN_BRACE))
3130 {
3131 /* Parse an enum definition. */
7114359f 3132 struct c_enum_contents the_enum;
575bfb00 3133 tree type;
27bf414c
JM
3134 tree postfix_attrs;
3135 /* We chain the enumerators in reverse order, then put them in
3136 forward order at the end. */
575bfb00
LC
3137 tree values;
3138 timevar_push (TV_PARSE_ENUM);
3139 type = start_enum (enum_loc, &the_enum, ident);
3140 values = NULL_TREE;
27bf414c
JM
3141 c_parser_consume_token (parser);
3142 while (true)
3143 {
3144 tree enum_id;
3145 tree enum_value;
3146 tree enum_decl;
3147 bool seen_comma;
5af28c74 3148 c_token *token;
922f2908 3149 location_t comma_loc = UNKNOWN_LOCATION; /* Quiet warning. */
7370e0da 3150 location_t decl_loc, value_loc;
27bf414c
JM
3151 if (c_parser_next_token_is_not (parser, CPP_NAME))
3152 {
d04ff417
MP
3153 /* Give a nicer error for "enum {}". */
3154 if (c_parser_next_token_is (parser, CPP_CLOSE_BRACE)
3155 && !parser->error)
3156 {
3157 error_at (c_parser_peek_token (parser)->location,
3158 "empty enum is invalid");
3159 parser->error = true;
3160 }
3161 else
3162 c_parser_error (parser, "expected identifier");
27bf414c
JM
3163 c_parser_skip_until_found (parser, CPP_CLOSE_BRACE, NULL);
3164 values = error_mark_node;
3165 break;
3166 }
5af28c74
TT
3167 token = c_parser_peek_token (parser);
3168 enum_id = token->value;
3169 /* Set the location in case we create a decl now. */
3170 c_parser_set_source_position_from_token (token);
7370e0da 3171 decl_loc = value_loc = token->location;
27bf414c 3172 c_parser_consume_token (parser);
fd5c817a 3173 /* Parse any specified attributes. */
4e03c3a7
JM
3174 tree std_attrs = NULL_TREE;
3175 if (c_parser_nth_token_starts_std_attributes (parser, 1))
3176 std_attrs = c_parser_std_attribute_specifier_sequence (parser);
3177 tree enum_attrs = chainon (std_attrs,
3178 c_parser_gnu_attributes (parser));
27bf414c
JM
3179 if (c_parser_next_token_is (parser, CPP_EQ))
3180 {
3181 c_parser_consume_token (parser);
85790e66 3182 value_loc = c_parser_peek_token (parser)->location;
27bf414c
JM
3183 enum_value = c_parser_expr_no_commas (parser, NULL).value;
3184 }
3185 else
3186 enum_value = NULL_TREE;
7370e0da 3187 enum_decl = build_enumerator (decl_loc, value_loc,
fd5c817a
MP
3188 &the_enum, enum_id, enum_value);
3189 if (enum_attrs)
3190 decl_attributes (&TREE_PURPOSE (enum_decl), enum_attrs, 0);
27bf414c
JM
3191 TREE_CHAIN (enum_decl) = values;
3192 values = enum_decl;
3193 seen_comma = false;
3194 if (c_parser_next_token_is (parser, CPP_COMMA))
3195 {
c7412148 3196 comma_loc = c_parser_peek_token (parser)->location;
27bf414c
JM
3197 seen_comma = true;
3198 c_parser_consume_token (parser);
3199 }
3200 if (c_parser_next_token_is (parser, CPP_CLOSE_BRACE))
3201 {
f3bede71
MP
3202 if (seen_comma)
3203 pedwarn_c90 (comma_loc, OPT_Wpedantic,
3204 "comma at end of enumerator list");
27bf414c
JM
3205 c_parser_consume_token (parser);
3206 break;
3207 }
3208 if (!seen_comma)
3209 {
3210 c_parser_error (parser, "expected %<,%> or %<}%>");
3211 c_parser_skip_until_found (parser, CPP_CLOSE_BRACE, NULL);
3212 values = error_mark_node;
3213 break;
3214 }
3215 }
783bfe5e 3216 postfix_attrs = c_parser_gnu_attributes (parser);
27bf414c 3217 ret.spec = finish_enum (type, nreverse (values),
4e03c3a7
JM
3218 chainon (std_attrs,
3219 chainon (attrs, postfix_attrs)));
27bf414c 3220 ret.kind = ctsk_tagdef;
928c19bb
JM
3221 ret.expr = NULL_TREE;
3222 ret.expr_const_operands = true;
575bfb00 3223 timevar_pop (TV_PARSE_ENUM);
27bf414c
JM
3224 return ret;
3225 }
3226 else if (!ident)
3227 {
3228 c_parser_error (parser, "expected %<{%>");
3229 ret.spec = error_mark_node;
3230 ret.kind = ctsk_tagref;
928c19bb
JM
3231 ret.expr = NULL_TREE;
3232 ret.expr_const_operands = true;
27bf414c
JM
3233 return ret;
3234 }
4e03c3a7
JM
3235 /* Attributes may only appear when the members are defined or in
3236 certain forward declarations (treat enum forward declarations in
3237 GNU C analogously to struct and union forward declarations in
3238 standard C). */
3239 if (have_std_attrs && c_parser_next_token_is_not (parser, CPP_SEMICOLON))
3240 c_parser_error (parser, "expected %<;%>");
3241 ret = parser_xref_tag (ident_loc, ENUMERAL_TYPE, ident, have_std_attrs,
3242 std_attrs);
27bf414c
JM
3243 /* In ISO C, enumerated types can be referred to only if already
3244 defined. */
3245 if (pedantic && !COMPLETE_TYPE_P (ret.spec))
c7412148
TT
3246 {
3247 gcc_assert (ident);
c1771a20 3248 pedwarn (enum_loc, OPT_Wpedantic,
509c9d60 3249 "ISO C forbids forward references to %<enum%> types");
c7412148 3250 }
27bf414c
JM
3251 return ret;
3252}
3253
31dc71a8 3254/* Parse a struct or union specifier (C90 6.5.2.1, C99 6.7.2.1, C11 6.7.2.1).
27bf414c
JM
3255
3256 struct-or-union-specifier:
4e03c3a7
JM
3257 struct-or-union attribute-specifier-sequence[opt] gnu-attributes[opt]
3258 identifier[opt] { struct-contents } gnu-attributes[opt]
3259 struct-or-union attribute-specifier-sequence[opt] gnu-attributes[opt]
3260 identifier
27bf414c
JM
3261
3262 struct-contents:
3263 struct-declaration-list
3264
3265 struct-declaration-list:
3266 struct-declaration ;
3267 struct-declaration-list struct-declaration ;
3268
3269 GNU extensions:
3270
3271 struct-contents:
3272 empty
3273 struct-declaration
3274 struct-declaration-list struct-declaration
3275
3276 struct-declaration-list:
3277 struct-declaration-list ;
3278 ;
3279
3280 (Note that in the syntax here, unlike that in ISO C, the semicolons
3281 are included here rather than in struct-declaration, in order to
3282 describe the syntax with extra semicolons and missing semicolon at
3283 end.)
3284
3285 Objective-C:
3286
3287 struct-declaration-list:
3288 @defs ( class-name )
3289
3290 (Note this does not include a trailing semicolon, but can be
3291 followed by further declarations, and gets a pedwarn-if-pedantic
3292 when followed by a semicolon.) */
3293
3294static struct c_typespec
3295c_parser_struct_or_union_specifier (c_parser *parser)
3296{
3297 struct c_typespec ret;
4e03c3a7
JM
3298 bool have_std_attrs;
3299 tree std_attrs = NULL_TREE;
27bf414c
JM
3300 tree attrs;
3301 tree ident = NULL_TREE;
24b97832
ILT
3302 location_t struct_loc;
3303 location_t ident_loc = UNKNOWN_LOCATION;
27bf414c
JM
3304 enum tree_code code;
3305 switch (c_parser_peek_token (parser)->keyword)
3306 {
3307 case RID_STRUCT:
3308 code = RECORD_TYPE;
3309 break;
3310 case RID_UNION:
3311 code = UNION_TYPE;
3312 break;
3313 default:
3314 gcc_unreachable ();
3315 }
24b97832 3316 struct_loc = c_parser_peek_token (parser)->location;
27bf414c 3317 c_parser_consume_token (parser);
4e03c3a7
JM
3318 have_std_attrs = c_parser_nth_token_starts_std_attributes (parser, 1);
3319 if (have_std_attrs)
3320 std_attrs = c_parser_std_attribute_specifier_sequence (parser);
783bfe5e 3321 attrs = c_parser_gnu_attributes (parser);
c2255bc4 3322
5af28c74
TT
3323 /* Set the location in case we create a decl now. */
3324 c_parser_set_source_position_from_token (c_parser_peek_token (parser));
c2255bc4 3325
27bf414c
JM
3326 if (c_parser_next_token_is (parser, CPP_NAME))
3327 {
3328 ident = c_parser_peek_token (parser)->value;
24b97832
ILT
3329 ident_loc = c_parser_peek_token (parser)->location;
3330 struct_loc = ident_loc;
27bf414c
JM
3331 c_parser_consume_token (parser);
3332 }
3333 if (c_parser_next_token_is (parser, CPP_OPEN_BRACE))
3334 {
3335 /* Parse a struct or union definition. Start the scope of the
3336 tag before parsing components. */
99b1c316 3337 class c_struct_parse_info *struct_info;
dc491a25 3338 tree type = start_struct (struct_loc, code, ident, &struct_info);
27bf414c
JM
3339 tree postfix_attrs;
3340 /* We chain the components in reverse order, then put them in
3341 forward order at the end. Each struct-declaration may
3342 declare multiple components (comma-separated), so we must use
3343 chainon to join them, although when parsing each
3344 struct-declaration we can use TREE_CHAIN directly.
3345
3346 The theory behind all this is that there will be more
3347 semicolon separated fields than comma separated fields, and
3348 so we'll be minimizing the number of node traversals required
3349 by chainon. */
575bfb00
LC
3350 tree contents;
3351 timevar_push (TV_PARSE_STRUCT);
3352 contents = NULL_TREE;
27bf414c
JM
3353 c_parser_consume_token (parser);
3354 /* Handle the Objective-C @defs construct,
3355 e.g. foo(sizeof(struct{ @defs(ClassName) }));. */
3356 if (c_parser_next_token_is_keyword (parser, RID_AT_DEFS))
3357 {
3358 tree name;
3359 gcc_assert (c_dialect_objc ());
3360 c_parser_consume_token (parser);
32129a17
DM
3361 matching_parens parens;
3362 if (!parens.require_open (parser))
27bf414c
JM
3363 goto end_at_defs;
3364 if (c_parser_next_token_is (parser, CPP_NAME)
3365 && c_parser_peek_token (parser)->id_kind == C_ID_CLASSNAME)
3366 {
3367 name = c_parser_peek_token (parser)->value;
3368 c_parser_consume_token (parser);
3369 }
3370 else
3371 {
3372 c_parser_error (parser, "expected class name");
3373 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN, NULL);
3374 goto end_at_defs;
3375 }
32129a17 3376 parens.skip_until_found_close (parser);
27bf414c
JM
3377 contents = nreverse (objc_get_class_ivars (name));
3378 }
3379 end_at_defs:
3380 /* Parse the struct-declarations and semicolons. Problems with
3381 semicolons are diagnosed here; empty structures are diagnosed
3382 elsewhere. */
3383 while (true)
3384 {
3385 tree decls;
3386 /* Parse any stray semicolon. */
3387 if (c_parser_next_token_is (parser, CPP_SEMICOLON))
3388 {
1c4ea66f
DM
3389 location_t semicolon_loc
3390 = c_parser_peek_token (parser)->location;
3391 gcc_rich_location richloc (semicolon_loc);
3392 richloc.add_fixit_remove ();
64a5912c
DM
3393 pedwarn (&richloc, OPT_Wpedantic,
3394 "extra semicolon in struct or union specified");
27bf414c
JM
3395 c_parser_consume_token (parser);
3396 continue;
3397 }
3398 /* Stop if at the end of the struct or union contents. */
3399 if (c_parser_next_token_is (parser, CPP_CLOSE_BRACE))
3400 {
3401 c_parser_consume_token (parser);
3402 break;
3403 }
bc4071dd
RH
3404 /* Accept #pragmas at struct scope. */
3405 if (c_parser_next_token_is (parser, CPP_PRAGMA))
3406 {
dda1bf61 3407 c_parser_pragma (parser, pragma_struct, NULL);
bc4071dd
RH
3408 continue;
3409 }
27bf414c
JM
3410 /* Parse some comma-separated declarations, but not the
3411 trailing semicolon if any. */
3412 decls = c_parser_struct_declaration (parser);
3413 contents = chainon (decls, contents);
3414 /* If no semicolon follows, either we have a parse error or
3415 are at the end of the struct or union and should
3416 pedwarn. */
3417 if (c_parser_next_token_is (parser, CPP_SEMICOLON))
3418 c_parser_consume_token (parser);
3419 else
3420 {
3421 if (c_parser_next_token_is (parser, CPP_CLOSE_BRACE))
b8698a0f 3422 pedwarn (c_parser_peek_token (parser)->location, 0,
509c9d60 3423 "no semicolon at end of struct or union");
f725e721
PB
3424 else if (parser->error
3425 || !c_parser_next_token_starts_declspecs (parser))
27bf414c
JM
3426 {
3427 c_parser_error (parser, "expected %<;%>");
3428 c_parser_skip_until_found (parser, CPP_CLOSE_BRACE, NULL);
3429 break;
3430 }
f725e721
PB
3431
3432 /* If we come here, we have already emitted an error
3433 for an expected `;', identifier or `(', and we also
3434 recovered already. Go on with the next field. */
27bf414c
JM
3435 }
3436 }
783bfe5e 3437 postfix_attrs = c_parser_gnu_attributes (parser);
c2255bc4 3438 ret.spec = finish_struct (struct_loc, type, nreverse (contents),
4e03c3a7
JM
3439 chainon (std_attrs,
3440 chainon (attrs, postfix_attrs)),
3441 struct_info);
27bf414c 3442 ret.kind = ctsk_tagdef;
928c19bb
JM
3443 ret.expr = NULL_TREE;
3444 ret.expr_const_operands = true;
575bfb00 3445 timevar_pop (TV_PARSE_STRUCT);
27bf414c
JM
3446 return ret;
3447 }
3448 else if (!ident)
3449 {
3450 c_parser_error (parser, "expected %<{%>");
3451 ret.spec = error_mark_node;
3452 ret.kind = ctsk_tagref;
928c19bb
JM
3453 ret.expr = NULL_TREE;
3454 ret.expr_const_operands = true;
67c2939d 3455 return ret;
27bf414c 3456 }
4e03c3a7
JM
3457 /* Attributes may only appear when the members are defined or in
3458 certain forward declarations. */
3459 if (have_std_attrs && c_parser_next_token_is_not (parser, CPP_SEMICOLON))
3460 c_parser_error (parser, "expected %<;%>");
3461 /* ??? Existing practice is that GNU attributes are ignored after
3462 the struct or union keyword when not defining the members. */
3463 ret = parser_xref_tag (ident_loc, code, ident, have_std_attrs, std_attrs);
27bf414c
JM
3464 return ret;
3465}
3466
31dc71a8
MP
3467/* Parse a struct-declaration (C90 6.5.2.1, C99 6.7.2.1, C11 6.7.2.1),
3468 *without* the trailing semicolon.
27bf414c
JM
3469
3470 struct-declaration:
4e03c3a7
JM
3471 attribute-specifier-sequence[opt] specifier-qualifier-list
3472 attribute-specifier-sequence[opt] struct-declarator-list
32912286 3473 static_assert-declaration-no-semi
27bf414c
JM
3474
3475 specifier-qualifier-list:
3476 type-specifier specifier-qualifier-list[opt]
3477 type-qualifier specifier-qualifier-list[opt]
4b2b493f 3478 alignment-specifier specifier-qualifier-list[opt]
783bfe5e 3479 gnu-attributes specifier-qualifier-list[opt]
27bf414c
JM
3480
3481 struct-declarator-list:
3482 struct-declarator
783bfe5e 3483 struct-declarator-list , gnu-attributes[opt] struct-declarator
27bf414c
JM
3484
3485 struct-declarator:
783bfe5e
JM
3486 declarator gnu-attributes[opt]
3487 declarator[opt] : constant-expression gnu-attributes[opt]
27bf414c
JM
3488
3489 GNU extensions:
3490
3491 struct-declaration:
3492 __extension__ struct-declaration
3493 specifier-qualifier-list
3494
3495 Unlike the ISO C syntax, semicolons are handled elsewhere. The use
783bfe5e 3496 of gnu-attributes where shown is a GNU extension. In GNU C, we accept
27bf414c
JM
3497 any expression without commas in the syntax (assignment
3498 expressions, not just conditional expressions); assignment
3499 expressions will be diagnosed as non-constant. */
3500
3501static tree
3502c_parser_struct_declaration (c_parser *parser)
3503{
3504 struct c_declspecs *specs;
3505 tree prefix_attrs;
3506 tree all_prefix_attrs;
3507 tree decls;
c7412148 3508 location_t decl_loc;
27bf414c
JM
3509 if (c_parser_next_token_is_keyword (parser, RID_EXTENSION))
3510 {
3511 int ext;
3512 tree decl;
3513 ext = disable_extension_diagnostics ();
3514 c_parser_consume_token (parser);
3515 decl = c_parser_struct_declaration (parser);
3516 restore_extension_diagnostics (ext);
3517 return decl;
3518 }
32912286
JM
3519 if (c_parser_next_token_is_keyword (parser, RID_STATIC_ASSERT))
3520 {
3521 c_parser_static_assert_declaration_no_semi (parser);
3522 return NULL_TREE;
3523 }
27bf414c 3524 specs = build_null_declspecs ();
c7412148 3525 decl_loc = c_parser_peek_token (parser)->location;
f28aa681
MP
3526 /* Strictly by the standard, we shouldn't allow _Alignas here,
3527 but it appears to have been intended to allow it there, so
3528 we're keeping it as it is until WG14 reaches a conclusion
3529 of N1731.
3530 <http://www.open-std.org/jtc1/sc22/wg14/www/docs/n1731.pdf> */
568a31f2 3531 c_parser_declspecs (parser, specs, false, true, true,
4e03c3a7 3532 true, false, true, true, cla_nonabstract_decl);
27bf414c 3533 if (parser->error)
67c2939d 3534 return NULL_TREE;
27bf414c
JM
3535 if (!specs->declspecs_seen_p)
3536 {
3537 c_parser_error (parser, "expected specifier-qualifier-list");
3538 return NULL_TREE;
3539 }
3540 finish_declspecs (specs);
b8cbdff5
JM
3541 if (c_parser_next_token_is (parser, CPP_SEMICOLON)
3542 || c_parser_next_token_is (parser, CPP_CLOSE_BRACE))
27bf414c
JM
3543 {
3544 tree ret;
9e5b2115 3545 if (specs->typespec_kind == ctsk_none)
27bf414c 3546 {
c1771a20 3547 pedwarn (decl_loc, OPT_Wpedantic,
509c9d60 3548 "ISO C forbids member declarations with no members");
27bf414c
JM
3549 shadow_tag_warned (specs, pedantic);
3550 ret = NULL_TREE;
3551 }
3552 else
3553 {
3554 /* Support for unnamed structs or unions as members of
3555 structs or unions (which is [a] useful and [b] supports
3556 MS P-SDK). */
b9baeecd 3557 tree attrs = NULL;
3d10ed6c
AH
3558
3559 ret = grokfield (c_parser_peek_token (parser)->location,
3560 build_id_declarator (NULL_TREE), specs,
b9baeecd 3561 NULL_TREE, &attrs);
0ad7e054
RS
3562 if (ret)
3563 decl_attributes (&ret, attrs, 0);
27bf414c
JM
3564 }
3565 return ret;
3566 }
f725e721
PB
3567
3568 /* Provide better error recovery. Note that a type name here is valid,
3569 and will be treated as a field name. */
3570 if (specs->typespec_kind == ctsk_tagdef
3571 && TREE_CODE (specs->type) != ENUMERAL_TYPE
3572 && c_parser_next_token_starts_declspecs (parser)
3573 && !c_parser_next_token_is (parser, CPP_NAME))
3574 {
3575 c_parser_error (parser, "expected %<;%>, identifier or %<(%>");
3576 parser->error = false;
3577 return NULL_TREE;
3578 }
3579
27bf414c
JM
3580 pending_xref_error ();
3581 prefix_attrs = specs->attrs;
3582 all_prefix_attrs = prefix_attrs;
3583 specs->attrs = NULL_TREE;
3584 decls = NULL_TREE;
3585 while (true)
3586 {
3587 /* Declaring one or more declarators or un-named bit-fields. */
3588 struct c_declarator *declarator;
3589 bool dummy = false;
3590 if (c_parser_next_token_is (parser, CPP_COLON))
3591 declarator = build_id_declarator (NULL_TREE);
3592 else
9e5b2115
PB
3593 declarator = c_parser_declarator (parser,
3594 specs->typespec_kind != ctsk_none,
27bf414c
JM
3595 C_DTR_NORMAL, &dummy);
3596 if (declarator == NULL)
3597 {
3598 c_parser_skip_to_end_of_block_or_statement (parser);
3599 break;
3600 }
3601 if (c_parser_next_token_is (parser, CPP_COLON)
3602 || c_parser_next_token_is (parser, CPP_COMMA)
3603 || c_parser_next_token_is (parser, CPP_SEMICOLON)
3604 || c_parser_next_token_is (parser, CPP_CLOSE_BRACE)
3605 || c_parser_next_token_is_keyword (parser, RID_ATTRIBUTE))
3606 {
3607 tree postfix_attrs = NULL_TREE;
3608 tree width = NULL_TREE;
3609 tree d;
3610 if (c_parser_next_token_is (parser, CPP_COLON))
3611 {
3612 c_parser_consume_token (parser);
3613 width = c_parser_expr_no_commas (parser, NULL).value;
3614 }
3615 if (c_parser_next_token_is_keyword (parser, RID_ATTRIBUTE))
783bfe5e 3616 postfix_attrs = c_parser_gnu_attributes (parser);
3d10ed6c
AH
3617 d = grokfield (c_parser_peek_token (parser)->location,
3618 declarator, specs, width, &all_prefix_attrs);
27bf414c
JM
3619 decl_attributes (&d, chainon (postfix_attrs,
3620 all_prefix_attrs), 0);
910ad8de 3621 DECL_CHAIN (d) = decls;
27bf414c
JM
3622 decls = d;
3623 if (c_parser_next_token_is_keyword (parser, RID_ATTRIBUTE))
783bfe5e 3624 all_prefix_attrs = chainon (c_parser_gnu_attributes (parser),
27bf414c
JM
3625 prefix_attrs);
3626 else
3627 all_prefix_attrs = prefix_attrs;
3628 if (c_parser_next_token_is (parser, CPP_COMMA))
3629 c_parser_consume_token (parser);
3630 else if (c_parser_next_token_is (parser, CPP_SEMICOLON)
3631 || c_parser_next_token_is (parser, CPP_CLOSE_BRACE))
3632 {
3633 /* Semicolon consumed in caller. */
3634 break;
3635 }
3636 else
3637 {
3638 c_parser_error (parser, "expected %<,%>, %<;%> or %<}%>");
3639 break;
3640 }
3641 }
3642 else
3643 {
3644 c_parser_error (parser,
3645 "expected %<:%>, %<,%>, %<;%>, %<}%> or "
3646 "%<__attribute__%>");
3647 break;
3648 }
3649 }
3650 return decls;
3651}
3652
3653/* Parse a typeof specifier (a GNU extension).
3654
3655 typeof-specifier:
3656 typeof ( expression )
3657 typeof ( type-name )
3658*/
3659
3660static struct c_typespec
3661c_parser_typeof_specifier (c_parser *parser)
3662{
3663 struct c_typespec ret;
3664 ret.kind = ctsk_typeof;
3665 ret.spec = error_mark_node;
928c19bb
JM
3666 ret.expr = NULL_TREE;
3667 ret.expr_const_operands = true;
27bf414c
JM
3668 gcc_assert (c_parser_next_token_is_keyword (parser, RID_TYPEOF));
3669 c_parser_consume_token (parser);
7d882b83 3670 c_inhibit_evaluation_warnings++;
27bf414c 3671 in_typeof++;
32129a17
DM
3672 matching_parens parens;
3673 if (!parens.require_open (parser))
27bf414c 3674 {
7d882b83 3675 c_inhibit_evaluation_warnings--;
27bf414c
JM
3676 in_typeof--;
3677 return ret;
3678 }
29ce73cb 3679 if (c_parser_next_tokens_start_typename (parser, cla_prefer_id))
27bf414c
JM
3680 {
3681 struct c_type_name *type = c_parser_type_name (parser);
7d882b83 3682 c_inhibit_evaluation_warnings--;
27bf414c
JM
3683 in_typeof--;
3684 if (type != NULL)
3685 {
928c19bb 3686 ret.spec = groktypename (type, &ret.expr, &ret.expr_const_operands);
27bf414c
JM
3687 pop_maybe_used (variably_modified_type_p (ret.spec, NULL_TREE));
3688 }
3689 }
3690 else
3691 {
52ffd86e 3692 bool was_vm;
c7412148 3693 location_t here = c_parser_peek_token (parser)->location;
27bf414c 3694 struct c_expr expr = c_parser_expression (parser);
7d882b83 3695 c_inhibit_evaluation_warnings--;
27bf414c
JM
3696 in_typeof--;
3697 if (TREE_CODE (expr.value) == COMPONENT_REF
3698 && DECL_C_BIT_FIELD (TREE_OPERAND (expr.value, 1)))
3ba09659 3699 error_at (here, "%<typeof%> applied to a bit-field");
ebfbbdc5 3700 mark_exp_read (expr.value);
27bf414c 3701 ret.spec = TREE_TYPE (expr.value);
52ffd86e 3702 was_vm = variably_modified_type_p (ret.spec, NULL_TREE);
928c19bb
JM
3703 /* This is returned with the type so that when the type is
3704 evaluated, this can be evaluated. */
3705 if (was_vm)
3706 ret.expr = c_fully_fold (expr.value, false, &ret.expr_const_operands);
52ffd86e 3707 pop_maybe_used (was_vm);
9698b078
SH
3708 /* For use in macros such as those in <stdatomic.h>, remove all
3709 qualifiers from atomic types. (const can be an issue for more macros
3710 using typeof than just the <stdatomic.h> ones.) */
267bac10 3711 if (ret.spec != error_mark_node && TYPE_ATOMIC (ret.spec))
9698b078 3712 ret.spec = c_build_qualified_type (ret.spec, TYPE_UNQUALIFIED);
27bf414c 3713 }
32129a17 3714 parens.skip_until_found_close (parser);
27bf414c
JM
3715 return ret;
3716}
3717
d19fa6b5
JM
3718/* Parse an alignment-specifier.
3719
48b0b196 3720 C11 6.7.5:
d19fa6b5
JM
3721
3722 alignment-specifier:
3723 _Alignas ( type-name )
3724 _Alignas ( constant-expression )
3725*/
3726
3727static tree
3728c_parser_alignas_specifier (c_parser * parser)
3729{
3730 tree ret = error_mark_node;
3731 location_t loc = c_parser_peek_token (parser)->location;
3732 gcc_assert (c_parser_next_token_is_keyword (parser, RID_ALIGNAS));
3733 c_parser_consume_token (parser);
35aff4fb
MP
3734 if (flag_isoc99)
3735 pedwarn_c99 (loc, OPT_Wpedantic,
d19fa6b5 3736 "ISO C99 does not support %<_Alignas%>");
35aff4fb
MP
3737 else
3738 pedwarn_c99 (loc, OPT_Wpedantic,
d19fa6b5 3739 "ISO C90 does not support %<_Alignas%>");
32129a17
DM
3740 matching_parens parens;
3741 if (!parens.require_open (parser))
d19fa6b5
JM
3742 return ret;
3743 if (c_parser_next_tokens_start_typename (parser, cla_prefer_id))
3744 {
3745 struct c_type_name *type = c_parser_type_name (parser);
3746 if (type != NULL)
296674db
JM
3747 ret = c_sizeof_or_alignof_type (loc, groktypename (type, NULL, NULL),
3748 false, true, 1);
d19fa6b5
JM
3749 }
3750 else
3751 ret = c_parser_expr_no_commas (parser, NULL).value;
32129a17 3752 parens.skip_until_found_close (parser);
d19fa6b5
JM
3753 return ret;
3754}
3755
27bf414c 3756/* Parse a declarator, possibly an abstract declarator (C90 6.5.4,
31dc71a8
MP
3757 6.5.5, C99 6.7.5, 6.7.6, C11 6.7.6, 6.7.7). If TYPE_SEEN_P then
3758 a typedef name may be redeclared; otherwise it may not. KIND
3759 indicates which kind of declarator is wanted. Returns a valid
3760 declarator except in the case of a syntax error in which case NULL is
3761 returned. *SEEN_ID is set to true if an identifier being declared is
3762 seen; this is used to diagnose bad forms of abstract array declarators
3763 and to determine whether an identifier list is syntactically permitted.
27bf414c
JM
3764
3765 declarator:
3766 pointer[opt] direct-declarator
3767
3768 direct-declarator:
3769 identifier
783bfe5e 3770 ( gnu-attributes[opt] declarator )
27bf414c
JM
3771 direct-declarator array-declarator
3772 direct-declarator ( parameter-type-list )
3773 direct-declarator ( identifier-list[opt] )
3774
3775 pointer:
3776 * type-qualifier-list[opt]
3777 * type-qualifier-list[opt] pointer
3778
3779 type-qualifier-list:
3780 type-qualifier
783bfe5e 3781 gnu-attributes
27bf414c 3782 type-qualifier-list type-qualifier
783bfe5e 3783 type-qualifier-list gnu-attributes
27bf414c 3784
568a31f2
MP
3785 array-declarator:
3786 [ type-qualifier-list[opt] assignment-expression[opt] ]
3787 [ static type-qualifier-list[opt] assignment-expression ]
3788 [ type-qualifier-list static assignment-expression ]
3789 [ type-qualifier-list[opt] * ]
3790
27bf414c
JM
3791 parameter-type-list:
3792 parameter-list
3793 parameter-list , ...
3794
3795 parameter-list:
3796 parameter-declaration
3797 parameter-list , parameter-declaration
3798
3799 parameter-declaration:
783bfe5e
JM
3800 declaration-specifiers declarator gnu-attributes[opt]
3801 declaration-specifiers abstract-declarator[opt] gnu-attributes[opt]
27bf414c
JM
3802
3803 identifier-list:
3804 identifier
3805 identifier-list , identifier
3806
3807 abstract-declarator:
3808 pointer
3809 pointer[opt] direct-abstract-declarator
3810
3811 direct-abstract-declarator:
783bfe5e 3812 ( gnu-attributes[opt] abstract-declarator )
27bf414c
JM
3813 direct-abstract-declarator[opt] array-declarator
3814 direct-abstract-declarator[opt] ( parameter-type-list[opt] )
3815
3816 GNU extensions:
3817
3818 direct-declarator:
3819 direct-declarator ( parameter-forward-declarations
3820 parameter-type-list[opt] )
3821
3822 direct-abstract-declarator:
c22cacf3 3823 direct-abstract-declarator[opt] ( parameter-forward-declarations
27bf414c
JM
3824 parameter-type-list[opt] )
3825
3826 parameter-forward-declarations:
3827 parameter-list ;
3828 parameter-forward-declarations parameter-list ;
3829
783bfe5e 3830 The uses of gnu-attributes shown above are GNU extensions.
27bf414c
JM
3831
3832 Some forms of array declarator are not included in C99 in the
3833 syntax for abstract declarators; these are disallowed elsewhere.
3834 This may be a defect (DR#289).
3835
3836 This function also accepts an omitted abstract declarator as being
3837 an abstract declarator, although not part of the formal syntax. */
3838
1ee62b92 3839struct c_declarator *
27bf414c
JM
3840c_parser_declarator (c_parser *parser, bool type_seen_p, c_dtr_syn kind,
3841 bool *seen_id)
3842{
3843 /* Parse any initial pointer part. */
3844 if (c_parser_next_token_is (parser, CPP_MULT))
3845 {
3846 struct c_declspecs *quals_attrs = build_null_declspecs ();
3847 struct c_declarator *inner;
3848 c_parser_consume_token (parser);
568a31f2 3849 c_parser_declspecs (parser, quals_attrs, false, false, true,
4e03c3a7 3850 false, false, true, false, cla_prefer_id);
27bf414c
JM
3851 inner = c_parser_declarator (parser, type_seen_p, kind, seen_id);
3852 if (inner == NULL)
3853 return NULL;
3854 else
3855 return make_pointer_declarator (quals_attrs, inner);
3856 }
3857 /* Now we have a direct declarator, direct abstract declarator or
3858 nothing (which counts as a direct abstract declarator here). */
3859 return c_parser_direct_declarator (parser, type_seen_p, kind, seen_id);
3860}
3861
3862/* Parse a direct declarator or direct abstract declarator; arguments
3863 as c_parser_declarator. */
3864
3865static struct c_declarator *
3866c_parser_direct_declarator (c_parser *parser, bool type_seen_p, c_dtr_syn kind,
3867 bool *seen_id)
3868{
3869 /* The direct declarator must start with an identifier (possibly
3870 omitted) or a parenthesized declarator (possibly abstract). In
3871 an ordinary declarator, initial parentheses must start a
3872 parenthesized declarator. In an abstract declarator or parameter
3873 declarator, they could start a parenthesized declarator or a
3874 parameter list. To tell which, the open parenthesis and any
4e03c3a7
JM
3875 following gnu-attributes must be read. If a declaration
3876 specifier or standard attributes follow, then it is a parameter
3877 list; if the specifier is a typedef name, there might be an
3878 ambiguity about redeclaring it, which is resolved in the
3879 direction of treating it as a typedef name. If a close
3880 parenthesis follows, it is also an empty parameter list, as the
3881 syntax does not permit empty abstract declarators. Otherwise, it
3882 is a parenthesized declarator (in which case the analysis may be
3883 repeated inside it, recursively).
27bf414c
JM
3884
3885 ??? There is an ambiguity in a parameter declaration "int
3886 (__attribute__((foo)) x)", where x is not a typedef name: it
3887 could be an abstract declarator for a function, or declare x with
3888 parentheses. The proper resolution of this ambiguity needs
3889 documenting. At present we follow an accident of the old
3890 parser's implementation, whereby the first parameter must have
783bfe5e 3891 some declaration specifiers other than just gnu-attributes. Thus as
0fa2e4df 3892 a parameter declaration it is treated as a parenthesized
27bf414c
JM
3893 parameter named x, and as an abstract declarator it is
3894 rejected.
3895
783bfe5e 3896 ??? Also following the old parser, gnu-attributes inside an empty
27bf414c
JM
3897 parameter list are ignored, making it a list not yielding a
3898 prototype, rather than giving an error or making it have one
3899 parameter with implicit type int.
3900
3901 ??? Also following the old parser, typedef names may be
3902 redeclared in declarators, but not Objective-C class names. */
3903
3904 if (kind != C_DTR_ABSTRACT
3905 && c_parser_next_token_is (parser, CPP_NAME)
3906 && ((type_seen_p
a6341d57
NP
3907 && (c_parser_peek_token (parser)->id_kind == C_ID_TYPENAME
3908 || c_parser_peek_token (parser)->id_kind == C_ID_CLASSNAME))
27bf414c
JM
3909 || c_parser_peek_token (parser)->id_kind == C_ID_ID))
3910 {
3911 struct c_declarator *inner
3912 = build_id_declarator (c_parser_peek_token (parser)->value);
3913 *seen_id = true;
6037d88d 3914 inner->id_loc = c_parser_peek_token (parser)->location;
27bf414c 3915 c_parser_consume_token (parser);
4e03c3a7 3916 if (c_parser_nth_token_starts_std_attributes (parser, 1))
1723e1be 3917 inner->u.id.attrs = c_parser_std_attribute_specifier_sequence (parser);
27bf414c
JM
3918 return c_parser_direct_declarator_inner (parser, *seen_id, inner);
3919 }
3920
3921 if (kind != C_DTR_NORMAL
4e03c3a7
JM
3922 && c_parser_next_token_is (parser, CPP_OPEN_SQUARE)
3923 && !c_parser_nth_token_starts_std_attributes (parser, 1))
27bf414c
JM
3924 {
3925 struct c_declarator *inner = build_id_declarator (NULL_TREE);
1f40cff3 3926 inner->id_loc = c_parser_peek_token (parser)->location;
27bf414c
JM
3927 return c_parser_direct_declarator_inner (parser, *seen_id, inner);
3928 }
3929
3930 /* Either we are at the end of an abstract declarator, or we have
3931 parentheses. */
3932
3933 if (c_parser_next_token_is (parser, CPP_OPEN_PAREN))
3934 {
3935 tree attrs;
3936 struct c_declarator *inner;
3937 c_parser_consume_token (parser);
4e03c3a7
JM
3938 bool have_gnu_attrs = c_parser_next_token_is_keyword (parser,
3939 RID_ATTRIBUTE);
783bfe5e 3940 attrs = c_parser_gnu_attributes (parser);
27bf414c
JM
3941 if (kind != C_DTR_NORMAL
3942 && (c_parser_next_token_starts_declspecs (parser)
4e03c3a7
JM
3943 || (!have_gnu_attrs
3944 && c_parser_nth_token_starts_std_attributes (parser, 1))
27bf414c
JM
3945 || c_parser_next_token_is (parser, CPP_CLOSE_PAREN)))
3946 {
3947 struct c_arg_info *args
3948 = c_parser_parms_declarator (parser, kind == C_DTR_NORMAL,
4e03c3a7 3949 attrs, have_gnu_attrs);
27bf414c
JM
3950 if (args == NULL)
3951 return NULL;
3952 else
3953 {
1723e1be 3954 inner = build_id_declarator (NULL_TREE);
4e03c3a7
JM
3955 if (!(args->types
3956 && args->types != error_mark_node
3957 && TREE_CODE (TREE_VALUE (args->types)) == IDENTIFIER_NODE)
3958 && c_parser_nth_token_starts_std_attributes (parser, 1))
3959 {
3960 tree std_attrs
3961 = c_parser_std_attribute_specifier_sequence (parser);
3962 if (std_attrs)
3963 inner = build_attrs_declarator (std_attrs, inner);
3964 }
1723e1be 3965 inner = build_function_declarator (args, inner);
27bf414c
JM
3966 return c_parser_direct_declarator_inner (parser, *seen_id,
3967 inner);
3968 }
3969 }
3970 /* A parenthesized declarator. */
3971 inner = c_parser_declarator (parser, type_seen_p, kind, seen_id);
3972 if (inner != NULL && attrs != NULL)
3973 inner = build_attrs_declarator (attrs, inner);
3974 if (c_parser_next_token_is (parser, CPP_CLOSE_PAREN))
3975 {
3976 c_parser_consume_token (parser);
3977 if (inner == NULL)
3978 return NULL;
3979 else
3980 return c_parser_direct_declarator_inner (parser, *seen_id, inner);
3981 }
3982 else
3983 {
3984 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN,
3985 "expected %<)%>");
3986 return NULL;
3987 }
3988 }
3989 else
3990 {
3991 if (kind == C_DTR_NORMAL)
3992 {
3993 c_parser_error (parser, "expected identifier or %<(%>");
3994 return NULL;
3995 }
3996 else
3997 return build_id_declarator (NULL_TREE);
3998 }
3999}
4000
4001/* Parse part of a direct declarator or direct abstract declarator,
4002 given that some (in INNER) has already been parsed; ID_PRESENT is
4003 true if an identifier is present, false for an abstract
4004 declarator. */
4005
4006static struct c_declarator *
4007c_parser_direct_declarator_inner (c_parser *parser, bool id_present,
4008 struct c_declarator *inner)
4009{
4010 /* Parse a sequence of array declarators and parameter lists. */
4e03c3a7
JM
4011 if (c_parser_next_token_is (parser, CPP_OPEN_SQUARE)
4012 && !c_parser_nth_token_starts_std_attributes (parser, 1))
27bf414c 4013 {
b8698a0f 4014 location_t brace_loc = c_parser_peek_token (parser)->location;
27bf414c
JM
4015 struct c_declarator *declarator;
4016 struct c_declspecs *quals_attrs = build_null_declspecs ();
4017 bool static_seen;
4018 bool star_seen;
267bac10
JM
4019 struct c_expr dimen;
4020 dimen.value = NULL_TREE;
4021 dimen.original_code = ERROR_MARK;
4022 dimen.original_type = NULL_TREE;
27bf414c 4023 c_parser_consume_token (parser);
568a31f2 4024 c_parser_declspecs (parser, quals_attrs, false, false, true,
4e03c3a7 4025 false, false, false, false, cla_prefer_id);
27bf414c
JM
4026 static_seen = c_parser_next_token_is_keyword (parser, RID_STATIC);
4027 if (static_seen)
4028 c_parser_consume_token (parser);
4029 if (static_seen && !quals_attrs->declspecs_seen_p)
568a31f2 4030 c_parser_declspecs (parser, quals_attrs, false, false, true,
4e03c3a7 4031 false, false, false, false, cla_prefer_id);
27bf414c
JM
4032 if (!quals_attrs->declspecs_seen_p)
4033 quals_attrs = NULL;
4034 /* If "static" is present, there must be an array dimension.
4035 Otherwise, there may be a dimension, "*", or no
4036 dimension. */
4037 if (static_seen)
4038 {
4039 star_seen = false;
267bac10 4040 dimen = c_parser_expr_no_commas (parser, NULL);
27bf414c
JM
4041 }
4042 else
4043 {
4044 if (c_parser_next_token_is (parser, CPP_CLOSE_SQUARE))
4045 {
267bac10 4046 dimen.value = NULL_TREE;
27bf414c
JM
4047 star_seen = false;
4048 }
4049 else if (c_parser_next_token_is (parser, CPP_MULT))
4050 {
4051 if (c_parser_peek_2nd_token (parser)->type == CPP_CLOSE_SQUARE)
4052 {
267bac10 4053 dimen.value = NULL_TREE;
27bf414c
JM
4054 star_seen = true;
4055 c_parser_consume_token (parser);
4056 }
4057 else
4058 {
4059 star_seen = false;
267bac10 4060 dimen = c_parser_expr_no_commas (parser, NULL);
27bf414c
JM
4061 }
4062 }
4063 else
4064 {
4065 star_seen = false;
267bac10 4066 dimen = c_parser_expr_no_commas (parser, NULL);
27bf414c
JM
4067 }
4068 }
4069 if (c_parser_next_token_is (parser, CPP_CLOSE_SQUARE))
4070 c_parser_consume_token (parser);
4071 else
4072 {
4073 c_parser_skip_until_found (parser, CPP_CLOSE_SQUARE,
4074 "expected %<]%>");
4075 return NULL;
4076 }
267bac10
JM
4077 if (dimen.value)
4078 dimen = convert_lvalue_to_rvalue (brace_loc, dimen, true, true);
4079 declarator = build_array_declarator (brace_loc, dimen.value, quals_attrs,
c2255bc4 4080 static_seen, star_seen);
52ffd86e
MS
4081 if (declarator == NULL)
4082 return NULL;
4e03c3a7
JM
4083 if (c_parser_nth_token_starts_std_attributes (parser, 1))
4084 {
4085 tree std_attrs
4086 = c_parser_std_attribute_specifier_sequence (parser);
4087 if (std_attrs)
4088 inner = build_attrs_declarator (std_attrs, inner);
4089 }
1723e1be 4090 inner = set_array_declarator_inner (declarator, inner);
27bf414c
JM
4091 return c_parser_direct_declarator_inner (parser, id_present, inner);
4092 }
4093 else if (c_parser_next_token_is (parser, CPP_OPEN_PAREN))
4094 {
4095 tree attrs;
4096 struct c_arg_info *args;
4097 c_parser_consume_token (parser);
4e03c3a7
JM
4098 bool have_gnu_attrs = c_parser_next_token_is_keyword (parser,
4099 RID_ATTRIBUTE);
783bfe5e 4100 attrs = c_parser_gnu_attributes (parser);
4e03c3a7
JM
4101 args = c_parser_parms_declarator (parser, id_present, attrs,
4102 have_gnu_attrs);
27bf414c
JM
4103 if (args == NULL)
4104 return NULL;
4105 else
4106 {
4e03c3a7
JM
4107 if (!(args->types
4108 && args->types != error_mark_node
4109 && TREE_CODE (TREE_VALUE (args->types)) == IDENTIFIER_NODE)
4110 && c_parser_nth_token_starts_std_attributes (parser, 1))
4111 {
4112 tree std_attrs
4113 = c_parser_std_attribute_specifier_sequence (parser);
4114 if (std_attrs)
4115 inner = build_attrs_declarator (std_attrs, inner);
4116 }
1723e1be 4117 inner = build_function_declarator (args, inner);
27bf414c
JM
4118 return c_parser_direct_declarator_inner (parser, id_present, inner);
4119 }
4120 }
4121 return inner;
4122}
4123
4124/* Parse a parameter list or identifier list, including the closing
4e03c3a7
JM
4125 parenthesis but not the opening one. ATTRS are the gnu-attributes
4126 at the start of the list. ID_LIST_OK is true if an identifier list
4127 is acceptable; such a list must not have attributes at the start.
4128 HAVE_GNU_ATTRS says whether any gnu-attributes (including empty
4129 attributes) were present (in which case standard attributes cannot
4130 occur). */
27bf414c
JM
4131
4132static struct c_arg_info *
4e03c3a7
JM
4133c_parser_parms_declarator (c_parser *parser, bool id_list_ok, tree attrs,
4134 bool have_gnu_attrs)
27bf414c
JM
4135{
4136 push_scope ();
4137 declare_parm_level ();
4138 /* If the list starts with an identifier, it is an identifier list.
4139 Otherwise, it is either a prototype list or an empty list. */
4140 if (id_list_ok
4141 && !attrs
4142 && c_parser_next_token_is (parser, CPP_NAME)
29ce73cb
PB
4143 && c_parser_peek_token (parser)->id_kind == C_ID_ID
4144
4145 /* Look ahead to detect typos in type names. */
4146 && c_parser_peek_2nd_token (parser)->type != CPP_NAME
4147 && c_parser_peek_2nd_token (parser)->type != CPP_MULT
4148 && c_parser_peek_2nd_token (parser)->type != CPP_OPEN_PAREN
1a4f11c8
DM
4149 && c_parser_peek_2nd_token (parser)->type != CPP_OPEN_SQUARE
4150 && c_parser_peek_2nd_token (parser)->type != CPP_KEYWORD)
27bf414c 4151 {
7fa3585c 4152 tree list = NULL_TREE, *nextp = &list;
27bf414c
JM
4153 while (c_parser_next_token_is (parser, CPP_NAME)
4154 && c_parser_peek_token (parser)->id_kind == C_ID_ID)
4155 {
7fa3585c
GK
4156 *nextp = build_tree_list (NULL_TREE,
4157 c_parser_peek_token (parser)->value);
4158 nextp = & TREE_CHAIN (*nextp);
27bf414c
JM
4159 c_parser_consume_token (parser);
4160 if (c_parser_next_token_is_not (parser, CPP_COMMA))
4161 break;
4162 c_parser_consume_token (parser);
4163 if (c_parser_next_token_is (parser, CPP_CLOSE_PAREN))
4164 {
4165 c_parser_error (parser, "expected identifier");
4166 break;
4167 }
4168 }
4169 if (c_parser_next_token_is (parser, CPP_CLOSE_PAREN))
4170 {
b3399d18 4171 struct c_arg_info *ret = build_arg_info ();
27bf414c 4172 ret->types = list;
27bf414c
JM
4173 c_parser_consume_token (parser);
4174 pop_scope ();
4175 return ret;
4176 }
4177 else
4178 {
4179 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN,
4180 "expected %<)%>");
4181 pop_scope ();
4182 return NULL;
4183 }
4184 }
4185 else
4186 {
4e03c3a7
JM
4187 struct c_arg_info *ret
4188 = c_parser_parms_list_declarator (parser, attrs, NULL, have_gnu_attrs);
27bf414c
JM
4189 pop_scope ();
4190 return ret;
4191 }
4192}
4193
4194/* Parse a parameter list (possibly empty), including the closing
4e03c3a7
JM
4195 parenthesis but not the opening one. ATTRS are the gnu-attributes
4196 at the start of the list; if HAVE_GNU_ATTRS, there were some such
4197 attributes (possibly empty, in which case ATTRS is NULL_TREE),
4198 which means standard attributes cannot start the list. EXPR is
4199 NULL or an expression that needs to be evaluated for the side
4200 effects of array size expressions in the parameters. */
27bf414c
JM
4201
4202static struct c_arg_info *
4e03c3a7
JM
4203c_parser_parms_list_declarator (c_parser *parser, tree attrs, tree expr,
4204 bool have_gnu_attrs)
27bf414c 4205{
09a1e889 4206 bool bad_parm = false;
a04a722b 4207
27bf414c
JM
4208 /* ??? Following the old parser, forward parameter declarations may
4209 use abstract declarators, and if no real parameter declarations
4210 follow the forward declarations then this is not diagnosed. Also
4e03c3a7 4211 note as above that gnu-attributes are ignored as the only contents of
27bf414c
JM
4212 the parentheses, or as the only contents after forward
4213 declarations. */
4214 if (c_parser_next_token_is (parser, CPP_CLOSE_PAREN))
4215 {
b3399d18 4216 struct c_arg_info *ret = build_arg_info ();
27bf414c
JM
4217 c_parser_consume_token (parser);
4218 return ret;
4219 }
4220 if (c_parser_next_token_is (parser, CPP_ELLIPSIS))
4221 {
b3399d18 4222 struct c_arg_info *ret = build_arg_info ();
6637388f
TG
4223
4224 if (flag_allow_parameterless_variadic_functions)
4225 {
4226 /* F (...) is allowed. */
4227 ret->types = NULL_TREE;
4228 }
4229 else
4230 {
4231 /* Suppress -Wold-style-definition for this case. */
4232 ret->types = error_mark_node;
4233 error_at (c_parser_peek_token (parser)->location,
4234 "ISO C requires a named argument before %<...%>");
4235 }
27bf414c
JM
4236 c_parser_consume_token (parser);
4237 if (c_parser_next_token_is (parser, CPP_CLOSE_PAREN))
4238 {
4239 c_parser_consume_token (parser);
4240 return ret;
4241 }
4242 else
4243 {
4244 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN,
4245 "expected %<)%>");
4246 return NULL;
4247 }
4248 }
4249 /* Nonempty list of parameters, either terminated with semicolon
4250 (forward declarations; recurse) or with close parenthesis (normal
4251 function) or with ", ... )" (variadic function). */
4252 while (true)
4253 {
4254 /* Parse a parameter. */
4e03c3a7
JM
4255 struct c_parm *parm = c_parser_parameter_declaration (parser, attrs,
4256 have_gnu_attrs);
27bf414c 4257 attrs = NULL_TREE;
4e03c3a7 4258 have_gnu_attrs = false;
09a1e889
SZ
4259 if (parm == NULL)
4260 bad_parm = true;
4261 else
a04a722b 4262 push_parm_decl (parm, &expr);
27bf414c
JM
4263 if (c_parser_next_token_is (parser, CPP_SEMICOLON))
4264 {
4265 tree new_attrs;
4266 c_parser_consume_token (parser);
91d975b8 4267 mark_forward_parm_decls ();
4e03c3a7
JM
4268 bool new_have_gnu_attrs
4269 = c_parser_next_token_is_keyword (parser, RID_ATTRIBUTE);
783bfe5e 4270 new_attrs = c_parser_gnu_attributes (parser);
4e03c3a7
JM
4271 return c_parser_parms_list_declarator (parser, new_attrs, expr,
4272 new_have_gnu_attrs);
27bf414c
JM
4273 }
4274 if (c_parser_next_token_is (parser, CPP_CLOSE_PAREN))
4275 {
4276 c_parser_consume_token (parser);
09a1e889 4277 if (bad_parm)
a04a722b 4278 return NULL;
09a1e889 4279 else
a04a722b 4280 return get_parm_info (false, expr);
27bf414c
JM
4281 }
4282 if (!c_parser_require (parser, CPP_COMMA,
62e1c678
DM
4283 "expected %<;%>, %<,%> or %<)%>",
4284 UNKNOWN_LOCATION, false))
27bf414c
JM
4285 {
4286 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN, NULL);
4287 return NULL;
4288 }
4289 if (c_parser_next_token_is (parser, CPP_ELLIPSIS))
4290 {
4291 c_parser_consume_token (parser);
4292 if (c_parser_next_token_is (parser, CPP_CLOSE_PAREN))
4293 {
4294 c_parser_consume_token (parser);
09a1e889 4295 if (bad_parm)
a04a722b 4296 return NULL;
09a1e889 4297 else
a04a722b 4298 return get_parm_info (true, expr);
27bf414c
JM
4299 }
4300 else
4301 {
4302 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN,
4303 "expected %<)%>");
4304 return NULL;
4305 }
4306 }
4307 }
4308}
4309
4e03c3a7
JM
4310/* Parse a parameter declaration. ATTRS are the gnu-attributes at the
4311 start of the declaration if it is the first parameter;
4312 HAVE_GNU_ATTRS is true if there were any gnu-attributes there (even
4313 empty) there. */
27bf414c
JM
4314
4315static struct c_parm *
4e03c3a7
JM
4316c_parser_parameter_declaration (c_parser *parser, tree attrs,
4317 bool have_gnu_attrs)
27bf414c
JM
4318{
4319 struct c_declspecs *specs;
4320 struct c_declarator *declarator;
4321 tree prefix_attrs;
4322 tree postfix_attrs = NULL_TREE;
4323 bool dummy = false;
51a1aacf
TG
4324
4325 /* Accept #pragmas between parameter declarations. */
4326 while (c_parser_next_token_is (parser, CPP_PRAGMA))
dda1bf61 4327 c_parser_pragma (parser, pragma_param, NULL);
51a1aacf 4328
4e03c3a7
JM
4329 if (!c_parser_next_token_starts_declspecs (parser)
4330 && !c_parser_nth_token_starts_std_attributes (parser, 1))
27bf414c 4331 {
09a1e889
SZ
4332 c_token *token = c_parser_peek_token (parser);
4333 if (parser->error)
4334 return NULL;
4335 c_parser_set_source_position_from_token (token);
29ce73cb 4336 if (c_parser_next_tokens_start_typename (parser, cla_prefer_type))
09a1e889 4337 {
097f82ec 4338 auto_diagnostic_group d;
6c7a259b
DM
4339 name_hint hint = lookup_name_fuzzy (token->value,
4340 FUZZY_LOOKUP_TYPENAME,
4341 token->location);
7e2de6df 4342 if (const char *suggestion = hint.suggestion ())
1a4f11c8 4343 {
1a4f11c8 4344 gcc_rich_location richloc (token->location);
7e2de6df 4345 richloc.add_fixit_replace (suggestion);
64a5912c
DM
4346 error_at (&richloc,
4347 "unknown type name %qE; did you mean %qs?",
7e2de6df 4348 token->value, suggestion);
1a4f11c8
DM
4349 }
4350 else
4351 error_at (token->location, "unknown type name %qE", token->value);
09a1e889
SZ
4352 parser->error = true;
4353 }
27bf414c
JM
4354 /* ??? In some Objective-C cases '...' isn't applicable so there
4355 should be a different message. */
09a1e889
SZ
4356 else
4357 c_parser_error (parser,
4358 "expected declaration specifiers or %<...%>");
27bf414c
JM
4359 c_parser_skip_to_end_of_parameter (parser);
4360 return NULL;
4361 }
8139a48e
DM
4362
4363 location_t start_loc = c_parser_peek_token (parser)->location;
4364
27bf414c
JM
4365 specs = build_null_declspecs ();
4366 if (attrs)
4367 {
0b2c4be5 4368 declspecs_add_attrs (input_location, specs, attrs);
27bf414c
JM
4369 attrs = NULL_TREE;
4370 }
38b7bc7f 4371 c_parser_declspecs (parser, specs, true, true, true, true, false,
4e03c3a7 4372 !have_gnu_attrs, true, cla_nonabstract_decl);
27bf414c
JM
4373 finish_declspecs (specs);
4374 pending_xref_error ();
4375 prefix_attrs = specs->attrs;
4376 specs->attrs = NULL_TREE;
9e5b2115
PB
4377 declarator = c_parser_declarator (parser,
4378 specs->typespec_kind != ctsk_none,
27bf414c
JM
4379 C_DTR_PARM, &dummy);
4380 if (declarator == NULL)
4381 {
4382 c_parser_skip_until_found (parser, CPP_COMMA, NULL);
4383 return NULL;
4384 }
4385 if (c_parser_next_token_is_keyword (parser, RID_ATTRIBUTE))
783bfe5e 4386 postfix_attrs = c_parser_gnu_attributes (parser);
8139a48e
DM
4387
4388 /* Generate a location for the parameter, ranging from the start of the
4389 initial token to the end of the final token.
4390
4391 If we have a identifier, then use it for the caret location, e.g.
4392
4393 extern int callee (int one, int (*two)(int, int), float three);
4394 ~~~~~~^~~~~~~~~~~~~~
4395
4396 otherwise, reuse the start location for the caret location e.g.:
4397
4398 extern int callee (int one, int (*)(int, int), float three);
4399 ^~~~~~~~~~~~~~~~~
4400 */
4401 location_t end_loc = parser->last_token_location;
4402
4403 /* Find any cdk_id declarator; determine if we have an identifier. */
4404 c_declarator *id_declarator = declarator;
4405 while (id_declarator && id_declarator->kind != cdk_id)
4406 id_declarator = id_declarator->declarator;
1723e1be 4407 location_t caret_loc = (id_declarator->u.id.id
8139a48e
DM
4408 ? id_declarator->id_loc
4409 : start_loc);
4410 location_t param_loc = make_location (caret_loc, start_loc, end_loc);
4411
27bf414c 4412 return build_c_parm (specs, chainon (postfix_attrs, prefix_attrs),
8139a48e 4413 declarator, param_loc);
27bf414c
JM
4414}
4415
4416/* Parse a string literal in an asm expression. It should not be
4417 translated, and wide string literals are an error although
4418 permitted by the syntax. This is a GNU extension.
4419
4420 asm-string-literal:
4421 string-literal
471c5330 4422*/
27bf414c
JM
4423
4424static tree
4425c_parser_asm_string_literal (c_parser *parser)
4426{
4427 tree str;
87f9e23d
TT
4428 int save_flag = warn_overlength_strings;
4429 warn_overlength_strings = 0;
471c5330 4430 str = c_parser_string_literal (parser, false, false).value;
87f9e23d 4431 warn_overlength_strings = save_flag;
27bf414c
JM
4432 return str;
4433}
4434
4435/* Parse a simple asm expression. This is used in restricted
4436 contexts, where a full expression with inputs and outputs does not
4437 make sense. This is a GNU extension.
4438
4439 simple-asm-expr:
4440 asm ( asm-string-literal )
4441*/
4442
4443static tree
4444c_parser_simple_asm_expr (c_parser *parser)
4445{
4446 tree str;
4447 gcc_assert (c_parser_next_token_is_keyword (parser, RID_ASM));
27bf414c 4448 c_parser_consume_token (parser);
32129a17
DM
4449 matching_parens parens;
4450 if (!parens.require_open (parser))
471c5330 4451 return NULL_TREE;
27bf414c 4452 str = c_parser_asm_string_literal (parser);
32129a17 4453 if (!parens.require_close (parser))
27bf414c
JM
4454 {
4455 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN, NULL);
4456 return NULL_TREE;
4457 }
4458 return str;
4459}
4460
0a35513e 4461static tree
783bfe5e 4462c_parser_gnu_attribute_any_word (c_parser *parser)
0a35513e
AH
4463{
4464 tree attr_name = NULL_TREE;
4465
4466 if (c_parser_next_token_is (parser, CPP_KEYWORD))
4467 {
4468 /* ??? See comment above about what keywords are accepted here. */
4469 bool ok;
4470 switch (c_parser_peek_token (parser)->keyword)
4471 {
4472 case RID_STATIC:
4473 case RID_UNSIGNED:
4474 case RID_LONG:
0a35513e
AH
4475 case RID_CONST:
4476 case RID_EXTERN:
4477 case RID_REGISTER:
4478 case RID_TYPEDEF:
4479 case RID_SHORT:
4480 case RID_INLINE:
4481 case RID_NORETURN:
4482 case RID_VOLATILE:
4483 case RID_SIGNED:
4484 case RID_AUTO:
4485 case RID_RESTRICT:
4486 case RID_COMPLEX:
4487 case RID_THREAD:
4488 case RID_INT:
4489 case RID_CHAR:
4490 case RID_FLOAT:
4491 case RID_DOUBLE:
4492 case RID_VOID:
4493 case RID_DFLOAT32:
4494 case RID_DFLOAT64:
4495 case RID_DFLOAT128:
c65699ef 4496 CASE_RID_FLOATN_NX:
0a35513e
AH
4497 case RID_BOOL:
4498 case RID_FRACT:
4499 case RID_ACCUM:
4500 case RID_SAT:
4501 case RID_TRANSACTION_ATOMIC:
4502 case RID_TRANSACTION_CANCEL:
267bac10 4503 case RID_ATOMIC:
38b7bc7f 4504 case RID_AUTO_TYPE:
78a7c317
DD
4505 case RID_INT_N_0:
4506 case RID_INT_N_1:
4507 case RID_INT_N_2:
4508 case RID_INT_N_3:
0a35513e
AH
4509 ok = true;
4510 break;
4511 default:
4512 ok = false;
4513 break;
4514 }
4515 if (!ok)
4516 return NULL_TREE;
4517
4518 /* Accept __attribute__((__const)) as __attribute__((const)) etc. */
4519 attr_name = ridpointers[(int) c_parser_peek_token (parser)->keyword];
4520 }
4521 else if (c_parser_next_token_is (parser, CPP_NAME))
4522 attr_name = c_parser_peek_token (parser)->value;
4523
4524 return attr_name;
4525}
4526
c01bd174
JM
4527/* Parse attribute arguments. This is a common form of syntax
4528 covering all currently valid GNU and standard attributes.
4529
4530 gnu-attribute-arguments:
4531 identifier
4532 identifier , nonempty-expr-list
4533 expr-list
4534
4535 where the "identifier" must not be declared as a type. ??? Why not
4536 allow identifiers declared as types to start the arguments? */
4537
4538static tree
2cc94aa8
JM
4539c_parser_attribute_arguments (c_parser *parser, bool takes_identifier,
4540 bool require_string, bool allow_empty_args)
c01bd174
JM
4541{
4542 vec<tree, va_gc> *expr_list;
4543 tree attr_args;
4544 /* Parse the attribute contents. If they start with an
4545 identifier which is followed by a comma or close
4546 parenthesis, then the arguments start with that
4547 identifier; otherwise they are an expression list.
4548 In objective-c the identifier may be a classname. */
4549 if (c_parser_next_token_is (parser, CPP_NAME)
4550 && (c_parser_peek_token (parser)->id_kind == C_ID_ID
4551 || (c_dialect_objc ()
4552 && c_parser_peek_token (parser)->id_kind
4553 == C_ID_CLASSNAME))
4554 && ((c_parser_peek_2nd_token (parser)->type == CPP_COMMA)
4555 || (c_parser_peek_2nd_token (parser)->type
4556 == CPP_CLOSE_PAREN))
4557 && (takes_identifier
4558 || (c_dialect_objc ()
4559 && c_parser_peek_token (parser)->id_kind
4560 == C_ID_CLASSNAME)))
4561 {
4562 tree arg1 = c_parser_peek_token (parser)->value;
4563 c_parser_consume_token (parser);
4564 if (c_parser_next_token_is (parser, CPP_CLOSE_PAREN))
4565 attr_args = build_tree_list (NULL_TREE, arg1);
4566 else
4567 {
4568 tree tree_list;
4569 c_parser_consume_token (parser);
4570 expr_list = c_parser_expr_list (parser, false, true,
4571 NULL, NULL, NULL, NULL);
4572 tree_list = build_tree_list_vec (expr_list);
4573 attr_args = tree_cons (NULL_TREE, arg1, tree_list);
4574 release_tree_vector (expr_list);
4575 }
4576 }
4577 else
4578 {
4579 if (c_parser_next_token_is (parser, CPP_CLOSE_PAREN))
2cc94aa8
JM
4580 {
4581 if (!allow_empty_args)
4582 error_at (c_parser_peek_token (parser)->location,
4583 "parentheses must be omitted if "
4584 "attribute argument list is empty");
4585 attr_args = NULL_TREE;
4586 }
4587 else if (require_string)
4588 {
4589 /* The only valid argument for this attribute is a string
4590 literal. Handle this specially here to avoid accepting
4591 string literals with excess parentheses. */
4592 tree string = c_parser_string_literal (parser, false, true).value;
4593 attr_args = build_tree_list (NULL_TREE, string);
4594 }
c01bd174
JM
4595 else
4596 {
4597 expr_list = c_parser_expr_list (parser, false, true,
4598 NULL, NULL, NULL, NULL);
4599 attr_args = build_tree_list_vec (expr_list);
4600 release_tree_vector (expr_list);
4601 }
4602 }
4603 return attr_args;
4604}
4605
783bfe5e 4606/* Parse (possibly empty) gnu-attributes. This is a GNU extension.
27bf414c 4607
783bfe5e 4608 gnu-attributes:
27bf414c 4609 empty
783bfe5e 4610 gnu-attributes gnu-attribute
27bf414c 4611
783bfe5e
JM
4612 gnu-attribute:
4613 __attribute__ ( ( gnu-attribute-list ) )
27bf414c 4614
783bfe5e
JM
4615 gnu-attribute-list:
4616 gnu-attrib
4617 gnu-attribute_list , gnu-attrib
27bf414c 4618
783bfe5e 4619 gnu-attrib:
27bf414c
JM
4620 empty
4621 any-word
c01bd174 4622 any-word ( gnu-attribute-arguments )
27bf414c 4623
c01bd174 4624 where "any-word" may be any identifier (including one declared as a
27bf414c
JM
4625 type), a reserved word storage class specifier, type specifier or
4626 type qualifier. ??? This still leaves out most reserved keywords
c01bd174 4627 (following the old parser), shouldn't we include them?
98f08eb8
MS
4628 When EXPECT_COMMA is true, expect the attribute to be preceded
4629 by a comma and fail if it isn't.
4630 When EMPTY_OK is true, allow and consume any number of consecutive
4631 commas with no attributes in between. */
4632
4633static tree
783bfe5e
JM
4634c_parser_gnu_attribute (c_parser *parser, tree attrs,
4635 bool expect_comma = false, bool empty_ok = true)
98f08eb8
MS
4636{
4637 bool comma_first = c_parser_next_token_is (parser, CPP_COMMA);
4638 if (!comma_first
4639 && !c_parser_next_token_is (parser, CPP_NAME)
4640 && !c_parser_next_token_is (parser, CPP_KEYWORD))
4641 return NULL_TREE;
4642
4643 while (c_parser_next_token_is (parser, CPP_COMMA))
4644 {
4645 c_parser_consume_token (parser);
4646 if (!empty_ok)
4647 return attrs;
4648 }
4649
783bfe5e 4650 tree attr_name = c_parser_gnu_attribute_any_word (parser);
98f08eb8
MS
4651 if (attr_name == NULL_TREE)
4652 return NULL_TREE;
4653
4654 attr_name = canonicalize_attr_name (attr_name);
4655 c_parser_consume_token (parser);
4656
4657 tree attr;
4658 if (c_parser_next_token_is_not (parser, CPP_OPEN_PAREN))
4659 {
4660 if (expect_comma && !comma_first)
4661 {
4662 /* A comma is missing between the last attribute on the chain
4663 and this one. */
4664 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN,
4665 "expected %<)%>");
4666 return error_mark_node;
4667 }
4668 attr = build_tree_list (attr_name, NULL_TREE);
4669 /* Add this attribute to the list. */
4670 attrs = chainon (attrs, attr);
4671 return attrs;
4672 }
4673 c_parser_consume_token (parser);
4674
c01bd174
JM
4675 tree attr_args
4676 = c_parser_attribute_arguments (parser,
2cc94aa8
JM
4677 attribute_takes_identifier_p (attr_name),
4678 false, true);
98f08eb8
MS
4679
4680 attr = build_tree_list (attr_name, attr_args);
4681 if (c_parser_next_token_is (parser, CPP_CLOSE_PAREN))
4682 c_parser_consume_token (parser);
4683 else
4684 {
98f08eb8
MS
4685 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN,
4686 "expected %<)%>");
4687 return error_mark_node;
4688 }
4689
4690 if (expect_comma && !comma_first)
4691 {
4692 /* A comma is missing between the last attribute on the chain
4693 and this one. */
4694 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN,
4695 "expected %<)%>");
4696 return error_mark_node;
4697 }
4698
4699 /* Add this attribute to the list. */
4700 attrs = chainon (attrs, attr);
4701 return attrs;
4702}
27bf414c
JM
4703
4704static tree
783bfe5e 4705c_parser_gnu_attributes (c_parser *parser)
27bf414c
JM
4706{
4707 tree attrs = NULL_TREE;
4708 while (c_parser_next_token_is_keyword (parser, RID_ATTRIBUTE))
4709 {
471c5330
JM
4710 bool save_translate_strings_p = parser->translate_strings_p;
4711 parser->translate_strings_p = false;
2c7020eb 4712 /* Consume the `__attribute__' keyword. */
27bf414c 4713 c_parser_consume_token (parser);
2c7020eb 4714 /* Look for the two `(' tokens. */
27bf414c
JM
4715 if (!c_parser_require (parser, CPP_OPEN_PAREN, "expected %<(%>"))
4716 {
471c5330 4717 parser->translate_strings_p = save_translate_strings_p;
27bf414c
JM
4718 return attrs;
4719 }
4720 if (!c_parser_require (parser, CPP_OPEN_PAREN, "expected %<(%>"))
4721 {
471c5330 4722 parser->translate_strings_p = save_translate_strings_p;
27bf414c
JM
4723 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN, NULL);
4724 return attrs;
4725 }
98f08eb8
MS
4726 /* Parse the attribute list. Require a comma between successive
4727 (possibly empty) attributes. */
4728 for (bool expect_comma = false; ; expect_comma = true)
27bf414c 4729 {
98f08eb8 4730 /* Parse a single attribute. */
783bfe5e 4731 tree attr = c_parser_gnu_attribute (parser, attrs, expect_comma);
98f08eb8
MS
4732 if (attr == error_mark_node)
4733 return attrs;
4734 if (!attr)
0a35513e 4735 break;
98f08eb8
MS
4736 attrs = attr;
4737 }
577eec56 4738
2c7020eb 4739 /* Look for the two `)' tokens. */
27bf414c
JM
4740 if (c_parser_next_token_is (parser, CPP_CLOSE_PAREN))
4741 c_parser_consume_token (parser);
4742 else
4743 {
471c5330 4744 parser->translate_strings_p = save_translate_strings_p;
27bf414c
JM
4745 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN,
4746 "expected %<)%>");
4747 return attrs;
4748 }
4749 if (c_parser_next_token_is (parser, CPP_CLOSE_PAREN))
4750 c_parser_consume_token (parser);
4751 else
4752 {
471c5330 4753 parser->translate_strings_p = save_translate_strings_p;
27bf414c
JM
4754 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN,
4755 "expected %<)%>");
4756 return attrs;
4757 }
471c5330 4758 parser->translate_strings_p = save_translate_strings_p;
27bf414c 4759 }
41958c28 4760
27bf414c
JM
4761 return attrs;
4762}
4763
c01bd174
JM
4764/* Parse an optional balanced token sequence.
4765
4766 balanced-token-sequence:
4767 balanced-token
4768 balanced-token-sequence balanced-token
4769
4770 balanced-token:
4771 ( balanced-token-sequence[opt] )
4772 [ balanced-token-sequence[opt] ]
4773 { balanced-token-sequence[opt] }
4774 any token other than ()[]{}
4775*/
4776
4777static void
4778c_parser_balanced_token_sequence (c_parser *parser)
4779{
4780 while (true)
4781 {
4782 c_token *token = c_parser_peek_token (parser);
4783 switch (token->type)
4784 {
4785 case CPP_OPEN_BRACE:
4786 {
4787 matching_braces braces;
4788 braces.consume_open (parser);
4789 c_parser_balanced_token_sequence (parser);
4790 braces.require_close (parser);
4791 break;
4792 }
4793
4794 case CPP_OPEN_PAREN:
4795 {
4796 matching_parens parens;
4797 parens.consume_open (parser);
4798 c_parser_balanced_token_sequence (parser);
4799 parens.require_close (parser);
4800 break;
4801 }
4802
4803 case CPP_OPEN_SQUARE:
4804 c_parser_consume_token (parser);
4805 c_parser_balanced_token_sequence (parser);
4806 c_parser_require (parser, CPP_CLOSE_SQUARE, "expected %<]%>");
4807 break;
4808
4809 case CPP_CLOSE_BRACE:
4810 case CPP_CLOSE_PAREN:
4811 case CPP_CLOSE_SQUARE:
4812 case CPP_EOF:
4813 return;
4814
4815 default:
4816 c_parser_consume_token (parser);
4817 break;
4818 }
4819 }
4820}
4821
4822/* Parse standard (C2X) attributes (including GNU attributes in the
4823 gnu:: namespace).
4824
4825 attribute-specifier-sequence:
4826 attribute-specifier-sequence[opt] attribute-specifier
4827
4828 attribute-specifier:
4829 [ [ attribute-list ] ]
4830
4831 attribute-list:
4832 attribute[opt]
4833 attribute-list, attribute[opt]
4834
4835 attribute:
4836 attribute-token attribute-argument-clause[opt]
4837
4838 attribute-token:
4839 standard-attribute
4840 attribute-prefixed-token
4841
4842 standard-attribute:
4843 identifier
4844
4845 attribute-prefixed-token:
4846 attribute-prefix :: identifier
4847
4848 attribute-prefix:
4849 identifier
4850
4851 attribute-argument-clause:
4852 ( balanced-token-sequence[opt] )
4853
4854 Keywords are accepted as identifiers for this purpose.
4855*/
4856
4857static tree
192961ff 4858c_parser_std_attribute (c_parser *parser, bool for_tm)
c01bd174
JM
4859{
4860 c_token *token = c_parser_peek_token (parser);
4861 tree ns, name, attribute;
4862
4863 /* Parse the attribute-token. */
4864 if (token->type != CPP_NAME && token->type != CPP_KEYWORD)
4865 {
4866 c_parser_error (parser, "expected identifier");
4867 return error_mark_node;
4868 }
4869 name = canonicalize_attr_name (token->value);
4870 c_parser_consume_token (parser);
4871 if (c_parser_next_token_is (parser, CPP_SCOPE))
4872 {
4873 ns = name;
4874 c_parser_consume_token (parser);
4875 token = c_parser_peek_token (parser);
4876 if (token->type != CPP_NAME && token->type != CPP_KEYWORD)
4877 {
4878 c_parser_error (parser, "expected identifier");
4879 return error_mark_node;
4880 }
4881 name = canonicalize_attr_name (token->value);
4882 c_parser_consume_token (parser);
4883 }
4884 else
4885 ns = NULL_TREE;
4886 attribute = build_tree_list (build_tree_list (ns, name), NULL_TREE);
4887
4888 /* Parse the arguments, if any. */
c01bd174 4889 const attribute_spec *as = lookup_attribute_spec (TREE_PURPOSE (attribute));
192961ff
JM
4890 if (c_parser_next_token_is_not (parser, CPP_OPEN_PAREN))
4891 goto out;
4892 {
4893 location_t open_loc = c_parser_peek_token (parser)->location;
4894 matching_parens parens;
4895 parens.consume_open (parser);
4896 if ((as && as->max_length == 0)
4897 /* Special-case the transactional-memory attribute "outer",
4898 which is specially handled but not registered as an
4899 attribute, to avoid allowing arbitrary balanced token
4900 sequences as arguments. */
4901 || is_attribute_p ("outer", name))
4902 {
4903 error_at (open_loc, "%qE attribute does not take any arguments", name);
4904 parens.skip_until_found_close (parser);
4905 return error_mark_node;
4906 }
4907 if (as)
4908 {
4909 bool takes_identifier
4910 = (ns != NULL_TREE
4911 && strcmp (IDENTIFIER_POINTER (ns), "gnu") == 0
4912 && attribute_takes_identifier_p (name));
4913 bool require_string
4914 = (ns == NULL_TREE
4915 && strcmp (IDENTIFIER_POINTER (name), "deprecated") == 0);
4916 TREE_VALUE (attribute)
4917 = c_parser_attribute_arguments (parser, takes_identifier,
4918 require_string, false);
4919 }
4920 else
4921 c_parser_balanced_token_sequence (parser);
4922 parens.require_close (parser);
4923 }
4924 out:
4925 if (ns == NULL_TREE && !for_tm && !as && !is_attribute_p ("nodiscard", name))
c01bd174 4926 {
192961ff
JM
4927 /* An attribute with standard syntax and no namespace specified
4928 is a constraint violation if it is not one of the known
4929 standard attributes (of which nodiscard is the only one
4930 without a handler in GCC). Diagnose it here with a pedwarn
4931 and then discard it to prevent a duplicate warning later. */
4932 pedwarn (input_location, OPT_Wattributes, "%qE attribute ignored",
4933 name);
c01bd174
JM
4934 return error_mark_node;
4935 }
c01bd174
JM
4936 return attribute;
4937}
4938
4939static tree
4940c_parser_std_attribute_specifier (c_parser *parser, bool for_tm)
4941{
d5fbe5e0
JM
4942 bool seen_deprecated = false;
4943 bool seen_fallthrough = false;
4944 bool seen_maybe_unused = false;
c01bd174
JM
4945 location_t loc = c_parser_peek_token (parser)->location;
4946 if (!c_parser_require (parser, CPP_OPEN_SQUARE, "expected %<[%>"))
4947 return NULL_TREE;
4948 if (!c_parser_require (parser, CPP_OPEN_SQUARE, "expected %<[%>"))
4949 {
4950 c_parser_skip_until_found (parser, CPP_CLOSE_SQUARE, "expected %<]%>");
4951 return NULL_TREE;
4952 }
4953 if (!for_tm)
4954 pedwarn_c11 (loc, OPT_Wpedantic,
4955 "ISO C does not support %<[[]]%> attributes before C2X");
4956 tree attributes = NULL_TREE;
4957 while (true)
4958 {
4959 c_token *token = c_parser_peek_token (parser);
4960 if (token->type == CPP_CLOSE_SQUARE)
4961 break;
4962 if (token->type == CPP_COMMA)
4963 {
4964 c_parser_consume_token (parser);
4965 continue;
4966 }
192961ff 4967 tree attribute = c_parser_std_attribute (parser, for_tm);
c01bd174
JM
4968 if (attribute != error_mark_node)
4969 {
d5fbe5e0
JM
4970 bool duplicate = false;
4971 tree name = get_attribute_name (attribute);
4972 tree ns = get_attribute_namespace (attribute);
4973 if (ns == NULL_TREE)
4974 {
4975 /* Some standard attributes may appear at most once in
4976 each attribute list. Diagnose duplicates and remove
4977 them from the list to avoid subsequent diagnostics
4978 such as the more general one for multiple
4979 "fallthrough" attributes in the same place (including
4980 in separate attribute lists in the same attribute
4981 specifier sequence, which is not a constraint
4982 violation). */
4983 if (is_attribute_p ("deprecated", name))
4984 {
4985 if (seen_deprecated)
4986 {
4987 error ("attribute %<deprecated%> can appear at most "
4988 "once in an attribute-list");
4989 duplicate = true;
4990 }
4991 seen_deprecated = true;
4992 }
4993 else if (is_attribute_p ("fallthrough", name))
4994 {
4995 if (seen_fallthrough)
4996 {
4997 error ("attribute %<fallthrough%> can appear at most "
4998 "once in an attribute-list");
4999 duplicate = true;
5000 }
5001 seen_fallthrough = true;
5002 }
5003 else if (is_attribute_p ("maybe_unused", name))
5004 {
5005 if (seen_maybe_unused)
5006 {
5007 error ("attribute %<maybe_unused%> can appear at most "
5008 "once in an attribute-list");
5009 duplicate = true;
5010 }
5011 seen_maybe_unused = true;
5012 }
5013 }
5014 if (!duplicate)
5015 {
5016 TREE_CHAIN (attribute) = attributes;
5017 attributes = attribute;
5018 }
c01bd174
JM
5019 }
5020 if (c_parser_next_token_is_not (parser, CPP_COMMA))
5021 break;
5022 }
5023 c_parser_skip_until_found (parser, CPP_CLOSE_SQUARE, "expected %<]%>");
5024 c_parser_skip_until_found (parser, CPP_CLOSE_SQUARE, "expected %<]%>");
5025 return nreverse (attributes);
5026}
5027
34b43828
JM
5028/* Look past an optional balanced token sequence of raw look-ahead
5029 tokens starting with the *Nth token. *N is updated to point to the
5030 following token. Return true if such a sequence was found, false
5031 if the tokens parsed were not balanced. */
5032
5033static bool
5034c_parser_check_balanced_raw_token_sequence (c_parser *parser, unsigned int *n)
5035{
5036 while (true)
5037 {
5038 c_token *token = c_parser_peek_nth_token_raw (parser, *n);
5039 switch (token->type)
5040 {
5041 case CPP_OPEN_BRACE:
5042 {
5043 ++*n;
5044 if (c_parser_check_balanced_raw_token_sequence (parser, n))
5045 {
5046 token = c_parser_peek_nth_token_raw (parser, *n);
5047 if (token->type == CPP_CLOSE_BRACE)
5048 ++*n;
5049 else
5050 return false;
5051 }
5052 else
5053 return false;
5054 break;
5055 }
5056
5057 case CPP_OPEN_PAREN:
5058 {
5059 ++*n;
5060 if (c_parser_check_balanced_raw_token_sequence (parser, n))
5061 {
5062 token = c_parser_peek_nth_token_raw (parser, *n);
5063 if (token->type == CPP_CLOSE_PAREN)
5064 ++*n;
5065 else
5066 return false;
5067 }
5068 else
5069 return false;
5070 break;
5071 }
5072
5073 case CPP_OPEN_SQUARE:
5074 {
5075 ++*n;
5076 if (c_parser_check_balanced_raw_token_sequence (parser, n))
5077 {
5078 token = c_parser_peek_nth_token_raw (parser, *n);
5079 if (token->type == CPP_CLOSE_SQUARE)
5080 ++*n;
5081 else
5082 return false;
5083 }
5084 else
5085 return false;
5086 break;
5087 }
5088
5089 case CPP_CLOSE_BRACE:
5090 case CPP_CLOSE_PAREN:
5091 case CPP_CLOSE_SQUARE:
5092 case CPP_EOF:
5093 return true;
5094
5095 default:
5096 ++*n;
5097 break;
5098 }
5099 }
5100}
5101
4e03c3a7
JM
5102/* Return whether standard attributes start with the Nth token. */
5103
5104static bool
5105c_parser_nth_token_starts_std_attributes (c_parser *parser, unsigned int n)
5106{
5107 if (!(c_parser_peek_nth_token (parser, n)->type == CPP_OPEN_SQUARE
5108 && c_parser_peek_nth_token (parser, n + 1)->type == CPP_OPEN_SQUARE))
5109 return false;
34b43828
JM
5110 /* In C, '[[' must start attributes. In Objective-C, we need to
5111 check whether '[[' is matched by ']]'. */
5112 if (!c_dialect_objc ())
5113 return true;
5114 n += 2;
5115 if (!c_parser_check_balanced_raw_token_sequence (parser, &n))
5116 return false;
5117 c_token *token = c_parser_peek_nth_token_raw (parser, n);
5118 if (token->type != CPP_CLOSE_SQUARE)
5119 return false;
5120 token = c_parser_peek_nth_token_raw (parser, n + 1);
5121 return token->type == CPP_CLOSE_SQUARE;
4e03c3a7
JM
5122}
5123
5124static tree
5125c_parser_std_attribute_specifier_sequence (c_parser *parser)
5126{
5127 tree attributes = NULL_TREE;
5128 do
5129 {
5130 tree attrs = c_parser_std_attribute_specifier (parser, false);
5131 attributes = chainon (attributes, attrs);
5132 }
5133 while (c_parser_nth_token_starts_std_attributes (parser, 1));
5134 return attributes;
5135}
5136
4b2b493f
JM
5137/* Parse a type name (C90 6.5.5, C99 6.7.6, C11 6.7.7). ALIGNAS_OK
5138 says whether alignment specifiers are OK (only in cases that might
5139 be the type name of a compound literal).
27bf414c
JM
5140
5141 type-name:
5142 specifier-qualifier-list abstract-declarator[opt]
5143*/
5144
1ee62b92 5145struct c_type_name *
4b2b493f 5146c_parser_type_name (c_parser *parser, bool alignas_ok)
27bf414c
JM
5147{
5148 struct c_declspecs *specs = build_null_declspecs ();
5149 struct c_declarator *declarator;
5150 struct c_type_name *ret;
5151 bool dummy = false;
4b2b493f 5152 c_parser_declspecs (parser, specs, false, true, true, alignas_ok, false,
4e03c3a7 5153 false, true, cla_prefer_type);
27bf414c
JM
5154 if (!specs->declspecs_seen_p)
5155 {
5156 c_parser_error (parser, "expected specifier-qualifier-list");
5157 return NULL;
5158 }
29ce73cb
PB
5159 if (specs->type != error_mark_node)
5160 {
5161 pending_xref_error ();
5162 finish_declspecs (specs);
5163 }
9e5b2115
PB
5164 declarator = c_parser_declarator (parser,
5165 specs->typespec_kind != ctsk_none,
27bf414c
JM
5166 C_DTR_ABSTRACT, &dummy);
5167 if (declarator == NULL)
5168 return NULL;
5169 ret = XOBNEW (&parser_obstack, struct c_type_name);
5170 ret->specs = specs;
5171 ret->declarator = declarator;
5172 return ret;
5173}
5174
31dc71a8 5175/* Parse an initializer (C90 6.5.7, C99 6.7.8, C11 6.7.9).
27bf414c
JM
5176
5177 initializer:
5178 assignment-expression
5179 { initializer-list }
5180 { initializer-list , }
5181
5182 initializer-list:
5183 designation[opt] initializer
5184 initializer-list , designation[opt] initializer
5185
5186 designation:
5187 designator-list =
5188
5189 designator-list:
5190 designator
5191 designator-list designator
5192
5193 designator:
5194 array-designator
5195 . identifier
5196
5197 array-designator:
5198 [ constant-expression ]
5199
5200 GNU extensions:
5201
5202 initializer:
5203 { }
5204
5205 designation:
5206 array-designator
5207 identifier :
5208
5209 array-designator:
5210 [ constant-expression ... constant-expression ]
5211
5212 Any expression without commas is accepted in the syntax for the
5213 constant-expressions, with non-constant expressions rejected later.
5214
5215 This function is only used for top-level initializers; for nested
5216 ones, see c_parser_initval. */
5217
5218static struct c_expr
5219c_parser_initializer (c_parser *parser)
5220{
5221 if (c_parser_next_token_is (parser, CPP_OPEN_BRACE))
16595a1f 5222 return c_parser_braced_init (parser, NULL_TREE, false, NULL);
27bf414c 5223 else
46bdb9cf
JM
5224 {
5225 struct c_expr ret;
c2255bc4 5226 location_t loc = c_parser_peek_token (parser)->location;
46bdb9cf
JM
5227 ret = c_parser_expr_no_commas (parser, NULL);
5228 if (TREE_CODE (ret.value) != STRING_CST
5229 && TREE_CODE (ret.value) != COMPOUND_LITERAL_EXPR)
267bac10 5230 ret = convert_lvalue_to_rvalue (loc, ret, true, true);
46bdb9cf
JM
5231 return ret;
5232 }
27bf414c
JM
5233}
5234
5dd9a9d0
DM
5235/* The location of the last comma within the current initializer list,
5236 or UNKNOWN_LOCATION if not within one. */
5237
5238location_t last_init_list_comma;
5239
27bf414c
JM
5240/* Parse a braced initializer list. TYPE is the type specified for a
5241 compound literal, and NULL_TREE for other initializers and for
5242 nested braced lists. NESTED_P is true for nested braced lists,
5243 false for the list of a compound literal or the list that is the
5244 top-level initializer in a declaration. */
5245
5246static struct c_expr
16595a1f
BS
5247c_parser_braced_init (c_parser *parser, tree type, bool nested_p,
5248 struct obstack *outer_obstack)
27bf414c 5249{
a1e3b3d9
LB
5250 struct c_expr ret;
5251 struct obstack braced_init_obstack;
c7412148 5252 location_t brace_loc = c_parser_peek_token (parser)->location;
a1e3b3d9 5253 gcc_obstack_init (&braced_init_obstack);
27bf414c 5254 gcc_assert (c_parser_next_token_is (parser, CPP_OPEN_BRACE));
32129a17
DM
5255 matching_braces braces;
5256 braces.consume_open (parser);
27bf414c 5257 if (nested_p)
16595a1f
BS
5258 {
5259 finish_implicit_inits (brace_loc, outer_obstack);
5260 push_init_level (brace_loc, 0, &braced_init_obstack);
5261 }
27bf414c
JM
5262 else
5263 really_start_incremental_init (type);
5264 if (c_parser_next_token_is (parser, CPP_CLOSE_BRACE))
5265 {
c1771a20 5266 pedwarn (brace_loc, OPT_Wpedantic, "ISO C forbids empty initializer braces");
27bf414c
JM
5267 }
5268 else
5269 {
5270 /* Parse a non-empty initializer list, possibly with a trailing
5271 comma. */
5272 while (true)
5273 {
a1e3b3d9 5274 c_parser_initelt (parser, &braced_init_obstack);
27bf414c
JM
5275 if (parser->error)
5276 break;
5277 if (c_parser_next_token_is (parser, CPP_COMMA))
5dd9a9d0
DM
5278 {
5279 last_init_list_comma = c_parser_peek_token (parser)->location;
5280 c_parser_consume_token (parser);
5281 }
27bf414c
JM
5282 else
5283 break;
5284 if (c_parser_next_token_is (parser, CPP_CLOSE_BRACE))
5285 break;
5286 }
5287 }
bef08b71
DM
5288 c_token *next_tok = c_parser_peek_token (parser);
5289 if (next_tok->type != CPP_CLOSE_BRACE)
27bf414c 5290 {
913884f7 5291 ret.set_error ();
27bf414c 5292 ret.original_code = ERROR_MARK;
6866c6e8 5293 ret.original_type = NULL;
32129a17 5294 braces.skip_until_found_close (parser);
5dd9a9d0 5295 pop_init_level (brace_loc, 0, &braced_init_obstack, last_init_list_comma);
a1e3b3d9 5296 obstack_free (&braced_init_obstack, NULL);
27bf414c
JM
5297 return ret;
5298 }
bef08b71 5299 location_t close_loc = next_tok->location;
27bf414c 5300 c_parser_consume_token (parser);
5dd9a9d0 5301 ret = pop_init_level (brace_loc, 0, &braced_init_obstack, close_loc);
a1e3b3d9 5302 obstack_free (&braced_init_obstack, NULL);
bef08b71 5303 set_c_expr_source_range (&ret, brace_loc, close_loc);
a1e3b3d9 5304 return ret;
27bf414c
JM
5305}
5306
5307/* Parse a nested initializer, including designators. */
5308
5309static void
a1e3b3d9 5310c_parser_initelt (c_parser *parser, struct obstack * braced_init_obstack)
27bf414c
JM
5311{
5312 /* Parse any designator or designator list. A single array
5313 designator may have the subsequent "=" omitted in GNU C, but a
5314 longer list or a structure member designator may not. */
5315 if (c_parser_next_token_is (parser, CPP_NAME)
5316 && c_parser_peek_2nd_token (parser)->type == CPP_COLON)
5317 {
5318 /* Old-style structure member designator. */
ea58ef42
MP
5319 set_init_label (c_parser_peek_token (parser)->location,
5320 c_parser_peek_token (parser)->value,
f7e4f2e3 5321 c_parser_peek_token (parser)->location,
a1e3b3d9 5322 braced_init_obstack);
fcf73884 5323 /* Use the colon as the error location. */
c1771a20 5324 pedwarn (c_parser_peek_2nd_token (parser)->location, OPT_Wpedantic,
509c9d60 5325 "obsolete use of designated initializer with %<:%>");
27bf414c
JM
5326 c_parser_consume_token (parser);
5327 c_parser_consume_token (parser);
5328 }
5329 else
5330 {
5331 /* des_seen is 0 if there have been no designators, 1 if there
5332 has been a single array designator and 2 otherwise. */
5333 int des_seen = 0;
c7412148 5334 /* Location of a designator. */
922f2908 5335 location_t des_loc = UNKNOWN_LOCATION; /* Quiet warning. */
27bf414c
JM
5336 while (c_parser_next_token_is (parser, CPP_OPEN_SQUARE)
5337 || c_parser_next_token_is (parser, CPP_DOT))
5338 {
5339 int des_prev = des_seen;
c7412148
TT
5340 if (!des_seen)
5341 des_loc = c_parser_peek_token (parser)->location;
27bf414c
JM
5342 if (des_seen < 2)
5343 des_seen++;
5344 if (c_parser_next_token_is (parser, CPP_DOT))
5345 {
5346 des_seen = 2;
5347 c_parser_consume_token (parser);
5348 if (c_parser_next_token_is (parser, CPP_NAME))
5349 {
ea58ef42 5350 set_init_label (des_loc, c_parser_peek_token (parser)->value,
f7e4f2e3 5351 c_parser_peek_token (parser)->location,
a1e3b3d9 5352 braced_init_obstack);
27bf414c
JM
5353 c_parser_consume_token (parser);
5354 }
5355 else
5356 {
5357 struct c_expr init;
913884f7 5358 init.set_error ();
27bf414c 5359 init.original_code = ERROR_MARK;
6866c6e8 5360 init.original_type = NULL;
27bf414c
JM
5361 c_parser_error (parser, "expected identifier");
5362 c_parser_skip_until_found (parser, CPP_COMMA, NULL);
34cf811f
MP
5363 process_init_element (input_location, init, false,
5364 braced_init_obstack);
27bf414c
JM
5365 return;
5366 }
5367 }
5368 else
5369 {
5370 tree first, second;
922f2908 5371 location_t ellipsis_loc = UNKNOWN_LOCATION; /* Quiet warning. */
ea58ef42 5372 location_t array_index_loc = UNKNOWN_LOCATION;
27bf414c
JM
5373 /* ??? Following the old parser, [ objc-receiver
5374 objc-message-args ] is accepted as an initializer,
5375 being distinguished from a designator by what follows
5376 the first assignment expression inside the square
5377 brackets, but after a first array designator a
5378 subsequent square bracket is for Objective-C taken to
5379 start an expression, using the obsolete form of
5380 designated initializer without '=', rather than
5381 possibly being a second level of designation: in LALR
5382 terms, the '[' is shifted rather than reducing
5383 designator to designator-list. */
5384 if (des_prev == 1 && c_dialect_objc ())
5385 {
5386 des_seen = des_prev;
5387 break;
5388 }
5389 if (des_prev == 0 && c_dialect_objc ())
5390 {
5391 /* This might be an array designator or an
5392 Objective-C message expression. If the former,
5393 continue parsing here; if the latter, parse the
5394 remainder of the initializer given the starting
5395 primary-expression. ??? It might make sense to
5396 distinguish when des_prev == 1 as well; see
5397 previous comment. */
5398 tree rec, args;
5399 struct c_expr mexpr;
5400 c_parser_consume_token (parser);
5401 if (c_parser_peek_token (parser)->type == CPP_NAME
5402 && ((c_parser_peek_token (parser)->id_kind
5403 == C_ID_TYPENAME)
5404 || (c_parser_peek_token (parser)->id_kind
5405 == C_ID_CLASSNAME)))
5406 {
5407 /* Type name receiver. */
5408 tree id = c_parser_peek_token (parser)->value;
5409 c_parser_consume_token (parser);
5410 rec = objc_get_class_reference (id);
5411 goto parse_message_args;
5412 }
5413 first = c_parser_expr_no_commas (parser, NULL).value;
ebfbbdc5 5414 mark_exp_read (first);
27bf414c
JM
5415 if (c_parser_next_token_is (parser, CPP_ELLIPSIS)
5416 || c_parser_next_token_is (parser, CPP_CLOSE_SQUARE))
5417 goto array_desig_after_first;
5418 /* Expression receiver. So far only one part
5419 without commas has been parsed; there might be
5420 more of the expression. */
5421 rec = first;
5422 while (c_parser_next_token_is (parser, CPP_COMMA))
5423 {
f2a71bbc 5424 struct c_expr next;
c2255bc4
AH
5425 location_t comma_loc, exp_loc;
5426 comma_loc = c_parser_peek_token (parser)->location;
27bf414c 5427 c_parser_consume_token (parser);
c2255bc4 5428 exp_loc = c_parser_peek_token (parser)->location;
f2a71bbc 5429 next = c_parser_expr_no_commas (parser, NULL);
267bac10
JM
5430 next = convert_lvalue_to_rvalue (exp_loc, next,
5431 true, true);
c2255bc4 5432 rec = build_compound_expr (comma_loc, rec, next.value);
27bf414c
JM
5433 }
5434 parse_message_args:
5435 /* Now parse the objc-message-args. */
5436 args = c_parser_objc_message_args (parser);
5437 c_parser_skip_until_found (parser, CPP_CLOSE_SQUARE,
5438 "expected %<]%>");
5439 mexpr.value
eb345401 5440 = objc_build_message_expr (rec, args);
27bf414c 5441 mexpr.original_code = ERROR_MARK;
6866c6e8 5442 mexpr.original_type = NULL;
27bf414c
JM
5443 /* Now parse and process the remainder of the
5444 initializer, starting with this message
5445 expression as a primary-expression. */
a1e3b3d9 5446 c_parser_initval (parser, &mexpr, braced_init_obstack);
27bf414c
JM
5447 return;
5448 }
5449 c_parser_consume_token (parser);
ea58ef42 5450 array_index_loc = c_parser_peek_token (parser)->location;
27bf414c 5451 first = c_parser_expr_no_commas (parser, NULL).value;
ebfbbdc5 5452 mark_exp_read (first);
27bf414c
JM
5453 array_desig_after_first:
5454 if (c_parser_next_token_is (parser, CPP_ELLIPSIS))
5455 {
c7412148 5456 ellipsis_loc = c_parser_peek_token (parser)->location;
27bf414c
JM
5457 c_parser_consume_token (parser);
5458 second = c_parser_expr_no_commas (parser, NULL).value;
ebfbbdc5 5459 mark_exp_read (second);
27bf414c
JM
5460 }
5461 else
5462 second = NULL_TREE;
5463 if (c_parser_next_token_is (parser, CPP_CLOSE_SQUARE))
5464 {
5465 c_parser_consume_token (parser);
ea58ef42
MP
5466 set_init_index (array_index_loc, first, second,
5467 braced_init_obstack);
fcf73884 5468 if (second)
c1771a20 5469 pedwarn (ellipsis_loc, OPT_Wpedantic,
509c9d60 5470 "ISO C forbids specifying range of elements to initialize");
27bf414c
JM
5471 }
5472 else
5473 c_parser_skip_until_found (parser, CPP_CLOSE_SQUARE,
5474 "expected %<]%>");
5475 }
5476 }
5477 if (des_seen >= 1)
5478 {
5479 if (c_parser_next_token_is (parser, CPP_EQ))
5480 {
f3bede71
MP
5481 pedwarn_c90 (des_loc, OPT_Wpedantic,
5482 "ISO C90 forbids specifying subobject "
5483 "to initialize");
27bf414c
JM
5484 c_parser_consume_token (parser);
5485 }
5486 else
5487 {
5488 if (des_seen == 1)
c1771a20 5489 pedwarn (c_parser_peek_token (parser)->location, OPT_Wpedantic,
509c9d60 5490 "obsolete use of designated initializer without %<=%>");
27bf414c
JM
5491 else
5492 {
5493 struct c_expr init;
913884f7 5494 init.set_error ();
27bf414c 5495 init.original_code = ERROR_MARK;
6866c6e8 5496 init.original_type = NULL;
27bf414c
JM
5497 c_parser_error (parser, "expected %<=%>");
5498 c_parser_skip_until_found (parser, CPP_COMMA, NULL);
34cf811f
MP
5499 process_init_element (input_location, init, false,
5500 braced_init_obstack);
27bf414c
JM
5501 return;
5502 }
5503 }
5504 }
5505 }
a1e3b3d9 5506 c_parser_initval (parser, NULL, braced_init_obstack);
27bf414c
JM
5507}
5508
5509/* Parse a nested initializer; as c_parser_initializer but parses
5510 initializers within braced lists, after any designators have been
5511 applied. If AFTER is not NULL then it is an Objective-C message
5512 expression which is the primary-expression starting the
5513 initializer. */
5514
5515static void
a1e3b3d9
LB
5516c_parser_initval (c_parser *parser, struct c_expr *after,
5517 struct obstack * braced_init_obstack)
27bf414c
JM
5518{
5519 struct c_expr init;
5520 gcc_assert (!after || c_dialect_objc ());
34cf811f
MP
5521 location_t loc = c_parser_peek_token (parser)->location;
5522
27bf414c 5523 if (c_parser_next_token_is (parser, CPP_OPEN_BRACE) && !after)
16595a1f
BS
5524 init = c_parser_braced_init (parser, NULL_TREE, true,
5525 braced_init_obstack);
27bf414c 5526 else
46bdb9cf
JM
5527 {
5528 init = c_parser_expr_no_commas (parser, after);
5529 if (init.value != NULL_TREE
5530 && TREE_CODE (init.value) != STRING_CST
5531 && TREE_CODE (init.value) != COMPOUND_LITERAL_EXPR)
267bac10 5532 init = convert_lvalue_to_rvalue (loc, init, true, true);
46bdb9cf 5533 }
34cf811f 5534 process_init_element (loc, init, false, braced_init_obstack);
27bf414c
JM
5535}
5536
5537/* Parse a compound statement (possibly a function body) (C90 6.6.2,
31dc71a8 5538 C99 6.8.2, C11 6.8.2).
27bf414c
JM
5539
5540 compound-statement:
5541 { block-item-list[opt] }
5542 { label-declarations block-item-list }
5543
5544 block-item-list:
5545 block-item
5546 block-item-list block-item
5547
5548 block-item:
5549 nested-declaration
5550 statement
5551
5552 nested-declaration:
5553 declaration
5554
5555 GNU extensions:
5556
5557 compound-statement:
5558 { label-declarations block-item-list }
5559
5560 nested-declaration:
5561 __extension__ nested-declaration
5562 nested-function-definition
5563
5564 label-declarations:
5565 label-declaration
5566 label-declarations label-declaration
5567
5568 label-declaration:
5569 __label__ identifier-list ;
5570
5571 Allowing the mixing of declarations and code is new in C99. The
5572 GNU syntax also permits (not shown above) labels at the end of
5573 compound statements, which yield an error. We don't allow labels
5574 on declarations; this might seem like a natural extension, but
783bfe5e
JM
5575 there would be a conflict between gnu-attributes on the label and
5576 prefix gnu-attributes on the declaration. ??? The syntax follows the
27bf414c
JM
5577 old parser in requiring something after label declarations.
5578 Although they are erroneous if the labels declared aren't defined,
953ff289 5579 is it useful for the syntax to be this way?
b8698a0f 5580
41dbbb37
TS
5581 OpenACC:
5582
5583 block-item:
5584 openacc-directive
5585
5586 openacc-directive:
5587 update-directive
5588
953ff289 5589 OpenMP:
b8698a0f 5590
953ff289
DN
5591 block-item:
5592 openmp-directive
5593
5594 openmp-directive:
5595 barrier-directive
acf0174b
JJ
5596 flush-directive
5597 taskwait-directive
5598 taskyield-directive
5599 cancel-directive
5600 cancellation-point-directive */
27bf414c
JM
5601
5602static tree
9def91e9 5603c_parser_compound_statement (c_parser *parser, location_t *endlocp)
27bf414c
JM
5604{
5605 tree stmt;
c2255bc4
AH
5606 location_t brace_loc;
5607 brace_loc = c_parser_peek_token (parser)->location;
27bf414c 5608 if (!c_parser_require (parser, CPP_OPEN_BRACE, "expected %<{%>"))
5600f233
JM
5609 {
5610 /* Ensure a scope is entered and left anyway to avoid confusion
5611 if we have just prepared to enter a function body. */
5612 stmt = c_begin_compound_stmt (true);
c2255bc4 5613 c_end_compound_stmt (brace_loc, stmt, true);
5600f233
JM
5614 return error_mark_node;
5615 }
27bf414c 5616 stmt = c_begin_compound_stmt (true);
9def91e9
JJ
5617 location_t end_loc = c_parser_compound_statement_nostart (parser);
5618 if (endlocp)
5619 *endlocp = end_loc;
36536d79 5620
c2255bc4 5621 return c_end_compound_stmt (brace_loc, stmt, true);
27bf414c
JM
5622}
5623
5624/* Parse a compound statement except for the opening brace. This is
5625 used for parsing both compound statements and statement expressions
5626 (which follow different paths to handling the opening). */
5627
9def91e9 5628static location_t
27bf414c
JM
5629c_parser_compound_statement_nostart (c_parser *parser)
5630{
5631 bool last_stmt = false;
5632 bool last_label = false;
6ec637a4 5633 bool save_valid_for_pragma = valid_location_for_stdc_pragma_p ();
3ba09659 5634 location_t label_loc = UNKNOWN_LOCATION; /* Quiet warning. */
27bf414c
JM
5635 if (c_parser_next_token_is (parser, CPP_CLOSE_BRACE))
5636 {
9def91e9
JJ
5637 location_t endloc = c_parser_peek_token (parser)->location;
5638 add_debug_begin_stmt (endloc);
27bf414c 5639 c_parser_consume_token (parser);
9def91e9 5640 return endloc;
27bf414c 5641 }
6ec637a4 5642 mark_valid_location_for_stdc_pragma (true);
27bf414c
JM
5643 if (c_parser_next_token_is_keyword (parser, RID_LABEL))
5644 {
5645 /* Read zero or more forward-declarations for labels that nested
5646 functions can jump to. */
6ec637a4 5647 mark_valid_location_for_stdc_pragma (false);
27bf414c
JM
5648 while (c_parser_next_token_is_keyword (parser, RID_LABEL))
5649 {
c2255bc4 5650 label_loc = c_parser_peek_token (parser)->location;
27bf414c
JM
5651 c_parser_consume_token (parser);
5652 /* Any identifiers, including those declared as type names,
5653 are OK here. */
5654 while (true)
5655 {
5656 tree label;
5657 if (c_parser_next_token_is_not (parser, CPP_NAME))
5658 {
5659 c_parser_error (parser, "expected identifier");
5660 break;
5661 }
5662 label
5663 = declare_label (c_parser_peek_token (parser)->value);
5664 C_DECLARED_LABEL_FLAG (label) = 1;
c2255bc4 5665 add_stmt (build_stmt (label_loc, DECL_EXPR, label));
27bf414c
JM
5666 c_parser_consume_token (parser);
5667 if (c_parser_next_token_is (parser, CPP_COMMA))
5668 c_parser_consume_token (parser);
5669 else
5670 break;
5671 }
5672 c_parser_skip_until_found (parser, CPP_SEMICOLON, "expected %<;%>");
5673 }
c1771a20 5674 pedwarn (label_loc, OPT_Wpedantic, "ISO C forbids label declarations");
27bf414c
JM
5675 }
5676 /* We must now have at least one statement, label or declaration. */
5677 if (c_parser_next_token_is (parser, CPP_CLOSE_BRACE))
5678 {
6ec637a4 5679 mark_valid_location_for_stdc_pragma (save_valid_for_pragma);
27bf414c 5680 c_parser_error (parser, "expected declaration or statement");
9def91e9 5681 location_t endloc = c_parser_peek_token (parser)->location;
27bf414c 5682 c_parser_consume_token (parser);
9def91e9 5683 return endloc;
27bf414c
JM
5684 }
5685 while (c_parser_next_token_is_not (parser, CPP_CLOSE_BRACE))
5686 {
5687 location_t loc = c_parser_peek_token (parser)->location;
2be4dfcb 5688 loc = expansion_point_location_if_in_system_header (loc);
4e03c3a7
JM
5689 /* Standard attributes may start a statement or a declaration. */
5690 bool have_std_attrs
5691 = c_parser_nth_token_starts_std_attributes (parser, 1);
5692 tree std_attrs = NULL_TREE;
5693 if (have_std_attrs)
5694 std_attrs = c_parser_std_attribute_specifier_sequence (parser);
27bf414c
JM
5695 if (c_parser_next_token_is_keyword (parser, RID_CASE)
5696 || c_parser_next_token_is_keyword (parser, RID_DEFAULT)
5697 || (c_parser_next_token_is (parser, CPP_NAME)
5698 && c_parser_peek_2nd_token (parser)->type == CPP_COLON))
5699 {
4e03c3a7 5700 c_warn_unused_attributes (std_attrs);
c7412148
TT
5701 if (c_parser_next_token_is_keyword (parser, RID_CASE))
5702 label_loc = c_parser_peek_2nd_token (parser)->location;
5703 else
5704 label_loc = c_parser_peek_token (parser)->location;
27bf414c
JM
5705 last_label = true;
5706 last_stmt = false;
6ec637a4 5707 mark_valid_location_for_stdc_pragma (false);
27bf414c
JM
5708 c_parser_label (parser);
5709 }
5710 else if (!last_label
4e03c3a7
JM
5711 && (c_parser_next_tokens_start_declaration (parser)
5712 || (have_std_attrs
5713 && c_parser_next_token_is (parser, CPP_SEMICOLON))))
27bf414c
JM
5714 {
5715 last_label = false;
6ec637a4 5716 mark_valid_location_for_stdc_pragma (false);
81fea426 5717 bool fallthru_attr_p = false;
4e03c3a7
JM
5718 c_parser_declaration_or_fndef (parser, true, !have_std_attrs,
5719 true, true, true, NULL,
5720 vNULL, have_std_attrs, std_attrs,
5721 NULL, &fallthru_attr_p);
81fea426 5722 if (last_stmt && !fallthru_attr_p)
177cce46 5723 pedwarn_c90 (loc, OPT_Wdeclaration_after_statement,
509c9d60 5724 "ISO C90 forbids mixed declarations and code");
81fea426 5725 last_stmt = fallthru_attr_p;
27bf414c
JM
5726 }
5727 else if (!last_label
5728 && c_parser_next_token_is_keyword (parser, RID_EXTENSION))
5729 {
5730 /* __extension__ can start a declaration, but is also an
5731 unary operator that can start an expression. Consume all
5732 but the last of a possible series of __extension__ to
4e03c3a7
JM
5733 determine which. If standard attributes have already
5734 been seen, it must start a statement, not a declaration,
5735 but standard attributes starting a declaration may appear
5736 after __extension__. */
27bf414c
JM
5737 while (c_parser_peek_2nd_token (parser)->type == CPP_KEYWORD
5738 && (c_parser_peek_2nd_token (parser)->keyword
5739 == RID_EXTENSION))
5740 c_parser_consume_token (parser);
4e03c3a7
JM
5741 if (!have_std_attrs
5742 && (c_token_starts_declaration (c_parser_peek_2nd_token (parser))
5743 || c_parser_nth_token_starts_std_attributes (parser, 2)))
27bf414c
JM
5744 {
5745 int ext;
5746 ext = disable_extension_diagnostics ();
5747 c_parser_consume_token (parser);
5748 last_label = false;
6ec637a4 5749 mark_valid_location_for_stdc_pragma (false);
32912286 5750 c_parser_declaration_or_fndef (parser, true, true, true, true,
acf0174b 5751 true, NULL, vNULL);
27bf414c
JM
5752 /* Following the old parser, __extension__ does not
5753 disable this diagnostic. */
5754 restore_extension_diagnostics (ext);
fcf73884 5755 if (last_stmt)
177cce46 5756 pedwarn_c90 (loc, OPT_Wdeclaration_after_statement,
509c9d60 5757 "ISO C90 forbids mixed declarations and code");
27bf414c
JM
5758 last_stmt = false;
5759 }
5760 else
5761 goto statement;
5762 }
bc4071dd
RH
5763 else if (c_parser_next_token_is (parser, CPP_PRAGMA))
5764 {
4e03c3a7
JM
5765 if (have_std_attrs)
5766 c_parser_error (parser, "expected declaration or statement");
bc4071dd
RH
5767 /* External pragmas, and some omp pragmas, are not associated
5768 with regular c code, and so are not to be considered statements
5769 syntactically. This ensures that the user doesn't put them
5770 places that would turn into syntax errors if the directive
5771 were ignored. */
aec17bfe 5772 if (c_parser_pragma (parser,
dda1bf61
JJ
5773 last_label ? pragma_stmt : pragma_compound,
5774 NULL))
bc4071dd
RH
5775 last_label = false, last_stmt = true;
5776 }
5777 else if (c_parser_next_token_is (parser, CPP_EOF))
5778 {
6ec637a4 5779 mark_valid_location_for_stdc_pragma (save_valid_for_pragma);
bc4071dd 5780 c_parser_error (parser, "expected declaration or statement");
9def91e9 5781 return c_parser_peek_token (parser)->location;
bc4071dd 5782 }
b4b56033
MLI
5783 else if (c_parser_next_token_is_keyword (parser, RID_ELSE))
5784 {
b8698a0f 5785 if (parser->in_if_block)
b4b56033 5786 {
6ec637a4 5787 mark_valid_location_for_stdc_pragma (save_valid_for_pragma);
92fa0f9e 5788 error_at (loc, "expected %<}%> before %<else%>");
9def91e9 5789 return c_parser_peek_token (parser)->location;
b4b56033 5790 }
b8698a0f 5791 else
b4b56033 5792 {
3ba09659 5793 error_at (loc, "%<else%> without a previous %<if%>");
b4b56033
MLI
5794 c_parser_consume_token (parser);
5795 continue;
5796 }
5797 }
27bf414c
JM
5798 else
5799 {
5800 statement:
4e03c3a7 5801 c_warn_unused_attributes (std_attrs);
27bf414c
JM
5802 last_label = false;
5803 last_stmt = true;
6ec637a4 5804 mark_valid_location_for_stdc_pragma (false);
99cd9857 5805 c_parser_statement_after_labels (parser, NULL);
27bf414c 5806 }
2c14ae9a
VR
5807
5808 parser->error = false;
27bf414c
JM
5809 }
5810 if (last_label)
3ba09659 5811 error_at (label_loc, "label at end of compound statement");
9def91e9 5812 location_t endloc = c_parser_peek_token (parser)->location;
27bf414c 5813 c_parser_consume_token (parser);
6ec637a4
JJ
5814 /* Restore the value we started with. */
5815 mark_valid_location_for_stdc_pragma (save_valid_for_pragma);
9def91e9 5816 return endloc;
27bf414c
JM
5817}
5818
4e03c3a7
JM
5819/* Parse all consecutive labels, possibly preceded by standard
5820 attributes. In this context, a statement is required, not a
5821 declaration, so attributes must be followed by a statement that is
5822 not just a semicolon. */
74d98c1e
AB
5823
5824static void
5825c_parser_all_labels (c_parser *parser)
5826{
4e03c3a7
JM
5827 if (c_parser_nth_token_starts_std_attributes (parser, 1))
5828 {
5829 tree std_attrs = c_parser_std_attribute_specifier_sequence (parser);
5830 if (c_parser_next_token_is (parser, CPP_SEMICOLON))
5831 c_parser_error (parser, "expected statement");
5832 else
5833 c_warn_unused_attributes (std_attrs);
5834 }
74d98c1e
AB
5835 while (c_parser_next_token_is_keyword (parser, RID_CASE)
5836 || c_parser_next_token_is_keyword (parser, RID_DEFAULT)
5837 || (c_parser_next_token_is (parser, CPP_NAME)
5838 && c_parser_peek_2nd_token (parser)->type == CPP_COLON))
5839 c_parser_label (parser);
5840}
5841
31dc71a8 5842/* Parse a label (C90 6.6.1, C99 6.8.1, C11 6.8.1).
27bf414c
JM
5843
5844 label:
783bfe5e 5845 identifier : gnu-attributes[opt]
27bf414c
JM
5846 case constant-expression :
5847 default :
5848
5849 GNU extensions:
5850
5851 label:
5852 case constant-expression ... constant-expression :
5853
783bfe5e 5854 The use of gnu-attributes on labels is a GNU extension. The syntax in
27bf414c 5855 GNU C accepts any expressions without commas, non-constant
4e03c3a7
JM
5856 expressions being rejected later. Any standard
5857 attribute-specifier-sequence before the first label has been parsed
5858 in the caller, to distinguish statements from declarations. Any
5859 attribute-specifier-sequence after the label is parsed in this
5860 function. */
27bf414c
JM
5861
5862static void
5863c_parser_label (c_parser *parser)
5864{
5865 location_t loc1 = c_parser_peek_token (parser)->location;
5866 tree label = NULL_TREE;
81fea426
MP
5867
5868 /* Remember whether this case or a user-defined label is allowed to fall
5869 through to. */
5870 bool fallthrough_p = c_parser_peek_token (parser)->flags & PREV_FALLTHROUGH;
5871
27bf414c
JM
5872 if (c_parser_next_token_is_keyword (parser, RID_CASE))
5873 {
5874 tree exp1, exp2;
5875 c_parser_consume_token (parser);
5876 exp1 = c_parser_expr_no_commas (parser, NULL).value;
5877 if (c_parser_next_token_is (parser, CPP_COLON))
5878 {
5879 c_parser_consume_token (parser);
c2255bc4 5880 label = do_case (loc1, exp1, NULL_TREE);
27bf414c
JM
5881 }
5882 else if (c_parser_next_token_is (parser, CPP_ELLIPSIS))
5883 {
5884 c_parser_consume_token (parser);
5885 exp2 = c_parser_expr_no_commas (parser, NULL).value;
5886 if (c_parser_require (parser, CPP_COLON, "expected %<:%>"))
c2255bc4 5887 label = do_case (loc1, exp1, exp2);
27bf414c
JM
5888 }
5889 else
5890 c_parser_error (parser, "expected %<:%> or %<...%>");
5891 }
5892 else if (c_parser_next_token_is_keyword (parser, RID_DEFAULT))
5893 {
5894 c_parser_consume_token (parser);
5895 if (c_parser_require (parser, CPP_COLON, "expected %<:%>"))
c2255bc4 5896 label = do_case (loc1, NULL_TREE, NULL_TREE);
27bf414c
JM
5897 }
5898 else
5899 {
5900 tree name = c_parser_peek_token (parser)->value;
5901 tree tlab;
27bf414c 5902 tree attrs;
c7412148 5903 location_t loc2 = c_parser_peek_token (parser)->location;
27bf414c
JM
5904 gcc_assert (c_parser_next_token_is (parser, CPP_NAME));
5905 c_parser_consume_token (parser);
5906 gcc_assert (c_parser_next_token_is (parser, CPP_COLON));
27bf414c 5907 c_parser_consume_token (parser);
783bfe5e 5908 attrs = c_parser_gnu_attributes (parser);
27bf414c
JM
5909 tlab = define_label (loc2, name);
5910 if (tlab)
5911 {
5912 decl_attributes (&tlab, attrs, 0);
c2255bc4 5913 label = add_stmt (build_stmt (loc1, LABEL_EXPR, tlab));
27bf414c
JM
5914 }
5915 }
5916 if (label)
3d57f0f0 5917 {
81fea426
MP
5918 if (TREE_CODE (label) == LABEL_EXPR)
5919 FALLTHROUGH_LABEL_P (LABEL_EXPR_LABEL (label)) = fallthrough_p;
5920 else
5921 FALLTHROUGH_LABEL_P (CASE_LABEL (label)) = fallthrough_p;
5922
4e03c3a7
JM
5923 /* Standard attributes are only allowed here if they start a
5924 statement, not a declaration (including the case of an
5925 attribute-declaration with only attributes). */
5926 bool have_std_attrs
5927 = c_parser_nth_token_starts_std_attributes (parser, 1);
5928 tree std_attrs = NULL_TREE;
5929 if (have_std_attrs)
5930 std_attrs = c_parser_std_attribute_specifier_sequence (parser);
5931
81fea426 5932 /* Allow '__attribute__((fallthrough));'. */
4e03c3a7
JM
5933 if (!have_std_attrs
5934 && c_parser_next_token_is_keyword (parser, RID_ATTRIBUTE))
81fea426
MP
5935 {
5936 location_t loc = c_parser_peek_token (parser)->location;
783bfe5e 5937 tree attrs = c_parser_gnu_attributes (parser);
81fea426
MP
5938 if (attribute_fallthrough_p (attrs))
5939 {
5940 if (c_parser_next_token_is (parser, CPP_SEMICOLON))
5941 {
5942 tree fn = build_call_expr_internal_loc (loc,
5943 IFN_FALLTHROUGH,
5944 void_type_node, 0);
5945 add_stmt (fn);
5946 }
5947 else
5948 warning_at (loc, OPT_Wattributes, "%<fallthrough%> attribute "
5949 "not followed by %<;%>");
5950 }
5951 else if (attrs != NULL_TREE)
5952 warning_at (loc, OPT_Wattributes, "only attribute %<fallthrough%>"
5953 " can be applied to a null statement");
5954 }
4e03c3a7
JM
5955 if (c_parser_next_tokens_start_declaration (parser)
5956 || (have_std_attrs
5957 && c_parser_next_token_is (parser, CPP_SEMICOLON)))
3d57f0f0 5958 {
3ba09659
AH
5959 error_at (c_parser_peek_token (parser)->location,
5960 "a label can only be part of a statement and "
5961 "a declaration is not a statement");
b8698a0f 5962 c_parser_declaration_or_fndef (parser, /*fndef_ok*/ false,
32912286 5963 /*static_assert_ok*/ true,
6265d07c 5964 /*empty_ok*/ true, /*nested*/ true,
acf0174b 5965 /*start_attr_ok*/ true, NULL,
4e03c3a7 5966 vNULL, have_std_attrs, std_attrs);
3d57f0f0 5967 }
4e03c3a7
JM
5968 else if (std_attrs)
5969 /* Nonempty attributes on the following statement are ignored. */
5970 c_warn_unused_attributes (std_attrs);
3d57f0f0 5971 }
27bf414c
JM
5972}
5973
31dc71a8 5974/* Parse a statement (C90 6.6, C99 6.8, C11 6.8).
27bf414c
JM
5975
5976 statement:
5977 labeled-statement
4e03c3a7 5978 attribute-specifier-sequence[opt] compound-statement
27bf414c 5979 expression-statement
4e03c3a7
JM
5980 attribute-specifier-sequence[opt] selection-statement
5981 attribute-specifier-sequence[opt] iteration-statement
5982 attribute-specifier-sequence[opt] jump-statement
27bf414c
JM
5983
5984 labeled-statement:
4e03c3a7 5985 attribute-specifier-sequence[opt] label statement
27bf414c
JM
5986
5987 expression-statement:
5988 expression[opt] ;
4e03c3a7 5989 attribute-specifier-sequence expression ;
27bf414c
JM
5990
5991 selection-statement:
5992 if-statement
5993 switch-statement
5994
5995 iteration-statement:
5996 while-statement
5997 do-statement
5998 for-statement
5999
6000 jump-statement:
6001 goto identifier ;
6002 continue ;
6003 break ;
6004 return expression[opt] ;
6005
6006 GNU extensions:
6007
6008 statement:
4e03c3a7 6009 attribute-specifier-sequence[opt] asm-statement
27bf414c
JM
6010
6011 jump-statement:
6012 goto * expression ;
6013
81fea426 6014 expression-statement:
783bfe5e 6015 gnu-attributes ;
81fea426 6016
27bf414c
JM
6017 Objective-C:
6018
6019 statement:
4e03c3a7
JM
6020 attribute-specifier-sequence[opt] objc-throw-statement
6021 attribute-specifier-sequence[opt] objc-try-catch-statement
6022 attribute-specifier-sequence[opt] objc-synchronized-statement
27bf414c
JM
6023
6024 objc-throw-statement:
6025 @throw expression ;
6026 @throw ;
953ff289 6027
41dbbb37
TS
6028 OpenACC:
6029
6030 statement:
4e03c3a7 6031 attribute-specifier-sequence[opt] openacc-construct
41dbbb37
TS
6032
6033 openacc-construct:
6034 parallel-construct
6035 kernels-construct
6036 data-construct
6037 loop-construct
6038
6039 parallel-construct:
6040 parallel-directive structured-block
6041
6042 kernels-construct:
6043 kernels-directive structured-block
6044
6045 data-construct:
6046 data-directive structured-block
6047
6048 loop-construct:
6049 loop-directive structured-block
6050
953ff289
DN
6051 OpenMP:
6052
6053 statement:
4e03c3a7 6054 attribute-specifier-sequence[opt] openmp-construct
953ff289
DN
6055
6056 openmp-construct:
6057 parallel-construct
6058 for-construct
acf0174b
JJ
6059 simd-construct
6060 for-simd-construct
953ff289
DN
6061 sections-construct
6062 single-construct
6063 parallel-for-construct
acf0174b 6064 parallel-for-simd-construct
953ff289
DN
6065 parallel-sections-construct
6066 master-construct
6067 critical-construct
6068 atomic-construct
6069 ordered-construct
6070
6071 parallel-construct:
6072 parallel-directive structured-block
6073
6074 for-construct:
6075 for-directive iteration-statement
6076
acf0174b
JJ
6077 simd-construct:
6078 simd-directive iteration-statements
6079
6080 for-simd-construct:
6081 for-simd-directive iteration-statements
6082
953ff289
DN
6083 sections-construct:
6084 sections-directive section-scope
6085
6086 single-construct:
6087 single-directive structured-block
6088
6089 parallel-for-construct:
6090 parallel-for-directive iteration-statement
6091
acf0174b
JJ
6092 parallel-for-simd-construct:
6093 parallel-for-simd-directive iteration-statement
6094
953ff289
DN
6095 parallel-sections-construct:
6096 parallel-sections-directive section-scope
6097
6098 master-construct:
6099 master-directive structured-block
6100
6101 critical-construct:
6102 critical-directive structured-block
6103
6104 atomic-construct:
6105 atomic-directive expression-statement
6106
6107 ordered-construct:
0a35513e
AH
6108 ordered-directive structured-block
6109
6110 Transactional Memory:
6111
6112 statement:
4e03c3a7
JM
6113 attribute-specifier-sequence[opt] transaction-statement
6114 attribute-specifier-sequence[opt] transaction-cancel-statement
99cd9857
MP
6115
6116 IF_P is used to track whether there's a (possibly labeled) if statement
6117 which is not enclosed in braces and has an else clause. This is used to
6118 implement -Wparentheses. */
27bf414c
JM
6119
6120static void
3e2becc4 6121c_parser_statement (c_parser *parser, bool *if_p, location_t *loc_after_labels)
27bf414c 6122{
74d98c1e 6123 c_parser_all_labels (parser);
3e2becc4
MP
6124 if (loc_after_labels)
6125 *loc_after_labels = c_parser_peek_token (parser)->location;
99cd9857 6126 c_parser_statement_after_labels (parser, if_p, NULL);
27bf414c
JM
6127}
6128
3e3b8d63 6129/* Parse a statement, other than a labeled statement. CHAIN is a vector
4e03c3a7
JM
6130 of if-else-if conditions. All labels and standard attributes have
6131 been parsed in the caller.
99cd9857
MP
6132
6133 IF_P is used to track whether there's a (possibly labeled) if statement
6134 which is not enclosed in braces and has an else clause. This is used to
6135 implement -Wparentheses. */
27bf414c
JM
6136
6137static void
99cd9857
MP
6138c_parser_statement_after_labels (c_parser *parser, bool *if_p,
6139 vec<tree> *chain)
27bf414c
JM
6140{
6141 location_t loc = c_parser_peek_token (parser)->location;
6142 tree stmt = NULL_TREE;
b4b56033
MLI
6143 bool in_if_block = parser->in_if_block;
6144 parser->in_if_block = false;
99cd9857
MP
6145 if (if_p != NULL)
6146 *if_p = false;
96a95ac1
AO
6147
6148 if (c_parser_peek_token (parser)->type != CPP_OPEN_BRACE)
6149 add_debug_begin_stmt (loc);
6150
27bf414c
JM
6151 switch (c_parser_peek_token (parser)->type)
6152 {
6153 case CPP_OPEN_BRACE:
6154 add_stmt (c_parser_compound_statement (parser));
6155 break;
6156 case CPP_KEYWORD:
6157 switch (c_parser_peek_token (parser)->keyword)
6158 {
6159 case RID_IF:
99cd9857 6160 c_parser_if_statement (parser, if_p, chain);
27bf414c
JM
6161 break;
6162 case RID_SWITCH:
351f85c5 6163 c_parser_switch_statement (parser, if_p);
27bf414c
JM
6164 break;
6165 case RID_WHILE:
170a8bd6 6166 c_parser_while_statement (parser, false, 0, if_p);
27bf414c
JM
6167 break;
6168 case RID_DO:
170a8bd6 6169 c_parser_do_statement (parser, 0, false);
27bf414c
JM
6170 break;
6171 case RID_FOR:
170a8bd6 6172 c_parser_for_statement (parser, false, 0, if_p);
27bf414c
JM
6173 break;
6174 case RID_GOTO:
6175 c_parser_consume_token (parser);
6176 if (c_parser_next_token_is (parser, CPP_NAME))
6177 {
c2255bc4
AH
6178 stmt = c_finish_goto_label (loc,
6179 c_parser_peek_token (parser)->value);
27bf414c
JM
6180 c_parser_consume_token (parser);
6181 }
6182 else if (c_parser_next_token_is (parser, CPP_MULT))
6183 {
267bac10 6184 struct c_expr val;
84628aa8 6185
27bf414c 6186 c_parser_consume_token (parser);
267bac10
JM
6187 val = c_parser_expression (parser);
6188 val = convert_lvalue_to_rvalue (loc, val, false, true);
6189 stmt = c_finish_goto_ptr (loc, val.value);
27bf414c
JM
6190 }
6191 else
6192 c_parser_error (parser, "expected identifier or %<*%>");
6193 goto expect_semicolon;
6194 case RID_CONTINUE:
6195 c_parser_consume_token (parser);
c2255bc4 6196 stmt = c_finish_bc_stmt (loc, &c_cont_label, false);
27bf414c
JM
6197 goto expect_semicolon;
6198 case RID_BREAK:
6199 c_parser_consume_token (parser);
c2255bc4 6200 stmt = c_finish_bc_stmt (loc, &c_break_label, true);
27bf414c
JM
6201 goto expect_semicolon;
6202 case RID_RETURN:
6203 c_parser_consume_token (parser);
6204 if (c_parser_next_token_is (parser, CPP_SEMICOLON))
6205 {
c2255bc4 6206 stmt = c_finish_return (loc, NULL_TREE, NULL_TREE);
27bf414c
JM
6207 c_parser_consume_token (parser);
6208 }
6209 else
6210 {
6e07c515 6211 location_t xloc = c_parser_peek_token (parser)->location;
bbbbb16a 6212 struct c_expr expr = c_parser_expression_conv (parser);
ebfbbdc5 6213 mark_exp_read (expr.value);
94c40e19
DM
6214 stmt = c_finish_return (EXPR_LOC_OR_LOC (expr.value, xloc),
6215 expr.value, expr.original_type);
27bf414c
JM
6216 goto expect_semicolon;
6217 }
6218 break;
6219 case RID_ASM:
6220 stmt = c_parser_asm_statement (parser);
6221 break;
0a35513e
AH
6222 case RID_TRANSACTION_ATOMIC:
6223 case RID_TRANSACTION_RELAXED:
6224 stmt = c_parser_transaction (parser,
6225 c_parser_peek_token (parser)->keyword);
6226 break;
6227 case RID_TRANSACTION_CANCEL:
6228 stmt = c_parser_transaction_cancel (parser);
6229 goto expect_semicolon;
49b91f05 6230 case RID_AT_THROW:
27bf414c
JM
6231 gcc_assert (c_dialect_objc ());
6232 c_parser_consume_token (parser);
6233 if (c_parser_next_token_is (parser, CPP_SEMICOLON))
6234 {
c2255bc4 6235 stmt = objc_build_throw_stmt (loc, NULL_TREE);
27bf414c
JM
6236 c_parser_consume_token (parser);
6237 }
6238 else
6239 {
267bac10
JM
6240 struct c_expr expr = c_parser_expression (parser);
6241 expr = convert_lvalue_to_rvalue (loc, expr, false, false);
5e9d6aa4
JK
6242 expr.value = c_fully_fold (expr.value, false, NULL);
6243 stmt = objc_build_throw_stmt (loc, expr.value);
27bf414c
JM
6244 goto expect_semicolon;
6245 }
6246 break;
49b91f05 6247 case RID_AT_TRY:
27bf414c 6248 gcc_assert (c_dialect_objc ());
437c2322 6249 c_parser_objc_try_catch_finally_statement (parser);
27bf414c
JM
6250 break;
6251 case RID_AT_SYNCHRONIZED:
6252 gcc_assert (c_dialect_objc ());
6253 c_parser_objc_synchronized_statement (parser);
6254 break;
81fea426
MP
6255 case RID_ATTRIBUTE:
6256 {
6257 /* Allow '__attribute__((fallthrough));'. */
783bfe5e 6258 tree attrs = c_parser_gnu_attributes (parser);
81fea426
MP
6259 if (attribute_fallthrough_p (attrs))
6260 {
6261 if (c_parser_next_token_is (parser, CPP_SEMICOLON))
6262 {
6263 tree fn = build_call_expr_internal_loc (loc,
6264 IFN_FALLTHROUGH,
6265 void_type_node, 0);
6266 add_stmt (fn);
6267 /* Eat the ';'. */
6268 c_parser_consume_token (parser);
6269 }
6270 else
6271 warning_at (loc, OPT_Wattributes,
6272 "%<fallthrough%> attribute not followed "
6273 "by %<;%>");
6274 }
6275 else if (attrs != NULL_TREE)
6276 warning_at (loc, OPT_Wattributes, "only attribute %<fallthrough%>"
6277 " can be applied to a null statement");
6278 break;
6279 }
27bf414c
JM
6280 default:
6281 goto expr_stmt;
6282 }
6283 break;
6284 case CPP_SEMICOLON:
6285 c_parser_consume_token (parser);
6286 break;
6287 case CPP_CLOSE_PAREN:
6288 case CPP_CLOSE_SQUARE:
6289 /* Avoid infinite loop in error recovery:
6290 c_parser_skip_until_found stops at a closing nesting
6291 delimiter without consuming it, but here we need to consume
6292 it to proceed further. */
6293 c_parser_error (parser, "expected statement");
6294 c_parser_consume_token (parser);
6295 break;
bc4071dd 6296 case CPP_PRAGMA:
dda1bf61 6297 c_parser_pragma (parser, pragma_stmt, if_p);
bc4071dd 6298 break;
27bf414c
JM
6299 default:
6300 expr_stmt:
c2255bc4 6301 stmt = c_finish_expr_stmt (loc, c_parser_expression_conv (parser).value);
27bf414c
JM
6302 expect_semicolon:
6303 c_parser_skip_until_found (parser, CPP_SEMICOLON, "expected %<;%>");
6304 break;
6305 }
6306 /* Two cases cannot and do not have line numbers associated: If stmt
6307 is degenerate, such as "2;", then stmt is an INTEGER_CST, which
6308 cannot hold line numbers. But that's OK because the statement
6309 will either be changed to a MODIFY_EXPR during gimplification of
6310 the statement expr, or discarded. If stmt was compound, but
6311 without new variables, we will have skipped the creation of a
6312 BIND and will have a bare STATEMENT_LIST. But that's OK because
6313 (recursively) all of the component statements should already have
6314 line numbers assigned. ??? Can we discard no-op statements
6315 earlier? */
21ba0cea
MP
6316 if (EXPR_LOCATION (stmt) == UNKNOWN_LOCATION)
6317 protected_set_expr_location (stmt, loc);
b4b56033
MLI
6318
6319 parser->in_if_block = in_if_block;
27bf414c
JM
6320}
6321
ca085fd7
MLI
6322/* Parse the condition from an if, do, while or for statements. */
6323
6324static tree
6325c_parser_condition (c_parser *parser)
6326{
c2255bc4 6327 location_t loc = c_parser_peek_token (parser)->location;
ca085fd7 6328 tree cond;
928c19bb
JM
6329 cond = c_parser_expression_conv (parser).value;
6330 cond = c_objc_common_truthvalue_conversion (loc, cond);
6331 cond = c_fully_fold (cond, false, NULL);
ca085fd7
MLI
6332 if (warn_sequence_point)
6333 verify_sequence_points (cond);
6334 return cond;
6335}
6336
27bf414c
JM
6337/* Parse a parenthesized condition from an if, do or while statement.
6338
6339 condition:
6340 ( expression )
6341*/
6342static tree
6343c_parser_paren_condition (c_parser *parser)
6344{
27bf414c 6345 tree cond;
32129a17
DM
6346 matching_parens parens;
6347 if (!parens.require_open (parser))
27bf414c 6348 return error_mark_node;
ca085fd7 6349 cond = c_parser_condition (parser);
32129a17 6350 parens.skip_until_found_close (parser);
27bf414c
JM
6351 return cond;
6352}
6353
99cd9857
MP
6354/* Parse a statement which is a block in C99.
6355
6356 IF_P is used to track whether there's a (possibly labeled) if statement
6357 which is not enclosed in braces and has an else clause. This is used to
6358 implement -Wparentheses. */
27bf414c
JM
6359
6360static tree
3e2becc4
MP
6361c_parser_c99_block_statement (c_parser *parser, bool *if_p,
6362 location_t *loc_after_labels)
27bf414c
JM
6363{
6364 tree block = c_begin_compound_stmt (flag_isoc99);
c2255bc4 6365 location_t loc = c_parser_peek_token (parser)->location;
3e2becc4 6366 c_parser_statement (parser, if_p, loc_after_labels);
c2255bc4 6367 return c_end_compound_stmt (loc, block, flag_isoc99);
27bf414c
JM
6368}
6369
b4b56033
MLI
6370/* Parse the body of an if statement. This is just parsing a
6371 statement but (a) it is a block in C99, (b) we track whether the
6372 body is an if statement for the sake of -Wparentheses warnings, (c)
6373 we handle an empty body specially for the sake of -Wempty-body
6374 warnings, and (d) we call parser_compound_statement directly
6375 because c_parser_statement_after_labels resets
99cd9857
MP
6376 parser->in_if_block.
6377
6378 IF_P is used to track whether there's a (possibly labeled) if statement
6379 which is not enclosed in braces and has an else clause. This is used to
6380 implement -Wparentheses. */
27bf414c
JM
6381
6382static tree
992118a1
PP
6383c_parser_if_body (c_parser *parser, bool *if_p,
6384 const token_indent_info &if_tinfo)
27bf414c
JM
6385{
6386 tree block = c_begin_compound_stmt (flag_isoc99);
c2255bc4 6387 location_t body_loc = c_parser_peek_token (parser)->location;
3e2becc4 6388 location_t body_loc_after_labels = UNKNOWN_LOCATION;
992118a1
PP
6389 token_indent_info body_tinfo
6390 = get_token_indent_info (c_parser_peek_token (parser));
6391
74d98c1e 6392 c_parser_all_labels (parser);
62e00e94 6393 if (c_parser_next_token_is (parser, CPP_SEMICOLON))
b4b56033 6394 {
626c34b5 6395 location_t loc = c_parser_peek_token (parser)->location;
c2255bc4 6396 add_stmt (build_empty_stmt (loc));
b4b56033 6397 c_parser_consume_token (parser);
626c34b5
PB
6398 if (!c_parser_next_token_is_keyword (parser, RID_ELSE))
6399 warning_at (loc, OPT_Wempty_body,
6400 "suggest braces around empty body in an %<if%> statement");
b4b56033
MLI
6401 }
6402 else if (c_parser_next_token_is (parser, CPP_OPEN_BRACE))
6403 add_stmt (c_parser_compound_statement (parser));
6404 else
3e2becc4
MP
6405 {
6406 body_loc_after_labels = c_parser_peek_token (parser)->location;
6407 c_parser_statement_after_labels (parser, if_p);
6408 }
992118a1
PP
6409
6410 token_indent_info next_tinfo
6411 = get_token_indent_info (c_parser_peek_token (parser));
6412 warn_for_misleading_indentation (if_tinfo, body_tinfo, next_tinfo);
3e2becc4
MP
6413 if (body_loc_after_labels != UNKNOWN_LOCATION
6414 && next_tinfo.type != CPP_SEMICOLON)
6415 warn_for_multistatement_macros (body_loc_after_labels, next_tinfo.location,
6416 if_tinfo.location, RID_IF);
c3388e62 6417
c2255bc4 6418 return c_end_compound_stmt (body_loc, block, flag_isoc99);
b4b56033
MLI
6419}
6420
6421/* Parse the else body of an if statement. This is just parsing a
6422 statement but (a) it is a block in C99, (b) we handle an empty body
3e3b8d63
MP
6423 specially for the sake of -Wempty-body warnings. CHAIN is a vector
6424 of if-else-if conditions. */
b4b56033
MLI
6425
6426static tree
3e3b8d63
MP
6427c_parser_else_body (c_parser *parser, const token_indent_info &else_tinfo,
6428 vec<tree> *chain)
b4b56033 6429{
c3388e62 6430 location_t body_loc = c_parser_peek_token (parser)->location;
b4b56033 6431 tree block = c_begin_compound_stmt (flag_isoc99);
992118a1
PP
6432 token_indent_info body_tinfo
6433 = get_token_indent_info (c_parser_peek_token (parser));
3e2becc4 6434 location_t body_loc_after_labels = UNKNOWN_LOCATION;
992118a1 6435
74d98c1e 6436 c_parser_all_labels (parser);
b4b56033
MLI
6437 if (c_parser_next_token_is (parser, CPP_SEMICOLON))
6438 {
c2255bc4
AH
6439 location_t loc = c_parser_peek_token (parser)->location;
6440 warning_at (loc,
626c34b5
PB
6441 OPT_Wempty_body,
6442 "suggest braces around empty body in an %<else%> statement");
c2255bc4 6443 add_stmt (build_empty_stmt (loc));
b4b56033
MLI
6444 c_parser_consume_token (parser);
6445 }
b8698a0f 6446 else
3e2becc4 6447 {
d49718d6
MP
6448 if (!c_parser_next_token_is (parser, CPP_OPEN_BRACE))
6449 body_loc_after_labels = c_parser_peek_token (parser)->location;
3e2becc4
MP
6450 c_parser_statement_after_labels (parser, NULL, chain);
6451 }
992118a1
PP
6452
6453 token_indent_info next_tinfo
6454 = get_token_indent_info (c_parser_peek_token (parser));
6455 warn_for_misleading_indentation (else_tinfo, body_tinfo, next_tinfo);
3e2becc4
MP
6456 if (body_loc_after_labels != UNKNOWN_LOCATION
6457 && next_tinfo.type != CPP_SEMICOLON)
6458 warn_for_multistatement_macros (body_loc_after_labels, next_tinfo.location,
6459 else_tinfo.location, RID_ELSE);
992118a1 6460
c3388e62 6461 return c_end_compound_stmt (body_loc, block, flag_isoc99);
27bf414c
JM
6462}
6463
2448a956
MP
6464/* We might need to reclassify any previously-lexed identifier, e.g.
6465 when we've left a for loop with an if-statement without else in the
6466 body - we might have used a wrong scope for the token. See PR67784. */
6467
6468static void
6469c_parser_maybe_reclassify_token (c_parser *parser)
6470{
6471 if (c_parser_next_token_is (parser, CPP_NAME))
6472 {
6473 c_token *token = c_parser_peek_token (parser);
6474
6475 if (token->id_kind != C_ID_CLASSNAME)
6476 {
6477 tree decl = lookup_name (token->value);
6478
6479 token->id_kind = C_ID_ID;
6480 if (decl)
6481 {
6482 if (TREE_CODE (decl) == TYPE_DECL)
6483 token->id_kind = C_ID_TYPENAME;
6484 }
6485 else if (c_dialect_objc ())
6486 {
6487 tree objc_interface_decl = objc_is_class_name (token->value);
6488 /* Objective-C class names are in the same namespace as
6489 variables and typedefs, and hence are shadowed by local
6490 declarations. */
6491 if (objc_interface_decl)
6492 {
6493 token->value = objc_interface_decl;
6494 token->id_kind = C_ID_CLASSNAME;
6495 }
6496 }
6497 }
6498 }
6499}
6500
31dc71a8 6501/* Parse an if statement (C90 6.6.4, C99 6.8.4, C11 6.8.4).
27bf414c
JM
6502
6503 if-statement:
6504 if ( expression ) statement
6505 if ( expression ) statement else statement
3e3b8d63 6506
99cd9857
MP
6507 CHAIN is a vector of if-else-if conditions.
6508 IF_P is used to track whether there's a (possibly labeled) if statement
6509 which is not enclosed in braces and has an else clause. This is used to
6510 implement -Wparentheses. */
27bf414c
JM
6511
6512static void
99cd9857 6513c_parser_if_statement (c_parser *parser, bool *if_p, vec<tree> *chain)
27bf414c
JM
6514{
6515 tree block;
6516 location_t loc;
6517 tree cond;
99cd9857 6518 bool nested_if = false;
27bf414c 6519 tree first_body, second_body;
b4b56033
MLI
6520 bool in_if_block;
6521
27bf414c 6522 gcc_assert (c_parser_next_token_is_keyword (parser, RID_IF));
992118a1
PP
6523 token_indent_info if_tinfo
6524 = get_token_indent_info (c_parser_peek_token (parser));
27bf414c
JM
6525 c_parser_consume_token (parser);
6526 block = c_begin_compound_stmt (flag_isoc99);
6527 loc = c_parser_peek_token (parser)->location;
6528 cond = c_parser_paren_condition (parser);
b4b56033
MLI
6529 in_if_block = parser->in_if_block;
6530 parser->in_if_block = true;
99cd9857 6531 first_body = c_parser_if_body (parser, &nested_if, if_tinfo);
b4b56033 6532 parser->in_if_block = in_if_block;
3e3b8d63
MP
6533
6534 if (warn_duplicated_cond)
6535 warn_duplicated_cond_add_or_warn (EXPR_LOCATION (cond), cond, &chain);
6536
27bf414c
JM
6537 if (c_parser_next_token_is_keyword (parser, RID_ELSE))
6538 {
992118a1
PP
6539 token_indent_info else_tinfo
6540 = get_token_indent_info (c_parser_peek_token (parser));
27bf414c 6541 c_parser_consume_token (parser);
3e3b8d63
MP
6542 if (warn_duplicated_cond)
6543 {
6544 if (c_parser_next_token_is_keyword (parser, RID_IF)
6545 && chain == NULL)
6546 {
6547 /* We've got "if (COND) else if (COND2)". Start the
6548 condition chain and add COND as the first element. */
6549 chain = new vec<tree> ();
6550 if (!CONSTANT_CLASS_P (cond) && !TREE_SIDE_EFFECTS (cond))
6551 chain->safe_push (cond);
6552 }
6553 else if (!c_parser_next_token_is_keyword (parser, RID_IF))
6554 {
6555 /* This is if-else without subsequent if. Zap the condition
6556 chain; we would have already warned at this point. */
6557 delete chain;
6558 chain = NULL;
6559 }
6560 }
6561 second_body = c_parser_else_body (parser, else_tinfo, chain);
99cd9857
MP
6562 /* Set IF_P to true to indicate that this if statement has an
6563 else clause. This may trigger the Wparentheses warning
6564 below when we get back up to the parent if statement. */
6565 if (if_p != NULL)
6566 *if_p = true;
27bf414c
JM
6567 }
6568 else
3e3b8d63
MP
6569 {
6570 second_body = NULL_TREE;
99cd9857
MP
6571
6572 /* Diagnose an ambiguous else if if-then-else is nested inside
6573 if-then. */
6574 if (nested_if)
deef7113 6575 warning_at (loc, OPT_Wdangling_else,
99cd9857
MP
6576 "suggest explicit braces to avoid ambiguous %<else%>");
6577
3e3b8d63
MP
6578 if (warn_duplicated_cond)
6579 {
6580 /* This if statement does not have an else clause. We don't
6581 need the condition chain anymore. */
6582 delete chain;
6583 chain = NULL;
6584 }
6585 }
99cd9857 6586 c_finish_if_stmt (loc, cond, first_body, second_body);
5e9d6aa4 6587 add_stmt (c_end_compound_stmt (loc, block, flag_isoc99));
36536d79 6588
2448a956 6589 c_parser_maybe_reclassify_token (parser);
27bf414c
JM
6590}
6591
31dc71a8 6592/* Parse a switch statement (C90 6.6.4, C99 6.8.4, C11 6.8.4).
27bf414c
JM
6593
6594 switch-statement:
6595 switch (expression) statement
6596*/
6597
6598static void
351f85c5 6599c_parser_switch_statement (c_parser *parser, bool *if_p)
27bf414c 6600{
267bac10 6601 struct c_expr ce;
27bf414c 6602 tree block, expr, body, save_break;
c2255bc4
AH
6603 location_t switch_loc = c_parser_peek_token (parser)->location;
6604 location_t switch_cond_loc;
27bf414c
JM
6605 gcc_assert (c_parser_next_token_is_keyword (parser, RID_SWITCH));
6606 c_parser_consume_token (parser);
6607 block = c_begin_compound_stmt (flag_isoc99);
fedfecef 6608 bool explicit_cast_p = false;
32129a17
DM
6609 matching_parens parens;
6610 if (parens.require_open (parser))
27bf414c 6611 {
c2255bc4 6612 switch_cond_loc = c_parser_peek_token (parser)->location;
fedfecef
MP
6613 if (c_parser_next_token_is (parser, CPP_OPEN_PAREN)
6614 && c_token_starts_typename (c_parser_peek_2nd_token (parser)))
6615 explicit_cast_p = true;
267bac10 6616 ce = c_parser_expression (parser);
f9eb0973 6617 ce = convert_lvalue_to_rvalue (switch_cond_loc, ce, true, true);
267bac10 6618 expr = ce.value;
e5e44252 6619 /* ??? expr has no valid location? */
32129a17 6620 parens.skip_until_found_close (parser);
27bf414c
JM
6621 }
6622 else
c2255bc4
AH
6623 {
6624 switch_cond_loc = UNKNOWN_LOCATION;
6625 expr = error_mark_node;
efd0786f 6626 ce.original_type = error_mark_node;
c2255bc4 6627 }
fedfecef 6628 c_start_case (switch_loc, switch_cond_loc, expr, explicit_cast_p);
27bf414c
JM
6629 save_break = c_break_label;
6630 c_break_label = NULL_TREE;
3e2becc4
MP
6631 location_t loc_after_labels;
6632 bool open_brace_p = c_parser_peek_token (parser)->type == CPP_OPEN_BRACE;
6633 body = c_parser_c99_block_statement (parser, if_p, &loc_after_labels);
6634 location_t next_loc = c_parser_peek_token (parser)->location;
6635 if (!open_brace_p && c_parser_peek_token (parser)->type != CPP_SEMICOLON)
6636 warn_for_multistatement_macros (loc_after_labels, next_loc, switch_loc,
6637 RID_SWITCH);
27bf414c 6638 if (c_break_label)
c2255bc4
AH
6639 {
6640 location_t here = c_parser_peek_token (parser)->location;
6641 tree t = build1 (LABEL_EXPR, void_type_node, c_break_label);
6642 SET_EXPR_LOCATION (t, here);
65791f42
JJ
6643 SWITCH_BREAK_LABEL_P (c_break_label) = 1;
6644 append_to_statement_list_force (t, &body);
c2255bc4 6645 }
65791f42 6646 c_finish_case (body, ce.original_type);
27bf414c 6647 c_break_label = save_break;
c2255bc4 6648 add_stmt (c_end_compound_stmt (switch_loc, block, flag_isoc99));
2448a956 6649 c_parser_maybe_reclassify_token (parser);
27bf414c
JM
6650}
6651
31dc71a8 6652/* Parse a while statement (C90 6.6.5, C99 6.8.5, C11 6.8.5).
27bf414c
JM
6653
6654 while-statement:
6655 while (expression) statement
99cd9857
MP
6656
6657 IF_P is used to track whether there's a (possibly labeled) if statement
6658 which is not enclosed in braces and has an else clause. This is used to
6659 implement -Wparentheses. */
27bf414c
JM
6660
6661static void
170a8bd6
EB
6662c_parser_while_statement (c_parser *parser, bool ivdep, unsigned short unroll,
6663 bool *if_p)
27bf414c
JM
6664{
6665 tree block, cond, body, save_break, save_cont;
6666 location_t loc;
6667 gcc_assert (c_parser_next_token_is_keyword (parser, RID_WHILE));
992118a1
PP
6668 token_indent_info while_tinfo
6669 = get_token_indent_info (c_parser_peek_token (parser));
27bf414c
JM
6670 c_parser_consume_token (parser);
6671 block = c_begin_compound_stmt (flag_isoc99);
6672 loc = c_parser_peek_token (parser)->location;
6673 cond = c_parser_paren_condition (parser);
d4af74d4 6674 if (ivdep && cond != error_mark_node)
ac9effed 6675 cond = build3 (ANNOTATE_EXPR, TREE_TYPE (cond), cond,
d4af74d4 6676 build_int_cst (integer_type_node,
ac9effed
EB
6677 annot_expr_ivdep_kind),
6678 integer_zero_node);
170a8bd6
EB
6679 if (unroll && cond != error_mark_node)
6680 cond = build3 (ANNOTATE_EXPR, TREE_TYPE (cond), cond,
6681 build_int_cst (integer_type_node,
6682 annot_expr_unroll_kind),
6683 build_int_cst (integer_type_node, unroll));
27bf414c
JM
6684 save_break = c_break_label;
6685 c_break_label = NULL_TREE;
6686 save_cont = c_cont_label;
6687 c_cont_label = NULL_TREE;
c3388e62 6688
992118a1
PP
6689 token_indent_info body_tinfo
6690 = get_token_indent_info (c_parser_peek_token (parser));
6691
3e2becc4 6692 location_t loc_after_labels;
d49718d6 6693 bool open_brace = c_parser_next_token_is (parser, CPP_OPEN_BRACE);
3e2becc4 6694 body = c_parser_c99_block_statement (parser, if_p, &loc_after_labels);
f179b64e
JJ
6695 c_finish_loop (loc, loc, cond, UNKNOWN_LOCATION, NULL, body,
6696 c_break_label, c_cont_label, true);
f6b0b3db 6697 add_stmt (c_end_compound_stmt (loc, block, flag_isoc99));
2448a956 6698 c_parser_maybe_reclassify_token (parser);
992118a1
PP
6699
6700 token_indent_info next_tinfo
6701 = get_token_indent_info (c_parser_peek_token (parser));
6702 warn_for_misleading_indentation (while_tinfo, body_tinfo, next_tinfo);
c3388e62 6703
d49718d6 6704 if (next_tinfo.type != CPP_SEMICOLON && !open_brace)
3e2becc4
MP
6705 warn_for_multistatement_macros (loc_after_labels, next_tinfo.location,
6706 while_tinfo.location, RID_WHILE);
6707
27bf414c
JM
6708 c_break_label = save_break;
6709 c_cont_label = save_cont;
6710}
6711
31dc71a8 6712/* Parse a do statement (C90 6.6.5, C99 6.8.5, C11 6.8.5).
27bf414c
JM
6713
6714 do-statement:
6715 do statement while ( expression ) ;
6716*/
6717
6718static void
170a8bd6 6719c_parser_do_statement (c_parser *parser, bool ivdep, unsigned short unroll)
27bf414c
JM
6720{
6721 tree block, cond, body, save_break, save_cont, new_break, new_cont;
6722 location_t loc;
6723 gcc_assert (c_parser_next_token_is_keyword (parser, RID_DO));
6724 c_parser_consume_token (parser);
62e00e94 6725 if (c_parser_next_token_is (parser, CPP_SEMICOLON))
3ba09659
AH
6726 warning_at (c_parser_peek_token (parser)->location,
6727 OPT_Wempty_body,
6728 "suggest braces around empty body in %<do%> statement");
27bf414c
JM
6729 block = c_begin_compound_stmt (flag_isoc99);
6730 loc = c_parser_peek_token (parser)->location;
6731 save_break = c_break_label;
6732 c_break_label = NULL_TREE;
6733 save_cont = c_cont_label;
6734 c_cont_label = NULL_TREE;
99cd9857 6735 body = c_parser_c99_block_statement (parser, NULL);
27bf414c
JM
6736 c_parser_require_keyword (parser, RID_WHILE, "expected %<while%>");
6737 new_break = c_break_label;
6738 c_break_label = save_break;
6739 new_cont = c_cont_label;
6740 c_cont_label = save_cont;
f179b64e 6741 location_t cond_loc = c_parser_peek_token (parser)->location;
27bf414c 6742 cond = c_parser_paren_condition (parser);
d4af74d4 6743 if (ivdep && cond != error_mark_node)
ac9effed 6744 cond = build3 (ANNOTATE_EXPR, TREE_TYPE (cond), cond,
d4af74d4 6745 build_int_cst (integer_type_node,
ac9effed
EB
6746 annot_expr_ivdep_kind),
6747 integer_zero_node);
170a8bd6
EB
6748 if (unroll && cond != error_mark_node)
6749 cond = build3 (ANNOTATE_EXPR, TREE_TYPE (cond), cond,
6750 build_int_cst (integer_type_node,
6751 annot_expr_unroll_kind),
6752 build_int_cst (integer_type_node, unroll));
27bf414c
JM
6753 if (!c_parser_require (parser, CPP_SEMICOLON, "expected %<;%>"))
6754 c_parser_skip_to_end_of_block_or_statement (parser);
f179b64e
JJ
6755 c_finish_loop (loc, cond_loc, cond, UNKNOWN_LOCATION, NULL, body,
6756 new_break, new_cont, false);
c2255bc4 6757 add_stmt (c_end_compound_stmt (loc, block, flag_isoc99));
27bf414c
JM
6758}
6759
31dc71a8 6760/* Parse a for statement (C90 6.6.5, C99 6.8.5, C11 6.8.5).
27bf414c
JM
6761
6762 for-statement:
6763 for ( expression[opt] ; expression[opt] ; expression[opt] ) statement
6764 for ( nested-declaration expression[opt] ; expression[opt] ) statement
6765
6766 The form with a declaration is new in C99.
6767
6768 ??? In accordance with the old parser, the declaration may be a
6769 nested function, which is then rejected in check_for_loop_decls,
6770 but does it make any sense for this to be included in the grammar?
6771 Note in particular that the nested function does not include a
6772 trailing ';', whereas the "declaration" production includes one.
6773 Also, can we reject bad declarations earlier and cheaper than
f05b9d93
NP
6774 check_for_loop_decls?
6775
6776 In Objective-C, there are two additional variants:
6777
6778 foreach-statement:
6779 for ( expression in expresssion ) statement
6780 for ( declaration in expression ) statement
6781
6782 This is inconsistent with C, because the second variant is allowed
6783 even if c99 is not enabled.
6784
6785 The rest of the comment documents these Objective-C foreach-statement.
6786
6787 Here is the canonical example of the first variant:
6788 for (object in array) { do something with object }
6789 we call the first expression ("object") the "object_expression" and
6790 the second expression ("array") the "collection_expression".
6791 object_expression must be an lvalue of type "id" (a generic Objective-C
6792 object) because the loop works by assigning to object_expression the
6793 various objects from the collection_expression. collection_expression
6794 must evaluate to something of type "id" which responds to the method
6795 countByEnumeratingWithState:objects:count:.
6796
6797 The canonical example of the second variant is:
6798 for (id object in array) { do something with object }
6799 which is completely equivalent to
6800 {
6801 id object;
6802 for (object in array) { do something with object }
6803 }
6804 Note that initizializing 'object' in some way (eg, "for ((object =
6805 xxx) in array) { do something with object }") is possibly
6806 technically valid, but completely pointless as 'object' will be
6807 assigned to something else as soon as the loop starts. We should
6808 most likely reject it (TODO).
6809
6810 The beginning of the Objective-C foreach-statement looks exactly
6811 like the beginning of the for-statement, and we can tell it is a
6812 foreach-statement only because the initial declaration or
6813 expression is terminated by 'in' instead of ';'.
99cd9857
MP
6814
6815 IF_P is used to track whether there's a (possibly labeled) if statement
6816 which is not enclosed in braces and has an else clause. This is used to
6817 implement -Wparentheses. */
27bf414c
JM
6818
6819static void
170a8bd6
EB
6820c_parser_for_statement (c_parser *parser, bool ivdep, unsigned short unroll,
6821 bool *if_p)
27bf414c
JM
6822{
6823 tree block, cond, incr, save_break, save_cont, body;
f05b9d93 6824 /* The following are only used when parsing an ObjC foreach statement. */
689f2c82
AO
6825 tree object_expression;
6826 /* Silence the bogus uninitialized warning. */
6827 tree collection_expression = NULL;
c2255bc4 6828 location_t loc = c_parser_peek_token (parser)->location;
f179b64e
JJ
6829 location_t for_loc = loc;
6830 location_t cond_loc = UNKNOWN_LOCATION;
6831 location_t incr_loc = UNKNOWN_LOCATION;
f05b9d93 6832 bool is_foreach_statement = false;
27bf414c 6833 gcc_assert (c_parser_next_token_is_keyword (parser, RID_FOR));
992118a1
PP
6834 token_indent_info for_tinfo
6835 = get_token_indent_info (c_parser_peek_token (parser));
27bf414c 6836 c_parser_consume_token (parser);
f05b9d93
NP
6837 /* Open a compound statement in Objective-C as well, just in case this is
6838 as foreach expression. */
6839 block = c_begin_compound_stmt (flag_isoc99 || c_dialect_objc ());
91b90ead
UB
6840 cond = error_mark_node;
6841 incr = error_mark_node;
32129a17
DM
6842 matching_parens parens;
6843 if (parens.require_open (parser))
27bf414c
JM
6844 {
6845 /* Parse the initialization declaration or expression. */
f05b9d93 6846 object_expression = error_mark_node;
a5812bdc 6847 parser->objc_could_be_foreach_context = c_dialect_objc ();
27bf414c
JM
6848 if (c_parser_next_token_is (parser, CPP_SEMICOLON))
6849 {
a5812bdc 6850 parser->objc_could_be_foreach_context = false;
27bf414c 6851 c_parser_consume_token (parser);
c2255bc4 6852 c_finish_expr_stmt (loc, NULL_TREE);
27bf414c 6853 }
4e03c3a7
JM
6854 else if (c_parser_next_tokens_start_declaration (parser)
6855 || c_parser_nth_token_starts_std_attributes (parser, 1))
27bf414c 6856 {
f05b9d93 6857 c_parser_declaration_or_fndef (parser, true, true, true, true, true,
acf0174b 6858 &object_expression, vNULL);
f05b9d93
NP
6859 parser->objc_could_be_foreach_context = false;
6860
6861 if (c_parser_next_token_is_keyword (parser, RID_IN))
6862 {
6863 c_parser_consume_token (parser);
6864 is_foreach_statement = true;
6865 if (check_for_loop_decls (for_loc, true) == NULL_TREE)
f179b64e
JJ
6866 c_parser_error (parser, "multiple iterating variables in "
6867 "fast enumeration");
f05b9d93
NP
6868 }
6869 else
6870 check_for_loop_decls (for_loc, flag_isoc99);
27bf414c
JM
6871 }
6872 else if (c_parser_next_token_is_keyword (parser, RID_EXTENSION))
6873 {
6874 /* __extension__ can start a declaration, but is also an
6875 unary operator that can start an expression. Consume all
6876 but the last of a possible series of __extension__ to
6877 determine which. */
6878 while (c_parser_peek_2nd_token (parser)->type == CPP_KEYWORD
6879 && (c_parser_peek_2nd_token (parser)->keyword
6880 == RID_EXTENSION))
6881 c_parser_consume_token (parser);
4e03c3a7
JM
6882 if (c_token_starts_declaration (c_parser_peek_2nd_token (parser))
6883 || c_parser_nth_token_starts_std_attributes (parser, 2))
27bf414c
JM
6884 {
6885 int ext;
6886 ext = disable_extension_diagnostics ();
6887 c_parser_consume_token (parser);
32912286 6888 c_parser_declaration_or_fndef (parser, true, true, true, true,
acf0174b 6889 true, &object_expression, vNULL);
f05b9d93
NP
6890 parser->objc_could_be_foreach_context = false;
6891
27bf414c 6892 restore_extension_diagnostics (ext);
f05b9d93
NP
6893 if (c_parser_next_token_is_keyword (parser, RID_IN))
6894 {
6895 c_parser_consume_token (parser);
6896 is_foreach_statement = true;
6897 if (check_for_loop_decls (for_loc, true) == NULL_TREE)
f179b64e
JJ
6898 c_parser_error (parser, "multiple iterating variables in "
6899 "fast enumeration");
f05b9d93
NP
6900 }
6901 else
6902 check_for_loop_decls (for_loc, flag_isoc99);
27bf414c
JM
6903 }
6904 else
6905 goto init_expr;
6906 }
6907 else
6908 {
6909 init_expr:
f05b9d93 6910 {
267bac10 6911 struct c_expr ce;
f05b9d93 6912 tree init_expression;
267bac10
JM
6913 ce = c_parser_expression (parser);
6914 init_expression = ce.value;
f05b9d93
NP
6915 parser->objc_could_be_foreach_context = false;
6916 if (c_parser_next_token_is_keyword (parser, RID_IN))
6917 {
6918 c_parser_consume_token (parser);
6919 is_foreach_statement = true;
6920 if (! lvalue_p (init_expression))
f179b64e
JJ
6921 c_parser_error (parser, "invalid iterating variable in "
6922 "fast enumeration");
6923 object_expression
6924 = c_fully_fold (init_expression, false, NULL);
f05b9d93
NP
6925 }
6926 else
6927 {
267bac10
JM
6928 ce = convert_lvalue_to_rvalue (loc, ce, true, false);
6929 init_expression = ce.value;
f05b9d93 6930 c_finish_expr_stmt (loc, init_expression);
f179b64e
JJ
6931 c_parser_skip_until_found (parser, CPP_SEMICOLON,
6932 "expected %<;%>");
f05b9d93
NP
6933 }
6934 }
27bf414c 6935 }
f05b9d93
NP
6936 /* Parse the loop condition. In the case of a foreach
6937 statement, there is no loop condition. */
a5812bdc 6938 gcc_assert (!parser->objc_could_be_foreach_context);
f05b9d93 6939 if (!is_foreach_statement)
27bf414c 6940 {
f179b64e 6941 cond_loc = c_parser_peek_token (parser)->location;
f05b9d93
NP
6942 if (c_parser_next_token_is (parser, CPP_SEMICOLON))
6943 {
8170608b
TB
6944 if (ivdep)
6945 {
f179b64e
JJ
6946 c_parser_error (parser, "missing loop condition in loop "
6947 "with %<GCC ivdep%> pragma");
8170608b
TB
6948 cond = error_mark_node;
6949 }
170a8bd6
EB
6950 else if (unroll)
6951 {
f179b64e
JJ
6952 c_parser_error (parser, "missing loop condition in loop "
6953 "with %<GCC unroll%> pragma");
170a8bd6
EB
6954 cond = error_mark_node;
6955 }
8170608b
TB
6956 else
6957 {
6958 c_parser_consume_token (parser);
6959 cond = NULL_TREE;
6960 }
f05b9d93
NP
6961 }
6962 else
6963 {
6964 cond = c_parser_condition (parser);
36536d79
BI
6965 c_parser_skip_until_found (parser, CPP_SEMICOLON,
6966 "expected %<;%>");
f05b9d93 6967 }
8170608b 6968 if (ivdep && cond != error_mark_node)
ac9effed 6969 cond = build3 (ANNOTATE_EXPR, TREE_TYPE (cond), cond,
8170608b 6970 build_int_cst (integer_type_node,
ac9effed
EB
6971 annot_expr_ivdep_kind),
6972 integer_zero_node);
170a8bd6
EB
6973 if (unroll && cond != error_mark_node)
6974 cond = build3 (ANNOTATE_EXPR, TREE_TYPE (cond), cond,
6975 build_int_cst (integer_type_node,
6976 annot_expr_unroll_kind),
6977 build_int_cst (integer_type_node, unroll));
27bf414c 6978 }
f05b9d93
NP
6979 /* Parse the increment expression (the third expression in a
6980 for-statement). In the case of a foreach-statement, this is
6981 the expression that follows the 'in'. */
f179b64e 6982 loc = incr_loc = c_parser_peek_token (parser)->location;
f05b9d93 6983 if (c_parser_next_token_is (parser, CPP_CLOSE_PAREN))
27bf414c 6984 {
f05b9d93
NP
6985 if (is_foreach_statement)
6986 {
f179b64e
JJ
6987 c_parser_error (parser,
6988 "missing collection in fast enumeration");
f05b9d93
NP
6989 collection_expression = error_mark_node;
6990 }
6991 else
6992 incr = c_process_expr_stmt (loc, NULL_TREE);
27bf414c 6993 }
27bf414c 6994 else
f05b9d93
NP
6995 {
6996 if (is_foreach_statement)
f179b64e
JJ
6997 collection_expression
6998 = c_fully_fold (c_parser_expression (parser).value, false, NULL);
f05b9d93 6999 else
267bac10
JM
7000 {
7001 struct c_expr ce = c_parser_expression (parser);
7002 ce = convert_lvalue_to_rvalue (loc, ce, true, false);
7003 incr = c_process_expr_stmt (loc, ce.value);
7004 }
f05b9d93 7005 }
32129a17 7006 parens.skip_until_found_close (parser);
27bf414c 7007 }
27bf414c
JM
7008 save_break = c_break_label;
7009 c_break_label = NULL_TREE;
7010 save_cont = c_cont_label;
7011 c_cont_label = NULL_TREE;
c3388e62 7012
992118a1
PP
7013 token_indent_info body_tinfo
7014 = get_token_indent_info (c_parser_peek_token (parser));
7015
3e2becc4 7016 location_t loc_after_labels;
d49718d6 7017 bool open_brace = c_parser_next_token_is (parser, CPP_OPEN_BRACE);
3e2becc4 7018 body = c_parser_c99_block_statement (parser, if_p, &loc_after_labels);
992118a1 7019
f05b9d93 7020 if (is_foreach_statement)
f179b64e
JJ
7021 objc_finish_foreach_loop (for_loc, object_expression,
7022 collection_expression, body, c_break_label,
7023 c_cont_label);
f05b9d93 7024 else
f179b64e
JJ
7025 c_finish_loop (for_loc, cond_loc, cond, incr_loc, incr, body,
7026 c_break_label, c_cont_label, true);
7027 add_stmt (c_end_compound_stmt (for_loc, block,
7028 flag_isoc99 || c_dialect_objc ()));
2448a956 7029 c_parser_maybe_reclassify_token (parser);
9be4f715 7030
f6b0b3db
AA
7031 token_indent_info next_tinfo
7032 = get_token_indent_info (c_parser_peek_token (parser));
7033 warn_for_misleading_indentation (for_tinfo, body_tinfo, next_tinfo);
7034
d49718d6 7035 if (next_tinfo.type != CPP_SEMICOLON && !open_brace)
3e2becc4
MP
7036 warn_for_multistatement_macros (loc_after_labels, next_tinfo.location,
7037 for_tinfo.location, RID_FOR);
7038
27bf414c
JM
7039 c_break_label = save_break;
7040 c_cont_label = save_cont;
7041}
7042
7043/* Parse an asm statement, a GNU extension. This is a full-blown asm
5b76e75f
SB
7044 statement with inputs, outputs, clobbers, and volatile, inline, and goto
7045 tags allowed.
27bf414c 7046
30bd42b9
SB
7047 asm-qualifier:
7048 volatile
5b76e75f 7049 inline
30bd42b9
SB
7050 goto
7051
7052 asm-qualifier-list:
7053 asm-qualifier-list asm-qualifier
7054 asm-qualifier
7055
27bf414c 7056 asm-statement:
30bd42b9 7057 asm asm-qualifier-list[opt] ( asm-argument ) ;
27bf414c
JM
7058
7059 asm-argument:
7060 asm-string-literal
7061 asm-string-literal : asm-operands[opt]
7062 asm-string-literal : asm-operands[opt] : asm-operands[opt]
30bd42b9
SB
7063 asm-string-literal : asm-operands[opt] : asm-operands[opt] \
7064 : asm-clobbers[opt]
1c384bf1
RH
7065 asm-string-literal : : asm-operands[opt] : asm-clobbers[opt] \
7066 : asm-goto-operands
27bf414c 7067
30bd42b9
SB
7068 The form with asm-goto-operands is valid if and only if the
7069 asm-qualifier-list contains goto, and is the only allowed form in that case.
93313b94
JM
7070 Duplicate asm-qualifiers are not allowed.
7071
7072 The :: token is considered equivalent to two consecutive : tokens. */
27bf414c
JM
7073
7074static tree
7075c_parser_asm_statement (c_parser *parser)
7076{
db4fd626
SB
7077 tree str, outputs, inputs, clobbers, labels, ret;
7078 bool simple;
c2255bc4 7079 location_t asm_loc = c_parser_peek_token (parser)->location;
1c384bf1
RH
7080 int section, nsections;
7081
27bf414c
JM
7082 gcc_assert (c_parser_next_token_is_keyword (parser, RID_ASM));
7083 c_parser_consume_token (parser);
1c384bf1 7084
db4fd626
SB
7085 /* Handle the asm-qualifier-list. */
7086 location_t volatile_loc = UNKNOWN_LOCATION;
7087 location_t inline_loc = UNKNOWN_LOCATION;
7088 location_t goto_loc = UNKNOWN_LOCATION;
9c9cfcbb
SB
7089 for (;;)
7090 {
db4fd626
SB
7091 c_token *token = c_parser_peek_token (parser);
7092 location_t loc = token->location;
7093 switch (token->keyword)
9c9cfcbb
SB
7094 {
7095 case RID_VOLATILE:
db4fd626
SB
7096 if (volatile_loc)
7097 {
a9c697b8 7098 error_at (loc, "duplicate %<asm%> qualifier %qE", token->value);
db4fd626
SB
7099 inform (volatile_loc, "first seen here");
7100 }
7101 else
7102 volatile_loc = loc;
9c9cfcbb
SB
7103 c_parser_consume_token (parser);
7104 continue;
7105
7106 case RID_INLINE:
db4fd626
SB
7107 if (inline_loc)
7108 {
a9c697b8 7109 error_at (loc, "duplicate %<asm%> qualifier %qE", token->value);
db4fd626
SB
7110 inform (inline_loc, "first seen here");
7111 }
7112 else
7113 inline_loc = loc;
9c9cfcbb
SB
7114 c_parser_consume_token (parser);
7115 continue;
7116
7117 case RID_GOTO:
db4fd626
SB
7118 if (goto_loc)
7119 {
a9c697b8 7120 error_at (loc, "duplicate %<asm%> qualifier %qE", token->value);
db4fd626
SB
7121 inform (goto_loc, "first seen here");
7122 }
7123 else
7124 goto_loc = loc;
9c9cfcbb
SB
7125 c_parser_consume_token (parser);
7126 continue;
7127
1edf8866
SB
7128 case RID_CONST:
7129 case RID_RESTRICT:
a9c697b8 7130 error_at (loc, "%qE is not a valid %<asm%> qualifier", token->value);
1edf8866
SB
7131 c_parser_consume_token (parser);
7132 continue;
7133
9c9cfcbb
SB
7134 default:
7135 break;
7136 }
7137 break;
7138 }
1c384bf1 7139
db4fd626
SB
7140 bool is_volatile = (volatile_loc != UNKNOWN_LOCATION);
7141 bool is_inline = (inline_loc != UNKNOWN_LOCATION);
7142 bool is_goto = (goto_loc != UNKNOWN_LOCATION);
7143
1c384bf1
RH
7144 ret = NULL;
7145
32129a17
DM
7146 matching_parens parens;
7147 if (!parens.require_open (parser))
1c384bf1
RH
7148 goto error;
7149
27bf414c 7150 str = c_parser_asm_string_literal (parser);
b85eb797 7151 if (str == NULL_TREE)
1c384bf1
RH
7152 goto error_close_paren;
7153
7154 simple = true;
7155 outputs = NULL_TREE;
7156 inputs = NULL_TREE;
7157 clobbers = NULL_TREE;
7158 labels = NULL_TREE;
7159
7160 if (c_parser_next_token_is (parser, CPP_CLOSE_PAREN) && !is_goto)
7161 goto done_asm;
7162
7163 /* Parse each colon-delimited section of operands. */
7164 nsections = 3 + is_goto;
7165 for (section = 0; section < nsections; ++section)
b85eb797 7166 {
93313b94
JM
7167 if (c_parser_next_token_is (parser, CPP_SCOPE))
7168 {
7169 ++section;
7170 if (section == nsections)
7171 {
7172 c_parser_error (parser, "expected %<)%>");
7173 goto error_close_paren;
7174 }
7175 c_parser_consume_token (parser);
7176 }
7177 else if (!c_parser_require (parser, CPP_COLON,
7178 is_goto
7179 ? G_("expected %<:%>")
7180 : G_("expected %<:%> or %<)%>"),
7181 UNKNOWN_LOCATION, is_goto))
1c384bf1
RH
7182 goto error_close_paren;
7183
7184 /* Once past any colon, we're no longer a simple asm. */
7185 simple = false;
7186
7187 if ((!c_parser_next_token_is (parser, CPP_COLON)
93313b94 7188 && !c_parser_next_token_is (parser, CPP_SCOPE)
1c384bf1
RH
7189 && !c_parser_next_token_is (parser, CPP_CLOSE_PAREN))
7190 || section == 3)
7191 switch (section)
7192 {
7193 case 0:
7194 /* For asm goto, we don't allow output operands, but reserve
7195 the slot for a future extension that does allow them. */
7196 if (!is_goto)
eadd3d0d 7197 outputs = c_parser_asm_operands (parser);
1c384bf1
RH
7198 break;
7199 case 1:
eadd3d0d 7200 inputs = c_parser_asm_operands (parser);
1c384bf1
RH
7201 break;
7202 case 2:
7203 clobbers = c_parser_asm_clobbers (parser);
7204 break;
7205 case 3:
7206 labels = c_parser_asm_goto_operands (parser);
7207 break;
7208 default:
7209 gcc_unreachable ();
7210 }
7211
7212 if (c_parser_next_token_is (parser, CPP_CLOSE_PAREN) && !is_goto)
7213 goto done_asm;
27bf414c 7214 }
1c384bf1 7215
27bf414c 7216 done_asm:
32129a17 7217 if (!parens.require_close (parser))
27bf414c
JM
7218 {
7219 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN, NULL);
1c384bf1 7220 goto error;
27bf414c 7221 }
1c384bf1 7222
27bf414c
JM
7223 if (!c_parser_require (parser, CPP_SEMICOLON, "expected %<;%>"))
7224 c_parser_skip_to_end_of_block_or_statement (parser);
1c384bf1 7225
db4fd626
SB
7226 ret = build_asm_stmt (is_volatile,
7227 build_asm_expr (asm_loc, str, outputs, inputs,
7228 clobbers, labels, simple, is_inline));
1c384bf1
RH
7229
7230 error:
27bf414c 7231 return ret;
1c384bf1
RH
7232
7233 error_close_paren:
7234 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN, NULL);
7235 goto error;
27bf414c
JM
7236}
7237
eadd3d0d 7238/* Parse asm operands, a GNU extension.
27bf414c
JM
7239
7240 asm-operands:
7241 asm-operand
7242 asm-operands , asm-operand
7243
7244 asm-operand:
7245 asm-string-literal ( expression )
7246 [ identifier ] asm-string-literal ( expression )
7247*/
7248
7249static tree
eadd3d0d 7250c_parser_asm_operands (c_parser *parser)
27bf414c
JM
7251{
7252 tree list = NULL_TREE;
7253 while (true)
7254 {
f2a71bbc
JM
7255 tree name, str;
7256 struct c_expr expr;
27bf414c
JM
7257 if (c_parser_next_token_is (parser, CPP_OPEN_SQUARE))
7258 {
7259 c_parser_consume_token (parser);
7260 if (c_parser_next_token_is (parser, CPP_NAME))
7261 {
7262 tree id = c_parser_peek_token (parser)->value;
7263 c_parser_consume_token (parser);
7264 name = build_string (IDENTIFIER_LENGTH (id),
7265 IDENTIFIER_POINTER (id));
7266 }
7267 else
7268 {
7269 c_parser_error (parser, "expected identifier");
7270 c_parser_skip_until_found (parser, CPP_CLOSE_SQUARE, NULL);
7271 return NULL_TREE;
7272 }
7273 c_parser_skip_until_found (parser, CPP_CLOSE_SQUARE,
7274 "expected %<]%>");
7275 }
7276 else
7277 name = NULL_TREE;
7278 str = c_parser_asm_string_literal (parser);
7279 if (str == NULL_TREE)
7280 return NULL_TREE;
32129a17
DM
7281 matching_parens parens;
7282 if (!parens.require_open (parser))
471c5330 7283 return NULL_TREE;
f2a71bbc 7284 expr = c_parser_expression (parser);
ebfbbdc5 7285 mark_exp_read (expr.value);
32129a17 7286 if (!parens.require_close (parser))
27bf414c
JM
7287 {
7288 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN, NULL);
7289 return NULL_TREE;
7290 }
7291 list = chainon (list, build_tree_list (build_tree_list (name, str),
f2a71bbc 7292 expr.value));
27bf414c
JM
7293 if (c_parser_next_token_is (parser, CPP_COMMA))
7294 c_parser_consume_token (parser);
7295 else
7296 break;
7297 }
7298 return list;
7299}
7300
7301/* Parse asm clobbers, a GNU extension.
7302
7303 asm-clobbers:
7304 asm-string-literal
7305 asm-clobbers , asm-string-literal
7306*/
7307
7308static tree
7309c_parser_asm_clobbers (c_parser *parser)
7310{
7311 tree list = NULL_TREE;
7312 while (true)
7313 {
7314 tree str = c_parser_asm_string_literal (parser);
7315 if (str)
7316 list = tree_cons (NULL_TREE, str, list);
7317 else
7318 return NULL_TREE;
7319 if (c_parser_next_token_is (parser, CPP_COMMA))
7320 c_parser_consume_token (parser);
7321 else
7322 break;
7323 }
7324 return list;
7325}
7326
1c384bf1 7327/* Parse asm goto labels, a GNU extension.
b8698a0f 7328
1c384bf1
RH
7329 asm-goto-operands:
7330 identifier
7331 asm-goto-operands , identifier
7332*/
7333
7334static tree
7335c_parser_asm_goto_operands (c_parser *parser)
7336{
7337 tree list = NULL_TREE;
7338 while (true)
7339 {
7340 tree name, label;
7341
7342 if (c_parser_next_token_is (parser, CPP_NAME))
7343 {
7344 c_token *tok = c_parser_peek_token (parser);
7345 name = tok->value;
7346 label = lookup_label_for_goto (tok->location, name);
7347 c_parser_consume_token (parser);
7348 TREE_USED (label) = 1;
7349 }
7350 else
7351 {
7352 c_parser_error (parser, "expected identifier");
7353 return NULL_TREE;
7354 }
7355
7356 name = build_string (IDENTIFIER_LENGTH (name),
7357 IDENTIFIER_POINTER (name));
7358 list = tree_cons (name, label, list);
7359 if (c_parser_next_token_is (parser, CPP_COMMA))
7360 c_parser_consume_token (parser);
7361 else
7362 return nreverse (list);
7363 }
7364}
7365
471c5330
JM
7366/* Parse a possibly concatenated sequence of string literals.
7367 TRANSLATE says whether to translate them to the execution character
7368 set; WIDE_OK says whether any kind of prefixed string literal is
7369 permitted in this context. This code is based on that in
7370 lex_string. */
7371
7372struct c_expr
7373c_parser_string_literal (c_parser *parser, bool translate, bool wide_ok)
7374{
7375 struct c_expr ret;
7376 size_t count;
7377 struct obstack str_ob;
7378 struct obstack loc_ob;
7379 cpp_string str, istr, *strs;
7380 c_token *tok;
7381 location_t loc, last_tok_loc;
7382 enum cpp_ttype type;
7383 tree value, string_tree;
7384
7385 tok = c_parser_peek_token (parser);
7386 loc = tok->location;
7387 last_tok_loc = linemap_resolve_location (line_table, loc,
7388 LRK_MACRO_DEFINITION_LOCATION,
7389 NULL);
7390 type = tok->type;
7391 switch (type)
7392 {
7393 case CPP_STRING:
7394 case CPP_WSTRING:
7395 case CPP_STRING16:
7396 case CPP_STRING32:
7397 case CPP_UTF8STRING:
7398 string_tree = tok->value;
7399 break;
7400
7401 default:
7402 c_parser_error (parser, "expected string literal");
7403 ret.set_error ();
7404 ret.value = NULL_TREE;
7405 ret.original_code = ERROR_MARK;
7406 ret.original_type = NULL_TREE;
7407 return ret;
7408 }
7409
7410 /* Try to avoid the overhead of creating and destroying an obstack
7411 for the common case of just one string. */
7412 switch (c_parser_peek_2nd_token (parser)->type)
7413 {
7414 default:
7415 c_parser_consume_token (parser);
7416 str.text = (const unsigned char *) TREE_STRING_POINTER (string_tree);
7417 str.len = TREE_STRING_LENGTH (string_tree);
7418 count = 1;
7419 strs = &str;
7420 break;
7421
7422 case CPP_STRING:
7423 case CPP_WSTRING:
7424 case CPP_STRING16:
7425 case CPP_STRING32:
7426 case CPP_UTF8STRING:
7427 gcc_obstack_init (&str_ob);
7428 gcc_obstack_init (&loc_ob);
7429 count = 0;
7430 do
7431 {
7432 c_parser_consume_token (parser);
7433 count++;
7434 str.text = (const unsigned char *) TREE_STRING_POINTER (string_tree);
7435 str.len = TREE_STRING_LENGTH (string_tree);
7436 if (type != tok->type)
7437 {
7438 if (type == CPP_STRING)
7439 type = tok->type;
7440 else if (tok->type != CPP_STRING)
7441 error ("unsupported non-standard concatenation "
7442 "of string literals");
7443 }
7444 obstack_grow (&str_ob, &str, sizeof (cpp_string));
7445 obstack_grow (&loc_ob, &last_tok_loc, sizeof (location_t));
7446 tok = c_parser_peek_token (parser);
7447 string_tree = tok->value;
7448 last_tok_loc
7449 = linemap_resolve_location (line_table, tok->location,
7450 LRK_MACRO_DEFINITION_LOCATION, NULL);
7451 }
7452 while (tok->type == CPP_STRING
7453 || tok->type == CPP_WSTRING
7454 || tok->type == CPP_STRING16
7455 || tok->type == CPP_STRING32
7456 || tok->type == CPP_UTF8STRING);
7457 strs = (cpp_string *) obstack_finish (&str_ob);
7458 }
7459
7460 if (count > 1 && !in_system_header_at (input_location))
7461 warning (OPT_Wtraditional,
7462 "traditional C rejects string constant concatenation");
7463
7464 if ((type == CPP_STRING || wide_ok)
7465 && ((translate
7466 ? cpp_interpret_string : cpp_interpret_string_notranslate)
7467 (parse_in, strs, count, &istr, type)))
7468 {
7469 value = build_string (istr.len, (const char *) istr.text);
7470 free (CONST_CAST (unsigned char *, istr.text));
7471 if (count > 1)
7472 {
7473 location_t *locs = (location_t *) obstack_finish (&loc_ob);
7474 gcc_assert (g_string_concat_db);
7475 g_string_concat_db->record_string_concatenation (count, locs);
7476 }
7477 }
7478 else
7479 {
7480 if (type != CPP_STRING && !wide_ok)
7481 {
7482 error_at (loc, "a wide string is invalid in this context");
7483 type = CPP_STRING;
7484 }
7485 /* Callers cannot generally handle error_mark_node in this
7486 context, so return the empty string instead. An error has
7487 been issued, either above or from cpp_interpret_string. */
7488 switch (type)
7489 {
7490 default:
7491 case CPP_STRING:
7492 case CPP_UTF8STRING:
7493 value = build_string (1, "");
7494 break;
7495 case CPP_STRING16:
7496 value = build_string (TYPE_PRECISION (char16_type_node)
7497 / TYPE_PRECISION (char_type_node),
7498 "\0"); /* char16_t is 16 bits */
7499 break;
7500 case CPP_STRING32:
7501 value = build_string (TYPE_PRECISION (char32_type_node)
7502 / TYPE_PRECISION (char_type_node),
7503 "\0\0\0"); /* char32_t is 32 bits */
7504 break;
7505 case CPP_WSTRING:
7506 value = build_string (TYPE_PRECISION (wchar_type_node)
7507 / TYPE_PRECISION (char_type_node),
7508 "\0\0\0"); /* widest supported wchar_t
7509 is 32 bits */
7510 break;
7511 }
7512 }
7513
7514 switch (type)
7515 {
7516 default:
7517 case CPP_STRING:
7518 case CPP_UTF8STRING:
7519 TREE_TYPE (value) = char_array_type_node;
7520 break;
7521 case CPP_STRING16:
7522 TREE_TYPE (value) = char16_array_type_node;
7523 break;
7524 case CPP_STRING32:
7525 TREE_TYPE (value) = char32_array_type_node;
7526 break;
7527 case CPP_WSTRING:
7528 TREE_TYPE (value) = wchar_array_type_node;
7529 }
7530 value = fix_string_type (value);
7531
7532 if (count > 1)
7533 {
7534 obstack_free (&str_ob, 0);
7535 obstack_free (&loc_ob, 0);
7536 }
7537
7538 ret.value = value;
7539 ret.original_code = STRING_CST;
7540 ret.original_type = NULL_TREE;
7541 set_c_expr_source_range (&ret, get_range_from_loc (line_table, loc));
7542 return ret;
7543}
7544
27bf414c 7545/* Parse an expression other than a compound expression; that is, an
31dc71a8
MP
7546 assignment expression (C90 6.3.16, C99 6.5.16, C11 6.5.16). If
7547 AFTER is not NULL then it is an Objective-C message expression which
7548 is the primary-expression starting the expression as an initializer.
27bf414c
JM
7549
7550 assignment-expression:
7551 conditional-expression
7552 unary-expression assignment-operator assignment-expression
7553
7554 assignment-operator: one of
7555 = *= /= %= += -= <<= >>= &= ^= |=
7556
7557 In GNU C we accept any conditional expression on the LHS and
7558 diagnose the invalid lvalue rather than producing a syntax
7559 error. */
7560
7561static struct c_expr
acf0174b
JJ
7562c_parser_expr_no_commas (c_parser *parser, struct c_expr *after,
7563 tree omp_atomic_lhs)
27bf414c
JM
7564{
7565 struct c_expr lhs, rhs, ret;
7566 enum tree_code code;
c2255bc4 7567 location_t op_location, exp_location;
27bf414c 7568 gcc_assert (!after || c_dialect_objc ());
acf0174b 7569 lhs = c_parser_conditional_expression (parser, after, omp_atomic_lhs);
c9f9eb5d 7570 op_location = c_parser_peek_token (parser)->location;
27bf414c
JM
7571 switch (c_parser_peek_token (parser)->type)
7572 {
7573 case CPP_EQ:
7574 code = NOP_EXPR;
7575 break;
7576 case CPP_MULT_EQ:
7577 code = MULT_EXPR;
7578 break;
7579 case CPP_DIV_EQ:
7580 code = TRUNC_DIV_EXPR;
7581 break;
7582 case CPP_MOD_EQ:
7583 code = TRUNC_MOD_EXPR;
7584 break;
7585 case CPP_PLUS_EQ:
7586 code = PLUS_EXPR;
7587 break;
7588 case CPP_MINUS_EQ:
7589 code = MINUS_EXPR;
7590 break;
7591 case CPP_LSHIFT_EQ:
7592 code = LSHIFT_EXPR;
7593 break;
7594 case CPP_RSHIFT_EQ:
7595 code = RSHIFT_EXPR;
7596 break;
7597 case CPP_AND_EQ:
7598 code = BIT_AND_EXPR;
7599 break;
7600 case CPP_XOR_EQ:
7601 code = BIT_XOR_EXPR;
7602 break;
7603 case CPP_OR_EQ:
7604 code = BIT_IOR_EXPR;
7605 break;
7606 default:
7607 return lhs;
7608 }
7609 c_parser_consume_token (parser);
c2255bc4 7610 exp_location = c_parser_peek_token (parser)->location;
27bf414c 7611 rhs = c_parser_expr_no_commas (parser, NULL);
267bac10 7612 rhs = convert_lvalue_to_rvalue (exp_location, rhs, true, true);
36536d79 7613
25c22937
BI
7614 ret.value = build_modify_expr (op_location, lhs.value, lhs.original_type,
7615 code, exp_location, rhs.value,
7616 rhs.original_type);
ebedc9a3 7617 set_c_expr_source_range (&ret, lhs.get_start (), rhs.get_finish ());
27bf414c
JM
7618 if (code == NOP_EXPR)
7619 ret.original_code = MODIFY_EXPR;
7620 else
7621 {
7622 TREE_NO_WARNING (ret.value) = 1;
7623 ret.original_code = ERROR_MARK;
7624 }
6866c6e8 7625 ret.original_type = NULL;
27bf414c
JM
7626 return ret;
7627}
7628
31dc71a8
MP
7629/* Parse a conditional expression (C90 6.3.15, C99 6.5.15, C11 6.5.15). If
7630 AFTER is not NULL then it is an Objective-C message expression which is
27bf414c
JM
7631 the primary-expression starting the expression as an initializer.
7632
7633 conditional-expression:
7634 logical-OR-expression
7635 logical-OR-expression ? expression : conditional-expression
7636
7637 GNU extensions:
7638
7639 conditional-expression:
7640 logical-OR-expression ? : conditional-expression
7641*/
7642
7643static struct c_expr
acf0174b
JJ
7644c_parser_conditional_expression (c_parser *parser, struct c_expr *after,
7645 tree omp_atomic_lhs)
27bf414c
JM
7646{
7647 struct c_expr cond, exp1, exp2, ret;
a32c8316 7648 location_t start, cond_loc, colon_loc;
ba47d38d 7649
27bf414c 7650 gcc_assert (!after || c_dialect_objc ());
ba47d38d 7651
acf0174b 7652 cond = c_parser_binary_expression (parser, after, omp_atomic_lhs);
ba47d38d 7653
27bf414c
JM
7654 if (c_parser_next_token_is_not (parser, CPP_QUERY))
7655 return cond;
ebedc9a3
DM
7656 if (cond.value != error_mark_node)
7657 start = cond.get_start ();
7658 else
7659 start = UNKNOWN_LOCATION;
c2255bc4 7660 cond_loc = c_parser_peek_token (parser)->location;
267bac10 7661 cond = convert_lvalue_to_rvalue (cond_loc, cond, true, true);
27bf414c
JM
7662 c_parser_consume_token (parser);
7663 if (c_parser_next_token_is (parser, CPP_COLON))
7664 {
8ce94e44 7665 tree eptype = NULL_TREE;
d166d4c3 7666
a32c8316 7667 location_t middle_loc = c_parser_peek_token (parser)->location;
54dcdb88 7668 pedwarn (middle_loc, OPT_Wpedantic,
a9c697b8 7669 "ISO C forbids omitting the middle term of a %<?:%> expression");
8ce94e44
JM
7670 if (TREE_CODE (cond.value) == EXCESS_PRECISION_EXPR)
7671 {
7672 eptype = TREE_TYPE (cond.value);
7673 cond.value = TREE_OPERAND (cond.value, 0);
7674 }
54dcdb88
BE
7675 tree e = cond.value;
7676 while (TREE_CODE (e) == COMPOUND_EXPR)
7677 e = TREE_OPERAND (e, 1);
7678 warn_for_omitted_condop (middle_loc, e);
27bf414c 7679 /* Make sure first operand is calculated only once. */
b2fa0a8b 7680 exp1.value = save_expr (default_conversion (cond.value));
8ce94e44
JM
7681 if (eptype)
7682 exp1.value = build1 (EXCESS_PRECISION_EXPR, eptype, exp1.value);
6866c6e8 7683 exp1.original_type = NULL;
a32c8316 7684 exp1.src_range = cond.src_range;
ba47d38d 7685 cond.value = c_objc_common_truthvalue_conversion (cond_loc, exp1.value);
7d882b83 7686 c_inhibit_evaluation_warnings += cond.value == truthvalue_true_node;
27bf414c
JM
7687 }
7688 else
7689 {
7690 cond.value
85498824 7691 = c_objc_common_truthvalue_conversion
ba47d38d 7692 (cond_loc, default_conversion (cond.value));
7d882b83 7693 c_inhibit_evaluation_warnings += cond.value == truthvalue_false_node;
46bdb9cf 7694 exp1 = c_parser_expression_conv (parser);
ebfbbdc5 7695 mark_exp_read (exp1.value);
7d882b83
ILT
7696 c_inhibit_evaluation_warnings +=
7697 ((cond.value == truthvalue_true_node)
7698 - (cond.value == truthvalue_false_node));
27bf414c 7699 }
744aa42f
ILT
7700
7701 colon_loc = c_parser_peek_token (parser)->location;
27bf414c
JM
7702 if (!c_parser_require (parser, CPP_COLON, "expected %<:%>"))
7703 {
7d882b83 7704 c_inhibit_evaluation_warnings -= cond.value == truthvalue_true_node;
913884f7 7705 ret.set_error ();
27bf414c 7706 ret.original_code = ERROR_MARK;
6866c6e8 7707 ret.original_type = NULL;
27bf414c
JM
7708 return ret;
7709 }
c2255bc4
AH
7710 {
7711 location_t exp2_loc = c_parser_peek_token (parser)->location;
acf0174b 7712 exp2 = c_parser_conditional_expression (parser, NULL, NULL_TREE);
267bac10 7713 exp2 = convert_lvalue_to_rvalue (exp2_loc, exp2, true, true);
c2255bc4 7714 }
7d882b83 7715 c_inhibit_evaluation_warnings -= cond.value == truthvalue_true_node;
a32c8316
MP
7716 location_t loc1 = make_location (exp1.get_start (), exp1.src_range);
7717 location_t loc2 = make_location (exp2.get_start (), exp2.src_range);
744aa42f 7718 ret.value = build_conditional_expr (colon_loc, cond.value,
928c19bb 7719 cond.original_code == C_MAYBE_CONST_EXPR,
a32c8316
MP
7720 exp1.value, exp1.original_type, loc1,
7721 exp2.value, exp2.original_type, loc2);
27bf414c 7722 ret.original_code = ERROR_MARK;
6866c6e8
ILT
7723 if (exp1.value == error_mark_node || exp2.value == error_mark_node)
7724 ret.original_type = NULL;
7725 else
7726 {
7727 tree t1, t2;
7728
7729 /* If both sides are enum type, the default conversion will have
7730 made the type of the result be an integer type. We want to
7731 remember the enum types we started with. */
7732 t1 = exp1.original_type ? exp1.original_type : TREE_TYPE (exp1.value);
7733 t2 = exp2.original_type ? exp2.original_type : TREE_TYPE (exp2.value);
7734 ret.original_type = ((t1 != error_mark_node
7735 && t2 != error_mark_node
7736 && (TYPE_MAIN_VARIANT (t1)
7737 == TYPE_MAIN_VARIANT (t2)))
7738 ? t1
7739 : NULL);
7740 }
ebedc9a3 7741 set_c_expr_source_range (&ret, start, exp2.get_finish ());
27bf414c
JM
7742 return ret;
7743}
7744
7745/* Parse a binary expression; that is, a logical-OR-expression (C90
31dc71a8
MP
7746 6.3.5-6.3.14, C99 6.5.5-6.5.14, C11 6.5.5-6.5.14). If AFTER is not
7747 NULL then it is an Objective-C message expression which is the
7748 primary-expression starting the expression as an initializer.
acf0174b
JJ
7749
7750 OMP_ATOMIC_LHS is NULL, unless parsing OpenMP #pragma omp atomic,
7751 when it should be the unfolded lhs. In a valid OpenMP source,
7752 one of the operands of the toplevel binary expression must be equal
7753 to it. In that case, just return a build2 created binary operation
7754 rather than result of parser_build_binary_op.
27bf414c
JM
7755
7756 multiplicative-expression:
7757 cast-expression
7758 multiplicative-expression * cast-expression
7759 multiplicative-expression / cast-expression
7760 multiplicative-expression % cast-expression
7761
7762 additive-expression:
7763 multiplicative-expression
7764 additive-expression + multiplicative-expression
7765 additive-expression - multiplicative-expression
7766
7767 shift-expression:
7768 additive-expression
7769 shift-expression << additive-expression
7770 shift-expression >> additive-expression
7771
7772 relational-expression:
7773 shift-expression
7774 relational-expression < shift-expression
7775 relational-expression > shift-expression
7776 relational-expression <= shift-expression
7777 relational-expression >= shift-expression
7778
7779 equality-expression:
7780 relational-expression
7781 equality-expression == relational-expression
7782 equality-expression != relational-expression
7783
7784 AND-expression:
7785 equality-expression
7786 AND-expression & equality-expression
7787
7788 exclusive-OR-expression:
7789 AND-expression
7790 exclusive-OR-expression ^ AND-expression
7791
7792 inclusive-OR-expression:
7793 exclusive-OR-expression
7794 inclusive-OR-expression | exclusive-OR-expression
7795
7796 logical-AND-expression:
7797 inclusive-OR-expression
7798 logical-AND-expression && inclusive-OR-expression
7799
7800 logical-OR-expression:
7801 logical-AND-expression
7802 logical-OR-expression || logical-AND-expression
7803*/
7804
7805static struct c_expr
20906c66 7806c_parser_binary_expression (c_parser *parser, struct c_expr *after,
acf0174b 7807 tree omp_atomic_lhs)
27bf414c
JM
7808{
7809 /* A binary expression is parsed using operator-precedence parsing,
7810 with the operands being cast expressions. All the binary
7811 operators are left-associative. Thus a binary expression is of
7812 form:
7813
7814 E0 op1 E1 op2 E2 ...
7815
7816 which we represent on a stack. On the stack, the precedence
7817 levels are strictly increasing. When a new operator is
7818 encountered of higher precedence than that at the top of the
7819 stack, it is pushed; its LHS is the top expression, and its RHS
7820 is everything parsed until it is popped. When a new operator is
7821 encountered with precedence less than or equal to that at the top
7822 of the stack, triples E[i-1] op[i] E[i] are popped and replaced
7823 by the result of the operation until the operator at the top of
7824 the stack has lower precedence than the new operator or there is
7825 only one element on the stack; then the top expression is the LHS
7826 of the new operator. In the case of logical AND and OR
7d882b83
ILT
7827 expressions, we also need to adjust c_inhibit_evaluation_warnings
7828 as appropriate when the operators are pushed and popped. */
27bf414c 7829
27bf414c
JM
7830 struct {
7831 /* The expression at this stack level. */
7832 struct c_expr expr;
7833 /* The precedence of the operator on its left, PREC_NONE at the
7834 bottom of the stack. */
20906c66 7835 enum c_parser_prec prec;
27bf414c
JM
7836 /* The operation on its left. */
7837 enum tree_code op;
ca80e52b
EB
7838 /* The source location of this operation. */
7839 location_t loc;
40ffd95f
BE
7840 /* The sizeof argument if expr.original_code == SIZEOF_EXPR. */
7841 tree sizeof_arg;
27bf414c
JM
7842 } stack[NUM_PRECS];
7843 int sp;
ba47d38d 7844 /* Location of the binary operator. */
1f6d0c60 7845 location_t binary_loc = UNKNOWN_LOCATION; /* Quiet warning. */
27bf414c
JM
7846#define POP \
7847 do { \
7848 switch (stack[sp].op) \
7849 { \
7850 case TRUTH_ANDIF_EXPR: \
7d882b83
ILT
7851 c_inhibit_evaluation_warnings -= (stack[sp - 1].expr.value \
7852 == truthvalue_false_node); \
27bf414c
JM
7853 break; \
7854 case TRUTH_ORIF_EXPR: \
7d882b83
ILT
7855 c_inhibit_evaluation_warnings -= (stack[sp - 1].expr.value \
7856 == truthvalue_true_node); \
27bf414c 7857 break; \
40ffd95f
BE
7858 case TRUNC_DIV_EXPR: \
7859 if (stack[sp - 1].expr.original_code == SIZEOF_EXPR \
7860 && stack[sp].expr.original_code == SIZEOF_EXPR) \
7861 { \
7862 tree type0 = stack[sp - 1].sizeof_arg; \
7863 tree type1 = stack[sp].sizeof_arg; \
7864 tree first_arg = type0; \
7865 if (!TYPE_P (type0)) \
7866 type0 = TREE_TYPE (type0); \
7867 if (!TYPE_P (type1)) \
7868 type1 = TREE_TYPE (type1); \
7869 if (POINTER_TYPE_P (type0) \
7870 && comptypes (TREE_TYPE (type0), type1) \
7871 && !(TREE_CODE (first_arg) == PARM_DECL \
7872 && C_ARRAY_PARAMETER (first_arg) \
7873 && warn_sizeof_array_argument)) \
097f82ec
DM
7874 { \
7875 auto_diagnostic_group d; \
7876 if (warning_at (stack[sp].loc, OPT_Wsizeof_pointer_div, \
7877 "division %<sizeof (%T) / sizeof (%T)%> " \
7878 "does not compute the number of array " \
7879 "elements", \
7880 type0, type1)) \
7881 if (DECL_P (first_arg)) \
7882 inform (DECL_SOURCE_LOCATION (first_arg), \
7883 "first %<sizeof%> operand was declared here"); \
7884 } \
7885 } \
40ffd95f 7886 break; \
27bf414c
JM
7887 default: \
7888 break; \
7889 } \
f2a71bbc 7890 stack[sp - 1].expr \
267bac10
JM
7891 = convert_lvalue_to_rvalue (stack[sp - 1].loc, \
7892 stack[sp - 1].expr, true, true); \
f2a71bbc 7893 stack[sp].expr \
267bac10
JM
7894 = convert_lvalue_to_rvalue (stack[sp].loc, \
7895 stack[sp].expr, true, true); \
acf0174b
JJ
7896 if (__builtin_expect (omp_atomic_lhs != NULL_TREE, 0) && sp == 1 \
7897 && c_parser_peek_token (parser)->type == CPP_SEMICOLON \
7898 && ((1 << stack[sp].prec) \
fa01ffcc
JJ
7899 & ((1 << PREC_BITOR) | (1 << PREC_BITXOR) | (1 << PREC_BITAND) \
7900 | (1 << PREC_SHIFT) | (1 << PREC_ADD) | (1 << PREC_MULT))) \
acf0174b
JJ
7901 && stack[sp].op != TRUNC_MOD_EXPR \
7902 && stack[0].expr.value != error_mark_node \
7903 && stack[1].expr.value != error_mark_node \
7904 && (c_tree_equal (stack[0].expr.value, omp_atomic_lhs) \
7905 || c_tree_equal (stack[1].expr.value, omp_atomic_lhs))) \
7906 stack[0].expr.value \
7907 = build2 (stack[1].op, TREE_TYPE (stack[0].expr.value), \
7908 stack[0].expr.value, stack[1].expr.value); \
7909 else \
7910 stack[sp - 1].expr = parser_build_binary_op (stack[sp].loc, \
7911 stack[sp].op, \
7912 stack[sp - 1].expr, \
7913 stack[sp].expr); \
27bf414c
JM
7914 sp--; \
7915 } while (0)
7916 gcc_assert (!after || c_dialect_objc ());
ca80e52b 7917 stack[0].loc = c_parser_peek_token (parser)->location;
27bf414c 7918 stack[0].expr = c_parser_cast_expression (parser, after);
acf0174b 7919 stack[0].prec = PREC_NONE;
40ffd95f 7920 stack[0].sizeof_arg = c_last_sizeof_arg;
27bf414c
JM
7921 sp = 0;
7922 while (true)
7923 {
20906c66 7924 enum c_parser_prec oprec;
27bf414c 7925 enum tree_code ocode;
ebedc9a3 7926 source_range src_range;
27bf414c
JM
7927 if (parser->error)
7928 goto out;
7929 switch (c_parser_peek_token (parser)->type)
7930 {
7931 case CPP_MULT:
7932 oprec = PREC_MULT;
7933 ocode = MULT_EXPR;
7934 break;
7935 case CPP_DIV:
7936 oprec = PREC_MULT;
7937 ocode = TRUNC_DIV_EXPR;
7938 break;
7939 case CPP_MOD:
7940 oprec = PREC_MULT;
7941 ocode = TRUNC_MOD_EXPR;
7942 break;
7943 case CPP_PLUS:
7944 oprec = PREC_ADD;
7945 ocode = PLUS_EXPR;
7946 break;
7947 case CPP_MINUS:
7948 oprec = PREC_ADD;
7949 ocode = MINUS_EXPR;
7950 break;
7951 case CPP_LSHIFT:
7952 oprec = PREC_SHIFT;
7953 ocode = LSHIFT_EXPR;
7954 break;
7955 case CPP_RSHIFT:
7956 oprec = PREC_SHIFT;
7957 ocode = RSHIFT_EXPR;
7958 break;
7959 case CPP_LESS:
7960 oprec = PREC_REL;
7961 ocode = LT_EXPR;
7962 break;
7963 case CPP_GREATER:
7964 oprec = PREC_REL;
7965 ocode = GT_EXPR;
7966 break;
7967 case CPP_LESS_EQ:
7968 oprec = PREC_REL;
7969 ocode = LE_EXPR;
7970 break;
7971 case CPP_GREATER_EQ:
7972 oprec = PREC_REL;
7973 ocode = GE_EXPR;
7974 break;
7975 case CPP_EQ_EQ:
7976 oprec = PREC_EQ;
7977 ocode = EQ_EXPR;
7978 break;
7979 case CPP_NOT_EQ:
7980 oprec = PREC_EQ;
7981 ocode = NE_EXPR;
7982 break;
7983 case CPP_AND:
7984 oprec = PREC_BITAND;
7985 ocode = BIT_AND_EXPR;
7986 break;
7987 case CPP_XOR:
7988 oprec = PREC_BITXOR;
7989 ocode = BIT_XOR_EXPR;
7990 break;
7991 case CPP_OR:
7992 oprec = PREC_BITOR;
7993 ocode = BIT_IOR_EXPR;
7994 break;
7995 case CPP_AND_AND:
7996 oprec = PREC_LOGAND;
7997 ocode = TRUTH_ANDIF_EXPR;
7998 break;
7999 case CPP_OR_OR:
8000 oprec = PREC_LOGOR;
8001 ocode = TRUTH_ORIF_EXPR;
8002 break;
8003 default:
8004 /* Not a binary operator, so end of the binary
8005 expression. */
8006 goto out;
8007 }
ba47d38d 8008 binary_loc = c_parser_peek_token (parser)->location;
27bf414c 8009 while (oprec <= stack[sp].prec)
acf0174b 8010 POP;
20906c66 8011 c_parser_consume_token (parser);
27bf414c
JM
8012 switch (ocode)
8013 {
8014 case TRUTH_ANDIF_EXPR:
ebedc9a3 8015 src_range = stack[sp].expr.src_range;
f2a71bbc 8016 stack[sp].expr
267bac10
JM
8017 = convert_lvalue_to_rvalue (stack[sp].loc,
8018 stack[sp].expr, true, true);
85498824 8019 stack[sp].expr.value = c_objc_common_truthvalue_conversion
ca80e52b 8020 (stack[sp].loc, default_conversion (stack[sp].expr.value));
7d882b83
ILT
8021 c_inhibit_evaluation_warnings += (stack[sp].expr.value
8022 == truthvalue_false_node);
ebedc9a3 8023 set_c_expr_source_range (&stack[sp].expr, src_range);
27bf414c
JM
8024 break;
8025 case TRUTH_ORIF_EXPR:
ebedc9a3 8026 src_range = stack[sp].expr.src_range;
f2a71bbc 8027 stack[sp].expr
267bac10
JM
8028 = convert_lvalue_to_rvalue (stack[sp].loc,
8029 stack[sp].expr, true, true);
85498824 8030 stack[sp].expr.value = c_objc_common_truthvalue_conversion
ca80e52b 8031 (stack[sp].loc, default_conversion (stack[sp].expr.value));
7d882b83
ILT
8032 c_inhibit_evaluation_warnings += (stack[sp].expr.value
8033 == truthvalue_true_node);
ebedc9a3 8034 set_c_expr_source_range (&stack[sp].expr, src_range);
27bf414c
JM
8035 break;
8036 default:
8037 break;
8038 }
8039 sp++;
ca80e52b 8040 stack[sp].loc = binary_loc;
27bf414c
JM
8041 stack[sp].expr = c_parser_cast_expression (parser, NULL);
8042 stack[sp].prec = oprec;
8043 stack[sp].op = ocode;
40ffd95f 8044 stack[sp].sizeof_arg = c_last_sizeof_arg;
27bf414c
JM
8045 }
8046 out:
8047 while (sp > 0)
8048 POP;
8049 return stack[0].expr;
8050#undef POP
8051}
8052
31dc71a8
MP
8053/* Parse a cast expression (C90 6.3.4, C99 6.5.4, C11 6.5.4). If AFTER
8054 is not NULL then it is an Objective-C message expression which is the
27bf414c
JM
8055 primary-expression starting the expression as an initializer.
8056
8057 cast-expression:
8058 unary-expression
8059 ( type-name ) unary-expression
8060*/
8061
8062static struct c_expr
8063c_parser_cast_expression (c_parser *parser, struct c_expr *after)
8064{
c2255bc4 8065 location_t cast_loc = c_parser_peek_token (parser)->location;
27bf414c
JM
8066 gcc_assert (!after || c_dialect_objc ());
8067 if (after)
c2255bc4
AH
8068 return c_parser_postfix_expression_after_primary (parser,
8069 cast_loc, *after);
27bf414c
JM
8070 /* If the expression begins with a parenthesized type name, it may
8071 be either a cast or a compound literal; we need to see whether
8072 the next character is '{' to tell the difference. If not, it is
29ce73cb
PB
8073 an unary expression. Full detection of unknown typenames here
8074 would require a 3-token lookahead. */
27bf414c
JM
8075 if (c_parser_next_token_is (parser, CPP_OPEN_PAREN)
8076 && c_token_starts_typename (c_parser_peek_2nd_token (parser)))
8077 {
8078 struct c_type_name *type_name;
8079 struct c_expr ret;
f2a71bbc 8080 struct c_expr expr;
32129a17
DM
8081 matching_parens parens;
8082 parens.consume_open (parser);
4b2b493f 8083 type_name = c_parser_type_name (parser, true);
32129a17 8084 parens.skip_until_found_close (parser);
27bf414c
JM
8085 if (type_name == NULL)
8086 {
913884f7 8087 ret.set_error ();
27bf414c 8088 ret.original_code = ERROR_MARK;
6866c6e8 8089 ret.original_type = NULL;
27bf414c
JM
8090 return ret;
8091 }
33c9159e
AH
8092
8093 /* Save casted types in the function's used types hash table. */
8d8d1a28 8094 used_types_insert (type_name->specs->type);
33c9159e 8095
27bf414c 8096 if (c_parser_next_token_is (parser, CPP_OPEN_BRACE))
24b97832 8097 return c_parser_postfix_expression_after_paren_type (parser, type_name,
c2255bc4 8098 cast_loc);
4b2b493f
JM
8099 if (type_name->specs->alignas_p)
8100 error_at (type_name->specs->locations[cdw_alignas],
8101 "alignment specified for type name in cast");
c2255bc4
AH
8102 {
8103 location_t expr_loc = c_parser_peek_token (parser)->location;
8104 expr = c_parser_cast_expression (parser, NULL);
267bac10 8105 expr = convert_lvalue_to_rvalue (expr_loc, expr, true, true);
c2255bc4
AH
8106 }
8107 ret.value = c_cast_expr (cast_loc, type_name, expr.value);
ebedc9a3
DM
8108 if (ret.value && expr.value)
8109 set_c_expr_source_range (&ret, cast_loc, expr.get_finish ());
27bf414c 8110 ret.original_code = ERROR_MARK;
6866c6e8 8111 ret.original_type = NULL;
27bf414c
JM
8112 return ret;
8113 }
8114 else
8115 return c_parser_unary_expression (parser);
8116}
8117
31dc71a8 8118/* Parse an unary expression (C90 6.3.3, C99 6.5.3, C11 6.5.3).
27bf414c
JM
8119
8120 unary-expression:
8121 postfix-expression
8122 ++ unary-expression
8123 -- unary-expression
8124 unary-operator cast-expression
8125 sizeof unary-expression
8126 sizeof ( type-name )
8127
8128 unary-operator: one of
8129 & * + - ~ !
8130
8131 GNU extensions:
8132
8133 unary-expression:
8134 __alignof__ unary-expression
8135 __alignof__ ( type-name )
8136 && identifier
8137
48b0b196 8138 (C11 permits _Alignof with type names only.)
d19fa6b5 8139
27bf414c
JM
8140 unary-operator: one of
8141 __extension__ __real__ __imag__
8142
0a35513e
AH
8143 Transactional Memory:
8144
8145 unary-expression:
8146 transaction-expression
8147
27bf414c
JM
8148 In addition, the GNU syntax treats ++ and -- as unary operators, so
8149 they may be applied to cast expressions with errors for non-lvalues
8150 given later. */
8151
8152static struct c_expr
8153c_parser_unary_expression (c_parser *parser)
8154{
8155 int ext;
46bdb9cf 8156 struct c_expr ret, op;
c2255bc4
AH
8157 location_t op_loc = c_parser_peek_token (parser)->location;
8158 location_t exp_loc;
ebedc9a3 8159 location_t finish;
6866c6e8
ILT
8160 ret.original_code = ERROR_MARK;
8161 ret.original_type = NULL;
27bf414c
JM
8162 switch (c_parser_peek_token (parser)->type)
8163 {
8164 case CPP_PLUS_PLUS:
8165 c_parser_consume_token (parser);
c2255bc4 8166 exp_loc = c_parser_peek_token (parser)->location;
46bdb9cf 8167 op = c_parser_cast_expression (parser, NULL);
36536d79 8168
5e9d6aa4
JK
8169 op = default_function_array_read_conversion (exp_loc, op);
8170 return parser_build_unary_op (op_loc, PREINCREMENT_EXPR, op);
27bf414c
JM
8171 case CPP_MINUS_MINUS:
8172 c_parser_consume_token (parser);
c2255bc4 8173 exp_loc = c_parser_peek_token (parser)->location;
46bdb9cf 8174 op = c_parser_cast_expression (parser, NULL);
36536d79 8175
5e9d6aa4
JK
8176 op = default_function_array_read_conversion (exp_loc, op);
8177 return parser_build_unary_op (op_loc, PREDECREMENT_EXPR, op);
27bf414c
JM
8178 case CPP_AND:
8179 c_parser_consume_token (parser);
ebfbbdc5
JJ
8180 op = c_parser_cast_expression (parser, NULL);
8181 mark_exp_read (op.value);
8182 return parser_build_unary_op (op_loc, ADDR_EXPR, op);
27bf414c 8183 case CPP_MULT:
7443cf13
DM
8184 {
8185 c_parser_consume_token (parser);
8186 exp_loc = c_parser_peek_token (parser)->location;
8187 op = c_parser_cast_expression (parser, NULL);
8188 finish = op.get_finish ();
8189 op = convert_lvalue_to_rvalue (exp_loc, op, true, true);
8190 location_t combined_loc = make_location (op_loc, op_loc, finish);
8191 ret.value = build_indirect_ref (combined_loc, op.value, RO_UNARY_STAR);
8192 ret.src_range.m_start = op_loc;
8193 ret.src_range.m_finish = finish;
8194 return ret;
8195 }
27bf414c 8196 case CPP_PLUS:
8400e75e 8197 if (!c_dialect_objc () && !in_system_header_at (input_location))
c2255bc4 8198 warning_at (op_loc,
3ba09659
AH
8199 OPT_Wtraditional,
8200 "traditional C rejects the unary plus operator");
c7412148 8201 c_parser_consume_token (parser);
c2255bc4 8202 exp_loc = c_parser_peek_token (parser)->location;
46bdb9cf 8203 op = c_parser_cast_expression (parser, NULL);
267bac10 8204 op = convert_lvalue_to_rvalue (exp_loc, op, true, true);
c2255bc4 8205 return parser_build_unary_op (op_loc, CONVERT_EXPR, op);
27bf414c
JM
8206 case CPP_MINUS:
8207 c_parser_consume_token (parser);
c2255bc4 8208 exp_loc = c_parser_peek_token (parser)->location;
46bdb9cf 8209 op = c_parser_cast_expression (parser, NULL);
267bac10 8210 op = convert_lvalue_to_rvalue (exp_loc, op, true, true);
c2255bc4 8211 return parser_build_unary_op (op_loc, NEGATE_EXPR, op);
27bf414c
JM
8212 case CPP_COMPL:
8213 c_parser_consume_token (parser);
c2255bc4 8214 exp_loc = c_parser_peek_token (parser)->location;
46bdb9cf 8215 op = c_parser_cast_expression (parser, NULL);
267bac10 8216 op = convert_lvalue_to_rvalue (exp_loc, op, true, true);
c2255bc4 8217 return parser_build_unary_op (op_loc, BIT_NOT_EXPR, op);
27bf414c
JM
8218 case CPP_NOT:
8219 c_parser_consume_token (parser);
c2255bc4 8220 exp_loc = c_parser_peek_token (parser)->location;
46bdb9cf 8221 op = c_parser_cast_expression (parser, NULL);
267bac10 8222 op = convert_lvalue_to_rvalue (exp_loc, op, true, true);
c2255bc4 8223 return parser_build_unary_op (op_loc, TRUTH_NOT_EXPR, op);
27bf414c
JM
8224 case CPP_AND_AND:
8225 /* Refer to the address of a label as a pointer. */
8226 c_parser_consume_token (parser);
8227 if (c_parser_next_token_is (parser, CPP_NAME))
8228 {
8229 ret.value = finish_label_address_expr
c2255bc4 8230 (c_parser_peek_token (parser)->value, op_loc);
bef08b71
DM
8231 set_c_expr_source_range (&ret, op_loc,
8232 c_parser_peek_token (parser)->get_finish ());
27bf414c 8233 c_parser_consume_token (parser);
27bf414c
JM
8234 }
8235 else
8236 {
8237 c_parser_error (parser, "expected identifier");
f7b6353a 8238 ret.set_error ();
27bf414c 8239 }
f7b6353a 8240 return ret;
27bf414c
JM
8241 case CPP_KEYWORD:
8242 switch (c_parser_peek_token (parser)->keyword)
8243 {
8244 case RID_SIZEOF:
8245 return c_parser_sizeof_expression (parser);
8246 case RID_ALIGNOF:
8247 return c_parser_alignof_expression (parser);
98f08eb8
MS
8248 case RID_BUILTIN_HAS_ATTRIBUTE:
8249 return c_parser_has_attribute_expression (parser);
27bf414c
JM
8250 case RID_EXTENSION:
8251 c_parser_consume_token (parser);
8252 ext = disable_extension_diagnostics ();
8253 ret = c_parser_cast_expression (parser, NULL);
8254 restore_extension_diagnostics (ext);
8255 return ret;
8256 case RID_REALPART:
8257 c_parser_consume_token (parser);
c2255bc4 8258 exp_loc = c_parser_peek_token (parser)->location;
46bdb9cf 8259 op = c_parser_cast_expression (parser, NULL);
c2255bc4
AH
8260 op = default_function_array_conversion (exp_loc, op);
8261 return parser_build_unary_op (op_loc, REALPART_EXPR, op);
27bf414c
JM
8262 case RID_IMAGPART:
8263 c_parser_consume_token (parser);
c2255bc4 8264 exp_loc = c_parser_peek_token (parser)->location;
46bdb9cf 8265 op = c_parser_cast_expression (parser, NULL);
c2255bc4
AH
8266 op = default_function_array_conversion (exp_loc, op);
8267 return parser_build_unary_op (op_loc, IMAGPART_EXPR, op);
0a35513e
AH
8268 case RID_TRANSACTION_ATOMIC:
8269 case RID_TRANSACTION_RELAXED:
8270 return c_parser_transaction_expression (parser,
8271 c_parser_peek_token (parser)->keyword);
27bf414c
JM
8272 default:
8273 return c_parser_postfix_expression (parser);
8274 }
8275 default:
8276 return c_parser_postfix_expression (parser);
8277 }
8278}
8279
8280/* Parse a sizeof expression. */
8281
8282static struct c_expr
8283c_parser_sizeof_expression (c_parser *parser)
8284{
8285 struct c_expr expr;
ebedc9a3 8286 struct c_expr result;
c7412148 8287 location_t expr_loc;
27bf414c 8288 gcc_assert (c_parser_next_token_is_keyword (parser, RID_SIZEOF));
ebedc9a3
DM
8289
8290 location_t start;
8291 location_t finish = UNKNOWN_LOCATION;
8292
8293 start = c_parser_peek_token (parser)->location;
8294
27bf414c 8295 c_parser_consume_token (parser);
7d882b83 8296 c_inhibit_evaluation_warnings++;
27bf414c
JM
8297 in_sizeof++;
8298 if (c_parser_next_token_is (parser, CPP_OPEN_PAREN)
8299 && c_token_starts_typename (c_parser_peek_2nd_token (parser)))
8300 {
8301 /* Either sizeof ( type-name ) or sizeof unary-expression
8302 starting with a compound literal. */
8303 struct c_type_name *type_name;
32129a17
DM
8304 matching_parens parens;
8305 parens.consume_open (parser);
c7412148 8306 expr_loc = c_parser_peek_token (parser)->location;
4b2b493f 8307 type_name = c_parser_type_name (parser, true);
32129a17 8308 parens.skip_until_found_close (parser);
ebedc9a3 8309 finish = parser->tokens_buf[0].location;
27bf414c
JM
8310 if (type_name == NULL)
8311 {
8312 struct c_expr ret;
7d882b83 8313 c_inhibit_evaluation_warnings--;
27bf414c 8314 in_sizeof--;
913884f7 8315 ret.set_error ();
27bf414c 8316 ret.original_code = ERROR_MARK;
6866c6e8 8317 ret.original_type = NULL;
27bf414c
JM
8318 return ret;
8319 }
8320 if (c_parser_next_token_is (parser, CPP_OPEN_BRACE))
8321 {
4bd2511b
JL
8322 expr = c_parser_postfix_expression_after_paren_type (parser,
8323 type_name,
8324 expr_loc);
ebedc9a3 8325 finish = expr.get_finish ();
4bd2511b 8326 goto sizeof_expr;
27bf414c 8327 }
4bd2511b 8328 /* sizeof ( type-name ). */
4b2b493f
JM
8329 if (type_name->specs->alignas_p)
8330 error_at (type_name->specs->locations[cdw_alignas],
8331 "alignment specified for type name in %<sizeof%>");
4bd2511b
JL
8332 c_inhibit_evaluation_warnings--;
8333 in_sizeof--;
ebedc9a3 8334 result = c_expr_sizeof_type (expr_loc, type_name);
27bf414c
JM
8335 }
8336 else
8337 {
c7412148 8338 expr_loc = c_parser_peek_token (parser)->location;
27bf414c 8339 expr = c_parser_unary_expression (parser);
ebedc9a3 8340 finish = expr.get_finish ();
4bd2511b
JL
8341 sizeof_expr:
8342 c_inhibit_evaluation_warnings--;
8343 in_sizeof--;
8344 mark_exp_read (expr.value);
8345 if (TREE_CODE (expr.value) == COMPONENT_REF
8346 && DECL_C_BIT_FIELD (TREE_OPERAND (expr.value, 1)))
8347 error_at (expr_loc, "%<sizeof%> applied to a bit-field");
ebedc9a3 8348 result = c_expr_sizeof_expr (expr_loc, expr);
27bf414c 8349 }
a28351e7
JJ
8350 if (finish == UNKNOWN_LOCATION)
8351 finish = start;
8352 set_c_expr_source_range (&result, start, finish);
ebedc9a3 8353 return result;
27bf414c
JM
8354}
8355
8356/* Parse an alignof expression. */
8357
8358static struct c_expr
8359c_parser_alignof_expression (c_parser *parser)
8360{
8361 struct c_expr expr;
a1b93f8d
DM
8362 location_t start_loc = c_parser_peek_token (parser)->location;
8363 location_t end_loc;
d19fa6b5 8364 tree alignof_spelling = c_parser_peek_token (parser)->value;
27bf414c 8365 gcc_assert (c_parser_next_token_is_keyword (parser, RID_ALIGNOF));
296674db
JM
8366 bool is_c11_alignof = strcmp (IDENTIFIER_POINTER (alignof_spelling),
8367 "_Alignof") == 0;
d19fa6b5 8368 /* A diagnostic is not required for the use of this identifier in
48b0b196 8369 the implementation namespace; only diagnose it for the C11
d19fa6b5 8370 spelling because of existing code using the other spellings. */
35aff4fb 8371 if (is_c11_alignof)
d19fa6b5
JM
8372 {
8373 if (flag_isoc99)
a1b93f8d 8374 pedwarn_c99 (start_loc, OPT_Wpedantic, "ISO C99 does not support %qE",
35aff4fb 8375 alignof_spelling);
d19fa6b5 8376 else
a1b93f8d 8377 pedwarn_c99 (start_loc, OPT_Wpedantic, "ISO C90 does not support %qE",
35aff4fb 8378 alignof_spelling);
d19fa6b5 8379 }
27bf414c 8380 c_parser_consume_token (parser);
7d882b83 8381 c_inhibit_evaluation_warnings++;
27bf414c
JM
8382 in_alignof++;
8383 if (c_parser_next_token_is (parser, CPP_OPEN_PAREN)
8384 && c_token_starts_typename (c_parser_peek_2nd_token (parser)))
8385 {
8386 /* Either __alignof__ ( type-name ) or __alignof__
8387 unary-expression starting with a compound literal. */
24b97832 8388 location_t loc;
27bf414c
JM
8389 struct c_type_name *type_name;
8390 struct c_expr ret;
32129a17
DM
8391 matching_parens parens;
8392 parens.consume_open (parser);
24b97832 8393 loc = c_parser_peek_token (parser)->location;
4b2b493f 8394 type_name = c_parser_type_name (parser, true);
a1b93f8d 8395 end_loc = c_parser_peek_token (parser)->location;
32129a17 8396 parens.skip_until_found_close (parser);
27bf414c
JM
8397 if (type_name == NULL)
8398 {
8399 struct c_expr ret;
7d882b83 8400 c_inhibit_evaluation_warnings--;
27bf414c 8401 in_alignof--;
913884f7 8402 ret.set_error ();
27bf414c 8403 ret.original_code = ERROR_MARK;
6866c6e8 8404 ret.original_type = NULL;
27bf414c
JM
8405 return ret;
8406 }
8407 if (c_parser_next_token_is (parser, CPP_OPEN_BRACE))
8408 {
8409 expr = c_parser_postfix_expression_after_paren_type (parser,
24b97832
ILT
8410 type_name,
8411 loc);
27bf414c
JM
8412 goto alignof_expr;
8413 }
8414 /* alignof ( type-name ). */
4b2b493f
JM
8415 if (type_name->specs->alignas_p)
8416 error_at (type_name->specs->locations[cdw_alignas],
8417 "alignment specified for type name in %qE",
8418 alignof_spelling);
7d882b83 8419 c_inhibit_evaluation_warnings--;
27bf414c 8420 in_alignof--;
296674db
JM
8421 ret.value = c_sizeof_or_alignof_type (loc, groktypename (type_name,
8422 NULL, NULL),
8423 false, is_c11_alignof, 1);
27bf414c 8424 ret.original_code = ERROR_MARK;
6866c6e8 8425 ret.original_type = NULL;
a1b93f8d 8426 set_c_expr_source_range (&ret, start_loc, end_loc);
27bf414c
JM
8427 return ret;
8428 }
8429 else
8430 {
8431 struct c_expr ret;
8432 expr = c_parser_unary_expression (parser);
a1b93f8d 8433 end_loc = expr.src_range.m_finish;
27bf414c 8434 alignof_expr:
ebfbbdc5 8435 mark_exp_read (expr.value);
7d882b83 8436 c_inhibit_evaluation_warnings--;
27bf414c 8437 in_alignof--;
aa0db437
MS
8438 if (is_c11_alignof)
8439 pedwarn (start_loc,
8440 OPT_Wpedantic, "ISO C does not allow %<%E (expression)%>",
8441 alignof_spelling);
a1b93f8d 8442 ret.value = c_alignof_expr (start_loc, expr.value);
27bf414c 8443 ret.original_code = ERROR_MARK;
6866c6e8 8444 ret.original_type = NULL;
a1b93f8d 8445 set_c_expr_source_range (&ret, start_loc, end_loc);
27bf414c
JM
8446 return ret;
8447 }
8448}
8449
98f08eb8
MS
8450/* Parse the __builtin_has_attribute ([expr|type], attribute-spec)
8451 expression. */
8452
8453static struct c_expr
8454c_parser_has_attribute_expression (c_parser *parser)
8455{
8456 gcc_assert (c_parser_next_token_is_keyword (parser,
8457 RID_BUILTIN_HAS_ATTRIBUTE));
8458 c_parser_consume_token (parser);
8459
8460 c_inhibit_evaluation_warnings++;
8461
8462 matching_parens parens;
8463 if (!parens.require_open (parser))
8464 {
8465 c_inhibit_evaluation_warnings--;
8466 in_typeof--;
8467
8468 struct c_expr result;
8469 result.set_error ();
8470 result.original_code = ERROR_MARK;
8471 result.original_type = NULL;
8472 return result;
8473 }
8474
8475 /* Treat the type argument the same way as in typeof for the purposes
8476 of warnings. FIXME: Generalize this so the warning refers to
8477 __builtin_has_attribute rather than typeof. */
8478 in_typeof++;
8479
8480 /* The first operand: one of DECL, EXPR, or TYPE. */
8481 tree oper = NULL_TREE;
8482 if (c_parser_next_tokens_start_typename (parser, cla_prefer_id))
8483 {
8484 struct c_type_name *tname = c_parser_type_name (parser);
8485 in_typeof--;
8486 if (tname)
8487 {
8488 oper = groktypename (tname, NULL, NULL);
8489 pop_maybe_used (variably_modified_type_p (oper, NULL_TREE));
8490 }
8491 }
8492 else
8493 {
8494 struct c_expr cexpr = c_parser_expr_no_commas (parser, NULL);
8495 c_inhibit_evaluation_warnings--;
8496 in_typeof--;
8497 if (cexpr.value != error_mark_node)
8498 {
8499 mark_exp_read (cexpr.value);
8500 oper = cexpr.value;
8501 tree etype = TREE_TYPE (oper);
8502 bool was_vm = variably_modified_type_p (etype, NULL_TREE);
8503 /* This is returned with the type so that when the type is
8504 evaluated, this can be evaluated. */
8505 if (was_vm)
8506 oper = c_fully_fold (oper, false, NULL);
8507 pop_maybe_used (was_vm);
8508 }
8509 }
8510
8511 struct c_expr result;
8512 result.original_code = ERROR_MARK;
8513 result.original_type = NULL;
8514
8515 if (!c_parser_require (parser, CPP_COMMA, "expected %<,%>"))
8516 {
8517 /* Consume the closing parenthesis if that's the next token
8518 in the likely case the built-in was invoked with fewer
8519 than two arguments. */
8520 if (c_parser_next_token_is (parser, CPP_CLOSE_PAREN))
8521 c_parser_consume_token (parser);
8522 c_inhibit_evaluation_warnings--;
8523 result.set_error ();
8524 return result;
8525 }
8526
471c5330 8527 bool save_translate_strings_p = parser->translate_strings_p;
98f08eb8
MS
8528
8529 location_t atloc = c_parser_peek_token (parser)->location;
8530 /* Parse a single attribute. Require no leading comma and do not
8531 allow empty attributes. */
783bfe5e 8532 tree attr = c_parser_gnu_attribute (parser, NULL_TREE, false, false);
98f08eb8 8533
471c5330 8534 parser->translate_strings_p = save_translate_strings_p;
98f08eb8
MS
8535
8536 if (c_parser_next_token_is (parser, CPP_CLOSE_PAREN))
8537 c_parser_consume_token (parser);
8538 else
8539 {
8540 c_parser_error (parser, "expected identifier");
8541 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN, NULL);
8542
8543 result.set_error ();
8544 return result;
8545 }
8546
8547 if (!attr)
8548 {
8549 error_at (atloc, "expected identifier");
8550 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN,
8551 "expected %<)%>");
8552 result.set_error ();
8553 return result;
8554 }
8555
8556 result.original_code = INTEGER_CST;
8557 result.original_type = boolean_type_node;
8558
8559 if (has_attribute (atloc, oper, attr, default_conversion))
8560 result.value = boolean_true_node;
8561 else
8562 result.value = boolean_false_node;
8563
8564 return result;
8565}
8566
f90e8e2e 8567/* Helper function to read arguments of builtins which are interfaces
2205ed25 8568 for the middle-end nodes like COMPLEX_EXPR, VEC_PERM_EXPR and
f90e8e2e
AS
8569 others. The name of the builtin is passed using BNAME parameter.
8570 Function returns true if there were no errors while parsing and
46c6e1e2
DM
8571 stores the arguments in CEXPR_LIST. If it returns true,
8572 *OUT_CLOSE_PAREN_LOC is written to with the location of the closing
8573 parenthesis. */
f90e8e2e
AS
8574static bool
8575c_parser_get_builtin_args (c_parser *parser, const char *bname,
4e7d7b3d 8576 vec<c_expr_t, va_gc> **ret_cexpr_list,
46c6e1e2
DM
8577 bool choose_expr_p,
8578 location_t *out_close_paren_loc)
f90e8e2e
AS
8579{
8580 location_t loc = c_parser_peek_token (parser)->location;
9771b263 8581 vec<c_expr_t, va_gc> *cexpr_list;
86785830 8582 c_expr_t expr;
4e7d7b3d 8583 bool saved_force_folding_builtin_constant_p;
f90e8e2e 8584
86785830 8585 *ret_cexpr_list = NULL;
f90e8e2e
AS
8586 if (c_parser_next_token_is_not (parser, CPP_OPEN_PAREN))
8587 {
8588 error_at (loc, "cannot take address of %qs", bname);
8589 return false;
8590 }
8591
8592 c_parser_consume_token (parser);
8593
8594 if (c_parser_next_token_is (parser, CPP_CLOSE_PAREN))
8595 {
46c6e1e2 8596 *out_close_paren_loc = c_parser_peek_token (parser)->location;
f90e8e2e
AS
8597 c_parser_consume_token (parser);
8598 return true;
8599 }
86785830 8600
4e7d7b3d
JJ
8601 saved_force_folding_builtin_constant_p
8602 = force_folding_builtin_constant_p;
8603 force_folding_builtin_constant_p |= choose_expr_p;
86785830 8604 expr = c_parser_expr_no_commas (parser, NULL);
4e7d7b3d
JJ
8605 force_folding_builtin_constant_p
8606 = saved_force_folding_builtin_constant_p;
9771b263 8607 vec_alloc (cexpr_list, 1);
b581c05c 8608 vec_safe_push (cexpr_list, expr);
86785830
AS
8609 while (c_parser_next_token_is (parser, CPP_COMMA))
8610 {
8611 c_parser_consume_token (parser);
8612 expr = c_parser_expr_no_commas (parser, NULL);
b581c05c 8613 vec_safe_push (cexpr_list, expr);
86785830 8614 }
f90e8e2e 8615
46c6e1e2 8616 *out_close_paren_loc = c_parser_peek_token (parser)->location;
f90e8e2e
AS
8617 if (!c_parser_require (parser, CPP_CLOSE_PAREN, "expected %<)%>"))
8618 return false;
8619
86785830 8620 *ret_cexpr_list = cexpr_list;
f90e8e2e
AS
8621 return true;
8622}
8623
433cc7b0
TT
8624/* This represents a single generic-association. */
8625
8626struct c_generic_association
8627{
8628 /* The location of the starting token of the type. */
8629 location_t type_location;
fb48aadc 8630 /* The association's type, or NULL_TREE for 'default'. */
433cc7b0
TT
8631 tree type;
8632 /* The association's expression. */
8633 struct c_expr expression;
8634};
8635
8636/* Parse a generic-selection. (C11 6.5.1.1).
8637
8638 generic-selection:
8639 _Generic ( assignment-expression , generic-assoc-list )
8640
8641 generic-assoc-list:
8642 generic-association
8643 generic-assoc-list , generic-association
8644
8645 generic-association:
8646 type-name : assignment-expression
8647 default : assignment-expression
8648*/
8649
8650static struct c_expr
8651c_parser_generic_selection (c_parser *parser)
8652{
433cc7b0
TT
8653 struct c_expr selector, error_expr;
8654 tree selector_type;
8655 struct c_generic_association matched_assoc;
8656 bool match_found = false;
8657 location_t generic_loc, selector_loc;
8658
8659 error_expr.original_code = ERROR_MARK;
8660 error_expr.original_type = NULL;
8a40fef3 8661 error_expr.set_error ();
433cc7b0
TT
8662 matched_assoc.type_location = UNKNOWN_LOCATION;
8663 matched_assoc.type = NULL_TREE;
8664 matched_assoc.expression = error_expr;
8665
8666 gcc_assert (c_parser_next_token_is_keyword (parser, RID_GENERIC));
8667 generic_loc = c_parser_peek_token (parser)->location;
8668 c_parser_consume_token (parser);
35aff4fb
MP
8669 if (flag_isoc99)
8670 pedwarn_c99 (generic_loc, OPT_Wpedantic,
433cc7b0 8671 "ISO C99 does not support %<_Generic%>");
35aff4fb
MP
8672 else
8673 pedwarn_c99 (generic_loc, OPT_Wpedantic,
433cc7b0 8674 "ISO C90 does not support %<_Generic%>");
433cc7b0 8675
32129a17
DM
8676 matching_parens parens;
8677 if (!parens.require_open (parser))
433cc7b0
TT
8678 return error_expr;
8679
8680 c_inhibit_evaluation_warnings++;
8681 selector_loc = c_parser_peek_token (parser)->location;
8682 selector = c_parser_expr_no_commas (parser, NULL);
8683 selector = default_function_array_conversion (selector_loc, selector);
8684 c_inhibit_evaluation_warnings--;
8685
8686 if (selector.value == error_mark_node)
8687 {
8688 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN, NULL);
8689 return selector;
8690 }
8691 selector_type = TREE_TYPE (selector.value);
8692 /* In ISO C terms, rvalues (including the controlling expression of
8693 _Generic) do not have qualified types. */
8694 if (TREE_CODE (selector_type) != ARRAY_TYPE)
8695 selector_type = TYPE_MAIN_VARIANT (selector_type);
8696 /* In ISO C terms, _Noreturn is not part of the type of expressions
8697 such as &abort, but in GCC it is represented internally as a type
8698 qualifier. */
8699 if (FUNCTION_POINTER_TYPE_P (selector_type)
8700 && TYPE_QUALS (TREE_TYPE (selector_type)) != TYPE_UNQUALIFIED)
8701 selector_type
8702 = build_pointer_type (TYPE_MAIN_VARIANT (TREE_TYPE (selector_type)));
8703
8704 if (!c_parser_require (parser, CPP_COMMA, "expected %<,%>"))
8705 {
8706 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN, NULL);
8707 return error_expr;
8708 }
8709
8c681247 8710 auto_vec<c_generic_association> associations;
433cc7b0
TT
8711 while (1)
8712 {
8713 struct c_generic_association assoc, *iter;
8714 unsigned int ix;
8715 c_token *token = c_parser_peek_token (parser);
8716
8717 assoc.type_location = token->location;
8718 if (token->type == CPP_KEYWORD && token->keyword == RID_DEFAULT)
8719 {
8720 c_parser_consume_token (parser);
8721 assoc.type = NULL_TREE;
8722 }
8723 else
8724 {
8725 struct c_type_name *type_name;
8726
8727 type_name = c_parser_type_name (parser);
8728 if (type_name == NULL)
8729 {
8730 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN, NULL);
8c681247 8731 return error_expr;
433cc7b0
TT
8732 }
8733 assoc.type = groktypename (type_name, NULL, NULL);
8734 if (assoc.type == error_mark_node)
8735 {
8736 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN, NULL);
8c681247 8737 return error_expr;
433cc7b0
TT
8738 }
8739
8740 if (TREE_CODE (assoc.type) == FUNCTION_TYPE)
8741 error_at (assoc.type_location,
8742 "%<_Generic%> association has function type");
8743 else if (!COMPLETE_TYPE_P (assoc.type))
8744 error_at (assoc.type_location,
8745 "%<_Generic%> association has incomplete type");
8746
8747 if (variably_modified_type_p (assoc.type, NULL_TREE))
8748 error_at (assoc.type_location,
8749 "%<_Generic%> association has "
8750 "variable length type");
8751 }
8752
8753 if (!c_parser_require (parser, CPP_COLON, "expected %<:%>"))
8754 {
8755 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN, NULL);
8c681247 8756 return error_expr;
433cc7b0
TT
8757 }
8758
8759 assoc.expression = c_parser_expr_no_commas (parser, NULL);
8760 if (assoc.expression.value == error_mark_node)
8761 {
8762 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN, NULL);
8c681247 8763 return error_expr;
433cc7b0
TT
8764 }
8765
8766 for (ix = 0; associations.iterate (ix, &iter); ++ix)
8767 {
8768 if (assoc.type == NULL_TREE)
8769 {
8770 if (iter->type == NULL_TREE)
8771 {
8772 error_at (assoc.type_location,
8773 "duplicate %<default%> case in %<_Generic%>");
8774 inform (iter->type_location, "original %<default%> is here");
8775 }
8776 }
8777 else if (iter->type != NULL_TREE)
8778 {
8779 if (comptypes (assoc.type, iter->type))
8780 {
8781 error_at (assoc.type_location,
8782 "%<_Generic%> specifies two compatible types");
8783 inform (iter->type_location, "compatible type is here");
8784 }
8785 }
8786 }
8787
8788 if (assoc.type == NULL_TREE)
8789 {
8790 if (!match_found)
8791 {
8792 matched_assoc = assoc;
8793 match_found = true;
8794 }
8795 }
8796 else if (comptypes (assoc.type, selector_type))
8797 {
8798 if (!match_found || matched_assoc.type == NULL_TREE)
8799 {
8800 matched_assoc = assoc;
8801 match_found = true;
8802 }
8803 else
8804 {
8805 error_at (assoc.type_location,
883c8f06 8806 "%<_Generic%> selector matches multiple associations");
433cc7b0
TT
8807 inform (matched_assoc.type_location,
8808 "other match is here");
8809 }
8810 }
8811
8812 associations.safe_push (assoc);
8813
8814 if (c_parser_peek_token (parser)->type != CPP_COMMA)
8815 break;
8816 c_parser_consume_token (parser);
8817 }
8818
32129a17 8819 if (!parens.require_close (parser))
433cc7b0
TT
8820 {
8821 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN, NULL);
8822 return error_expr;
8823 }
8824
8825 if (!match_found)
8826 {
8827 error_at (selector_loc, "%<_Generic%> selector of type %qT is not "
8828 "compatible with any association",
8829 selector_type);
8830 return error_expr;
8831 }
8832
8833 return matched_assoc.expression;
433cc7b0 8834}
f90e8e2e 8835
3ca0dc60
JM
8836/* Check the validity of a function pointer argument *EXPR (argument
8837 position POS) to __builtin_tgmath. Return the number of function
8838 arguments if possibly valid; return 0 having reported an error if
8839 not valid. */
8840
8841static unsigned int
8842check_tgmath_function (c_expr *expr, unsigned int pos)
8843{
8844 tree type = TREE_TYPE (expr->value);
8845 if (!FUNCTION_POINTER_TYPE_P (type))
8846 {
8847 error_at (expr->get_location (),
8848 "argument %u of %<__builtin_tgmath%> is not a function pointer",
8849 pos);
8850 return 0;
8851 }
8852 type = TREE_TYPE (type);
8853 if (!prototype_p (type))
8854 {
8855 error_at (expr->get_location (),
8856 "argument %u of %<__builtin_tgmath%> is unprototyped", pos);
8857 return 0;
8858 }
8859 if (stdarg_p (type))
8860 {
8861 error_at (expr->get_location (),
8862 "argument %u of %<__builtin_tgmath%> has variable arguments",
8863 pos);
8864 return 0;
8865 }
8866 unsigned int nargs = 0;
8867 function_args_iterator iter;
8868 tree t;
8869 FOREACH_FUNCTION_ARGS (type, t, iter)
8870 {
8871 if (t == void_type_node)
8872 break;
8873 nargs++;
8874 }
8875 if (nargs == 0)
8876 {
8877 error_at (expr->get_location (),
8878 "argument %u of %<__builtin_tgmath%> has no arguments", pos);
8879 return 0;
8880 }
8881 return nargs;
8882}
8883
8884/* Ways in which a parameter or return value of a type-generic macro
8885 may vary between the different functions the macro may call. */
8886enum tgmath_parm_kind
8887 {
8888 tgmath_fixed, tgmath_real, tgmath_complex
8889 };
8890
59bc434a
JJ
8891/* Helper function for c_parser_postfix_expression. Parse predefined
8892 identifiers. */
8893
8894static struct c_expr
8895c_parser_predefined_identifier (c_parser *parser)
8896{
8897 location_t loc = c_parser_peek_token (parser)->location;
8898 switch (c_parser_peek_token (parser)->keyword)
8899 {
8900 case RID_FUNCTION_NAME:
8901 pedwarn (loc, OPT_Wpedantic, "ISO C does not support %qs predefined "
8902 "identifier", "__FUNCTION__");
8903 break;
8904 case RID_PRETTY_FUNCTION_NAME:
8905 pedwarn (loc, OPT_Wpedantic, "ISO C does not support %qs predefined "
8906 "identifier", "__PRETTY_FUNCTION__");
8907 break;
8908 case RID_C99_FUNCTION_NAME:
8909 pedwarn_c90 (loc, OPT_Wpedantic, "ISO C90 does not support "
8910 "%<__func__%> predefined identifier");
8911 break;
8912 default:
8913 gcc_unreachable ();
8914 }
8915
8916 struct c_expr expr;
8917 expr.original_code = ERROR_MARK;
8918 expr.original_type = NULL;
8919 expr.value = fname_decl (loc, c_parser_peek_token (parser)->keyword,
8920 c_parser_peek_token (parser)->value);
8921 set_c_expr_source_range (&expr, loc, loc);
8922 c_parser_consume_token (parser);
8923 return expr;
8924}
8925
31dc71a8 8926/* Parse a postfix expression (C90 6.3.1-6.3.2, C99 6.5.1-6.5.2,
3e7b80d7
MP
8927 C11 6.5.1-6.5.2). Compound literals aren't handled here; callers have to
8928 call c_parser_postfix_expression_after_paren_type on encountering them.
27bf414c
JM
8929
8930 postfix-expression:
8931 primary-expression
8932 postfix-expression [ expression ]
8933 postfix-expression ( argument-expression-list[opt] )
8934 postfix-expression . identifier
8935 postfix-expression -> identifier
8936 postfix-expression ++
8937 postfix-expression --
8938 ( type-name ) { initializer-list }
8939 ( type-name ) { initializer-list , }
8940
8941 argument-expression-list:
8942 argument-expression
8943 argument-expression-list , argument-expression
8944
8945 primary-expression:
8946 identifier
8947 constant
8948 string-literal
8949 ( expression )
433cc7b0 8950 generic-selection
27bf414c
JM
8951
8952 GNU extensions:
8953
8954 primary-expression:
8955 __func__
8956 (treated as a keyword in GNU C)
8957 __FUNCTION__
8958 __PRETTY_FUNCTION__
8959 ( compound-statement )
8960 __builtin_va_arg ( assignment-expression , type-name )
8961 __builtin_offsetof ( type-name , offsetof-member-designator )
8962 __builtin_choose_expr ( assignment-expression ,
8963 assignment-expression ,
8964 assignment-expression )
8965 __builtin_types_compatible_p ( type-name , type-name )
3ca0dc60 8966 __builtin_tgmath ( expr-list )
d4a83c10 8967 __builtin_complex ( assignment-expression , assignment-expression )
f90e8e2e 8968 __builtin_shuffle ( assignment-expression , assignment-expression )
3e7b80d7 8969 __builtin_shuffle ( assignment-expression ,
f90e8e2e
AS
8970 assignment-expression ,
8971 assignment-expression, )
d8fcab68 8972 __builtin_convertvector ( assignment-expression , type-name )
27bf414c
JM
8973
8974 offsetof-member-designator:
8975 identifier
8976 offsetof-member-designator . identifier
8977 offsetof-member-designator [ expression ]
8978
8979 Objective-C:
8980
8981 primary-expression:
8982 [ objc-receiver objc-message-args ]
8983 @selector ( objc-selector-arg )
8984 @protocol ( identifier )
8985 @encode ( type-name )
8986 objc-string-literal
bede2adc 8987 Classname . identifier
27bf414c
JM
8988*/
8989
8990static struct c_expr
8991c_parser_postfix_expression (c_parser *parser)
8992{
f90e8e2e 8993 struct c_expr expr, e1;
27bf414c 8994 struct c_type_name *t1, *t2;
5de73c05 8995 location_t loc = c_parser_peek_token (parser)->location;
ebedc9a3 8996 source_range tok_range = c_parser_peek_token (parser)->get_range ();
6866c6e8
ILT
8997 expr.original_code = ERROR_MARK;
8998 expr.original_type = NULL;
27bf414c
JM
8999 switch (c_parser_peek_token (parser)->type)
9000 {
9001 case CPP_NUMBER:
754ccf7c 9002 expr.value = c_parser_peek_token (parser)->value;
ebedc9a3 9003 set_c_expr_source_range (&expr, tok_range);
754ccf7c
JJ
9004 loc = c_parser_peek_token (parser)->location;
9005 c_parser_consume_token (parser);
9006 if (TREE_CODE (expr.value) == FIXED_CST
9007 && !targetm.fixed_point_supported_p ())
9008 {
9009 error_at (loc, "fixed-point types not supported for this target");
913884f7 9010 expr.set_error ();
754ccf7c
JJ
9011 }
9012 break;
27bf414c 9013 case CPP_CHAR:
b6baa67d
KVH
9014 case CPP_CHAR16:
9015 case CPP_CHAR32:
7c5890cc 9016 case CPP_UTF8CHAR:
27bf414c
JM
9017 case CPP_WCHAR:
9018 expr.value = c_parser_peek_token (parser)->value;
a9342885
MP
9019 /* For the purpose of warning when a pointer is compared with
9020 a zero character constant. */
9021 expr.original_type = char_type_node;
ebedc9a3 9022 set_c_expr_source_range (&expr, tok_range);
27bf414c
JM
9023 c_parser_consume_token (parser);
9024 break;
9025 case CPP_STRING:
b6baa67d
KVH
9026 case CPP_STRING16:
9027 case CPP_STRING32:
27bf414c 9028 case CPP_WSTRING:
2c6e3f55 9029 case CPP_UTF8STRING:
471c5330
JM
9030 expr = c_parser_string_literal (parser, parser->translate_strings_p,
9031 true);
27bf414c
JM
9032 break;
9033 case CPP_OBJC_STRING:
9034 gcc_assert (c_dialect_objc ());
9035 expr.value
9036 = objc_build_string_object (c_parser_peek_token (parser)->value);
ebedc9a3 9037 set_c_expr_source_range (&expr, tok_range);
27bf414c
JM
9038 c_parser_consume_token (parser);
9039 break;
9040 case CPP_NAME:
bede2adc 9041 switch (c_parser_peek_token (parser)->id_kind)
27bf414c 9042 {
bede2adc
NP
9043 case C_ID_ID:
9044 {
9045 tree id = c_parser_peek_token (parser)->value;
9046 c_parser_consume_token (parser);
9047 expr.value = build_external_ref (loc, id,
9048 (c_parser_peek_token (parser)->type
9049 == CPP_OPEN_PAREN),
9050 &expr.original_type);
ebedc9a3 9051 set_c_expr_source_range (&expr, tok_range);
bede2adc
NP
9052 break;
9053 }
9054 case C_ID_CLASSNAME:
9055 {
9056 /* Here we parse the Objective-C 2.0 Class.name dot
9057 syntax. */
9058 tree class_name = c_parser_peek_token (parser)->value;
9059 tree component;
9060 c_parser_consume_token (parser);
9061 gcc_assert (c_dialect_objc ());
9062 if (!c_parser_require (parser, CPP_DOT, "expected %<.%>"))
9063 {
8a40fef3 9064 expr.set_error ();
bede2adc
NP
9065 break;
9066 }
9067 if (c_parser_next_token_is_not (parser, CPP_NAME))
9068 {
9069 c_parser_error (parser, "expected identifier");
8a40fef3 9070 expr.set_error ();
bede2adc
NP
9071 break;
9072 }
cbd03aee
DM
9073 c_token *component_tok = c_parser_peek_token (parser);
9074 component = component_tok->value;
9075 location_t end_loc = component_tok->get_finish ();
bede2adc
NP
9076 c_parser_consume_token (parser);
9077 expr.value = objc_build_class_component_ref (class_name,
9078 component);
cbd03aee 9079 set_c_expr_source_range (&expr, loc, end_loc);
bede2adc
NP
9080 break;
9081 }
9082 default:
27bf414c 9083 c_parser_error (parser, "expected expression");
8a40fef3 9084 expr.set_error ();
27bf414c
JM
9085 break;
9086 }
27bf414c
JM
9087 break;
9088 case CPP_OPEN_PAREN:
9089 /* A parenthesized expression, statement expression or compound
9090 literal. */
9091 if (c_parser_peek_2nd_token (parser)->type == CPP_OPEN_BRACE)
9092 {
9093 /* A statement expression. */
9094 tree stmt;
c2255bc4 9095 location_t brace_loc;
27bf414c 9096 c_parser_consume_token (parser);
c2255bc4 9097 brace_loc = c_parser_peek_token (parser)->location;
27bf414c 9098 c_parser_consume_token (parser);
f7584c81
DP
9099 /* If we've not yet started the current function's statement list,
9100 or we're in the parameter scope of an old-style function
9101 declaration, statement expressions are not allowed. */
9102 if (!building_stmt_list_p () || old_style_parameter_scope ())
27bf414c 9103 {
c2255bc4 9104 error_at (loc, "braced-group within expression allowed "
3ba09659 9105 "only inside a function");
27bf414c
JM
9106 parser->error = true;
9107 c_parser_skip_until_found (parser, CPP_CLOSE_BRACE, NULL);
9108 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN, NULL);
8a40fef3 9109 expr.set_error ();
27bf414c
JM
9110 break;
9111 }
9112 stmt = c_begin_stmt_expr ();
9113 c_parser_compound_statement_nostart (parser);
bef08b71 9114 location_t close_loc = c_parser_peek_token (parser)->location;
27bf414c
JM
9115 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN,
9116 "expected %<)%>");
c1771a20 9117 pedwarn (loc, OPT_Wpedantic,
509c9d60 9118 "ISO C forbids braced-groups within expressions");
c2255bc4 9119 expr.value = c_finish_stmt_expr (brace_loc, stmt);
bef08b71 9120 set_c_expr_source_range (&expr, loc, close_loc);
82c3c067 9121 mark_exp_read (expr.value);
27bf414c 9122 }
27bf414c
JM
9123 else
9124 {
9125 /* A parenthesized expression. */
ebedc9a3 9126 location_t loc_open_paren = c_parser_peek_token (parser)->location;
27bf414c
JM
9127 c_parser_consume_token (parser);
9128 expr = c_parser_expression (parser);
9129 if (TREE_CODE (expr.value) == MODIFY_EXPR)
9130 TREE_NO_WARNING (expr.value) = 1;
40ffd95f
BE
9131 if (expr.original_code != C_MAYBE_CONST_EXPR
9132 && expr.original_code != SIZEOF_EXPR)
928c19bb 9133 expr.original_code = ERROR_MARK;
6866c6e8 9134 /* Don't change EXPR.ORIGINAL_TYPE. */
ebedc9a3
DM
9135 location_t loc_close_paren = c_parser_peek_token (parser)->location;
9136 set_c_expr_source_range (&expr, loc_open_paren, loc_close_paren);
27bf414c 9137 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN,
32129a17 9138 "expected %<)%>", loc_open_paren);
27bf414c
JM
9139 }
9140 break;
9141 case CPP_KEYWORD:
9142 switch (c_parser_peek_token (parser)->keyword)
9143 {
9144 case RID_FUNCTION_NAME:
9145 case RID_PRETTY_FUNCTION_NAME:
9146 case RID_C99_FUNCTION_NAME:
59bc434a 9147 expr = c_parser_predefined_identifier (parser);
27bf414c
JM
9148 break;
9149 case RID_VA_ARG:
bef08b71
DM
9150 {
9151 location_t start_loc = loc;
9152 c_parser_consume_token (parser);
32129a17
DM
9153 matching_parens parens;
9154 if (!parens.require_open (parser))
bef08b71 9155 {
8a40fef3 9156 expr.set_error ();
bef08b71
DM
9157 break;
9158 }
9159 e1 = c_parser_expr_no_commas (parser, NULL);
9160 mark_exp_read (e1.value);
9161 e1.value = c_fully_fold (e1.value, false, NULL);
9162 if (!c_parser_require (parser, CPP_COMMA, "expected %<,%>"))
9163 {
9164 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN, NULL);
8a40fef3 9165 expr.set_error ();
bef08b71
DM
9166 break;
9167 }
9168 loc = c_parser_peek_token (parser)->location;
9169 t1 = c_parser_type_name (parser);
9170 location_t end_loc = c_parser_peek_token (parser)->get_finish ();
9171 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN,
9172 "expected %<)%>");
9173 if (t1 == NULL)
9174 {
8a40fef3 9175 expr.set_error ();
bef08b71
DM
9176 }
9177 else
9178 {
9179 tree type_expr = NULL_TREE;
f187980b 9180 expr.value = c_build_va_arg (start_loc, e1.value, loc,
bef08b71
DM
9181 groktypename (t1, &type_expr, NULL));
9182 if (type_expr)
9183 {
9184 expr.value = build2 (C_MAYBE_CONST_EXPR,
9185 TREE_TYPE (expr.value), type_expr,
9186 expr.value);
9187 C_MAYBE_CONST_EXPR_NON_CONST (expr.value) = true;
9188 }
9189 set_c_expr_source_range (&expr, start_loc, end_loc);
9190 }
9191 }
27bf414c
JM
9192 break;
9193 case RID_OFFSETOF:
27bf414c 9194 {
32129a17
DM
9195 c_parser_consume_token (parser);
9196 matching_parens parens;
9197 if (!parens.require_open (parser))
9198 {
9199 expr.set_error ();
9200 break;
9201 }
9202 t1 = c_parser_type_name (parser);
9203 if (t1 == NULL)
9204 parser->error = true;
9205 if (!c_parser_require (parser, CPP_COMMA, "expected %<,%>"))
9206 gcc_assert (parser->error);
9207 if (parser->error)
9208 {
9209 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN, NULL);
9210 expr.set_error ();
9211 break;
9212 }
928c19bb 9213 tree type = groktypename (t1, NULL, NULL);
27bf414c
JM
9214 tree offsetof_ref;
9215 if (type == error_mark_node)
9216 offsetof_ref = error_mark_node;
9217 else
c2255bc4
AH
9218 {
9219 offsetof_ref = build1 (INDIRECT_REF, type, null_pointer_node);
9220 SET_EXPR_LOCATION (offsetof_ref, loc);
9221 }
27bf414c
JM
9222 /* Parse the second argument to __builtin_offsetof. We
9223 must have one identifier, and beyond that we want to
9224 accept sub structure and sub array references. */
9225 if (c_parser_next_token_is (parser, CPP_NAME))
9226 {
6ffd47b7 9227 c_token *comp_tok = c_parser_peek_token (parser);
27bf414c 9228 offsetof_ref = build_component_ref
6ffd47b7 9229 (loc, offsetof_ref, comp_tok->value, comp_tok->location);
27bf414c
JM
9230 c_parser_consume_token (parser);
9231 while (c_parser_next_token_is (parser, CPP_DOT)
9232 || c_parser_next_token_is (parser,
634b5df5
JJ
9233 CPP_OPEN_SQUARE)
9234 || c_parser_next_token_is (parser,
9235 CPP_DEREF))
27bf414c 9236 {
634b5df5
JJ
9237 if (c_parser_next_token_is (parser, CPP_DEREF))
9238 {
9239 loc = c_parser_peek_token (parser)->location;
c2255bc4
AH
9240 offsetof_ref = build_array_ref (loc,
9241 offsetof_ref,
9242 integer_zero_node);
634b5df5
JJ
9243 goto do_dot;
9244 }
9245 else if (c_parser_next_token_is (parser, CPP_DOT))
27bf414c 9246 {
634b5df5 9247 do_dot:
27bf414c
JM
9248 c_parser_consume_token (parser);
9249 if (c_parser_next_token_is_not (parser,
9250 CPP_NAME))
9251 {
9252 c_parser_error (parser, "expected identifier");
9253 break;
9254 }
6ffd47b7 9255 c_token *comp_tok = c_parser_peek_token (parser);
27bf414c 9256 offsetof_ref = build_component_ref
6ffd47b7
DM
9257 (loc, offsetof_ref, comp_tok->value,
9258 comp_tok->location);
27bf414c
JM
9259 c_parser_consume_token (parser);
9260 }
9261 else
9262 {
267bac10 9263 struct c_expr ce;
27bf414c 9264 tree idx;
6a3799eb 9265 loc = c_parser_peek_token (parser)->location;
27bf414c 9266 c_parser_consume_token (parser);
267bac10
JM
9267 ce = c_parser_expression (parser);
9268 ce = convert_lvalue_to_rvalue (loc, ce, false, false);
9269 idx = ce.value;
928c19bb 9270 idx = c_fully_fold (idx, false, NULL);
27bf414c
JM
9271 c_parser_skip_until_found (parser, CPP_CLOSE_SQUARE,
9272 "expected %<]%>");
c2255bc4 9273 offsetof_ref = build_array_ref (loc, offsetof_ref, idx);
27bf414c
JM
9274 }
9275 }
9276 }
9277 else
9278 c_parser_error (parser, "expected identifier");
bef08b71 9279 location_t end_loc = c_parser_peek_token (parser)->get_finish ();
27bf414c
JM
9280 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN,
9281 "expected %<)%>");
cf9e9959 9282 expr.value = fold_offsetof (offsetof_ref);
bef08b71 9283 set_c_expr_source_range (&expr, loc, end_loc);
27bf414c
JM
9284 }
9285 break;
9286 case RID_CHOOSE_EXPR:
27bf414c 9287 {
9771b263 9288 vec<c_expr_t, va_gc> *cexpr_list;
86785830
AS
9289 c_expr_t *e1_p, *e2_p, *e3_p;
9290 tree c;
46c6e1e2 9291 location_t close_paren_loc;
27bf414c 9292
f90e8e2e
AS
9293 c_parser_consume_token (parser);
9294 if (!c_parser_get_builtin_args (parser,
9295 "__builtin_choose_expr",
46c6e1e2
DM
9296 &cexpr_list, true,
9297 &close_paren_loc))
f90e8e2e 9298 {
8a40fef3 9299 expr.set_error ();
f90e8e2e
AS
9300 break;
9301 }
9302
9771b263 9303 if (vec_safe_length (cexpr_list) != 3)
f90e8e2e
AS
9304 {
9305 error_at (loc, "wrong number of arguments to "
9306 "%<__builtin_choose_expr%>");
8a40fef3 9307 expr.set_error ();
f90e8e2e
AS
9308 break;
9309 }
86785830 9310
9771b263
DN
9311 e1_p = &(*cexpr_list)[0];
9312 e2_p = &(*cexpr_list)[1];
9313 e3_p = &(*cexpr_list)[2];
86785830
AS
9314
9315 c = e1_p->value;
9316 mark_exp_read (e2_p->value);
9317 mark_exp_read (e3_p->value);
928c19bb
JM
9318 if (TREE_CODE (c) != INTEGER_CST
9319 || !INTEGRAL_TYPE_P (TREE_TYPE (c)))
3ba09659
AH
9320 error_at (loc,
9321 "first argument to %<__builtin_choose_expr%> not"
9322 " a constant");
928c19bb 9323 constant_expression_warning (c);
86785830 9324 expr = integer_zerop (c) ? *e3_p : *e2_p;
46c6e1e2 9325 set_c_expr_source_range (&expr, loc, close_paren_loc);
f90e8e2e 9326 break;
27bf414c 9327 }
27bf414c 9328 case RID_TYPES_COMPATIBLE_P:
27bf414c 9329 {
32129a17
DM
9330 c_parser_consume_token (parser);
9331 matching_parens parens;
9332 if (!parens.require_open (parser))
9333 {
9334 expr.set_error ();
9335 break;
9336 }
9337 t1 = c_parser_type_name (parser);
9338 if (t1 == NULL)
9339 {
9340 expr.set_error ();
9341 break;
9342 }
9343 if (!c_parser_require (parser, CPP_COMMA, "expected %<,%>"))
9344 {
9345 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN, NULL);
9346 expr.set_error ();
9347 break;
9348 }
9349 t2 = c_parser_type_name (parser);
9350 if (t2 == NULL)
9351 {
9352 expr.set_error ();
9353 break;
9354 }
4bbf545b 9355 location_t close_paren_loc = c_parser_peek_token (parser)->location;
32129a17 9356 parens.skip_until_found_close (parser);
27bf414c 9357 tree e1, e2;
9abfe986
AP
9358 e1 = groktypename (t1, NULL, NULL);
9359 e2 = groktypename (t2, NULL, NULL);
9360 if (e1 == error_mark_node || e2 == error_mark_node)
9361 {
8a40fef3 9362 expr.set_error ();
9abfe986
AP
9363 break;
9364 }
27bf414c 9365
9abfe986
AP
9366 e1 = TYPE_MAIN_VARIANT (e1);
9367 e2 = TYPE_MAIN_VARIANT (e2);
27bf414c 9368
9a9d280e
AS
9369 expr.value
9370 = comptypes (e1, e2) ? integer_one_node : integer_zero_node;
4bbf545b 9371 set_c_expr_source_range (&expr, loc, close_paren_loc);
27bf414c
JM
9372 }
9373 break;
3ca0dc60
JM
9374 case RID_BUILTIN_TGMATH:
9375 {
9376 vec<c_expr_t, va_gc> *cexpr_list;
9377 location_t close_paren_loc;
9378
9379 c_parser_consume_token (parser);
9380 if (!c_parser_get_builtin_args (parser,
9381 "__builtin_tgmath",
9382 &cexpr_list, false,
9383 &close_paren_loc))
9384 {
9385 expr.set_error ();
9386 break;
9387 }
9388
9389 if (vec_safe_length (cexpr_list) < 3)
9390 {
9391 error_at (loc, "too few arguments to %<__builtin_tgmath%>");
9392 expr.set_error ();
9393 break;
9394 }
9395
9396 unsigned int i;
9397 c_expr_t *p;
9398 FOR_EACH_VEC_ELT (*cexpr_list, i, p)
9399 *p = convert_lvalue_to_rvalue (loc, *p, true, true);
9400 unsigned int nargs = check_tgmath_function (&(*cexpr_list)[0], 1);
9401 if (nargs == 0)
9402 {
9403 expr.set_error ();
9404 break;
9405 }
9406 if (vec_safe_length (cexpr_list) < nargs)
9407 {
9408 error_at (loc, "too few arguments to %<__builtin_tgmath%>");
9409 expr.set_error ();
9410 break;
9411 }
9412 unsigned int num_functions = vec_safe_length (cexpr_list) - nargs;
9413 if (num_functions < 2)
9414 {
9415 error_at (loc, "too few arguments to %<__builtin_tgmath%>");
9416 expr.set_error ();
9417 break;
9418 }
9419
9420 /* The first NUM_FUNCTIONS expressions are the function
9421 pointers. The remaining NARGS expressions are the
9422 arguments that are to be passed to one of those
9423 functions, chosen following <tgmath.h> rules. */
9424 for (unsigned int j = 1; j < num_functions; j++)
9425 {
9426 unsigned int this_nargs
9427 = check_tgmath_function (&(*cexpr_list)[j], j + 1);
9428 if (this_nargs == 0)
9429 {
9430 expr.set_error ();
9431 goto out;
9432 }
9433 if (this_nargs != nargs)
9434 {
9435 error_at ((*cexpr_list)[j].get_location (),
9436 "argument %u of %<__builtin_tgmath%> has "
9437 "wrong number of arguments", j + 1);
9438 expr.set_error ();
9439 goto out;
9440 }
9441 }
9442
9443 /* The functions all have the same number of arguments.
9444 Determine whether arguments and return types vary in
9445 ways permitted for <tgmath.h> functions. */
9446 /* The first entry in each of these vectors is for the
9447 return type, subsequent entries for parameter
9448 types. */
9449 auto_vec<enum tgmath_parm_kind> parm_kind (nargs + 1);
9450 auto_vec<tree> parm_first (nargs + 1);
9451 auto_vec<bool> parm_complex (nargs + 1);
9452 auto_vec<bool> parm_varies (nargs + 1);
9453 tree first_type = TREE_TYPE (TREE_TYPE ((*cexpr_list)[0].value));
9454 tree first_ret = TYPE_MAIN_VARIANT (TREE_TYPE (first_type));
9455 parm_first.quick_push (first_ret);
9456 parm_complex.quick_push (TREE_CODE (first_ret) == COMPLEX_TYPE);
9457 parm_varies.quick_push (false);
9458 function_args_iterator iter;
9459 tree t;
9460 unsigned int argpos;
9461 FOREACH_FUNCTION_ARGS (first_type, t, iter)
9462 {
9463 if (t == void_type_node)
9464 break;
9465 parm_first.quick_push (TYPE_MAIN_VARIANT (t));
9466 parm_complex.quick_push (TREE_CODE (t) == COMPLEX_TYPE);
9467 parm_varies.quick_push (false);
9468 }
9469 for (unsigned int j = 1; j < num_functions; j++)
9470 {
9471 tree type = TREE_TYPE (TREE_TYPE ((*cexpr_list)[j].value));
9472 tree ret = TYPE_MAIN_VARIANT (TREE_TYPE (type));
9473 if (ret != parm_first[0])
9474 {
9475 parm_varies[0] = true;
9476 if (!SCALAR_FLOAT_TYPE_P (parm_first[0])
9477 && !COMPLEX_FLOAT_TYPE_P (parm_first[0]))
9478 {
9479 error_at ((*cexpr_list)[0].get_location (),
9480 "invalid type-generic return type for "
9481 "argument %u of %<__builtin_tgmath%>",
9482 1);
9483 expr.set_error ();
9484 goto out;
9485 }
9486 if (!SCALAR_FLOAT_TYPE_P (ret)
9487 && !COMPLEX_FLOAT_TYPE_P (ret))
9488 {
9489 error_at ((*cexpr_list)[j].get_location (),
9490 "invalid type-generic return type for "
9491 "argument %u of %<__builtin_tgmath%>",
9492 j + 1);
9493 expr.set_error ();
9494 goto out;
9495 }
9496 }
9497 if (TREE_CODE (ret) == COMPLEX_TYPE)
9498 parm_complex[0] = true;
9499 argpos = 1;
9500 FOREACH_FUNCTION_ARGS (type, t, iter)
9501 {
9502 if (t == void_type_node)
9503 break;
9504 t = TYPE_MAIN_VARIANT (t);
9505 if (t != parm_first[argpos])
9506 {
9507 parm_varies[argpos] = true;
9508 if (!SCALAR_FLOAT_TYPE_P (parm_first[argpos])
9509 && !COMPLEX_FLOAT_TYPE_P (parm_first[argpos]))
9510 {
9511 error_at ((*cexpr_list)[0].get_location (),
9512 "invalid type-generic type for "
9513 "argument %u of argument %u of "
9514 "%<__builtin_tgmath%>", argpos, 1);
9515 expr.set_error ();
9516 goto out;
9517 }
9518 if (!SCALAR_FLOAT_TYPE_P (t)
9519 && !COMPLEX_FLOAT_TYPE_P (t))
9520 {
9521 error_at ((*cexpr_list)[j].get_location (),
9522 "invalid type-generic type for "
9523 "argument %u of argument %u of "
9524 "%<__builtin_tgmath%>", argpos, j + 1);
9525 expr.set_error ();
9526 goto out;
9527 }
9528 }
9529 if (TREE_CODE (t) == COMPLEX_TYPE)
9530 parm_complex[argpos] = true;
9531 argpos++;
9532 }
9533 }
9534 enum tgmath_parm_kind max_variation = tgmath_fixed;
9535 for (unsigned int j = 0; j <= nargs; j++)
9536 {
9537 enum tgmath_parm_kind this_kind;
9538 if (parm_varies[j])
9539 {
9540 if (parm_complex[j])
9541 max_variation = this_kind = tgmath_complex;
9542 else
9543 {
9544 this_kind = tgmath_real;
9545 if (max_variation != tgmath_complex)
9546 max_variation = tgmath_real;
9547 }
9548 }
9549 else
9550 this_kind = tgmath_fixed;
9551 parm_kind.quick_push (this_kind);
9552 }
9553 if (max_variation == tgmath_fixed)
9554 {
9555 error_at (loc, "function arguments of %<__builtin_tgmath%> "
9556 "all have the same type");
9557 expr.set_error ();
9558 break;
9559 }
9560
9561 /* Identify a parameter (not the return type) that varies,
9562 including with complex types if any variation includes
9563 complex types; there must be at least one such
9564 parameter. */
9565 unsigned int tgarg = 0;
9566 for (unsigned int j = 1; j <= nargs; j++)
9567 if (parm_kind[j] == max_variation)
9568 {
9569 tgarg = j;
9570 break;
9571 }
9572 if (tgarg == 0)
9573 {
9574 error_at (loc, "function arguments of %<__builtin_tgmath%> "
9575 "lack type-generic parameter");
9576 expr.set_error ();
9577 break;
9578 }
9579
9580 /* Determine the type of the relevant parameter for each
9581 function. */
9582 auto_vec<tree> tg_type (num_functions);
9583 for (unsigned int j = 0; j < num_functions; j++)
9584 {
9585 tree type = TREE_TYPE (TREE_TYPE ((*cexpr_list)[j].value));
9586 argpos = 1;
9587 FOREACH_FUNCTION_ARGS (type, t, iter)
9588 {
9589 if (argpos == tgarg)
9590 {
9591 tg_type.quick_push (TYPE_MAIN_VARIANT (t));
9592 break;
9593 }
9594 argpos++;
9595 }
9596 }
9597
9598 /* Verify that the corresponding types are different for
9599 all the listed functions. Also determine whether all
9600 the types are complex, whether all the types are
9601 standard or binary, and whether all the types are
9602 decimal. */
9603 bool all_complex = true;
9604 bool all_binary = true;
9605 bool all_decimal = true;
9606 hash_set<tree> tg_types;
9607 FOR_EACH_VEC_ELT (tg_type, i, t)
9608 {
9609 if (TREE_CODE (t) == COMPLEX_TYPE)
9610 all_decimal = false;
9611 else
9612 {
9613 all_complex = false;
9614 if (DECIMAL_FLOAT_TYPE_P (t))
9615 all_binary = false;
9616 else
9617 all_decimal = false;
9618 }
9619 if (tg_types.add (t))
9620 {
9621 error_at ((*cexpr_list)[i].get_location (),
9622 "duplicate type-generic parameter type for "
9623 "function argument %u of %<__builtin_tgmath%>",
9624 i + 1);
9625 expr.set_error ();
9626 goto out;
9627 }
9628 }
9629
9630 /* Verify that other parameters and the return type whose
9631 types vary have their types varying in the correct
9632 way. */
9633 for (unsigned int j = 0; j < num_functions; j++)
9634 {
9635 tree exp_type = tg_type[j];
9636 tree exp_real_type = exp_type;
9637 if (TREE_CODE (exp_type) == COMPLEX_TYPE)
9638 exp_real_type = TREE_TYPE (exp_type);
9639 tree type = TREE_TYPE (TREE_TYPE ((*cexpr_list)[j].value));
9640 tree ret = TYPE_MAIN_VARIANT (TREE_TYPE (type));
9641 if ((parm_kind[0] == tgmath_complex && ret != exp_type)
9642 || (parm_kind[0] == tgmath_real && ret != exp_real_type))
9643 {
9644 error_at ((*cexpr_list)[j].get_location (),
9645 "bad return type for function argument %u "
9646 "of %<__builtin_tgmath%>", j + 1);
9647 expr.set_error ();
9648 goto out;
9649 }
9650 argpos = 1;
9651 FOREACH_FUNCTION_ARGS (type, t, iter)
9652 {
9653 if (t == void_type_node)
9654 break;
9655 t = TYPE_MAIN_VARIANT (t);
9656 if ((parm_kind[argpos] == tgmath_complex
9657 && t != exp_type)
9658 || (parm_kind[argpos] == tgmath_real
9659 && t != exp_real_type))
9660 {
9661 error_at ((*cexpr_list)[j].get_location (),
9662 "bad type for argument %u of "
9663 "function argument %u of "
9664 "%<__builtin_tgmath%>", argpos, j + 1);
9665 expr.set_error ();
9666 goto out;
9667 }
9668 argpos++;
9669 }
9670 }
9671
9672 /* The functions listed are a valid set of functions for a
9673 <tgmath.h> macro to select between. Identify the
9674 matching function, if any. First, the argument types
9675 must be combined following <tgmath.h> rules. Integer
9676 types are treated as _Decimal64 if any type-generic
9677 argument is decimal, or if the only alternatives for
9678 type-generic arguments are of decimal types, and are
9679 otherwise treated as double (or _Complex double for
c5c5822a
JM
9680 complex integer types, or _Float64 or _Complex _Float64
9681 if all the return types are the same _FloatN or
9682 _FloatNx type). After that adjustment, types are
9683 combined following the usual arithmetic conversions.
9684 If the function only accepts complex arguments, a
9685 complex type is produced. */
3ca0dc60
JM
9686 bool arg_complex = all_complex;
9687 bool arg_binary = all_binary;
9688 bool arg_int_decimal = all_decimal;
9689 for (unsigned int j = 1; j <= nargs; j++)
9690 {
9691 if (parm_kind[j] == tgmath_fixed)
9692 continue;
9693 c_expr_t *ce = &(*cexpr_list)[num_functions + j - 1];
9694 tree type = TREE_TYPE (ce->value);
9695 if (!INTEGRAL_TYPE_P (type)
9696 && !SCALAR_FLOAT_TYPE_P (type)
9697 && TREE_CODE (type) != COMPLEX_TYPE)
9698 {
9699 error_at (ce->get_location (),
9700 "invalid type of argument %u of type-generic "
9701 "function", j);
9702 expr.set_error ();
9703 goto out;
9704 }
9705 if (DECIMAL_FLOAT_TYPE_P (type))
9706 {
9707 arg_int_decimal = true;
9708 if (all_complex)
9709 {
9710 error_at (ce->get_location (),
9711 "decimal floating-point argument %u to "
9712 "complex-only type-generic function", j);
9713 expr.set_error ();
9714 goto out;
9715 }
9716 else if (all_binary)
9717 {
9718 error_at (ce->get_location (),
9719 "decimal floating-point argument %u to "
9720 "binary-only type-generic function", j);
9721 expr.set_error ();
9722 goto out;
9723 }
9724 else if (arg_complex)
9725 {
9726 error_at (ce->get_location (),
9727 "both complex and decimal floating-point "
9728 "arguments to type-generic function");
9729 expr.set_error ();
9730 goto out;
9731 }
9732 else if (arg_binary)
9733 {
9734 error_at (ce->get_location (),
9735 "both binary and decimal floating-point "
9736 "arguments to type-generic function");
9737 expr.set_error ();
9738 goto out;
9739 }
9740 }
9741 else if (TREE_CODE (type) == COMPLEX_TYPE)
9742 {
9743 arg_complex = true;
9744 if (COMPLEX_FLOAT_TYPE_P (type))
9745 arg_binary = true;
9746 if (all_decimal)
9747 {
9748 error_at (ce->get_location (),
9749 "complex argument %u to "
9750 "decimal-only type-generic function", j);
9751 expr.set_error ();
9752 goto out;
9753 }
9754 else if (arg_int_decimal)
9755 {
9756 error_at (ce->get_location (),
9757 "both complex and decimal floating-point "
9758 "arguments to type-generic function");
9759 expr.set_error ();
9760 goto out;
9761 }
9762 }
9763 else if (SCALAR_FLOAT_TYPE_P (type))
9764 {
9765 arg_binary = true;
9766 if (all_decimal)
9767 {
9768 error_at (ce->get_location (),
9769 "binary argument %u to "
9770 "decimal-only type-generic function", j);
9771 expr.set_error ();
9772 goto out;
9773 }
9774 else if (arg_int_decimal)
9775 {
9776 error_at (ce->get_location (),
9777 "both binary and decimal floating-point "
9778 "arguments to type-generic function");
9779 expr.set_error ();
9780 goto out;
9781 }
9782 }
9783 }
c5c5822a
JM
9784 /* For a macro rounding its result to a narrower type, map
9785 integer types to _Float64 not double if the return type
9786 is a _FloatN or _FloatNx type. */
9787 bool arg_int_float64 = false;
9788 if (parm_kind[0] == tgmath_fixed
9789 && SCALAR_FLOAT_TYPE_P (parm_first[0])
9790 && float64_type_node != NULL_TREE)
9791 for (unsigned int j = 0; j < NUM_FLOATN_NX_TYPES; j++)
9792 if (parm_first[0] == FLOATN_TYPE_NODE (j))
9793 {
9794 arg_int_float64 = true;
9795 break;
9796 }
3ca0dc60
JM
9797 tree arg_real = NULL_TREE;
9798 for (unsigned int j = 1; j <= nargs; j++)
9799 {
9800 if (parm_kind[j] == tgmath_fixed)
9801 continue;
9802 c_expr_t *ce = &(*cexpr_list)[num_functions + j - 1];
9803 tree type = TYPE_MAIN_VARIANT (TREE_TYPE (ce->value));
9804 if (TREE_CODE (type) == COMPLEX_TYPE)
9805 type = TREE_TYPE (type);
9806 if (INTEGRAL_TYPE_P (type))
9807 type = (arg_int_decimal
9808 ? dfloat64_type_node
c5c5822a
JM
9809 : arg_int_float64
9810 ? float64_type_node
3ca0dc60
JM
9811 : double_type_node);
9812 if (arg_real == NULL_TREE)
9813 arg_real = type;
9814 else
9815 arg_real = common_type (arg_real, type);
9816 if (arg_real == error_mark_node)
9817 {
9818 expr.set_error ();
9819 goto out;
9820 }
9821 }
9822 tree arg_type = (arg_complex
9823 ? build_complex_type (arg_real)
9824 : arg_real);
9825
9826 /* Look for a function to call with type-generic parameter
9827 type ARG_TYPE. */
9828 c_expr_t *fn = NULL;
9829 for (unsigned int j = 0; j < num_functions; j++)
9830 {
9831 if (tg_type[j] == arg_type)
9832 {
9833 fn = &(*cexpr_list)[j];
9834 break;
9835 }
9836 }
9837 if (fn == NULL
9838 && parm_kind[0] == tgmath_fixed
9839 && SCALAR_FLOAT_TYPE_P (parm_first[0]))
9840 {
9841 /* Presume this is a macro that rounds its result to a
9842 narrower type, and look for the first function with
9843 at least the range and precision of the argument
9844 type. */
9845 for (unsigned int j = 0; j < num_functions; j++)
9846 {
9847 if (arg_complex
9848 != (TREE_CODE (tg_type[j]) == COMPLEX_TYPE))
9849 continue;
9850 tree real_tg_type = (arg_complex
9851 ? TREE_TYPE (tg_type[j])
9852 : tg_type[j]);
9853 if (DECIMAL_FLOAT_TYPE_P (arg_real)
9854 != DECIMAL_FLOAT_TYPE_P (real_tg_type))
9855 continue;
9856 scalar_float_mode arg_mode
9857 = SCALAR_FLOAT_TYPE_MODE (arg_real);
9858 scalar_float_mode tg_mode
9859 = SCALAR_FLOAT_TYPE_MODE (real_tg_type);
9860 const real_format *arg_fmt = REAL_MODE_FORMAT (arg_mode);
9861 const real_format *tg_fmt = REAL_MODE_FORMAT (tg_mode);
9862 if (arg_fmt->b == tg_fmt->b
9863 && arg_fmt->p <= tg_fmt->p
9864 && arg_fmt->emax <= tg_fmt->emax
9865 && (arg_fmt->emin - arg_fmt->p
9866 >= tg_fmt->emin - tg_fmt->p))
9867 {
9868 fn = &(*cexpr_list)[j];
9869 break;
9870 }
9871 }
9872 }
9873 if (fn == NULL)
9874 {
9875 error_at (loc, "no matching function for type-generic call");
9876 expr.set_error ();
9877 break;
9878 }
9879
9880 /* Construct a call to FN. */
9881 vec<tree, va_gc> *args;
9882 vec_alloc (args, nargs);
9883 vec<tree, va_gc> *origtypes;
9884 vec_alloc (origtypes, nargs);
9885 auto_vec<location_t> arg_loc (nargs);
9886 for (unsigned int j = 0; j < nargs; j++)
9887 {
9888 c_expr_t *ce = &(*cexpr_list)[num_functions + j];
9889 args->quick_push (ce->value);
9890 arg_loc.quick_push (ce->get_location ());
9891 origtypes->quick_push (ce->original_type);
9892 }
9893 expr.value = c_build_function_call_vec (loc, arg_loc, fn->value,
9894 args, origtypes);
9895 set_c_expr_source_range (&expr, loc, close_paren_loc);
9896 break;
9897 }
74893f25
RH
9898 case RID_BUILTIN_CALL_WITH_STATIC_CHAIN:
9899 {
9900 vec<c_expr_t, va_gc> *cexpr_list;
9901 c_expr_t *e2_p;
9902 tree chain_value;
46c6e1e2 9903 location_t close_paren_loc;
74893f25
RH
9904
9905 c_parser_consume_token (parser);
9906 if (!c_parser_get_builtin_args (parser,
9907 "__builtin_call_with_static_chain",
46c6e1e2
DM
9908 &cexpr_list, false,
9909 &close_paren_loc))
74893f25 9910 {
8a40fef3 9911 expr.set_error ();
74893f25
RH
9912 break;
9913 }
9914 if (vec_safe_length (cexpr_list) != 2)
9915 {
9916 error_at (loc, "wrong number of arguments to "
9917 "%<__builtin_call_with_static_chain%>");
8a40fef3 9918 expr.set_error ();
74893f25
RH
9919 break;
9920 }
9921
9922 expr = (*cexpr_list)[0];
9923 e2_p = &(*cexpr_list)[1];
9924 *e2_p = convert_lvalue_to_rvalue (loc, *e2_p, true, true);
9925 chain_value = e2_p->value;
9926 mark_exp_read (chain_value);
9927
9928 if (TREE_CODE (expr.value) != CALL_EXPR)
9929 error_at (loc, "first argument to "
9930 "%<__builtin_call_with_static_chain%> "
9931 "must be a call expression");
9932 else if (TREE_CODE (TREE_TYPE (chain_value)) != POINTER_TYPE)
9933 error_at (loc, "second argument to "
9934 "%<__builtin_call_with_static_chain%> "
9935 "must be a pointer type");
9936 else
9937 CALL_EXPR_STATIC_CHAIN (expr.value) = chain_value;
46c6e1e2 9938 set_c_expr_source_range (&expr, loc, close_paren_loc);
74893f25
RH
9939 break;
9940 }
d4a83c10 9941 case RID_BUILTIN_COMPLEX:
86785830 9942 {
9771b263 9943 vec<c_expr_t, va_gc> *cexpr_list;
86785830 9944 c_expr_t *e1_p, *e2_p;
46c6e1e2 9945 location_t close_paren_loc;
86785830 9946
f90e8e2e
AS
9947 c_parser_consume_token (parser);
9948 if (!c_parser_get_builtin_args (parser,
9949 "__builtin_complex",
46c6e1e2
DM
9950 &cexpr_list, false,
9951 &close_paren_loc))
f90e8e2e 9952 {
8a40fef3 9953 expr.set_error ();
f90e8e2e
AS
9954 break;
9955 }
9956
9771b263 9957 if (vec_safe_length (cexpr_list) != 2)
f90e8e2e
AS
9958 {
9959 error_at (loc, "wrong number of arguments to "
9960 "%<__builtin_complex%>");
8a40fef3 9961 expr.set_error ();
f90e8e2e
AS
9962 break;
9963 }
86785830 9964
9771b263
DN
9965 e1_p = &(*cexpr_list)[0];
9966 e2_p = &(*cexpr_list)[1];
86785830 9967
267bac10 9968 *e1_p = convert_lvalue_to_rvalue (loc, *e1_p, true, true);
86785830
AS
9969 if (TREE_CODE (e1_p->value) == EXCESS_PRECISION_EXPR)
9970 e1_p->value = convert (TREE_TYPE (e1_p->value),
9971 TREE_OPERAND (e1_p->value, 0));
267bac10 9972 *e2_p = convert_lvalue_to_rvalue (loc, *e2_p, true, true);
86785830
AS
9973 if (TREE_CODE (e2_p->value) == EXCESS_PRECISION_EXPR)
9974 e2_p->value = convert (TREE_TYPE (e2_p->value),
9975 TREE_OPERAND (e2_p->value, 0));
9976 if (!SCALAR_FLOAT_TYPE_P (TREE_TYPE (e1_p->value))
9977 || DECIMAL_FLOAT_TYPE_P (TREE_TYPE (e1_p->value))
9978 || !SCALAR_FLOAT_TYPE_P (TREE_TYPE (e2_p->value))
9979 || DECIMAL_FLOAT_TYPE_P (TREE_TYPE (e2_p->value)))
f90e8e2e
AS
9980 {
9981 error_at (loc, "%<__builtin_complex%> operand "
9982 "not of real binary floating-point type");
8a40fef3 9983 expr.set_error ();
f90e8e2e
AS
9984 break;
9985 }
86785830
AS
9986 if (TYPE_MAIN_VARIANT (TREE_TYPE (e1_p->value))
9987 != TYPE_MAIN_VARIANT (TREE_TYPE (e2_p->value)))
f90e8e2e
AS
9988 {
9989 error_at (loc,
9990 "%<__builtin_complex%> operands of different types");
8a40fef3 9991 expr.set_error ();
f90e8e2e
AS
9992 break;
9993 }
f3bede71
MP
9994 pedwarn_c90 (loc, OPT_Wpedantic,
9995 "ISO C90 does not support complex types");
46c6e1e2
DM
9996 expr.value = build2_loc (loc, COMPLEX_EXPR,
9997 build_complex_type
9998 (TYPE_MAIN_VARIANT
9999 (TREE_TYPE (e1_p->value))),
10000 e1_p->value, e2_p->value);
10001 set_c_expr_source_range (&expr, loc, close_paren_loc);
f90e8e2e
AS
10002 break;
10003 }
10004 case RID_BUILTIN_SHUFFLE:
10005 {
9771b263 10006 vec<c_expr_t, va_gc> *cexpr_list;
9243c51d
JJ
10007 unsigned int i;
10008 c_expr_t *p;
46c6e1e2 10009 location_t close_paren_loc;
86785830 10010
f90e8e2e
AS
10011 c_parser_consume_token (parser);
10012 if (!c_parser_get_builtin_args (parser,
10013 "__builtin_shuffle",
46c6e1e2
DM
10014 &cexpr_list, false,
10015 &close_paren_loc))
f90e8e2e 10016 {
8a40fef3 10017 expr.set_error ();
f90e8e2e
AS
10018 break;
10019 }
10020
9771b263 10021 FOR_EACH_VEC_SAFE_ELT (cexpr_list, i, p)
267bac10 10022 *p = convert_lvalue_to_rvalue (loc, *p, true, true);
9243c51d 10023
9771b263 10024 if (vec_safe_length (cexpr_list) == 2)
d8fcab68
JJ
10025 expr.value = c_build_vec_perm_expr (loc, (*cexpr_list)[0].value,
10026 NULL_TREE,
10027 (*cexpr_list)[1].value);
86785830 10028
9771b263 10029 else if (vec_safe_length (cexpr_list) == 3)
d8fcab68
JJ
10030 expr.value = c_build_vec_perm_expr (loc, (*cexpr_list)[0].value,
10031 (*cexpr_list)[1].value,
10032 (*cexpr_list)[2].value);
f90e8e2e
AS
10033 else
10034 {
10035 error_at (loc, "wrong number of arguments to "
10036 "%<__builtin_shuffle%>");
8a40fef3 10037 expr.set_error ();
f90e8e2e 10038 }
46c6e1e2 10039 set_c_expr_source_range (&expr, loc, close_paren_loc);
f90e8e2e
AS
10040 break;
10041 }
d8fcab68
JJ
10042 case RID_BUILTIN_CONVERTVECTOR:
10043 {
10044 location_t start_loc = loc;
10045 c_parser_consume_token (parser);
10046 matching_parens parens;
10047 if (!parens.require_open (parser))
10048 {
10049 expr.set_error ();
10050 break;
10051 }
10052 e1 = c_parser_expr_no_commas (parser, NULL);
10053 mark_exp_read (e1.value);
10054 if (!c_parser_require (parser, CPP_COMMA, "expected %<,%>"))
10055 {
10056 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN, NULL);
10057 expr.set_error ();
10058 break;
10059 }
10060 loc = c_parser_peek_token (parser)->location;
10061 t1 = c_parser_type_name (parser);
10062 location_t end_loc = c_parser_peek_token (parser)->get_finish ();
10063 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN,
10064 "expected %<)%>");
10065 if (t1 == NULL)
10066 expr.set_error ();
10067 else
10068 {
10069 tree type_expr = NULL_TREE;
10070 expr.value = c_build_vec_convert (start_loc, e1.value, loc,
10071 groktypename (t1, &type_expr,
10072 NULL));
10073 set_c_expr_source_range (&expr, start_loc, end_loc);
10074 }
10075 }
10076 break;
27bf414c 10077 case RID_AT_SELECTOR:
27bf414c 10078 {
32129a17
DM
10079 gcc_assert (c_dialect_objc ());
10080 c_parser_consume_token (parser);
10081 matching_parens parens;
10082 if (!parens.require_open (parser))
10083 {
10084 expr.set_error ();
10085 break;
10086 }
27bf414c 10087 tree sel = c_parser_objc_selector_arg (parser);
cbd03aee 10088 location_t close_loc = c_parser_peek_token (parser)->location;
32129a17 10089 parens.skip_until_found_close (parser);
c2255bc4 10090 expr.value = objc_build_selector_expr (loc, sel);
cbd03aee 10091 set_c_expr_source_range (&expr, loc, close_loc);
27bf414c
JM
10092 }
10093 break;
10094 case RID_AT_PROTOCOL:
27bf414c 10095 {
32129a17
DM
10096 gcc_assert (c_dialect_objc ());
10097 c_parser_consume_token (parser);
10098 matching_parens parens;
10099 if (!parens.require_open (parser))
10100 {
10101 expr.set_error ();
10102 break;
10103 }
10104 if (c_parser_next_token_is_not (parser, CPP_NAME))
10105 {
10106 c_parser_error (parser, "expected identifier");
10107 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN, NULL);
10108 expr.set_error ();
10109 break;
10110 }
27bf414c
JM
10111 tree id = c_parser_peek_token (parser)->value;
10112 c_parser_consume_token (parser);
cbd03aee 10113 location_t close_loc = c_parser_peek_token (parser)->location;
32129a17 10114 parens.skip_until_found_close (parser);
27bf414c 10115 expr.value = objc_build_protocol_expr (id);
cbd03aee 10116 set_c_expr_source_range (&expr, loc, close_loc);
27bf414c
JM
10117 }
10118 break;
10119 case RID_AT_ENCODE:
27bf414c 10120 {
32129a17
DM
10121 /* Extension to support C-structures in the archiver. */
10122 gcc_assert (c_dialect_objc ());
10123 c_parser_consume_token (parser);
10124 matching_parens parens;
10125 if (!parens.require_open (parser))
10126 {
10127 expr.set_error ();
10128 break;
10129 }
10130 t1 = c_parser_type_name (parser);
10131 if (t1 == NULL)
10132 {
10133 expr.set_error ();
10134 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN, NULL);
10135 break;
10136 }
cbd03aee 10137 location_t close_loc = c_parser_peek_token (parser)->location;
32129a17 10138 parens.skip_until_found_close (parser);
928c19bb 10139 tree type = groktypename (t1, NULL, NULL);
27bf414c 10140 expr.value = objc_build_encode_expr (type);
cbd03aee 10141 set_c_expr_source_range (&expr, loc, close_loc);
27bf414c
JM
10142 }
10143 break;
433cc7b0
TT
10144 case RID_GENERIC:
10145 expr = c_parser_generic_selection (parser);
10146 break;
27bf414c
JM
10147 default:
10148 c_parser_error (parser, "expected expression");
8a40fef3 10149 expr.set_error ();
27bf414c
JM
10150 break;
10151 }
10152 break;
10153 case CPP_OPEN_SQUARE:
10154 if (c_dialect_objc ())
10155 {
10156 tree receiver, args;
10157 c_parser_consume_token (parser);
10158 receiver = c_parser_objc_receiver (parser);
10159 args = c_parser_objc_message_args (parser);
cbd03aee 10160 location_t close_loc = c_parser_peek_token (parser)->location;
27bf414c
JM
10161 c_parser_skip_until_found (parser, CPP_CLOSE_SQUARE,
10162 "expected %<]%>");
eb345401 10163 expr.value = objc_build_message_expr (receiver, args);
cbd03aee 10164 set_c_expr_source_range (&expr, loc, close_loc);
27bf414c
JM
10165 break;
10166 }
10167 /* Else fall through to report error. */
191816a3 10168 /* FALLTHRU */
27bf414c
JM
10169 default:
10170 c_parser_error (parser, "expected expression");
8a40fef3 10171 expr.set_error ();
27bf414c
JM
10172 break;
10173 }
3ca0dc60 10174 out:
a10704e1
DM
10175 return c_parser_postfix_expression_after_primary
10176 (parser, EXPR_LOC_OR_LOC (expr.value, loc), expr);
27bf414c
JM
10177}
10178
10179/* Parse a postfix expression after a parenthesized type name: the
10180 brace-enclosed initializer of a compound literal, possibly followed
10181 by some postfix operators. This is separate because it is not
10182 possible to tell until after the type name whether a cast
10183 expression has a cast or a compound literal, or whether the operand
10184 of sizeof is a parenthesized type name or starts with a compound
24b97832
ILT
10185 literal. TYPE_LOC is the location where TYPE_NAME starts--the
10186 location of the first token after the parentheses around the type
10187 name. */
27bf414c
JM
10188
10189static struct c_expr
10190c_parser_postfix_expression_after_paren_type (c_parser *parser,
24b97832
ILT
10191 struct c_type_name *type_name,
10192 location_t type_loc)
27bf414c
JM
10193{
10194 tree type;
10195 struct c_expr init;
928c19bb 10196 bool non_const;
27bf414c 10197 struct c_expr expr;
c7412148 10198 location_t start_loc;
928c19bb
JM
10199 tree type_expr = NULL_TREE;
10200 bool type_expr_const = true;
c2255bc4 10201 check_compound_literal_type (type_loc, type_name);
5dd9a9d0
DM
10202 rich_location richloc (line_table, type_loc);
10203 start_init (NULL_TREE, NULL, 0, &richloc);
928c19bb 10204 type = groktypename (type_name, &type_expr, &type_expr_const);
c7412148 10205 start_loc = c_parser_peek_token (parser)->location;
85cad37c 10206 if (type != error_mark_node && C_TYPE_VARIABLE_SIZE (type))
27bf414c 10207 {
24b97832 10208 error_at (type_loc, "compound literal has variable size");
27bf414c
JM
10209 type = error_mark_node;
10210 }
16595a1f 10211 init = c_parser_braced_init (parser, type, false, NULL);
27bf414c 10212 finish_init ();
d033409e 10213 maybe_warn_string_init (type_loc, type, init);
27bf414c 10214
36c5e70a
BE
10215 if (type != error_mark_node
10216 && !ADDR_SPACE_GENERIC_P (TYPE_ADDR_SPACE (type))
10217 && current_function_decl)
10218 {
10219 error ("compound literal qualified by address-space qualifier");
10220 type = error_mark_node;
10221 }
10222
f3bede71 10223 pedwarn_c90 (start_loc, OPT_Wpedantic, "ISO C90 forbids compound literals");
928c19bb
JM
10224 non_const = ((init.value && TREE_CODE (init.value) == CONSTRUCTOR)
10225 ? CONSTRUCTOR_NON_CONST (init.value)
10226 : init.original_code == C_MAYBE_CONST_EXPR);
10227 non_const |= !type_expr_const;
4b2b493f
JM
10228 unsigned int alignas_align = 0;
10229 if (type != error_mark_node
10230 && type_name->specs->align_log != -1)
10231 {
10232 alignas_align = 1U << type_name->specs->align_log;
10233 if (alignas_align < min_align_of_type (type))
10234 {
10235 error_at (type_name->specs->locations[cdw_alignas],
10236 "%<_Alignas%> specifiers cannot reduce "
10237 "alignment of compound literal");
10238 alignas_align = 0;
10239 }
10240 }
10241 expr.value = build_compound_literal (start_loc, type, init.value, non_const,
10242 alignas_align);
bef08b71 10243 set_c_expr_source_range (&expr, init.src_range);
27bf414c 10244 expr.original_code = ERROR_MARK;
6866c6e8 10245 expr.original_type = NULL;
a5b5c8b6
MP
10246 if (type != error_mark_node
10247 && expr.value != error_mark_node
10248 && type_expr)
928c19bb
JM
10249 {
10250 if (TREE_CODE (expr.value) == C_MAYBE_CONST_EXPR)
10251 {
10252 gcc_assert (C_MAYBE_CONST_EXPR_PRE (expr.value) == NULL_TREE);
10253 C_MAYBE_CONST_EXPR_PRE (expr.value) = type_expr;
10254 }
10255 else
10256 {
10257 gcc_assert (!non_const);
10258 expr.value = build2 (C_MAYBE_CONST_EXPR, type,
10259 type_expr, expr.value);
10260 }
10261 }
c2255bc4 10262 return c_parser_postfix_expression_after_primary (parser, start_loc, expr);
27bf414c
JM
10263}
10264
1a4049e7
JJ
10265/* Callback function for sizeof_pointer_memaccess_warning to compare
10266 types. */
10267
10268static bool
10269sizeof_ptr_memacc_comptypes (tree type1, tree type2)
10270{
10271 return comptypes (type1, type2) == 1;
10272}
10273
80c6d1f4 10274/* Warn for patterns where abs-like function appears to be used incorrectly,
ce6f0888
MJ
10275 gracefully ignore any non-abs-like function. The warning location should
10276 be LOC. FNDECL is the declaration of called function, it must be a
80c6d1f4
MJ
10277 BUILT_IN_NORMAL function. ARG is the first and only argument of the
10278 call. */
10279
10280static void
10281warn_for_abs (location_t loc, tree fndecl, tree arg)
10282{
3c2a70cb
MS
10283 /* Avoid warning in unreachable subexpressions. */
10284 if (c_inhibit_evaluation_warnings)
10285 return;
10286
80c6d1f4
MJ
10287 tree atype = TREE_TYPE (arg);
10288
10289 /* Casts from pointers (and thus arrays and fndecls) will generate
10290 -Wint-conversion warnings. Most other wrong types hopefully lead to type
10291 mismatch errors. TODO: Think about what to do with FIXED_POINT_TYPE_P
10292 types and possibly other exotic types. */
10293 if (!INTEGRAL_TYPE_P (atype)
10294 && !SCALAR_FLOAT_TYPE_P (atype)
10295 && TREE_CODE (atype) != COMPLEX_TYPE)
10296 return;
10297
10298 enum built_in_function fcode = DECL_FUNCTION_CODE (fndecl);
10299
10300 switch (fcode)
10301 {
10302 case BUILT_IN_ABS:
10303 case BUILT_IN_LABS:
10304 case BUILT_IN_LLABS:
10305 case BUILT_IN_IMAXABS:
10306 if (!INTEGRAL_TYPE_P (atype))
10307 {
10308 if (SCALAR_FLOAT_TYPE_P (atype))
10309 warning_at (loc, OPT_Wabsolute_value,
10310 "using integer absolute value function %qD when "
0ecf545c 10311 "argument is of floating-point type %qT",
80c6d1f4
MJ
10312 fndecl, atype);
10313 else if (TREE_CODE (atype) == COMPLEX_TYPE)
10314 warning_at (loc, OPT_Wabsolute_value,
10315 "using integer absolute value function %qD when "
10316 "argument is of complex type %qT", fndecl, atype);
10317 else
10318 gcc_unreachable ();
10319 return;
10320 }
10321 if (TYPE_UNSIGNED (atype))
10322 warning_at (loc, OPT_Wabsolute_value,
10323 "taking the absolute value of unsigned type %qT "
10324 "has no effect", atype);
10325 break;
10326
10327 CASE_FLT_FN (BUILT_IN_FABS):
10328 CASE_FLT_FN_FLOATN_NX (BUILT_IN_FABS):
10329 if (!SCALAR_FLOAT_TYPE_P (atype)
10330 || DECIMAL_FLOAT_MODE_P (TYPE_MODE (atype)))
10331 {
10332 if (INTEGRAL_TYPE_P (atype))
10333 warning_at (loc, OPT_Wabsolute_value,
0ecf545c 10334 "using floating-point absolute value function %qD "
80c6d1f4
MJ
10335 "when argument is of integer type %qT", fndecl, atype);
10336 else if (DECIMAL_FLOAT_TYPE_P (atype))
10337 warning_at (loc, OPT_Wabsolute_value,
0ecf545c
MS
10338 "using floating-point absolute value function %qD "
10339 "when argument is of decimal floating-point type %qT",
80c6d1f4
MJ
10340 fndecl, atype);
10341 else if (TREE_CODE (atype) == COMPLEX_TYPE)
10342 warning_at (loc, OPT_Wabsolute_value,
0ecf545c 10343 "using floating-point absolute value function %qD when "
80c6d1f4
MJ
10344 "argument is of complex type %qT", fndecl, atype);
10345 else
10346 gcc_unreachable ();
10347 return;
10348 }
10349 break;
10350
10351 CASE_FLT_FN (BUILT_IN_CABS):
10352 if (TREE_CODE (atype) != COMPLEX_TYPE)
10353 {
10354 if (INTEGRAL_TYPE_P (atype))
10355 warning_at (loc, OPT_Wabsolute_value,
10356 "using complex absolute value function %qD when "
10357 "argument is of integer type %qT", fndecl, atype);
10358 else if (SCALAR_FLOAT_TYPE_P (atype))
10359 warning_at (loc, OPT_Wabsolute_value,
10360 "using complex absolute value function %qD when "
0ecf545c 10361 "argument is of floating-point type %qT",
80c6d1f4
MJ
10362 fndecl, atype);
10363 else
10364 gcc_unreachable ();
10365
10366 return;
10367 }
10368 break;
10369
10370 case BUILT_IN_FABSD32:
10371 case BUILT_IN_FABSD64:
10372 case BUILT_IN_FABSD128:
10373 if (!DECIMAL_FLOAT_TYPE_P (atype))
10374 {
10375 if (INTEGRAL_TYPE_P (atype))
10376 warning_at (loc, OPT_Wabsolute_value,
0ecf545c 10377 "using decimal floating-point absolute value "
80c6d1f4
MJ
10378 "function %qD when argument is of integer type %qT",
10379 fndecl, atype);
10380 else if (SCALAR_FLOAT_TYPE_P (atype))
10381 warning_at (loc, OPT_Wabsolute_value,
0ecf545c
MS
10382 "using decimal floating-point absolute value "
10383 "function %qD when argument is of floating-point "
80c6d1f4
MJ
10384 "type %qT", fndecl, atype);
10385 else if (TREE_CODE (atype) == COMPLEX_TYPE)
10386 warning_at (loc, OPT_Wabsolute_value,
0ecf545c 10387 "using decimal floating-point absolute value "
80c6d1f4
MJ
10388 "function %qD when argument is of complex type %qT",
10389 fndecl, atype);
10390 else
10391 gcc_unreachable ();
10392 return;
10393 }
10394 break;
10395
10396 default:
10397 return;
10398 }
10399
ce6f0888
MJ
10400 if (!TYPE_ARG_TYPES (TREE_TYPE (fndecl)))
10401 return;
10402
80c6d1f4
MJ
10403 tree ftype = TREE_VALUE (TYPE_ARG_TYPES (TREE_TYPE (fndecl)));
10404 if (TREE_CODE (atype) == COMPLEX_TYPE)
10405 {
10406 gcc_assert (TREE_CODE (ftype) == COMPLEX_TYPE);
10407 atype = TREE_TYPE (atype);
10408 ftype = TREE_TYPE (ftype);
10409 }
10410
10411 if (TYPE_PRECISION (ftype) < TYPE_PRECISION (atype))
10412 warning_at (loc, OPT_Wabsolute_value,
10413 "absolute value function %qD given an argument of type %qT "
10414 "but has parameter of type %qT which may cause truncation "
10415 "of value", fndecl, atype, ftype);
10416}
10417
10418
27bf414c 10419/* Parse a postfix expression after the initial primary or compound
c2255bc4
AH
10420 literal; that is, parse a series of postfix operators.
10421
10422 EXPR_LOC is the location of the primary expression. */
27bf414c
JM
10423
10424static struct c_expr
10425c_parser_postfix_expression_after_primary (c_parser *parser,
c2255bc4 10426 location_t expr_loc,
27bf414c
JM
10427 struct c_expr expr)
10428{
928c19bb 10429 struct c_expr orig_expr;
bbbbb16a 10430 tree ident, idx;
6ffd47b7 10431 location_t sizeof_arg_loc[3], comp_loc;
3a785c97 10432 tree sizeof_arg[3];
b108f48f 10433 unsigned int literal_zero_mask;
3a785c97 10434 unsigned int i;
9771b263 10435 vec<tree, va_gc> *exprlist;
2ee028f1 10436 vec<tree, va_gc> *origtypes = NULL;
81e5eca8 10437 vec<location_t> arg_loc = vNULL;
ebedc9a3
DM
10438 location_t start;
10439 location_t finish;
81e5eca8 10440
27bf414c
JM
10441 while (true)
10442 {
c2255bc4 10443 location_t op_loc = c_parser_peek_token (parser)->location;
27bf414c
JM
10444 switch (c_parser_peek_token (parser)->type)
10445 {
10446 case CPP_OPEN_SQUARE:
10447 /* Array reference. */
10448 c_parser_consume_token (parser);
5e9d6aa4
JK
10449 idx = c_parser_expression (parser).value;
10450 c_parser_skip_until_found (parser, CPP_CLOSE_SQUARE,
10451 "expected %<]%>");
10452 start = expr.get_start ();
10453 finish = parser->tokens_buf[0].location;
10454 expr.value = build_array_ref (op_loc, expr.value, idx);
10455 set_c_expr_source_range (&expr, start, finish);
27bf414c 10456 expr.original_code = ERROR_MARK;
6866c6e8 10457 expr.original_type = NULL;
27bf414c
JM
10458 break;
10459 case CPP_OPEN_PAREN:
10460 /* Function call. */
10461 c_parser_consume_token (parser);
3a785c97
JJ
10462 for (i = 0; i < 3; i++)
10463 {
10464 sizeof_arg[i] = NULL_TREE;
10465 sizeof_arg_loc[i] = UNKNOWN_LOCATION;
10466 }
b108f48f 10467 literal_zero_mask = 0;
27bf414c 10468 if (c_parser_next_token_is (parser, CPP_CLOSE_PAREN))
bbbbb16a 10469 exprlist = NULL;
27bf414c 10470 else
1a4049e7 10471 exprlist = c_parser_expr_list (parser, true, false, &origtypes,
81e5eca8 10472 sizeof_arg_loc, sizeof_arg,
b108f48f 10473 &arg_loc, &literal_zero_mask);
27bf414c
JM
10474 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN,
10475 "expected %<)%>");
928c19bb 10476 orig_expr = expr;
ebfbbdc5 10477 mark_exp_read (expr.value);
3a785c97
JJ
10478 if (warn_sizeof_pointer_memaccess)
10479 sizeof_pointer_memaccess_warning (sizeof_arg_loc,
1a4049e7 10480 expr.value, exprlist,
3a785c97 10481 sizeof_arg,
1a4049e7 10482 sizeof_ptr_memacc_comptypes);
80c6d1f4 10483 if (TREE_CODE (expr.value) == FUNCTION_DECL)
c1e1f433 10484 {
80c6d1f4
MJ
10485 if (fndecl_built_in_p (expr.value, BUILT_IN_MEMSET)
10486 && vec_safe_length (exprlist) == 3)
10487 {
10488 tree arg0 = (*exprlist)[0];
10489 tree arg2 = (*exprlist)[2];
10490 warn_for_memset (expr_loc, arg0, arg2, literal_zero_mask);
10491 }
10492 if (warn_absolute_value
10493 && fndecl_built_in_p (expr.value, BUILT_IN_NORMAL)
10494 && vec_safe_length (exprlist) == 1)
10495 warn_for_abs (expr_loc, expr.value, (*exprlist)[0]);
c1e1f433 10496 }
b108f48f 10497
ebedc9a3
DM
10498 start = expr.get_start ();
10499 finish = parser->tokens_buf[0].get_finish ();
8edbfaa6
JJ
10500 expr.value
10501 = c_build_function_call_vec (expr_loc, arg_loc, expr.value,
10502 exprlist, origtypes);
ebedc9a3
DM
10503 set_c_expr_source_range (&expr, start, finish);
10504
27bf414c 10505 expr.original_code = ERROR_MARK;
928c19bb
JM
10506 if (TREE_CODE (expr.value) == INTEGER_CST
10507 && TREE_CODE (orig_expr.value) == FUNCTION_DECL
3d78e008 10508 && fndecl_built_in_p (orig_expr.value, BUILT_IN_CONSTANT_P))
928c19bb 10509 expr.original_code = C_MAYBE_CONST_EXPR;
6866c6e8 10510 expr.original_type = NULL;
9771b263 10511 if (exprlist)
bbbbb16a 10512 {
c166b898
ILT
10513 release_tree_vector (exprlist);
10514 release_tree_vector (origtypes);
bbbbb16a 10515 }
81e5eca8 10516 arg_loc.release ();
27bf414c
JM
10517 break;
10518 case CPP_DOT:
10519 /* Structure element reference. */
10520 c_parser_consume_token (parser);
c2255bc4 10521 expr = default_function_array_conversion (expr_loc, expr);
27bf414c 10522 if (c_parser_next_token_is (parser, CPP_NAME))
6ffd47b7
DM
10523 {
10524 c_token *comp_tok = c_parser_peek_token (parser);
10525 ident = comp_tok->value;
10526 comp_loc = comp_tok->location;
10527 }
27bf414c
JM
10528 else
10529 {
10530 c_parser_error (parser, "expected identifier");
8a40fef3 10531 expr.set_error ();
27bf414c 10532 expr.original_code = ERROR_MARK;
6866c6e8 10533 expr.original_type = NULL;
27bf414c
JM
10534 return expr;
10535 }
ebedc9a3
DM
10536 start = expr.get_start ();
10537 finish = c_parser_peek_token (parser)->get_finish ();
27bf414c 10538 c_parser_consume_token (parser);
6ffd47b7
DM
10539 expr.value = build_component_ref (op_loc, expr.value, ident,
10540 comp_loc);
ebedc9a3 10541 set_c_expr_source_range (&expr, start, finish);
27bf414c 10542 expr.original_code = ERROR_MARK;
6866c6e8
ILT
10543 if (TREE_CODE (expr.value) != COMPONENT_REF)
10544 expr.original_type = NULL;
10545 else
10546 {
10547 /* Remember the original type of a bitfield. */
10548 tree field = TREE_OPERAND (expr.value, 1);
10549 if (TREE_CODE (field) != FIELD_DECL)
10550 expr.original_type = NULL;
10551 else
10552 expr.original_type = DECL_BIT_FIELD_TYPE (field);
10553 }
27bf414c
JM
10554 break;
10555 case CPP_DEREF:
10556 /* Structure element reference. */
10557 c_parser_consume_token (parser);
267bac10 10558 expr = convert_lvalue_to_rvalue (expr_loc, expr, true, false);
27bf414c 10559 if (c_parser_next_token_is (parser, CPP_NAME))
6ffd47b7
DM
10560 {
10561 c_token *comp_tok = c_parser_peek_token (parser);
10562 ident = comp_tok->value;
10563 comp_loc = comp_tok->location;
10564 }
27bf414c
JM
10565 else
10566 {
10567 c_parser_error (parser, "expected identifier");
8a40fef3 10568 expr.set_error ();
27bf414c 10569 expr.original_code = ERROR_MARK;
6866c6e8 10570 expr.original_type = NULL;
27bf414c
JM
10571 return expr;
10572 }
ebedc9a3
DM
10573 start = expr.get_start ();
10574 finish = c_parser_peek_token (parser)->get_finish ();
27bf414c 10575 c_parser_consume_token (parser);
c2255bc4
AH
10576 expr.value = build_component_ref (op_loc,
10577 build_indirect_ref (op_loc,
c9f9eb5d 10578 expr.value,
dd865ef6 10579 RO_ARROW),
6ffd47b7 10580 ident, comp_loc);
ebedc9a3 10581 set_c_expr_source_range (&expr, start, finish);
27bf414c 10582 expr.original_code = ERROR_MARK;
6866c6e8
ILT
10583 if (TREE_CODE (expr.value) != COMPONENT_REF)
10584 expr.original_type = NULL;
10585 else
10586 {
10587 /* Remember the original type of a bitfield. */
10588 tree field = TREE_OPERAND (expr.value, 1);
10589 if (TREE_CODE (field) != FIELD_DECL)
10590 expr.original_type = NULL;
10591 else
10592 expr.original_type = DECL_BIT_FIELD_TYPE (field);
10593 }
27bf414c
JM
10594 break;
10595 case CPP_PLUS_PLUS:
10596 /* Postincrement. */
ebedc9a3
DM
10597 start = expr.get_start ();
10598 finish = c_parser_peek_token (parser)->get_finish ();
27bf414c 10599 c_parser_consume_token (parser);
5e9d6aa4
JK
10600 expr = default_function_array_read_conversion (expr_loc, expr);
10601 expr.value = build_unary_op (op_loc, POSTINCREMENT_EXPR,
10602 expr.value, false);
ebedc9a3 10603 set_c_expr_source_range (&expr, start, finish);
27bf414c 10604 expr.original_code = ERROR_MARK;
6866c6e8 10605 expr.original_type = NULL;
27bf414c
JM
10606 break;
10607 case CPP_MINUS_MINUS:
10608 /* Postdecrement. */
ebedc9a3
DM
10609 start = expr.get_start ();
10610 finish = c_parser_peek_token (parser)->get_finish ();
27bf414c 10611 c_parser_consume_token (parser);
5e9d6aa4
JK
10612 expr = default_function_array_read_conversion (expr_loc, expr);
10613 expr.value = build_unary_op (op_loc, POSTDECREMENT_EXPR,
10614 expr.value, false);
ebedc9a3 10615 set_c_expr_source_range (&expr, start, finish);
27bf414c 10616 expr.original_code = ERROR_MARK;
6866c6e8 10617 expr.original_type = NULL;
27bf414c
JM
10618 break;
10619 default:
10620 return expr;
10621 }
10622 }
10623}
10624
31dc71a8 10625/* Parse an expression (C90 6.3.17, C99 6.5.17, C11 6.5.17).
27bf414c
JM
10626
10627 expression:
10628 assignment-expression
10629 expression , assignment-expression
10630*/
10631
10632static struct c_expr
10633c_parser_expression (c_parser *parser)
10634{
267bac10 10635 location_t tloc = c_parser_peek_token (parser)->location;
27bf414c
JM
10636 struct c_expr expr;
10637 expr = c_parser_expr_no_commas (parser, NULL);
267bac10
JM
10638 if (c_parser_next_token_is (parser, CPP_COMMA))
10639 expr = convert_lvalue_to_rvalue (tloc, expr, true, false);
27bf414c
JM
10640 while (c_parser_next_token_is (parser, CPP_COMMA))
10641 {
10642 struct c_expr next;
056928b2 10643 tree lhsval;
c2255bc4
AH
10644 location_t loc = c_parser_peek_token (parser)->location;
10645 location_t expr_loc;
27bf414c 10646 c_parser_consume_token (parser);
c2255bc4 10647 expr_loc = c_parser_peek_token (parser)->location;
056928b2
JJ
10648 lhsval = expr.value;
10649 while (TREE_CODE (lhsval) == COMPOUND_EXPR)
10650 lhsval = TREE_OPERAND (lhsval, 1);
10651 if (DECL_P (lhsval) || handled_component_p (lhsval))
10652 mark_exp_read (lhsval);
27bf414c 10653 next = c_parser_expr_no_commas (parser, NULL);
267bac10 10654 next = convert_lvalue_to_rvalue (expr_loc, next, true, false);
c2255bc4 10655 expr.value = build_compound_expr (loc, expr.value, next.value);
27bf414c 10656 expr.original_code = COMPOUND_EXPR;
81f40b79 10657 expr.original_type = next.original_type;
27bf414c
JM
10658 }
10659 return expr;
10660}
10661
267bac10
JM
10662/* Parse an expression and convert functions or arrays to pointers and
10663 lvalues to rvalues. */
46bdb9cf
JM
10664
10665static struct c_expr
10666c_parser_expression_conv (c_parser *parser)
10667{
10668 struct c_expr expr;
c2255bc4 10669 location_t loc = c_parser_peek_token (parser)->location;
46bdb9cf 10670 expr = c_parser_expression (parser);
267bac10 10671 expr = convert_lvalue_to_rvalue (loc, expr, true, false);
46bdb9cf
JM
10672 return expr;
10673}
10674
b108f48f
JJ
10675/* Helper function of c_parser_expr_list. Check if IDXth (0 based)
10676 argument is a literal zero alone and if so, set it in literal_zero_mask. */
10677
10678static inline void
10679c_parser_check_literal_zero (c_parser *parser, unsigned *literal_zero_mask,
10680 unsigned int idx)
10681{
10682 if (idx >= HOST_BITS_PER_INT)
10683 return;
10684
10685 c_token *tok = c_parser_peek_token (parser);
10686 switch (tok->type)
10687 {
10688 case CPP_NUMBER:
10689 case CPP_CHAR:
10690 case CPP_WCHAR:
10691 case CPP_CHAR16:
10692 case CPP_CHAR32:
7c5890cc 10693 case CPP_UTF8CHAR:
b108f48f
JJ
10694 /* If a parameter is literal zero alone, remember it
10695 for -Wmemset-transposed-args warning. */
10696 if (integer_zerop (tok->value)
10697 && !TREE_OVERFLOW (tok->value)
10698 && (c_parser_peek_2nd_token (parser)->type == CPP_COMMA
10699 || c_parser_peek_2nd_token (parser)->type == CPP_CLOSE_PAREN))
10700 *literal_zero_mask |= 1U << idx;
10701 default:
10702 break;
10703 }
10704}
10705
46bdb9cf 10706/* Parse a non-empty list of expressions. If CONVERT_P, convert
267bac10 10707 functions and arrays to pointers and lvalues to rvalues. If
81e5eca8
MP
10708 FOLD_P, fold the expressions. If LOCATIONS is non-NULL, save the
10709 locations of function arguments into this vector.
27bf414c
JM
10710
10711 nonempty-expr-list:
10712 assignment-expression
10713 nonempty-expr-list , assignment-expression
10714*/
10715
9771b263 10716static vec<tree, va_gc> *
bbbbb16a 10717c_parser_expr_list (c_parser *parser, bool convert_p, bool fold_p,
9771b263 10718 vec<tree, va_gc> **p_orig_types,
81e5eca8 10719 location_t *sizeof_arg_loc, tree *sizeof_arg,
b108f48f
JJ
10720 vec<location_t> *locations,
10721 unsigned int *literal_zero_mask)
27bf414c 10722{
9771b263
DN
10723 vec<tree, va_gc> *ret;
10724 vec<tree, va_gc> *orig_types;
27bf414c 10725 struct c_expr expr;
3a785c97 10726 unsigned int idx = 0;
bbbbb16a 10727
c166b898 10728 ret = make_tree_vector ();
bbbbb16a
ILT
10729 if (p_orig_types == NULL)
10730 orig_types = NULL;
10731 else
c166b898 10732 orig_types = make_tree_vector ();
bbbbb16a 10733
b108f48f
JJ
10734 if (literal_zero_mask)
10735 c_parser_check_literal_zero (parser, literal_zero_mask, 0);
27bf414c 10736 expr = c_parser_expr_no_commas (parser, NULL);
46bdb9cf 10737 if (convert_p)
7f204c0f 10738 expr = convert_lvalue_to_rvalue (expr.get_location (), expr, true, true);
928c19bb
JM
10739 if (fold_p)
10740 expr.value = c_fully_fold (expr.value, false, NULL);
9771b263
DN
10741 ret->quick_push (expr.value);
10742 if (orig_types)
10743 orig_types->quick_push (expr.original_type);
81e5eca8 10744 if (locations)
7f204c0f 10745 locations->safe_push (expr.get_location ());
3a785c97 10746 if (sizeof_arg != NULL
3a785c97
JJ
10747 && expr.original_code == SIZEOF_EXPR)
10748 {
10749 sizeof_arg[0] = c_last_sizeof_arg;
40ffd95f 10750 sizeof_arg_loc[0] = c_last_sizeof_loc;
3a785c97 10751 }
27bf414c
JM
10752 while (c_parser_next_token_is (parser, CPP_COMMA))
10753 {
10754 c_parser_consume_token (parser);
b108f48f
JJ
10755 if (literal_zero_mask)
10756 c_parser_check_literal_zero (parser, literal_zero_mask, idx + 1);
27bf414c 10757 expr = c_parser_expr_no_commas (parser, NULL);
46bdb9cf 10758 if (convert_p)
7f204c0f
DM
10759 expr = convert_lvalue_to_rvalue (expr.get_location (), expr, true,
10760 true);
928c19bb
JM
10761 if (fold_p)
10762 expr.value = c_fully_fold (expr.value, false, NULL);
9771b263
DN
10763 vec_safe_push (ret, expr.value);
10764 if (orig_types)
10765 vec_safe_push (orig_types, expr.original_type);
81e5eca8 10766 if (locations)
7f204c0f 10767 locations->safe_push (expr.get_location ());
3a785c97
JJ
10768 if (++idx < 3
10769 && sizeof_arg != NULL
1a4049e7
JJ
10770 && expr.original_code == SIZEOF_EXPR)
10771 {
3a785c97 10772 sizeof_arg[idx] = c_last_sizeof_arg;
40ffd95f 10773 sizeof_arg_loc[idx] = c_last_sizeof_loc;
1a4049e7
JJ
10774 }
10775 }
9771b263 10776 if (orig_types)
bbbbb16a 10777 *p_orig_types = orig_types;
27bf414c
JM
10778 return ret;
10779}
27bf414c
JM
10780\f
10781/* Parse Objective-C-specific constructs. */
10782
10783/* Parse an objc-class-definition.
10784
10785 objc-class-definition:
10786 @interface identifier objc-superclass[opt] objc-protocol-refs[opt]
10787 objc-class-instance-variables[opt] objc-methodprotolist @end
10788 @implementation identifier objc-superclass[opt]
10789 objc-class-instance-variables[opt]
10790 @interface identifier ( identifier ) objc-protocol-refs[opt]
10791 objc-methodprotolist @end
ec3e9f82
NP
10792 @interface identifier ( ) objc-protocol-refs[opt]
10793 objc-methodprotolist @end
27bf414c
JM
10794 @implementation identifier ( identifier )
10795
10796 objc-superclass:
10797 : identifier
10798
10799 "@interface identifier (" must start "@interface identifier (
10800 identifier ) ...": objc-methodprotolist in the first production may
0fa2e4df 10801 not start with a parenthesized identifier as a declarator of a data
27bf414c
JM
10802 definition with no declaration specifiers if the objc-superclass,
10803 objc-protocol-refs and objc-class-instance-variables are omitted. */
10804
10805static void
c165dca7 10806c_parser_objc_class_definition (c_parser *parser, tree attributes)
27bf414c
JM
10807{
10808 bool iface_p;
10809 tree id1;
10810 tree superclass;
10811 if (c_parser_next_token_is_keyword (parser, RID_AT_INTERFACE))
10812 iface_p = true;
10813 else if (c_parser_next_token_is_keyword (parser, RID_AT_IMPLEMENTATION))
10814 iface_p = false;
10815 else
10816 gcc_unreachable ();
c165dca7 10817
27bf414c
JM
10818 c_parser_consume_token (parser);
10819 if (c_parser_next_token_is_not (parser, CPP_NAME))
10820 {
10821 c_parser_error (parser, "expected identifier");
10822 return;
10823 }
10824 id1 = c_parser_peek_token (parser)->value;
10825 c_parser_consume_token (parser);
10826 if (c_parser_next_token_is (parser, CPP_OPEN_PAREN))
10827 {
ec3e9f82 10828 /* We have a category or class extension. */
27bf414c
JM
10829 tree id2;
10830 tree proto = NULL_TREE;
32129a17
DM
10831 matching_parens parens;
10832 parens.consume_open (parser);
27bf414c
JM
10833 if (c_parser_next_token_is_not (parser, CPP_NAME))
10834 {
ec3e9f82
NP
10835 if (iface_p && c_parser_next_token_is (parser, CPP_CLOSE_PAREN))
10836 {
10837 /* We have a class extension. */
10838 id2 = NULL_TREE;
10839 }
10840 else
10841 {
10842 c_parser_error (parser, "expected identifier or %<)%>");
10843 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN, NULL);
10844 return;
10845 }
10846 }
10847 else
10848 {
10849 id2 = c_parser_peek_token (parser)->value;
10850 c_parser_consume_token (parser);
27bf414c 10851 }
32129a17 10852 parens.skip_until_found_close (parser);
27bf414c
JM
10853 if (!iface_p)
10854 {
10855 objc_start_category_implementation (id1, id2);
10856 return;
10857 }
10858 if (c_parser_next_token_is (parser, CPP_LESS))
10859 proto = c_parser_objc_protocol_refs (parser);
c165dca7 10860 objc_start_category_interface (id1, id2, proto, attributes);
27bf414c
JM
10861 c_parser_objc_methodprotolist (parser);
10862 c_parser_require_keyword (parser, RID_AT_END, "expected %<@end%>");
10863 objc_finish_interface ();
10864 return;
10865 }
10866 if (c_parser_next_token_is (parser, CPP_COLON))
10867 {
10868 c_parser_consume_token (parser);
10869 if (c_parser_next_token_is_not (parser, CPP_NAME))
10870 {
10871 c_parser_error (parser, "expected identifier");
10872 return;
10873 }
10874 superclass = c_parser_peek_token (parser)->value;
10875 c_parser_consume_token (parser);
10876 }
10877 else
10878 superclass = NULL_TREE;
10879 if (iface_p)
10880 {
10881 tree proto = NULL_TREE;
10882 if (c_parser_next_token_is (parser, CPP_LESS))
10883 proto = c_parser_objc_protocol_refs (parser);
c165dca7 10884 objc_start_class_interface (id1, superclass, proto, attributes);
27bf414c
JM
10885 }
10886 else
10887 objc_start_class_implementation (id1, superclass);
10888 if (c_parser_next_token_is (parser, CPP_OPEN_BRACE))
10889 c_parser_objc_class_instance_variables (parser);
10890 if (iface_p)
10891 {
10892 objc_continue_interface ();
10893 c_parser_objc_methodprotolist (parser);
10894 c_parser_require_keyword (parser, RID_AT_END, "expected %<@end%>");
10895 objc_finish_interface ();
10896 }
10897 else
10898 {
10899 objc_continue_implementation ();
10900 return;
10901 }
10902}
10903
10904/* Parse objc-class-instance-variables.
10905
10906 objc-class-instance-variables:
10907 { objc-instance-variable-decl-list[opt] }
10908
10909 objc-instance-variable-decl-list:
10910 objc-visibility-spec
10911 objc-instance-variable-decl ;
10912 ;
10913 objc-instance-variable-decl-list objc-visibility-spec
10914 objc-instance-variable-decl-list objc-instance-variable-decl ;
10915 objc-instance-variable-decl-list ;
10916
10917 objc-visibility-spec:
10918 @private
10919 @protected
10920 @public
10921
10922 objc-instance-variable-decl:
10923 struct-declaration
10924*/
10925
10926static void
10927c_parser_objc_class_instance_variables (c_parser *parser)
10928{
10929 gcc_assert (c_parser_next_token_is (parser, CPP_OPEN_BRACE));
10930 c_parser_consume_token (parser);
10931 while (c_parser_next_token_is_not (parser, CPP_EOF))
10932 {
10933 tree decls;
10934 /* Parse any stray semicolon. */
10935 if (c_parser_next_token_is (parser, CPP_SEMICOLON))
10936 {
c1771a20 10937 pedwarn (c_parser_peek_token (parser)->location, OPT_Wpedantic,
4e26ba90 10938 "extra semicolon");
27bf414c
JM
10939 c_parser_consume_token (parser);
10940 continue;
10941 }
10942 /* Stop if at the end of the instance variables. */
10943 if (c_parser_next_token_is (parser, CPP_CLOSE_BRACE))
10944 {
10945 c_parser_consume_token (parser);
10946 break;
10947 }
10948 /* Parse any objc-visibility-spec. */
49b91f05 10949 if (c_parser_next_token_is_keyword (parser, RID_AT_PRIVATE))
27bf414c
JM
10950 {
10951 c_parser_consume_token (parser);
c37d8c30 10952 objc_set_visibility (OBJC_IVAR_VIS_PRIVATE);
27bf414c
JM
10953 continue;
10954 }
49b91f05 10955 else if (c_parser_next_token_is_keyword (parser, RID_AT_PROTECTED))
27bf414c
JM
10956 {
10957 c_parser_consume_token (parser);
c37d8c30 10958 objc_set_visibility (OBJC_IVAR_VIS_PROTECTED);
27bf414c
JM
10959 continue;
10960 }
49b91f05 10961 else if (c_parser_next_token_is_keyword (parser, RID_AT_PUBLIC))
27bf414c
JM
10962 {
10963 c_parser_consume_token (parser);
c37d8c30
IS
10964 objc_set_visibility (OBJC_IVAR_VIS_PUBLIC);
10965 continue;
10966 }
10967 else if (c_parser_next_token_is_keyword (parser, RID_AT_PACKAGE))
10968 {
10969 c_parser_consume_token (parser);
10970 objc_set_visibility (OBJC_IVAR_VIS_PACKAGE);
27bf414c
JM
10971 continue;
10972 }
bc4071dd
RH
10973 else if (c_parser_next_token_is (parser, CPP_PRAGMA))
10974 {
dda1bf61 10975 c_parser_pragma (parser, pragma_external, NULL);
bc4071dd
RH
10976 continue;
10977 }
10978
27bf414c
JM
10979 /* Parse some comma-separated declarations. */
10980 decls = c_parser_struct_declaration (parser);
4e26ba90
NP
10981 if (decls == NULL)
10982 {
10983 /* There is a syntax error. We want to skip the offending
10984 tokens up to the next ';' (included) or '}'
10985 (excluded). */
10986
10987 /* First, skip manually a ')' or ']'. This is because they
10988 reduce the nesting level, so c_parser_skip_until_found()
10989 wouldn't be able to skip past them. */
10990 c_token *token = c_parser_peek_token (parser);
10991 if (token->type == CPP_CLOSE_PAREN || token->type == CPP_CLOSE_SQUARE)
10992 c_parser_consume_token (parser);
10993
10994 /* Then, do the standard skipping. */
10995 c_parser_skip_until_found (parser, CPP_SEMICOLON, NULL);
10996
10997 /* We hopefully recovered. Start normal parsing again. */
10998 parser->error = false;
10999 continue;
11000 }
11001 else
11002 {
11003 /* Comma-separated instance variables are chained together
11004 in reverse order; add them one by one. */
11005 tree ivar = nreverse (decls);
11006 for (; ivar; ivar = DECL_CHAIN (ivar))
11007 objc_add_instance_variable (copy_node (ivar));
11008 }
27bf414c
JM
11009 c_parser_skip_until_found (parser, CPP_SEMICOLON, "expected %<;%>");
11010 }
11011}
11012
11013/* Parse an objc-class-declaration.
11014
11015 objc-class-declaration:
11016 @class identifier-list ;
11017*/
11018
11019static void
11020c_parser_objc_class_declaration (c_parser *parser)
11021{
49b91f05 11022 gcc_assert (c_parser_next_token_is_keyword (parser, RID_AT_CLASS));
27bf414c
JM
11023 c_parser_consume_token (parser);
11024 /* Any identifiers, including those declared as type names, are OK
11025 here. */
11026 while (true)
11027 {
11028 tree id;
11029 if (c_parser_next_token_is_not (parser, CPP_NAME))
11030 {
11031 c_parser_error (parser, "expected identifier");
da57d1b9
NP
11032 c_parser_skip_until_found (parser, CPP_SEMICOLON, NULL);
11033 parser->error = false;
11034 return;
27bf414c
JM
11035 }
11036 id = c_parser_peek_token (parser)->value;
32dabdaf 11037 objc_declare_class (id);
27bf414c
JM
11038 c_parser_consume_token (parser);
11039 if (c_parser_next_token_is (parser, CPP_COMMA))
11040 c_parser_consume_token (parser);
11041 else
11042 break;
11043 }
11044 c_parser_skip_until_found (parser, CPP_SEMICOLON, "expected %<;%>");
27bf414c
JM
11045}
11046
11047/* Parse an objc-alias-declaration.
11048
11049 objc-alias-declaration:
11050 @compatibility_alias identifier identifier ;
11051*/
11052
11053static void
11054c_parser_objc_alias_declaration (c_parser *parser)
11055{
11056 tree id1, id2;
11057 gcc_assert (c_parser_next_token_is_keyword (parser, RID_AT_ALIAS));
11058 c_parser_consume_token (parser);
11059 if (c_parser_next_token_is_not (parser, CPP_NAME))
11060 {
11061 c_parser_error (parser, "expected identifier");
11062 c_parser_skip_until_found (parser, CPP_SEMICOLON, NULL);
11063 return;
11064 }
11065 id1 = c_parser_peek_token (parser)->value;
11066 c_parser_consume_token (parser);
11067 if (c_parser_next_token_is_not (parser, CPP_NAME))
11068 {
11069 c_parser_error (parser, "expected identifier");
11070 c_parser_skip_until_found (parser, CPP_SEMICOLON, NULL);
11071 return;
11072 }
11073 id2 = c_parser_peek_token (parser)->value;
11074 c_parser_consume_token (parser);
11075 c_parser_skip_until_found (parser, CPP_SEMICOLON, "expected %<;%>");
11076 objc_declare_alias (id1, id2);
11077}
11078
11079/* Parse an objc-protocol-definition.
11080
11081 objc-protocol-definition:
11082 @protocol identifier objc-protocol-refs[opt] objc-methodprotolist @end
11083 @protocol identifier-list ;
11084
11085 "@protocol identifier ;" should be resolved as "@protocol
11086 identifier-list ;": objc-methodprotolist may not start with a
11087 semicolon in the first alternative if objc-protocol-refs are
11088 omitted. */
11089
11090static void
c165dca7 11091c_parser_objc_protocol_definition (c_parser *parser, tree attributes)
27bf414c
JM
11092{
11093 gcc_assert (c_parser_next_token_is_keyword (parser, RID_AT_PROTOCOL));
c165dca7 11094
27bf414c
JM
11095 c_parser_consume_token (parser);
11096 if (c_parser_next_token_is_not (parser, CPP_NAME))
11097 {
11098 c_parser_error (parser, "expected identifier");
11099 return;
11100 }
11101 if (c_parser_peek_2nd_token (parser)->type == CPP_COMMA
11102 || c_parser_peek_2nd_token (parser)->type == CPP_SEMICOLON)
11103 {
27bf414c
JM
11104 /* Any identifiers, including those declared as type names, are
11105 OK here. */
11106 while (true)
11107 {
11108 tree id;
11109 if (c_parser_next_token_is_not (parser, CPP_NAME))
11110 {
11111 c_parser_error (parser, "expected identifier");
11112 break;
11113 }
11114 id = c_parser_peek_token (parser)->value;
c59633d9 11115 objc_declare_protocol (id, attributes);
27bf414c
JM
11116 c_parser_consume_token (parser);
11117 if (c_parser_next_token_is (parser, CPP_COMMA))
11118 c_parser_consume_token (parser);
11119 else
11120 break;
11121 }
11122 c_parser_skip_until_found (parser, CPP_SEMICOLON, "expected %<;%>");
27bf414c
JM
11123 }
11124 else
11125 {
11126 tree id = c_parser_peek_token (parser)->value;
11127 tree proto = NULL_TREE;
11128 c_parser_consume_token (parser);
11129 if (c_parser_next_token_is (parser, CPP_LESS))
11130 proto = c_parser_objc_protocol_refs (parser);
0bacb8c7 11131 parser->objc_pq_context = true;
c165dca7 11132 objc_start_protocol (id, proto, attributes);
27bf414c
JM
11133 c_parser_objc_methodprotolist (parser);
11134 c_parser_require_keyword (parser, RID_AT_END, "expected %<@end%>");
0bacb8c7 11135 parser->objc_pq_context = false;
27bf414c
JM
11136 objc_finish_interface ();
11137 }
11138}
11139
11140/* Parse an objc-method-type.
11141
11142 objc-method-type:
11143 +
11144 -
27bf414c 11145
249a82c4
NP
11146 Return true if it is a class method (+) and false if it is
11147 an instance method (-).
11148*/
11149static inline bool
27bf414c
JM
11150c_parser_objc_method_type (c_parser *parser)
11151{
11152 switch (c_parser_peek_token (parser)->type)
11153 {
11154 case CPP_PLUS:
11155 c_parser_consume_token (parser);
249a82c4 11156 return true;
27bf414c
JM
11157 case CPP_MINUS:
11158 c_parser_consume_token (parser);
249a82c4 11159 return false;
27bf414c
JM
11160 default:
11161 gcc_unreachable ();
11162 }
11163}
11164
11165/* Parse an objc-method-definition.
11166
11167 objc-method-definition:
11168 objc-method-type objc-method-decl ;[opt] compound-statement
11169*/
11170
11171static void
11172c_parser_objc_method_definition (c_parser *parser)
11173{
249a82c4 11174 bool is_class_method = c_parser_objc_method_type (parser);
a04a722b 11175 tree decl, attributes = NULL_TREE, expr = NULL_TREE;
0bacb8c7 11176 parser->objc_pq_context = true;
a04a722b
JM
11177 decl = c_parser_objc_method_decl (parser, is_class_method, &attributes,
11178 &expr);
f7e71da5
IS
11179 if (decl == error_mark_node)
11180 return; /* Bail here. */
11181
27bf414c
JM
11182 if (c_parser_next_token_is (parser, CPP_SEMICOLON))
11183 {
11184 c_parser_consume_token (parser);
c1771a20 11185 pedwarn (c_parser_peek_token (parser)->location, OPT_Wpedantic,
509c9d60 11186 "extra semicolon in method definition specified");
27bf414c 11187 }
f7e71da5 11188
8f078c08
AP
11189 if (!c_parser_next_token_is (parser, CPP_OPEN_BRACE))
11190 {
11191 c_parser_error (parser, "expected %<{%>");
11192 return;
11193 }
f7e71da5 11194
0bacb8c7 11195 parser->objc_pq_context = false;
a04a722b 11196 if (objc_start_method_definition (is_class_method, decl, attributes, expr))
45547c7f
NP
11197 {
11198 add_stmt (c_parser_compound_statement (parser));
11199 objc_finish_method_definition (current_function_decl);
11200 }
11201 else
11202 {
11203 /* This code is executed when we find a method definition
a26d8862
NP
11204 outside of an @implementation context (or invalid for other
11205 reasons). Parse the method (to keep going) but do not emit
11206 any code.
45547c7f
NP
11207 */
11208 c_parser_compound_statement (parser);
11209 }
27bf414c
JM
11210}
11211
11212/* Parse an objc-methodprotolist.
11213
11214 objc-methodprotolist:
11215 empty
11216 objc-methodprotolist objc-methodproto
11217 objc-methodprotolist declaration
11218 objc-methodprotolist ;
92902b1b
IS
11219 @optional
11220 @required
27bf414c
JM
11221
11222 The declaration is a data definition, which may be missing
11223 declaration specifiers under the same rules and diagnostics as
11224 other data definitions outside functions, and the stray semicolon
11225 is diagnosed the same way as a stray semicolon outside a
11226 function. */
11227
11228static void
11229c_parser_objc_methodprotolist (c_parser *parser)
11230{
11231 while (true)
11232 {
11233 /* The list is terminated by @end. */
11234 switch (c_parser_peek_token (parser)->type)
11235 {
11236 case CPP_SEMICOLON:
c1771a20 11237 pedwarn (c_parser_peek_token (parser)->location, OPT_Wpedantic,
509c9d60 11238 "ISO C does not allow extra %<;%> outside of a function");
27bf414c
JM
11239 c_parser_consume_token (parser);
11240 break;
11241 case CPP_PLUS:
11242 case CPP_MINUS:
11243 c_parser_objc_methodproto (parser);
11244 break;
b9b58168 11245 case CPP_PRAGMA:
dda1bf61 11246 c_parser_pragma (parser, pragma_external, NULL);
b9b58168 11247 break;
27bf414c
JM
11248 case CPP_EOF:
11249 return;
11250 default:
11251 if (c_parser_next_token_is_keyword (parser, RID_AT_END))
11252 return;
668ea4b1 11253 else if (c_parser_next_token_is_keyword (parser, RID_AT_PROPERTY))
f614132b 11254 c_parser_objc_at_property_declaration (parser);
92902b1b
IS
11255 else if (c_parser_next_token_is_keyword (parser, RID_AT_OPTIONAL))
11256 {
11257 objc_set_method_opt (true);
11258 c_parser_consume_token (parser);
11259 }
11260 else if (c_parser_next_token_is_keyword (parser, RID_AT_REQUIRED))
11261 {
11262 objc_set_method_opt (false);
11263 c_parser_consume_token (parser);
11264 }
11265 else
11266 c_parser_declaration_or_fndef (parser, false, false, true,
acf0174b 11267 false, true, NULL, vNULL);
27bf414c
JM
11268 break;
11269 }
11270 }
11271}
11272
11273/* Parse an objc-methodproto.
11274
11275 objc-methodproto:
11276 objc-method-type objc-method-decl ;
11277*/
11278
11279static void
11280c_parser_objc_methodproto (c_parser *parser)
11281{
249a82c4 11282 bool is_class_method = c_parser_objc_method_type (parser);
f7e71da5 11283 tree decl, attributes = NULL_TREE;
249a82c4 11284
27bf414c 11285 /* Remember protocol qualifiers in prototypes. */
0bacb8c7 11286 parser->objc_pq_context = true;
a04a722b
JM
11287 decl = c_parser_objc_method_decl (parser, is_class_method, &attributes,
11288 NULL);
f7e71da5 11289 /* Forget protocol qualifiers now. */
0bacb8c7 11290 parser->objc_pq_context = false;
f7e71da5
IS
11291
11292 /* Do not allow the presence of attributes to hide an erroneous
11293 method implementation in the interface section. */
11294 if (!c_parser_next_token_is (parser, CPP_SEMICOLON))
11295 {
11296 c_parser_error (parser, "expected %<;%>");
11297 return;
11298 }
11299
11300 if (decl != error_mark_node)
249a82c4 11301 objc_add_method_declaration (is_class_method, decl, attributes);
f7e71da5 11302
27bf414c
JM
11303 c_parser_skip_until_found (parser, CPP_SEMICOLON, "expected %<;%>");
11304}
11305
f7e71da5
IS
11306/* If we are at a position that method attributes may be present, check that
11307 there are not any parsed already (a syntax error) and then collect any
11308 specified at the current location. Finally, if new attributes were present,
11309 check that the next token is legal ( ';' for decls and '{' for defs). */
11310
11311static bool
11312c_parser_objc_maybe_method_attributes (c_parser* parser, tree* attributes)
11313{
11314 bool bad = false;
11315 if (*attributes)
11316 {
11317 c_parser_error (parser,
11318 "method attributes must be specified at the end only");
11319 *attributes = NULL_TREE;
11320 bad = true;
11321 }
11322
11323 if (c_parser_next_token_is_keyword (parser, RID_ATTRIBUTE))
783bfe5e 11324 *attributes = c_parser_gnu_attributes (parser);
f7e71da5
IS
11325
11326 /* If there were no attributes here, just report any earlier error. */
11327 if (*attributes == NULL_TREE || bad)
11328 return bad;
11329
11330 /* If the attributes are followed by a ; or {, then just report any earlier
11331 error. */
11332 if (c_parser_next_token_is (parser, CPP_SEMICOLON)
11333 || c_parser_next_token_is (parser, CPP_OPEN_BRACE))
11334 return bad;
11335
11336 /* We've got attributes, but not at the end. */
11337 c_parser_error (parser,
11338 "expected %<;%> or %<{%> after method attribute definition");
11339 return true;
11340}
11341
27bf414c
JM
11342/* Parse an objc-method-decl.
11343
11344 objc-method-decl:
11345 ( objc-type-name ) objc-selector
11346 objc-selector
11347 ( objc-type-name ) objc-keyword-selector objc-optparmlist
11348 objc-keyword-selector objc-optparmlist
783bfe5e 11349 gnu-attributes
27bf414c
JM
11350
11351 objc-keyword-selector:
11352 objc-keyword-decl
11353 objc-keyword-selector objc-keyword-decl
11354
11355 objc-keyword-decl:
11356 objc-selector : ( objc-type-name ) identifier
11357 objc-selector : identifier
11358 : ( objc-type-name ) identifier
11359 : identifier
11360
11361 objc-optparmlist:
11362 objc-optparms objc-optellipsis
11363
11364 objc-optparms:
11365 empty
11366 objc-opt-parms , parameter-declaration
11367
11368 objc-optellipsis:
11369 empty
11370 , ...
11371*/
11372
11373static tree
a04a722b
JM
11374c_parser_objc_method_decl (c_parser *parser, bool is_class_method,
11375 tree *attributes, tree *expr)
27bf414c
JM
11376{
11377 tree type = NULL_TREE;
11378 tree sel;
11379 tree parms = NULL_TREE;
dbb74365 11380 bool ellipsis = false;
f7e71da5 11381 bool attr_err = false;
dbb74365 11382
f7e71da5 11383 *attributes = NULL_TREE;
27bf414c
JM
11384 if (c_parser_next_token_is (parser, CPP_OPEN_PAREN))
11385 {
32129a17
DM
11386 matching_parens parens;
11387 parens.consume_open (parser);
27bf414c 11388 type = c_parser_objc_type_name (parser);
32129a17 11389 parens.skip_until_found_close (parser);
27bf414c
JM
11390 }
11391 sel = c_parser_objc_selector (parser);
11392 /* If there is no selector, or a colon follows, we have an
11393 objc-keyword-selector. If there is a selector, and a colon does
11394 not follow, that selector ends the objc-method-decl. */
11395 if (!sel || c_parser_next_token_is (parser, CPP_COLON))
11396 {
11397 tree tsel = sel;
11398 tree list = NULL_TREE;
27bf414c
JM
11399 while (true)
11400 {
11401 tree atype = NULL_TREE, id, keyworddecl;
f7e71da5 11402 tree param_attr = NULL_TREE;
27bf414c
JM
11403 if (!c_parser_require (parser, CPP_COLON, "expected %<:%>"))
11404 break;
11405 if (c_parser_next_token_is (parser, CPP_OPEN_PAREN))
11406 {
11407 c_parser_consume_token (parser);
11408 atype = c_parser_objc_type_name (parser);
11409 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN,
11410 "expected %<)%>");
11411 }
f7e71da5
IS
11412 /* New ObjC allows attributes on method parameters. */
11413 if (c_parser_next_token_is_keyword (parser, RID_ATTRIBUTE))
783bfe5e 11414 param_attr = c_parser_gnu_attributes (parser);
27bf414c
JM
11415 if (c_parser_next_token_is_not (parser, CPP_NAME))
11416 {
11417 c_parser_error (parser, "expected identifier");
11418 return error_mark_node;
11419 }
11420 id = c_parser_peek_token (parser)->value;
11421 c_parser_consume_token (parser);
f7e71da5 11422 keyworddecl = objc_build_keyword_decl (tsel, atype, id, param_attr);
27bf414c
JM
11423 list = chainon (list, keyworddecl);
11424 tsel = c_parser_objc_selector (parser);
11425 if (!tsel && c_parser_next_token_is_not (parser, CPP_COLON))
11426 break;
11427 }
f7e71da5
IS
11428
11429 attr_err |= c_parser_objc_maybe_method_attributes (parser, attributes) ;
11430
27bf414c
JM
11431 /* Parse the optional parameter list. Optional Objective-C
11432 method parameters follow the C syntax, and may include '...'
11433 to denote a variable number of arguments. */
11434 parms = make_node (TREE_LIST);
27bf414c
JM
11435 while (c_parser_next_token_is (parser, CPP_COMMA))
11436 {
11437 struct c_parm *parm;
11438 c_parser_consume_token (parser);
11439 if (c_parser_next_token_is (parser, CPP_ELLIPSIS))
11440 {
11441 ellipsis = true;
11442 c_parser_consume_token (parser);
f7e71da5
IS
11443 attr_err |= c_parser_objc_maybe_method_attributes
11444 (parser, attributes) ;
27bf414c
JM
11445 break;
11446 }
4e03c3a7 11447 parm = c_parser_parameter_declaration (parser, NULL_TREE, false);
27bf414c
JM
11448 if (parm == NULL)
11449 break;
11450 parms = chainon (parms,
a04a722b 11451 build_tree_list (NULL_TREE, grokparm (parm, expr)));
27bf414c 11452 }
27bf414c
JM
11453 sel = list;
11454 }
f7e71da5
IS
11455 else
11456 attr_err |= c_parser_objc_maybe_method_attributes (parser, attributes) ;
11457
11458 if (sel == NULL)
11459 {
11460 c_parser_error (parser, "objective-c method declaration is expected");
11461 return error_mark_node;
11462 }
11463
11464 if (attr_err)
11465 return error_mark_node;
11466
249a82c4 11467 return objc_build_method_signature (is_class_method, type, sel, parms, ellipsis);
27bf414c
JM
11468}
11469
11470/* Parse an objc-type-name.
11471
11472 objc-type-name:
11473 objc-type-qualifiers[opt] type-name
11474 objc-type-qualifiers[opt]
11475
11476 objc-type-qualifiers:
11477 objc-type-qualifier
11478 objc-type-qualifiers objc-type-qualifier
11479
11480 objc-type-qualifier: one of
11481 in out inout bycopy byref oneway
11482*/
11483
11484static tree
11485c_parser_objc_type_name (c_parser *parser)
11486{
11487 tree quals = NULL_TREE;
d75d71e0 11488 struct c_type_name *type_name = NULL;
27bf414c
JM
11489 tree type = NULL_TREE;
11490 while (true)
11491 {
11492 c_token *token = c_parser_peek_token (parser);
11493 if (token->type == CPP_KEYWORD
11494 && (token->keyword == RID_IN
11495 || token->keyword == RID_OUT
11496 || token->keyword == RID_INOUT
11497 || token->keyword == RID_BYCOPY
11498 || token->keyword == RID_BYREF
11499 || token->keyword == RID_ONEWAY))
11500 {
71fc71d8 11501 quals = chainon (build_tree_list (NULL_TREE, token->value), quals);
27bf414c
JM
11502 c_parser_consume_token (parser);
11503 }
11504 else
11505 break;
11506 }
29ce73cb 11507 if (c_parser_next_tokens_start_typename (parser, cla_prefer_type))
d75d71e0
ILT
11508 type_name = c_parser_type_name (parser);
11509 if (type_name)
928c19bb 11510 type = groktypename (type_name, NULL, NULL);
046608a3
NP
11511
11512 /* If the type is unknown, and error has already been produced and
11513 we need to recover from the error. In that case, use NULL_TREE
11514 for the type, as if no type had been specified; this will use the
11515 default type ('id') which is good for error recovery. */
11516 if (type == error_mark_node)
11517 type = NULL_TREE;
11518
27bf414c
JM
11519 return build_tree_list (quals, type);
11520}
11521
11522/* Parse objc-protocol-refs.
11523
11524 objc-protocol-refs:
11525 < identifier-list >
11526*/
11527
11528static tree
11529c_parser_objc_protocol_refs (c_parser *parser)
11530{
11531 tree list = NULL_TREE;
11532 gcc_assert (c_parser_next_token_is (parser, CPP_LESS));
11533 c_parser_consume_token (parser);
11534 /* Any identifiers, including those declared as type names, are OK
11535 here. */
11536 while (true)
11537 {
11538 tree id;
11539 if (c_parser_next_token_is_not (parser, CPP_NAME))
11540 {
11541 c_parser_error (parser, "expected identifier");
11542 break;
11543 }
11544 id = c_parser_peek_token (parser)->value;
11545 list = chainon (list, build_tree_list (NULL_TREE, id));
11546 c_parser_consume_token (parser);
11547 if (c_parser_next_token_is (parser, CPP_COMMA))
11548 c_parser_consume_token (parser);
11549 else
11550 break;
11551 }
11552 c_parser_require (parser, CPP_GREATER, "expected %<>%>");
11553 return list;
11554}
11555
437c2322 11556/* Parse an objc-try-catch-finally-statement.
27bf414c 11557
437c2322 11558 objc-try-catch-finally-statement:
27bf414c
JM
11559 @try compound-statement objc-catch-list[opt]
11560 @try compound-statement objc-catch-list[opt] @finally compound-statement
11561
11562 objc-catch-list:
437c2322
NP
11563 @catch ( objc-catch-parameter-declaration ) compound-statement
11564 objc-catch-list @catch ( objc-catch-parameter-declaration ) compound-statement
11565
11566 objc-catch-parameter-declaration:
11567 parameter-declaration
11568 '...'
11569
11570 where '...' is to be interpreted literally, that is, it means CPP_ELLIPSIS.
11571
11572 PS: This function is identical to cp_parser_objc_try_catch_finally_statement
11573 for C++. Keep them in sync. */
27bf414c
JM
11574
11575static void
437c2322 11576c_parser_objc_try_catch_finally_statement (c_parser *parser)
27bf414c 11577{
437c2322 11578 location_t location;
27bf414c 11579 tree stmt;
437c2322 11580
49b91f05 11581 gcc_assert (c_parser_next_token_is_keyword (parser, RID_AT_TRY));
27bf414c 11582 c_parser_consume_token (parser);
437c2322 11583 location = c_parser_peek_token (parser)->location;
46270f14 11584 objc_maybe_warn_exceptions (location);
27bf414c 11585 stmt = c_parser_compound_statement (parser);
437c2322
NP
11586 objc_begin_try_stmt (location, stmt);
11587
49b91f05 11588 while (c_parser_next_token_is_keyword (parser, RID_AT_CATCH))
27bf414c
JM
11589 {
11590 struct c_parm *parm;
437c2322
NP
11591 tree parameter_declaration = error_mark_node;
11592 bool seen_open_paren = false;
11593
27bf414c 11594 c_parser_consume_token (parser);
32129a17
DM
11595 matching_parens parens;
11596 if (!parens.require_open (parser))
437c2322
NP
11597 seen_open_paren = true;
11598 if (c_parser_next_token_is (parser, CPP_ELLIPSIS))
27bf414c 11599 {
437c2322
NP
11600 /* We have "@catch (...)" (where the '...' are literally
11601 what is in the code). Skip the '...'.
11602 parameter_declaration is set to NULL_TREE, and
11603 objc_being_catch_clauses() knows that that means
11604 '...'. */
11605 c_parser_consume_token (parser);
11606 parameter_declaration = NULL_TREE;
27bf414c 11607 }
437c2322
NP
11608 else
11609 {
11610 /* We have "@catch (NSException *exception)" or something
11611 like that. Parse the parameter declaration. */
4e03c3a7 11612 parm = c_parser_parameter_declaration (parser, NULL_TREE, false);
437c2322
NP
11613 if (parm == NULL)
11614 parameter_declaration = error_mark_node;
11615 else
a04a722b 11616 parameter_declaration = grokparm (parm, NULL);
437c2322
NP
11617 }
11618 if (seen_open_paren)
32129a17 11619 parens.require_close (parser);
437c2322
NP
11620 else
11621 {
11622 /* If there was no open parenthesis, we are recovering from
11623 an error, and we are trying to figure out what mistake
11624 the user has made. */
11625
11626 /* If there is an immediate closing parenthesis, the user
11627 probably forgot the opening one (ie, they typed "@catch
11628 NSException *e)". Parse the closing parenthesis and keep
11629 going. */
11630 if (c_parser_next_token_is (parser, CPP_CLOSE_PAREN))
11631 c_parser_consume_token (parser);
11632
11633 /* If these is no immediate closing parenthesis, the user
11634 probably doesn't know that parenthesis are required at
11635 all (ie, they typed "@catch NSException *e"). So, just
11636 forget about the closing parenthesis and keep going. */
11637 }
11638 objc_begin_catch_clause (parameter_declaration);
27bf414c
JM
11639 if (c_parser_require (parser, CPP_OPEN_BRACE, "expected %<{%>"))
11640 c_parser_compound_statement_nostart (parser);
11641 objc_finish_catch_clause ();
11642 }
11643 if (c_parser_next_token_is_keyword (parser, RID_AT_FINALLY))
11644 {
27bf414c 11645 c_parser_consume_token (parser);
437c2322
NP
11646 location = c_parser_peek_token (parser)->location;
11647 stmt = c_parser_compound_statement (parser);
11648 objc_build_finally_clause (location, stmt);
27bf414c
JM
11649 }
11650 objc_finish_try_stmt ();
11651}
11652
11653/* Parse an objc-synchronized-statement.
11654
11655 objc-synchronized-statement:
11656 @synchronized ( expression ) compound-statement
11657*/
11658
11659static void
11660c_parser_objc_synchronized_statement (c_parser *parser)
11661{
11662 location_t loc;
11663 tree expr, stmt;
11664 gcc_assert (c_parser_next_token_is_keyword (parser, RID_AT_SYNCHRONIZED));
11665 c_parser_consume_token (parser);
11666 loc = c_parser_peek_token (parser)->location;
46270f14 11667 objc_maybe_warn_exceptions (loc);
32129a17
DM
11668 matching_parens parens;
11669 if (parens.require_open (parser))
27bf414c 11670 {
267bac10
JM
11671 struct c_expr ce = c_parser_expression (parser);
11672 ce = convert_lvalue_to_rvalue (loc, ce, false, false);
11673 expr = ce.value;
928c19bb 11674 expr = c_fully_fold (expr, false, NULL);
32129a17 11675 parens.skip_until_found_close (parser);
27bf414c
JM
11676 }
11677 else
11678 expr = error_mark_node;
11679 stmt = c_parser_compound_statement (parser);
11680 objc_build_synchronized (loc, expr, stmt);
11681}
11682
11683/* Parse an objc-selector; return NULL_TREE without an error if the
11684 next token is not an objc-selector.
11685
11686 objc-selector:
11687 identifier
11688 one of
11689 enum struct union if else while do for switch case default
11690 break continue return goto asm sizeof typeof __alignof
11691 unsigned long const short volatile signed restrict _Complex
11692 in out inout bycopy byref oneway int char float double void _Bool
267bac10 11693 _Atomic
27bf414c
JM
11694
11695 ??? Why this selection of keywords but not, for example, storage
11696 class specifiers? */
11697
11698static tree
11699c_parser_objc_selector (c_parser *parser)
11700{
11701 c_token *token = c_parser_peek_token (parser);
11702 tree value = token->value;
11703 if (token->type == CPP_NAME)
11704 {
11705 c_parser_consume_token (parser);
11706 return value;
11707 }
11708 if (token->type != CPP_KEYWORD)
11709 return NULL_TREE;
11710 switch (token->keyword)
11711 {
11712 case RID_ENUM:
11713 case RID_STRUCT:
11714 case RID_UNION:
11715 case RID_IF:
11716 case RID_ELSE:
11717 case RID_WHILE:
11718 case RID_DO:
11719 case RID_FOR:
11720 case RID_SWITCH:
11721 case RID_CASE:
11722 case RID_DEFAULT:
11723 case RID_BREAK:
11724 case RID_CONTINUE:
11725 case RID_RETURN:
11726 case RID_GOTO:
11727 case RID_ASM:
11728 case RID_SIZEOF:
11729 case RID_TYPEOF:
11730 case RID_ALIGNOF:
11731 case RID_UNSIGNED:
11732 case RID_LONG:
11733 case RID_CONST:
11734 case RID_SHORT:
11735 case RID_VOLATILE:
11736 case RID_SIGNED:
11737 case RID_RESTRICT:
11738 case RID_COMPLEX:
11739 case RID_IN:
11740 case RID_OUT:
11741 case RID_INOUT:
11742 case RID_BYCOPY:
11743 case RID_BYREF:
11744 case RID_ONEWAY:
11745 case RID_INT:
11746 case RID_CHAR:
11747 case RID_FLOAT:
11748 case RID_DOUBLE:
c65699ef 11749 CASE_RID_FLOATN_NX:
27bf414c
JM
11750 case RID_VOID:
11751 case RID_BOOL:
267bac10 11752 case RID_ATOMIC:
38b7bc7f 11753 case RID_AUTO_TYPE:
78a7c317
DD
11754 case RID_INT_N_0:
11755 case RID_INT_N_1:
11756 case RID_INT_N_2:
11757 case RID_INT_N_3:
27bf414c
JM
11758 c_parser_consume_token (parser);
11759 return value;
11760 default:
11761 return NULL_TREE;
11762 }
11763}
11764
11765/* Parse an objc-selector-arg.
11766
11767 objc-selector-arg:
11768 objc-selector
11769 objc-keywordname-list
11770
11771 objc-keywordname-list:
11772 objc-keywordname
11773 objc-keywordname-list objc-keywordname
11774
11775 objc-keywordname:
11776 objc-selector :
11777 :
11778*/
11779
11780static tree
11781c_parser_objc_selector_arg (c_parser *parser)
11782{
11783 tree sel = c_parser_objc_selector (parser);
11784 tree list = NULL_TREE;
e1113ffb
JJ
11785 if (sel
11786 && c_parser_next_token_is_not (parser, CPP_COLON)
11787 && c_parser_next_token_is_not (parser, CPP_SCOPE))
27bf414c
JM
11788 return sel;
11789 while (true)
11790 {
e1113ffb
JJ
11791 if (c_parser_next_token_is (parser, CPP_SCOPE))
11792 {
11793 c_parser_consume_token (parser);
11794 list = chainon (list, build_tree_list (sel, NULL_TREE));
11795 list = chainon (list, build_tree_list (NULL_TREE, NULL_TREE));
11796 }
11797 else
11798 {
11799 if (!c_parser_require (parser, CPP_COLON, "expected %<:%>"))
11800 return list;
11801 list = chainon (list, build_tree_list (sel, NULL_TREE));
11802 }
27bf414c 11803 sel = c_parser_objc_selector (parser);
e1113ffb
JJ
11804 if (!sel
11805 && c_parser_next_token_is_not (parser, CPP_COLON)
11806 && c_parser_next_token_is_not (parser, CPP_SCOPE))
27bf414c
JM
11807 break;
11808 }
11809 return list;
11810}
11811
11812/* Parse an objc-receiver.
11813
11814 objc-receiver:
11815 expression
11816 class-name
11817 type-name
11818*/
11819
11820static tree
11821c_parser_objc_receiver (c_parser *parser)
11822{
267bac10
JM
11823 location_t loc = c_parser_peek_token (parser)->location;
11824
27bf414c
JM
11825 if (c_parser_peek_token (parser)->type == CPP_NAME
11826 && (c_parser_peek_token (parser)->id_kind == C_ID_TYPENAME
11827 || c_parser_peek_token (parser)->id_kind == C_ID_CLASSNAME))
11828 {
11829 tree id = c_parser_peek_token (parser)->value;
11830 c_parser_consume_token (parser);
11831 return objc_get_class_reference (id);
11832 }
267bac10
JM
11833 struct c_expr ce = c_parser_expression (parser);
11834 ce = convert_lvalue_to_rvalue (loc, ce, false, false);
11835 return c_fully_fold (ce.value, false, NULL);
27bf414c
JM
11836}
11837
11838/* Parse objc-message-args.
11839
11840 objc-message-args:
11841 objc-selector
11842 objc-keywordarg-list
11843
11844 objc-keywordarg-list:
11845 objc-keywordarg
11846 objc-keywordarg-list objc-keywordarg
11847
11848 objc-keywordarg:
11849 objc-selector : objc-keywordexpr
11850 : objc-keywordexpr
11851*/
11852
11853static tree
11854c_parser_objc_message_args (c_parser *parser)
11855{
11856 tree sel = c_parser_objc_selector (parser);
11857 tree list = NULL_TREE;
11858 if (sel && c_parser_next_token_is_not (parser, CPP_COLON))
11859 return sel;
11860 while (true)
11861 {
11862 tree keywordexpr;
11863 if (!c_parser_require (parser, CPP_COLON, "expected %<:%>"))
0a7d7dea 11864 return error_mark_node;
27bf414c
JM
11865 keywordexpr = c_parser_objc_keywordexpr (parser);
11866 list = chainon (list, build_tree_list (sel, keywordexpr));
11867 sel = c_parser_objc_selector (parser);
11868 if (!sel && c_parser_next_token_is_not (parser, CPP_COLON))
11869 break;
11870 }
11871 return list;
11872}
11873
11874/* Parse an objc-keywordexpr.
11875
11876 objc-keywordexpr:
11877 nonempty-expr-list
11878*/
11879
11880static tree
11881c_parser_objc_keywordexpr (c_parser *parser)
11882{
bbbbb16a 11883 tree ret;
9771b263 11884 vec<tree, va_gc> *expr_list = c_parser_expr_list (parser, true, true,
81e5eca8 11885 NULL, NULL, NULL, NULL);
9771b263 11886 if (vec_safe_length (expr_list) == 1)
27bf414c
JM
11887 {
11888 /* Just return the expression, remove a level of
11889 indirection. */
9771b263 11890 ret = (*expr_list)[0];
27bf414c
JM
11891 }
11892 else
11893 {
11894 /* We have a comma expression, we will collapse later. */
c166b898 11895 ret = build_tree_list_vec (expr_list);
27bf414c 11896 }
c166b898 11897 release_tree_vector (expr_list);
bbbbb16a 11898 return ret;
27bf414c
JM
11899}
11900
c165dca7
IS
11901/* A check, needed in several places, that ObjC interface, implementation or
11902 method definitions are not prefixed by incorrect items. */
11903static bool
11904c_parser_objc_diagnose_bad_element_prefix (c_parser *parser,
11905 struct c_declspecs *specs)
11906{
9e5b2115
PB
11907 if (!specs->declspecs_seen_p || specs->non_sc_seen_p
11908 || specs->typespec_kind != ctsk_none)
c165dca7
IS
11909 {
11910 c_parser_error (parser,
11911 "no type or storage class may be specified here,");
11912 c_parser_skip_to_end_of_block_or_statement (parser);
11913 return true;
11914 }
11915 return false;
11916}
668ea4b1 11917
f614132b 11918/* Parse an Objective-C @property declaration. The syntax is:
668ea4b1 11919
f614132b
NP
11920 objc-property-declaration:
11921 '@property' objc-property-attributes[opt] struct-declaration ;
668ea4b1 11922
f614132b
NP
11923 objc-property-attributes:
11924 '(' objc-property-attribute-list ')'
11925
11926 objc-property-attribute-list:
11927 objc-property-attribute
11928 objc-property-attribute-list, objc-property-attribute
11929
11930 objc-property-attribute
11931 'getter' = identifier
11932 'setter' = identifier
11933 'readonly'
11934 'readwrite'
11935 'assign'
11936 'retain'
11937 'copy'
11938 'nonatomic'
11939
11940 For example:
11941 @property NSString *name;
11942 @property (readonly) id object;
11943 @property (retain, nonatomic, getter=getTheName) id name;
11944 @property int a, b, c;
11945
11946 PS: This function is identical to cp_parser_objc_at_propery_declaration
200290f2 11947 for C++. Keep them in sync. */
668ea4b1 11948static void
f614132b 11949c_parser_objc_at_property_declaration (c_parser *parser)
668ea4b1 11950{
200290f2
NP
11951 /* The following variables hold the attributes of the properties as
11952 parsed. They are 'false' or 'NULL_TREE' if the attribute was not
11953 seen. When we see an attribute, we set them to 'true' (if they
11954 are boolean properties) or to the identifier (if they have an
11955 argument, ie, for getter and setter). Note that here we only
11956 parse the list of attributes, check the syntax and accumulate the
11957 attributes that we find. objc_add_property_declaration() will
11958 then process the information. */
11959 bool property_assign = false;
11960 bool property_copy = false;
11961 tree property_getter_ident = NULL_TREE;
11962 bool property_nonatomic = false;
11963 bool property_readonly = false;
11964 bool property_readwrite = false;
11965 bool property_retain = false;
11966 tree property_setter_ident = NULL_TREE;
200290f2
NP
11967
11968 /* 'properties' is the list of properties that we read. Usually a
11969 single one, but maybe more (eg, in "@property int a, b, c;" there
11970 are three). */
f614132b
NP
11971 tree properties;
11972 location_t loc;
200290f2 11973
f614132b
NP
11974 loc = c_parser_peek_token (parser)->location;
11975 gcc_assert (c_parser_next_token_is_keyword (parser, RID_AT_PROPERTY));
668ea4b1 11976
f614132b 11977 c_parser_consume_token (parser); /* Eat '@property'. */
668ea4b1 11978
f614132b
NP
11979 /* Parse the optional attribute list... */
11980 if (c_parser_next_token_is (parser, CPP_OPEN_PAREN))
668ea4b1 11981 {
32129a17
DM
11982 matching_parens parens;
11983
f614132b 11984 /* Eat the '(' */
32129a17
DM
11985 parens.consume_open (parser);
11986
f614132b
NP
11987 /* Property attribute keywords are valid now. */
11988 parser->objc_property_attr_context = true;
11989
11990 while (true)
668ea4b1 11991 {
f614132b
NP
11992 bool syntax_error = false;
11993 c_token *token = c_parser_peek_token (parser);
11994 enum rid keyword;
11995
11996 if (token->type != CPP_KEYWORD)
11997 {
11998 if (token->type == CPP_CLOSE_PAREN)
11999 c_parser_error (parser, "expected identifier");
12000 else
12001 {
12002 c_parser_consume_token (parser);
12003 c_parser_error (parser, "unknown property attribute");
12004 }
12005 break;
12006 }
12007 keyword = token->keyword;
200290f2 12008 c_parser_consume_token (parser);
f614132b
NP
12009 switch (keyword)
12010 {
200290f2 12011 case RID_ASSIGN: property_assign = true; break;
200290f2
NP
12012 case RID_COPY: property_copy = true; break;
12013 case RID_NONATOMIC: property_nonatomic = true; break;
12014 case RID_READONLY: property_readonly = true; break;
12015 case RID_READWRITE: property_readwrite = true; break;
12016 case RID_RETAIN: property_retain = true; break;
12017
f614132b
NP
12018 case RID_GETTER:
12019 case RID_SETTER:
f614132b
NP
12020 if (c_parser_next_token_is_not (parser, CPP_EQ))
12021 {
d853ee42
NP
12022 if (keyword == RID_GETTER)
12023 c_parser_error (parser,
12024 "missing %<=%> (after %<getter%> attribute)");
12025 else
12026 c_parser_error (parser,
12027 "missing %<=%> (after %<setter%> attribute)");
f614132b
NP
12028 syntax_error = true;
12029 break;
12030 }
12031 c_parser_consume_token (parser); /* eat the = */
12032 if (c_parser_next_token_is_not (parser, CPP_NAME))
12033 {
12034 c_parser_error (parser, "expected identifier");
12035 syntax_error = true;
12036 break;
12037 }
f614132b
NP
12038 if (keyword == RID_SETTER)
12039 {
200290f2
NP
12040 if (property_setter_ident != NULL_TREE)
12041 c_parser_error (parser, "the %<setter%> attribute may only be specified once");
12042 else
12043 property_setter_ident = c_parser_peek_token (parser)->value;
f614132b 12044 c_parser_consume_token (parser);
200290f2
NP
12045 if (c_parser_next_token_is_not (parser, CPP_COLON))
12046 c_parser_error (parser, "setter name must terminate with %<:%>");
12047 else
12048 c_parser_consume_token (parser);
f614132b 12049 }
46a88c12 12050 else
f614132b 12051 {
200290f2
NP
12052 if (property_getter_ident != NULL_TREE)
12053 c_parser_error (parser, "the %<getter%> attribute may only be specified once");
12054 else
12055 property_getter_ident = c_parser_peek_token (parser)->value;
f614132b 12056 c_parser_consume_token (parser);
f614132b 12057 }
200290f2
NP
12058 break;
12059 default:
12060 c_parser_error (parser, "unknown property attribute");
f614132b
NP
12061 syntax_error = true;
12062 break;
12063 }
12064
12065 if (syntax_error)
668ea4b1 12066 break;
f614132b
NP
12067
12068 if (c_parser_next_token_is (parser, CPP_COMMA))
668ea4b1 12069 c_parser_consume_token (parser);
f614132b 12070 else
668ea4b1
IS
12071 break;
12072 }
f614132b 12073 parser->objc_property_attr_context = false;
32129a17 12074 parens.skip_until_found_close (parser);
f614132b
NP
12075 }
12076 /* ... and the property declaration(s). */
12077 properties = c_parser_struct_declaration (parser);
668ea4b1 12078
f614132b
NP
12079 if (properties == error_mark_node)
12080 {
12081 c_parser_skip_until_found (parser, CPP_SEMICOLON, NULL);
12082 parser->error = false;
12083 return;
12084 }
668ea4b1 12085
f614132b
NP
12086 if (properties == NULL_TREE)
12087 c_parser_error (parser, "expected identifier");
12088 else
12089 {
12090 /* Comma-separated properties are chained together in
12091 reverse order; add them one by one. */
12092 properties = nreverse (properties);
12093
12094 for (; properties; properties = TREE_CHAIN (properties))
200290f2
NP
12095 objc_add_property_declaration (loc, copy_node (properties),
12096 property_readonly, property_readwrite,
12097 property_assign, property_retain,
12098 property_copy, property_nonatomic,
46a88c12 12099 property_getter_ident, property_setter_ident);
f614132b 12100 }
668ea4b1
IS
12101
12102 c_parser_skip_until_found (parser, CPP_SEMICOLON, "expected %<;%>");
f614132b 12103 parser->error = false;
668ea4b1
IS
12104}
12105
da57d1b9
NP
12106/* Parse an Objective-C @synthesize declaration. The syntax is:
12107
12108 objc-synthesize-declaration:
12109 @synthesize objc-synthesize-identifier-list ;
12110
12111 objc-synthesize-identifier-list:
12112 objc-synthesize-identifier
12113 objc-synthesize-identifier-list, objc-synthesize-identifier
12114
12115 objc-synthesize-identifier
12116 identifier
12117 identifier = identifier
12118
12119 For example:
12120 @synthesize MyProperty;
12121 @synthesize OneProperty, AnotherProperty=MyIvar, YetAnotherProperty;
12122
12123 PS: This function is identical to cp_parser_objc_at_synthesize_declaration
12124 for C++. Keep them in sync.
12125*/
12126static void
12127c_parser_objc_at_synthesize_declaration (c_parser *parser)
12128{
12129 tree list = NULL_TREE;
12130 location_t loc;
12131 gcc_assert (c_parser_next_token_is_keyword (parser, RID_AT_SYNTHESIZE));
12132 loc = c_parser_peek_token (parser)->location;
12133
12134 c_parser_consume_token (parser);
12135 while (true)
12136 {
12137 tree property, ivar;
12138 if (c_parser_next_token_is_not (parser, CPP_NAME))
12139 {
12140 c_parser_error (parser, "expected identifier");
12141 c_parser_skip_until_found (parser, CPP_SEMICOLON, NULL);
12142 /* Once we find the semicolon, we can resume normal parsing.
12143 We have to reset parser->error manually because
12144 c_parser_skip_until_found() won't reset it for us if the
12145 next token is precisely a semicolon. */
12146 parser->error = false;
12147 return;
12148 }
12149 property = c_parser_peek_token (parser)->value;
12150 c_parser_consume_token (parser);
12151 if (c_parser_next_token_is (parser, CPP_EQ))
12152 {
12153 c_parser_consume_token (parser);
12154 if (c_parser_next_token_is_not (parser, CPP_NAME))
12155 {
12156 c_parser_error (parser, "expected identifier");
12157 c_parser_skip_until_found (parser, CPP_SEMICOLON, NULL);
12158 parser->error = false;
12159 return;
12160 }
12161 ivar = c_parser_peek_token (parser)->value;
12162 c_parser_consume_token (parser);
12163 }
12164 else
12165 ivar = NULL_TREE;
12166 list = chainon (list, build_tree_list (ivar, property));
12167 if (c_parser_next_token_is (parser, CPP_COMMA))
12168 c_parser_consume_token (parser);
12169 else
12170 break;
12171 }
12172 c_parser_skip_until_found (parser, CPP_SEMICOLON, "expected %<;%>");
12173 objc_add_synthesize_declaration (loc, list);
12174}
12175
12176/* Parse an Objective-C @dynamic declaration. The syntax is:
12177
12178 objc-dynamic-declaration:
12179 @dynamic identifier-list ;
12180
12181 For example:
12182 @dynamic MyProperty;
12183 @dynamic MyProperty, AnotherProperty;
12184
12185 PS: This function is identical to cp_parser_objc_at_dynamic_declaration
12186 for C++. Keep them in sync.
12187*/
12188static void
12189c_parser_objc_at_dynamic_declaration (c_parser *parser)
12190{
12191 tree list = NULL_TREE;
12192 location_t loc;
12193 gcc_assert (c_parser_next_token_is_keyword (parser, RID_AT_DYNAMIC));
12194 loc = c_parser_peek_token (parser)->location;
12195
12196 c_parser_consume_token (parser);
12197 while (true)
12198 {
12199 tree property;
12200 if (c_parser_next_token_is_not (parser, CPP_NAME))
12201 {
12202 c_parser_error (parser, "expected identifier");
12203 c_parser_skip_until_found (parser, CPP_SEMICOLON, NULL);
12204 parser->error = false;
12205 return;
12206 }
12207 property = c_parser_peek_token (parser)->value;
12208 list = chainon (list, build_tree_list (NULL_TREE, property));
12209 c_parser_consume_token (parser);
12210 if (c_parser_next_token_is (parser, CPP_COMMA))
12211 c_parser_consume_token (parser);
12212 else
12213 break;
12214 }
12215 c_parser_skip_until_found (parser, CPP_SEMICOLON, "expected %<;%>");
12216 objc_add_dynamic_declaration (loc, list);
12217}
12218
27bf414c 12219\f
170a8bd6
EB
12220/* Parse a pragma GCC ivdep. */
12221
12222static bool
12223c_parse_pragma_ivdep (c_parser *parser)
12224{
12225 c_parser_consume_pragma (parser);
12226 c_parser_skip_to_pragma_eol (parser);
12227 return true;
12228}
12229
12230/* Parse a pragma GCC unroll. */
12231
12232static unsigned short
12233c_parser_pragma_unroll (c_parser *parser)
12234{
12235 unsigned short unroll;
12236 c_parser_consume_pragma (parser);
12237 location_t location = c_parser_peek_token (parser)->location;
12238 tree expr = c_parser_expr_no_commas (parser, NULL).value;
12239 mark_exp_read (expr);
12240 expr = c_fully_fold (expr, false, NULL);
12241 HOST_WIDE_INT lunroll = 0;
12242 if (!INTEGRAL_TYPE_P (TREE_TYPE (expr))
12243 || TREE_CODE (expr) != INTEGER_CST
12244 || (lunroll = tree_to_shwi (expr)) < 0
12245 || lunroll >= USHRT_MAX)
12246 {
12247 error_at (location, "%<#pragma GCC unroll%> requires an"
12248 " assignment-expression that evaluates to a non-negative"
12249 " integral constant less than %u", USHRT_MAX);
12250 unroll = 0;
12251 }
12252 else
12253 {
12254 unroll = (unsigned short)lunroll;
12255 if (unroll == 0)
12256 unroll = 1;
12257 }
12258
12259 c_parser_skip_to_pragma_eol (parser);
12260 return unroll;
12261}
12262
953ff289
DN
12263/* Handle pragmas. Some OpenMP pragmas are associated with, and therefore
12264 should be considered, statements. ALLOW_STMT is true if we're within
12265 the context of a function and such pragmas are to be allowed. Returns
12266 true if we actually parsed such a pragma. */
27bf414c 12267
bc4071dd 12268static bool
dda1bf61 12269c_parser_pragma (c_parser *parser, enum pragma_context context, bool *if_p)
bc4071dd
RH
12270{
12271 unsigned int id;
a71dbc63 12272 const char *construct = NULL;
bc4071dd
RH
12273
12274 id = c_parser_peek_token (parser)->pragma_kind;
12275 gcc_assert (id != PRAGMA_NONE);
12276
12277 switch (id)
12278 {
6e232ba4
JN
12279 case PRAGMA_OACC_DECLARE:
12280 c_parser_oacc_declare (parser);
12281 return false;
12282
41dbbb37 12283 case PRAGMA_OACC_ENTER_DATA:
c5af52eb
CP
12284 if (context != pragma_compound)
12285 {
a71dbc63
JJ
12286 construct = "acc enter data";
12287 in_compound:
c5af52eb 12288 if (context == pragma_stmt)
a71dbc63
JJ
12289 {
12290 error_at (c_parser_peek_token (parser)->location,
12291 "%<#pragma %s%> may only be used in compound "
12292 "statements", construct);
12293 c_parser_skip_until_found (parser, CPP_PRAGMA_EOL, NULL);
12294 return false;
12295 }
c5af52eb
CP
12296 goto bad_stmt;
12297 }
41dbbb37
TS
12298 c_parser_oacc_enter_exit_data (parser, true);
12299 return false;
12300
12301 case PRAGMA_OACC_EXIT_DATA:
c5af52eb
CP
12302 if (context != pragma_compound)
12303 {
a71dbc63
JJ
12304 construct = "acc exit data";
12305 goto in_compound;
c5af52eb 12306 }
41dbbb37
TS
12307 c_parser_oacc_enter_exit_data (parser, false);
12308 return false;
12309
3a40d81d 12310 case PRAGMA_OACC_ROUTINE:
ae9281fc
TS
12311 if (context != pragma_external)
12312 {
12313 error_at (c_parser_peek_token (parser)->location,
12314 "%<#pragma acc routine%> must be at file scope");
12315 c_parser_skip_until_found (parser, CPP_PRAGMA_EOL, NULL);
12316 return false;
12317 }
3a40d81d
NS
12318 c_parser_oacc_routine (parser, context);
12319 return false;
12320
41dbbb37
TS
12321 case PRAGMA_OACC_UPDATE:
12322 if (context != pragma_compound)
12323 {
a71dbc63
JJ
12324 construct = "acc update";
12325 goto in_compound;
41dbbb37
TS
12326 }
12327 c_parser_oacc_update (parser);
12328 return false;
12329
953ff289
DN
12330 case PRAGMA_OMP_BARRIER:
12331 if (context != pragma_compound)
12332 {
a71dbc63
JJ
12333 construct = "omp barrier";
12334 goto in_compound;
953ff289
DN
12335 }
12336 c_parser_omp_barrier (parser);
12337 return false;
12338
28567c40
JJ
12339 case PRAGMA_OMP_DEPOBJ:
12340 if (context != pragma_compound)
12341 {
12342 construct = "omp depobj";
12343 goto in_compound;
12344 }
12345 c_parser_omp_depobj (parser);
12346 return false;
12347
953ff289
DN
12348 case PRAGMA_OMP_FLUSH:
12349 if (context != pragma_compound)
12350 {
a71dbc63
JJ
12351 construct = "omp flush";
12352 goto in_compound;
953ff289
DN
12353 }
12354 c_parser_omp_flush (parser);
12355 return false;
12356
a68ab351
JJ
12357 case PRAGMA_OMP_TASKWAIT:
12358 if (context != pragma_compound)
12359 {
a71dbc63
JJ
12360 construct = "omp taskwait";
12361 goto in_compound;
a68ab351
JJ
12362 }
12363 c_parser_omp_taskwait (parser);
12364 return false;
12365
20906c66
JJ
12366 case PRAGMA_OMP_TASKYIELD:
12367 if (context != pragma_compound)
12368 {
a71dbc63
JJ
12369 construct = "omp taskyield";
12370 goto in_compound;
20906c66
JJ
12371 }
12372 c_parser_omp_taskyield (parser);
12373 return false;
12374
acf0174b
JJ
12375 case PRAGMA_OMP_CANCEL:
12376 if (context != pragma_compound)
12377 {
a71dbc63
JJ
12378 construct = "omp cancel";
12379 goto in_compound;
acf0174b
JJ
12380 }
12381 c_parser_omp_cancel (parser);
12382 return false;
12383
12384 case PRAGMA_OMP_CANCELLATION_POINT:
54d19c3b 12385 c_parser_omp_cancellation_point (parser, context);
acf0174b
JJ
12386 return false;
12387
953ff289
DN
12388 case PRAGMA_OMP_THREADPRIVATE:
12389 c_parser_omp_threadprivate (parser);
12390 return false;
12391
acf0174b 12392 case PRAGMA_OMP_TARGET:
dda1bf61 12393 return c_parser_omp_target (parser, context, if_p);
acf0174b
JJ
12394
12395 case PRAGMA_OMP_END_DECLARE_TARGET:
12396 c_parser_omp_end_declare_target (parser);
12397 return false;
12398
bf38f7e9
JJ
12399 case PRAGMA_OMP_SCAN:
12400 error_at (c_parser_peek_token (parser)->location,
12401 "%<#pragma omp scan%> may only be used in "
12402 "a loop construct with %<inscan%> %<reduction%> clause");
12403 c_parser_skip_until_found (parser, CPP_PRAGMA_EOL, NULL);
12404 return false;
12405
953ff289 12406 case PRAGMA_OMP_SECTION:
3ba09659
AH
12407 error_at (c_parser_peek_token (parser)->location,
12408 "%<#pragma omp section%> may only be used in "
12409 "%<#pragma omp sections%> construct");
953ff289
DN
12410 c_parser_skip_until_found (parser, CPP_PRAGMA_EOL, NULL);
12411 return false;
12412
f9d8d994 12413 case PRAGMA_OMP_DECLARE:
acf0174b
JJ
12414 c_parser_omp_declare (parser, context);
12415 return false;
d9a6bd32 12416
28567c40 12417 case PRAGMA_OMP_REQUIRES:
2dc9294c
JJ
12418 if (context != pragma_external)
12419 {
12420 error_at (c_parser_peek_token (parser)->location,
12421 "%<#pragma omp requires%> may only be used at file scope");
12422 c_parser_skip_until_found (parser, CPP_PRAGMA_EOL, NULL);
12423 return false;
12424 }
28567c40
JJ
12425 c_parser_omp_requires (parser);
12426 return false;
12427
d9a6bd32 12428 case PRAGMA_OMP_ORDERED:
dda1bf61 12429 return c_parser_omp_ordered (parser, context, if_p);
d9a6bd32 12430
8170608b 12431 case PRAGMA_IVDEP:
170a8bd6
EB
12432 {
12433 const bool ivdep = c_parse_pragma_ivdep (parser);
12434 unsigned short unroll;
12435 if (c_parser_peek_token (parser)->pragma_kind == PRAGMA_UNROLL)
12436 unroll = c_parser_pragma_unroll (parser);
12437 else
12438 unroll = 0;
12439 if (!c_parser_next_token_is_keyword (parser, RID_FOR)
12440 && !c_parser_next_token_is_keyword (parser, RID_WHILE)
12441 && !c_parser_next_token_is_keyword (parser, RID_DO))
12442 {
12443 c_parser_error (parser, "for, while or do statement expected");
12444 return false;
12445 }
12446 if (c_parser_next_token_is_keyword (parser, RID_FOR))
12447 c_parser_for_statement (parser, ivdep, unroll, if_p);
12448 else if (c_parser_next_token_is_keyword (parser, RID_WHILE))
12449 c_parser_while_statement (parser, ivdep, unroll, if_p);
12450 else
12451 c_parser_do_statement (parser, ivdep, unroll);
12452 }
12453 return false;
12454
12455 case PRAGMA_UNROLL:
12456 {
12457 unsigned short unroll = c_parser_pragma_unroll (parser);
12458 bool ivdep;
12459 if (c_parser_peek_token (parser)->pragma_kind == PRAGMA_IVDEP)
12460 ivdep = c_parse_pragma_ivdep (parser);
12461 else
12462 ivdep = false;
12463 if (!c_parser_next_token_is_keyword (parser, RID_FOR)
12464 && !c_parser_next_token_is_keyword (parser, RID_WHILE)
12465 && !c_parser_next_token_is_keyword (parser, RID_DO))
12466 {
12467 c_parser_error (parser, "for, while or do statement expected");
12468 return false;
12469 }
12470 if (c_parser_next_token_is_keyword (parser, RID_FOR))
12471 c_parser_for_statement (parser, ivdep, unroll, if_p);
12472 else if (c_parser_next_token_is_keyword (parser, RID_WHILE))
12473 c_parser_while_statement (parser, ivdep, unroll, if_p);
12474 else
12475 c_parser_do_statement (parser, ivdep, unroll);
12476 }
8170608b 12477 return false;
acf0174b 12478
bc4071dd
RH
12479 case PRAGMA_GCC_PCH_PREPROCESS:
12480 c_parser_error (parser, "%<#pragma GCC pch_preprocess%> must be first");
12481 c_parser_skip_until_found (parser, CPP_PRAGMA_EOL, NULL);
12482 return false;
12483
c5af52eb
CP
12484 case PRAGMA_OACC_WAIT:
12485 if (context != pragma_compound)
12486 {
a71dbc63
JJ
12487 construct = "acc wait";
12488 goto in_compound;
c5af52eb
CP
12489 }
12490 /* FALL THROUGH. */
12491
bc4071dd 12492 default:
953ff289
DN
12493 if (id < PRAGMA_FIRST_EXTERNAL)
12494 {
acf0174b 12495 if (context != pragma_stmt && context != pragma_compound)
953ff289
DN
12496 {
12497 bad_stmt:
12498 c_parser_error (parser, "expected declaration specifiers");
12499 c_parser_skip_until_found (parser, CPP_PRAGMA_EOL, NULL);
12500 return false;
12501 }
dda1bf61 12502 c_parser_omp_construct (parser, if_p);
953ff289
DN
12503 return true;
12504 }
bc4071dd
RH
12505 break;
12506 }
12507
12508 c_parser_consume_pragma (parser);
12509 c_invoke_pragma_handler (id);
27bf414c 12510
b8698a0f 12511 /* Skip to EOL, but suppress any error message. Those will have been
bc4071dd
RH
12512 generated by the handler routine through calling error, as opposed
12513 to calling c_parser_error. */
12514 parser->error = true;
12515 c_parser_skip_to_pragma_eol (parser);
12516
12517 return false;
12518}
12519
12520/* The interface the pragma parsers have to the lexer. */
12521
12522enum cpp_ttype
c4914de6 12523pragma_lex (tree *value, location_t *loc)
bc4071dd
RH
12524{
12525 c_token *tok = c_parser_peek_token (the_parser);
12526 enum cpp_ttype ret = tok->type;
12527
12528 *value = tok->value;
c4914de6
MLI
12529 if (loc)
12530 *loc = tok->location;
12531
bc4071dd
RH
12532 if (ret == CPP_PRAGMA_EOL || ret == CPP_EOF)
12533 ret = CPP_EOF;
471c5330
JM
12534 else if (ret == CPP_STRING)
12535 *value = c_parser_string_literal (the_parser, false, false).value;
bc4071dd
RH
12536 else
12537 {
12538 if (ret == CPP_KEYWORD)
12539 ret = CPP_NAME;
12540 c_parser_consume_token (the_parser);
12541 }
12542
12543 return ret;
12544}
12545
12546static void
12547c_parser_pragma_pch_preprocess (c_parser *parser)
12548{
12549 tree name = NULL;
12550
471c5330 12551 parser->lex_joined_string = true;
bc4071dd
RH
12552 c_parser_consume_pragma (parser);
12553 if (c_parser_next_token_is (parser, CPP_STRING))
12554 {
12555 name = c_parser_peek_token (parser)->value;
12556 c_parser_consume_token (parser);
12557 }
12558 else
12559 c_parser_error (parser, "expected string literal");
12560 c_parser_skip_to_pragma_eol (parser);
471c5330 12561 parser->lex_joined_string = false;
bc4071dd
RH
12562
12563 if (name)
12564 c_common_pch_pragma (parse_in, TREE_STRING_POINTER (name));
12565}
953ff289 12566\f
41dbbb37 12567/* OpenACC and OpenMP parsing routines. */
953ff289
DN
12568
12569/* Returns name of the next clause.
12570 If the clause is not recognized PRAGMA_OMP_CLAUSE_NONE is returned and
12571 the token is not consumed. Otherwise appropriate pragma_omp_clause is
12572 returned and the token is consumed. */
12573
12574static pragma_omp_clause
12575c_parser_omp_clause_name (c_parser *parser)
12576{
12577 pragma_omp_clause result = PRAGMA_OMP_CLAUSE_NONE;
12578
41dbbb37
TS
12579 if (c_parser_next_token_is_keyword (parser, RID_AUTO))
12580 result = PRAGMA_OACC_CLAUSE_AUTO;
12581 else if (c_parser_next_token_is_keyword (parser, RID_IF))
953ff289
DN
12582 result = PRAGMA_OMP_CLAUSE_IF;
12583 else if (c_parser_next_token_is_keyword (parser, RID_DEFAULT))
12584 result = PRAGMA_OMP_CLAUSE_DEFAULT;
acf0174b
JJ
12585 else if (c_parser_next_token_is_keyword (parser, RID_FOR))
12586 result = PRAGMA_OMP_CLAUSE_FOR;
953ff289
DN
12587 else if (c_parser_next_token_is (parser, CPP_NAME))
12588 {
12589 const char *p = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
12590
12591 switch (p[0])
12592 {
acf0174b
JJ
12593 case 'a':
12594 if (!strcmp ("aligned", p))
12595 result = PRAGMA_OMP_CLAUSE_ALIGNED;
41dbbb37
TS
12596 else if (!strcmp ("async", p))
12597 result = PRAGMA_OACC_CLAUSE_ASYNC;
519d7496
JB
12598 else if (!strcmp ("attach", p))
12599 result = PRAGMA_OACC_CLAUSE_ATTACH;
acf0174b 12600 break;
554a530f
JJ
12601 case 'b':
12602 if (!strcmp ("bind", p))
12603 result = PRAGMA_OMP_CLAUSE_BIND;
12604 break;
953ff289 12605 case 'c':
a68ab351
JJ
12606 if (!strcmp ("collapse", p))
12607 result = PRAGMA_OMP_CLAUSE_COLLAPSE;
41dbbb37
TS
12608 else if (!strcmp ("copy", p))
12609 result = PRAGMA_OACC_CLAUSE_COPY;
a68ab351 12610 else if (!strcmp ("copyin", p))
953ff289 12611 result = PRAGMA_OMP_CLAUSE_COPYIN;
41dbbb37
TS
12612 else if (!strcmp ("copyout", p))
12613 result = PRAGMA_OACC_CLAUSE_COPYOUT;
953ff289
DN
12614 else if (!strcmp ("copyprivate", p))
12615 result = PRAGMA_OMP_CLAUSE_COPYPRIVATE;
41dbbb37
TS
12616 else if (!strcmp ("create", p))
12617 result = PRAGMA_OACC_CLAUSE_CREATE;
953ff289 12618 break;
acf0174b 12619 case 'd':
d9a6bd32
JJ
12620 if (!strcmp ("defaultmap", p))
12621 result = PRAGMA_OMP_CLAUSE_DEFAULTMAP;
12622 else if (!strcmp ("delete", p))
41dbbb37
TS
12623 result = PRAGMA_OACC_CLAUSE_DELETE;
12624 else if (!strcmp ("depend", p))
acf0174b 12625 result = PRAGMA_OMP_CLAUSE_DEPEND;
519d7496
JB
12626 else if (!strcmp ("detach", p))
12627 result = PRAGMA_OACC_CLAUSE_DETACH;
acf0174b
JJ
12628 else if (!strcmp ("device", p))
12629 result = PRAGMA_OMP_CLAUSE_DEVICE;
41dbbb37
TS
12630 else if (!strcmp ("deviceptr", p))
12631 result = PRAGMA_OACC_CLAUSE_DEVICEPTR;
6e232ba4
JN
12632 else if (!strcmp ("device_resident", p))
12633 result = PRAGMA_OACC_CLAUSE_DEVICE_RESIDENT;
77eb117f
JJ
12634 else if (!strcmp ("device_type", p))
12635 result = PRAGMA_OMP_CLAUSE_DEVICE_TYPE;
acf0174b
JJ
12636 else if (!strcmp ("dist_schedule", p))
12637 result = PRAGMA_OMP_CLAUSE_DIST_SCHEDULE;
12638 break;
953ff289 12639 case 'f':
20906c66
JJ
12640 if (!strcmp ("final", p))
12641 result = PRAGMA_OMP_CLAUSE_FINAL;
829c6349
CLT
12642 else if (!strcmp ("finalize", p))
12643 result = PRAGMA_OACC_CLAUSE_FINALIZE;
20906c66 12644 else if (!strcmp ("firstprivate", p))
953ff289 12645 result = PRAGMA_OMP_CLAUSE_FIRSTPRIVATE;
acf0174b
JJ
12646 else if (!strcmp ("from", p))
12647 result = PRAGMA_OMP_CLAUSE_FROM;
12648 break;
41dbbb37
TS
12649 case 'g':
12650 if (!strcmp ("gang", p))
12651 result = PRAGMA_OACC_CLAUSE_GANG;
d9a6bd32
JJ
12652 else if (!strcmp ("grainsize", p))
12653 result = PRAGMA_OMP_CLAUSE_GRAINSIZE;
41dbbb37
TS
12654 break;
12655 case 'h':
d9a6bd32
JJ
12656 if (!strcmp ("hint", p))
12657 result = PRAGMA_OMP_CLAUSE_HINT;
12658 else if (!strcmp ("host", p))
41dbbb37
TS
12659 result = PRAGMA_OACC_CLAUSE_HOST;
12660 break;
acf0174b 12661 case 'i':
829c6349
CLT
12662 if (!strcmp ("if_present", p))
12663 result = PRAGMA_OACC_CLAUSE_IF_PRESENT;
28567c40
JJ
12664 else if (!strcmp ("in_reduction", p))
12665 result = PRAGMA_OMP_CLAUSE_IN_REDUCTION;
829c6349 12666 else if (!strcmp ("inbranch", p))
acf0174b 12667 result = PRAGMA_OMP_CLAUSE_INBRANCH;
7a5e4956
CP
12668 else if (!strcmp ("independent", p))
12669 result = PRAGMA_OACC_CLAUSE_INDEPENDENT;
d9a6bd32
JJ
12670 else if (!strcmp ("is_device_ptr", p))
12671 result = PRAGMA_OMP_CLAUSE_IS_DEVICE_PTR;
953ff289
DN
12672 break;
12673 case 'l':
12674 if (!strcmp ("lastprivate", p))
12675 result = PRAGMA_OMP_CLAUSE_LASTPRIVATE;
acf0174b
JJ
12676 else if (!strcmp ("linear", p))
12677 result = PRAGMA_OMP_CLAUSE_LINEAR;
d9a6bd32
JJ
12678 else if (!strcmp ("link", p))
12679 result = PRAGMA_OMP_CLAUSE_LINK;
953ff289 12680 break;
20906c66 12681 case 'm':
acf0174b
JJ
12682 if (!strcmp ("map", p))
12683 result = PRAGMA_OMP_CLAUSE_MAP;
12684 else if (!strcmp ("mergeable", p))
20906c66
JJ
12685 result = PRAGMA_OMP_CLAUSE_MERGEABLE;
12686 break;
953ff289 12687 case 'n':
a6163563
JB
12688 if (!strcmp ("no_create", p))
12689 result = PRAGMA_OACC_CLAUSE_NO_CREATE;
12690 else if (!strcmp ("nogroup", p))
d9a6bd32 12691 result = PRAGMA_OMP_CLAUSE_NOGROUP;
28567c40
JJ
12692 else if (!strcmp ("nontemporal", p))
12693 result = PRAGMA_OMP_CLAUSE_NONTEMPORAL;
d9a6bd32 12694 else if (!strcmp ("notinbranch", p))
acf0174b
JJ
12695 result = PRAGMA_OMP_CLAUSE_NOTINBRANCH;
12696 else if (!strcmp ("nowait", p))
953ff289 12697 result = PRAGMA_OMP_CLAUSE_NOWAIT;
41dbbb37
TS
12698 else if (!strcmp ("num_gangs", p))
12699 result = PRAGMA_OACC_CLAUSE_NUM_GANGS;
d9a6bd32
JJ
12700 else if (!strcmp ("num_tasks", p))
12701 result = PRAGMA_OMP_CLAUSE_NUM_TASKS;
acf0174b
JJ
12702 else if (!strcmp ("num_teams", p))
12703 result = PRAGMA_OMP_CLAUSE_NUM_TEAMS;
953ff289
DN
12704 else if (!strcmp ("num_threads", p))
12705 result = PRAGMA_OMP_CLAUSE_NUM_THREADS;
41dbbb37
TS
12706 else if (!strcmp ("num_workers", p))
12707 result = PRAGMA_OACC_CLAUSE_NUM_WORKERS;
953ff289
DN
12708 break;
12709 case 'o':
12710 if (!strcmp ("ordered", p))
12711 result = PRAGMA_OMP_CLAUSE_ORDERED;
1fdd6f04
JJ
12712 else if (!strcmp ("order", p))
12713 result = PRAGMA_OMP_CLAUSE_ORDER;
953ff289
DN
12714 break;
12715 case 'p':
acf0174b
JJ
12716 if (!strcmp ("parallel", p))
12717 result = PRAGMA_OMP_CLAUSE_PARALLEL;
41dbbb37
TS
12718 else if (!strcmp ("present", p))
12719 result = PRAGMA_OACC_CLAUSE_PRESENT;
829c6349
CLT
12720 /* As of OpenACC 2.5, these are now aliases of the non-present_or
12721 clauses. */
41dbbb37
TS
12722 else if (!strcmp ("present_or_copy", p)
12723 || !strcmp ("pcopy", p))
829c6349 12724 result = PRAGMA_OACC_CLAUSE_COPY;
41dbbb37
TS
12725 else if (!strcmp ("present_or_copyin", p)
12726 || !strcmp ("pcopyin", p))
829c6349 12727 result = PRAGMA_OACC_CLAUSE_COPYIN;
41dbbb37
TS
12728 else if (!strcmp ("present_or_copyout", p)
12729 || !strcmp ("pcopyout", p))
829c6349 12730 result = PRAGMA_OACC_CLAUSE_COPYOUT;
41dbbb37
TS
12731 else if (!strcmp ("present_or_create", p)
12732 || !strcmp ("pcreate", p))
829c6349 12733 result = PRAGMA_OACC_CLAUSE_CREATE;
d9a6bd32
JJ
12734 else if (!strcmp ("priority", p))
12735 result = PRAGMA_OMP_CLAUSE_PRIORITY;
acf0174b 12736 else if (!strcmp ("private", p))
953ff289 12737 result = PRAGMA_OMP_CLAUSE_PRIVATE;
acf0174b
JJ
12738 else if (!strcmp ("proc_bind", p))
12739 result = PRAGMA_OMP_CLAUSE_PROC_BIND;
953ff289
DN
12740 break;
12741 case 'r':
12742 if (!strcmp ("reduction", p))
12743 result = PRAGMA_OMP_CLAUSE_REDUCTION;
12744 break;
12745 case 's':
acf0174b
JJ
12746 if (!strcmp ("safelen", p))
12747 result = PRAGMA_OMP_CLAUSE_SAFELEN;
12748 else if (!strcmp ("schedule", p))
953ff289 12749 result = PRAGMA_OMP_CLAUSE_SCHEDULE;
acf0174b
JJ
12750 else if (!strcmp ("sections", p))
12751 result = PRAGMA_OMP_CLAUSE_SECTIONS;
829c6349
CLT
12752 else if (!strcmp ("self", p)) /* "self" is a synonym for "host". */
12753 result = PRAGMA_OACC_CLAUSE_HOST;
41dbbb37
TS
12754 else if (!strcmp ("seq", p))
12755 result = PRAGMA_OACC_CLAUSE_SEQ;
953ff289
DN
12756 else if (!strcmp ("shared", p))
12757 result = PRAGMA_OMP_CLAUSE_SHARED;
d9a6bd32
JJ
12758 else if (!strcmp ("simd", p))
12759 result = PRAGMA_OMP_CLAUSE_SIMD;
acf0174b
JJ
12760 else if (!strcmp ("simdlen", p))
12761 result = PRAGMA_OMP_CLAUSE_SIMDLEN;
12762 break;
12763 case 't':
28567c40
JJ
12764 if (!strcmp ("task_reduction", p))
12765 result = PRAGMA_OMP_CLAUSE_TASK_REDUCTION;
12766 else if (!strcmp ("taskgroup", p))
acf0174b
JJ
12767 result = PRAGMA_OMP_CLAUSE_TASKGROUP;
12768 else if (!strcmp ("thread_limit", p))
12769 result = PRAGMA_OMP_CLAUSE_THREAD_LIMIT;
d9a6bd32
JJ
12770 else if (!strcmp ("threads", p))
12771 result = PRAGMA_OMP_CLAUSE_THREADS;
7a5e4956
CP
12772 else if (!strcmp ("tile", p))
12773 result = PRAGMA_OACC_CLAUSE_TILE;
acf0174b
JJ
12774 else if (!strcmp ("to", p))
12775 result = PRAGMA_OMP_CLAUSE_TO;
953ff289 12776 break;
a68ab351 12777 case 'u':
acf0174b
JJ
12778 if (!strcmp ("uniform", p))
12779 result = PRAGMA_OMP_CLAUSE_UNIFORM;
12780 else if (!strcmp ("untied", p))
a68ab351 12781 result = PRAGMA_OMP_CLAUSE_UNTIED;
37d5ad46
JB
12782 else if (!strcmp ("use_device", p))
12783 result = PRAGMA_OACC_CLAUSE_USE_DEVICE;
398e3feb
JJ
12784 else if (!strcmp ("use_device_addr", p))
12785 result = PRAGMA_OMP_CLAUSE_USE_DEVICE_ADDR;
ff7a55bf
TS
12786 else if (!strcmp ("use_device_ptr", p))
12787 result = PRAGMA_OMP_CLAUSE_USE_DEVICE_PTR;
a68ab351 12788 break;
41958c28 12789 case 'v':
41dbbb37
TS
12790 if (!strcmp ("vector", p))
12791 result = PRAGMA_OACC_CLAUSE_VECTOR;
12792 else if (!strcmp ("vector_length", p))
12793 result = PRAGMA_OACC_CLAUSE_VECTOR_LENGTH;
41958c28 12794 break;
41dbbb37
TS
12795 case 'w':
12796 if (!strcmp ("wait", p))
12797 result = PRAGMA_OACC_CLAUSE_WAIT;
12798 else if (!strcmp ("worker", p))
12799 result = PRAGMA_OACC_CLAUSE_WORKER;
12800 break;
953ff289
DN
12801 }
12802 }
12803
12804 if (result != PRAGMA_OMP_CLAUSE_NONE)
12805 c_parser_consume_token (parser);
12806
12807 return result;
12808}
12809
12810/* Validate that a clause of the given type does not already exist. */
12811
12812static void
d75d71e0
ILT
12813check_no_duplicate_clause (tree clauses, enum omp_clause_code code,
12814 const char *name)
953ff289 12815{
bb522e2e
JJ
12816 if (tree c = omp_find_clause (clauses, code))
12817 error_at (OMP_CLAUSE_LOCATION (c), "too many %qs clauses", name);
953ff289
DN
12818}
12819
41dbbb37
TS
12820/* OpenACC 2.0
12821 Parse wait clause or wait directive parameters. */
12822
12823static tree
12824c_parser_oacc_wait_list (c_parser *parser, location_t clause_loc, tree list)
12825{
12826 vec<tree, va_gc> *args;
12827 tree t, args_tree;
12828
32129a17
DM
12829 matching_parens parens;
12830 if (!parens.require_open (parser))
41dbbb37
TS
12831 return list;
12832
12833 args = c_parser_expr_list (parser, false, true, NULL, NULL, NULL, NULL);
41dbbb37
TS
12834 args_tree = build_tree_list_vec (args);
12835
12836 for (t = args_tree; t; t = TREE_CHAIN (t))
12837 {
12838 tree targ = TREE_VALUE (t);
12839
12840 if (targ != error_mark_node)
12841 {
12842 if (!INTEGRAL_TYPE_P (TREE_TYPE (targ)))
12843 {
12844 c_parser_error (parser, "expression must be integral");
12845 targ = error_mark_node;
12846 }
12847 else
12848 {
12849 tree c = build_omp_clause (clause_loc, OMP_CLAUSE_WAIT);
12850
12851 OMP_CLAUSE_DECL (c) = targ;
12852 OMP_CLAUSE_CHAIN (c) = list;
12853 list = c;
12854 }
12855 }
12856 }
12857
12858 release_tree_vector (args);
32129a17 12859 parens.require_close (parser);
41dbbb37
TS
12860 return list;
12861}
12862
12863/* OpenACC 2.0, OpenMP 2.5:
953ff289
DN
12864 variable-list:
12865 identifier
12866 variable-list , identifier
12867
c2255bc4
AH
12868 If KIND is nonzero, create the appropriate node and install the
12869 decl in OMP_CLAUSE_DECL and add the node to the head of the list.
12870 If KIND is nonzero, CLAUSE_LOC is the location of the clause.
953ff289
DN
12871
12872 If KIND is zero, create a TREE_LIST with the decl in TREE_PURPOSE;
519d7496
JB
12873 return the list created.
12874
12875 The optional ALLOW_DEREF argument is true if list items can use the deref
12876 (->) operator. */
953ff289
DN
12877
12878static tree
c2255bc4
AH
12879c_parser_omp_variable_list (c_parser *parser,
12880 location_t clause_loc,
519d7496
JB
12881 enum omp_clause_code kind, tree list,
12882 bool allow_deref = false)
953ff289 12883{
28567c40
JJ
12884 auto_vec<c_token> tokens;
12885 unsigned int tokens_avail = 0;
59bc434a 12886 bool first = true;
28567c40 12887
59bc434a 12888 while (1)
953ff289 12889 {
28567c40
JJ
12890 bool array_section_p = false;
12891 if (kind == OMP_CLAUSE_DEPEND)
12892 {
12893 if (c_parser_next_token_is_not (parser, CPP_NAME)
12894 || c_parser_peek_token (parser)->id_kind != C_ID_ID)
12895 {
12896 struct c_expr expr = c_parser_expr_no_commas (parser, NULL);
12897 if (expr.value != error_mark_node)
12898 {
12899 tree u = build_omp_clause (clause_loc, kind);
12900 OMP_CLAUSE_DECL (u) = expr.value;
12901 OMP_CLAUSE_CHAIN (u) = list;
12902 list = u;
12903 }
12904
12905 if (c_parser_next_token_is_not (parser, CPP_COMMA))
12906 break;
12907
12908 c_parser_consume_token (parser);
59bc434a 12909 first = false;
28567c40
JJ
12910 continue;
12911 }
12912
12913 tokens.truncate (0);
12914 unsigned int nesting_depth = 0;
12915 while (1)
12916 {
12917 c_token *token = c_parser_peek_token (parser);
12918 switch (token->type)
12919 {
12920 case CPP_EOF:
12921 case CPP_PRAGMA_EOL:
12922 break;
12923 case CPP_OPEN_BRACE:
12924 case CPP_OPEN_PAREN:
12925 case CPP_OPEN_SQUARE:
12926 ++nesting_depth;
12927 goto add;
12928 case CPP_CLOSE_BRACE:
12929 case CPP_CLOSE_PAREN:
12930 case CPP_CLOSE_SQUARE:
12931 if (nesting_depth-- == 0)
12932 break;
12933 goto add;
12934 case CPP_COMMA:
12935 if (nesting_depth == 0)
12936 break;
12937 goto add;
12938 default:
12939 add:
12940 tokens.safe_push (*token);
12941 c_parser_consume_token (parser);
12942 continue;
12943 }
12944 break;
12945 }
12946
12947 /* Make sure nothing tries to read past the end of the tokens. */
12948 c_token eof_token;
12949 memset (&eof_token, 0, sizeof (eof_token));
12950 eof_token.type = CPP_EOF;
12951 tokens.safe_push (eof_token);
12952 tokens.safe_push (eof_token);
12953
12954 tokens_avail = parser->tokens_avail;
12955 gcc_assert (parser->tokens == &parser->tokens_buf[0]);
12956 parser->tokens = tokens.address ();
12957 parser->tokens_avail = tokens.length ();
12958 }
12959
59bc434a 12960 tree t = NULL_TREE;
953ff289 12961
59bc434a
JJ
12962 if (c_parser_next_token_is (parser, CPP_NAME)
12963 && c_parser_peek_token (parser)->id_kind == C_ID_ID)
acf0174b 12964 {
59bc434a 12965 t = lookup_name (c_parser_peek_token (parser)->value);
acf0174b 12966
59bc434a
JJ
12967 if (t == NULL_TREE)
12968 {
12969 undeclared_variable (c_parser_peek_token (parser)->location,
12970 c_parser_peek_token (parser)->value);
12971 t = error_mark_node;
12972 }
12973
12974 c_parser_consume_token (parser);
12975 }
12976 else if (c_parser_next_token_is (parser, CPP_KEYWORD)
12977 && (c_parser_peek_token (parser)->keyword == RID_FUNCTION_NAME
12978 || (c_parser_peek_token (parser)->keyword
12979 == RID_PRETTY_FUNCTION_NAME)
12980 || (c_parser_peek_token (parser)->keyword
12981 == RID_C99_FUNCTION_NAME)))
12982 t = c_parser_predefined_identifier (parser).value;
12983 else
12984 {
12985 if (first)
12986 c_parser_error (parser, "expected identifier");
12987 break;
12988 }
acf0174b
JJ
12989
12990 if (t == error_mark_node)
953ff289
DN
12991 ;
12992 else if (kind != 0)
12993 {
acf0174b
JJ
12994 switch (kind)
12995 {
41dbbb37 12996 case OMP_CLAUSE__CACHE_:
4b1ffdb1
TS
12997 /* The OpenACC cache directive explicitly only allows "array
12998 elements or subarrays". */
41dbbb37
TS
12999 if (c_parser_peek_token (parser)->type != CPP_OPEN_SQUARE)
13000 {
13001 c_parser_error (parser, "expected %<[%>");
13002 t = error_mark_node;
13003 break;
13004 }
d9a6bd32 13005 /* FALLTHROUGH */
acf0174b
JJ
13006 case OMP_CLAUSE_MAP:
13007 case OMP_CLAUSE_FROM:
13008 case OMP_CLAUSE_TO:
519d7496
JB
13009 while (c_parser_next_token_is (parser, CPP_DOT)
13010 || (allow_deref
13011 && c_parser_next_token_is (parser, CPP_DEREF)))
d9a6bd32
JJ
13012 {
13013 location_t op_loc = c_parser_peek_token (parser)->location;
519d7496
JB
13014 if (c_parser_next_token_is (parser, CPP_DEREF))
13015 t = build_simple_mem_ref (t);
d9a6bd32
JJ
13016 c_parser_consume_token (parser);
13017 if (!c_parser_next_token_is (parser, CPP_NAME))
13018 {
13019 c_parser_error (parser, "expected identifier");
13020 t = error_mark_node;
13021 break;
13022 }
6ffd47b7
DM
13023
13024 c_token *comp_tok = c_parser_peek_token (parser);
13025 tree ident = comp_tok->value;
13026 location_t comp_loc = comp_tok->location;
d9a6bd32 13027 c_parser_consume_token (parser);
6ffd47b7 13028 t = build_component_ref (op_loc, t, ident, comp_loc);
d9a6bd32
JJ
13029 }
13030 /* FALLTHROUGH */
acf0174b 13031 case OMP_CLAUSE_DEPEND:
d9a6bd32 13032 case OMP_CLAUSE_REDUCTION:
28567c40
JJ
13033 case OMP_CLAUSE_IN_REDUCTION:
13034 case OMP_CLAUSE_TASK_REDUCTION:
acf0174b
JJ
13035 while (c_parser_next_token_is (parser, CPP_OPEN_SQUARE))
13036 {
13037 tree low_bound = NULL_TREE, length = NULL_TREE;
13038
13039 c_parser_consume_token (parser);
13040 if (!c_parser_next_token_is (parser, CPP_COLON))
d90c0a59 13041 {
9dc5773f
JJ
13042 location_t expr_loc
13043 = c_parser_peek_token (parser)->location;
13044 c_expr expr = c_parser_expression (parser);
13045 expr = convert_lvalue_to_rvalue (expr_loc, expr,
13046 false, true);
13047 low_bound = expr.value;
d90c0a59 13048 }
acf0174b
JJ
13049 if (c_parser_next_token_is (parser, CPP_CLOSE_SQUARE))
13050 length = integer_one_node;
13051 else
13052 {
13053 /* Look for `:'. */
13054 if (!c_parser_require (parser, CPP_COLON,
13055 "expected %<:%>"))
13056 {
13057 t = error_mark_node;
13058 break;
13059 }
28567c40 13060 array_section_p = true;
acf0174b 13061 if (!c_parser_next_token_is (parser, CPP_CLOSE_SQUARE))
d90c0a59 13062 {
9dc5773f
JJ
13063 location_t expr_loc
13064 = c_parser_peek_token (parser)->location;
13065 c_expr expr = c_parser_expression (parser);
13066 expr = convert_lvalue_to_rvalue (expr_loc, expr,
13067 false, true);
13068 length = expr.value;
d90c0a59 13069 }
acf0174b
JJ
13070 }
13071 /* Look for the closing `]'. */
13072 if (!c_parser_require (parser, CPP_CLOSE_SQUARE,
13073 "expected %<]%>"))
13074 {
13075 t = error_mark_node;
13076 break;
13077 }
41dbbb37 13078
acf0174b
JJ
13079 t = tree_cons (low_bound, length, t);
13080 }
28567c40
JJ
13081 if (kind == OMP_CLAUSE_DEPEND
13082 && t != error_mark_node
13083 && parser->tokens_avail != 2)
13084 {
13085 if (array_section_p)
13086 {
13087 error_at (c_parser_peek_token (parser)->location,
13088 "expected %<)%> or %<,%>");
13089 t = error_mark_node;
13090 }
13091 else
13092 {
13093 parser->tokens = tokens.address ();
13094 parser->tokens_avail = tokens.length ();
13095
13096 t = c_parser_expr_no_commas (parser, NULL).value;
13097 if (t != error_mark_node && parser->tokens_avail != 2)
13098 {
13099 error_at (c_parser_peek_token (parser)->location,
13100 "expected %<)%> or %<,%>");
13101 t = error_mark_node;
13102 }
13103 }
13104 }
acf0174b
JJ
13105 break;
13106 default:
13107 break;
13108 }
13109
13110 if (t != error_mark_node)
13111 {
13112 tree u = build_omp_clause (clause_loc, kind);
13113 OMP_CLAUSE_DECL (u) = t;
13114 OMP_CLAUSE_CHAIN (u) = list;
13115 list = u;
13116 }
953ff289
DN
13117 }
13118 else
13119 list = tree_cons (t, NULL_TREE, list);
13120
28567c40
JJ
13121 if (kind == OMP_CLAUSE_DEPEND)
13122 {
13123 parser->tokens = &parser->tokens_buf[0];
13124 parser->tokens_avail = tokens_avail;
13125 }
953ff289
DN
13126 if (c_parser_next_token_is_not (parser, CPP_COMMA))
13127 break;
13128
13129 c_parser_consume_token (parser);
59bc434a 13130 first = false;
953ff289
DN
13131 }
13132
13133 return list;
13134}
13135
13136/* Similarly, but expect leading and trailing parenthesis. This is a very
519d7496
JB
13137 common case for OpenACC and OpenMP clauses. The optional ALLOW_DEREF
13138 argument is true if list items can use the deref (->) operator. */
953ff289
DN
13139
13140static tree
d75d71e0 13141c_parser_omp_var_list_parens (c_parser *parser, enum omp_clause_code kind,
519d7496 13142 tree list, bool allow_deref = false)
953ff289 13143{
c2255bc4
AH
13144 /* The clauses location. */
13145 location_t loc = c_parser_peek_token (parser)->location;
13146
32129a17
DM
13147 matching_parens parens;
13148 if (parens.require_open (parser))
953ff289 13149 {
519d7496 13150 list = c_parser_omp_variable_list (parser, loc, kind, list, allow_deref);
32129a17 13151 parens.skip_until_found_close (parser);
953ff289
DN
13152 }
13153 return list;
13154}
13155
41dbbb37
TS
13156/* OpenACC 2.0:
13157 copy ( variable-list )
13158 copyin ( variable-list )
13159 copyout ( variable-list )
13160 create ( variable-list )
13161 delete ( variable-list )
a6163563
JB
13162 present ( variable-list )
13163
13164 OpenACC 2.6:
519d7496
JB
13165 no_create ( variable-list )
13166 attach ( variable-list )
13167 detach ( variable-list ) */
41dbbb37
TS
13168
13169static tree
13170c_parser_oacc_data_clause (c_parser *parser, pragma_omp_clause c_kind,
13171 tree list)
13172{
13173 enum gomp_map_kind kind;
13174 switch (c_kind)
13175 {
519d7496
JB
13176 case PRAGMA_OACC_CLAUSE_ATTACH:
13177 kind = GOMP_MAP_ATTACH;
13178 break;
41dbbb37 13179 case PRAGMA_OACC_CLAUSE_COPY:
829c6349 13180 kind = GOMP_MAP_TOFROM;
41dbbb37
TS
13181 break;
13182 case PRAGMA_OACC_CLAUSE_COPYIN:
829c6349 13183 kind = GOMP_MAP_TO;
41dbbb37
TS
13184 break;
13185 case PRAGMA_OACC_CLAUSE_COPYOUT:
829c6349 13186 kind = GOMP_MAP_FROM;
41dbbb37
TS
13187 break;
13188 case PRAGMA_OACC_CLAUSE_CREATE:
829c6349 13189 kind = GOMP_MAP_ALLOC;
41dbbb37
TS
13190 break;
13191 case PRAGMA_OACC_CLAUSE_DELETE:
829c6349 13192 kind = GOMP_MAP_RELEASE;
41dbbb37 13193 break;
519d7496
JB
13194 case PRAGMA_OACC_CLAUSE_DETACH:
13195 kind = GOMP_MAP_DETACH;
13196 break;
41dbbb37
TS
13197 case PRAGMA_OACC_CLAUSE_DEVICE:
13198 kind = GOMP_MAP_FORCE_TO;
13199 break;
6e232ba4
JN
13200 case PRAGMA_OACC_CLAUSE_DEVICE_RESIDENT:
13201 kind = GOMP_MAP_DEVICE_RESIDENT;
13202 break;
41dbbb37 13203 case PRAGMA_OACC_CLAUSE_HOST:
41dbbb37
TS
13204 kind = GOMP_MAP_FORCE_FROM;
13205 break;
6e232ba4
JN
13206 case PRAGMA_OACC_CLAUSE_LINK:
13207 kind = GOMP_MAP_LINK;
13208 break;
a6163563
JB
13209 case PRAGMA_OACC_CLAUSE_NO_CREATE:
13210 kind = GOMP_MAP_IF_PRESENT;
13211 break;
41dbbb37
TS
13212 case PRAGMA_OACC_CLAUSE_PRESENT:
13213 kind = GOMP_MAP_FORCE_PRESENT;
13214 break;
41dbbb37
TS
13215 default:
13216 gcc_unreachable ();
13217 }
13218 tree nl, c;
519d7496 13219 nl = c_parser_omp_var_list_parens (parser, OMP_CLAUSE_MAP, list, true);
41dbbb37
TS
13220
13221 for (c = nl; c != list; c = OMP_CLAUSE_CHAIN (c))
13222 OMP_CLAUSE_SET_MAP_KIND (c, kind);
13223
13224 return nl;
13225}
13226
13227/* OpenACC 2.0:
13228 deviceptr ( variable-list ) */
13229
13230static tree
13231c_parser_oacc_data_clause_deviceptr (c_parser *parser, tree list)
13232{
13233 location_t loc = c_parser_peek_token (parser)->location;
13234 tree vars, t;
13235
13236 /* Can't use OMP_CLAUSE_MAP here (that is, can't use the generic
13237 c_parser_oacc_data_clause), as for PRAGMA_OACC_CLAUSE_DEVICEPTR,
13238 variable-list must only allow for pointer variables. */
13239 vars = c_parser_omp_var_list_parens (parser, OMP_CLAUSE_ERROR, NULL);
13240 for (t = vars; t && t; t = TREE_CHAIN (t))
13241 {
13242 tree v = TREE_PURPOSE (t);
13243
13244 /* FIXME diagnostics: Ideally we should keep individual
13245 locations for all the variables in the var list to make the
13246 following errors more precise. Perhaps
13247 c_parser_omp_var_list_parens() should construct a list of
13248 locations to go along with the var list. */
13249
ba539195 13250 if (!VAR_P (v) && TREE_CODE (v) != PARM_DECL)
41dbbb37
TS
13251 error_at (loc, "%qD is not a variable", v);
13252 else if (TREE_TYPE (v) == error_mark_node)
13253 ;
13254 else if (!POINTER_TYPE_P (TREE_TYPE (v)))
13255 error_at (loc, "%qD is not a pointer variable", v);
13256
13257 tree u = build_omp_clause (loc, OMP_CLAUSE_MAP);
13258 OMP_CLAUSE_SET_MAP_KIND (u, GOMP_MAP_FORCE_DEVICEPTR);
13259 OMP_CLAUSE_DECL (u) = v;
13260 OMP_CLAUSE_CHAIN (u) = list;
13261 list = u;
13262 }
13263
13264 return list;
13265}
13266
13267/* OpenACC 2.0, OpenMP 3.0:
a68ab351
JJ
13268 collapse ( constant-expression ) */
13269
13270static tree
13271c_parser_omp_clause_collapse (c_parser *parser, tree list)
13272{
13273 tree c, num = error_mark_node;
13274 HOST_WIDE_INT n;
13275 location_t loc;
13276
13277 check_no_duplicate_clause (list, OMP_CLAUSE_COLLAPSE, "collapse");
02889d23 13278 check_no_duplicate_clause (list, OMP_CLAUSE_TILE, "tile");
a68ab351
JJ
13279
13280 loc = c_parser_peek_token (parser)->location;
32129a17
DM
13281 matching_parens parens;
13282 if (parens.require_open (parser))
a68ab351
JJ
13283 {
13284 num = c_parser_expr_no_commas (parser, NULL).value;
32129a17 13285 parens.skip_until_found_close (parser);
a68ab351
JJ
13286 }
13287 if (num == error_mark_node)
13288 return list;
acf0174b
JJ
13289 mark_exp_read (num);
13290 num = c_fully_fold (num, false, NULL);
a68ab351 13291 if (!INTEGRAL_TYPE_P (TREE_TYPE (num))
9541ffee 13292 || !tree_fits_shwi_p (num)
9439e9a1 13293 || (n = tree_to_shwi (num)) <= 0
a68ab351
JJ
13294 || (int) n != n)
13295 {
3ba09659
AH
13296 error_at (loc,
13297 "collapse argument needs positive constant integer expression");
a68ab351
JJ
13298 return list;
13299 }
c2255bc4 13300 c = build_omp_clause (loc, OMP_CLAUSE_COLLAPSE);
a68ab351
JJ
13301 OMP_CLAUSE_COLLAPSE_EXPR (c) = num;
13302 OMP_CLAUSE_CHAIN (c) = list;
13303 return c;
13304}
13305
953ff289
DN
13306/* OpenMP 2.5:
13307 copyin ( variable-list ) */
13308
13309static tree
13310c_parser_omp_clause_copyin (c_parser *parser, tree list)
13311{
13312 return c_parser_omp_var_list_parens (parser, OMP_CLAUSE_COPYIN, list);
13313}
13314
13315/* OpenMP 2.5:
13316 copyprivate ( variable-list ) */
13317
13318static tree
13319c_parser_omp_clause_copyprivate (c_parser *parser, tree list)
13320{
13321 return c_parser_omp_var_list_parens (parser, OMP_CLAUSE_COPYPRIVATE, list);
13322}
13323
13324/* OpenMP 2.5:
7fd549d2 13325 default ( none | shared )
7a5e4956 13326
7fd549d2
TS
13327 OpenACC:
13328 default ( none | present ) */
953ff289
DN
13329
13330static tree
7a5e4956 13331c_parser_omp_clause_default (c_parser *parser, tree list, bool is_oacc)
953ff289
DN
13332{
13333 enum omp_clause_default_kind kind = OMP_CLAUSE_DEFAULT_UNSPECIFIED;
c2255bc4 13334 location_t loc = c_parser_peek_token (parser)->location;
953ff289
DN
13335 tree c;
13336
32129a17
DM
13337 matching_parens parens;
13338 if (!parens.require_open (parser))
953ff289
DN
13339 return list;
13340 if (c_parser_next_token_is (parser, CPP_NAME))
13341 {
13342 const char *p = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
13343
13344 switch (p[0])
13345 {
13346 case 'n':
13347 if (strcmp ("none", p) != 0)
13348 goto invalid_kind;
13349 kind = OMP_CLAUSE_DEFAULT_NONE;
13350 break;
13351
7fd549d2
TS
13352 case 'p':
13353 if (strcmp ("present", p) != 0 || !is_oacc)
13354 goto invalid_kind;
13355 kind = OMP_CLAUSE_DEFAULT_PRESENT;
13356 break;
13357
953ff289 13358 case 's':
7a5e4956 13359 if (strcmp ("shared", p) != 0 || is_oacc)
953ff289
DN
13360 goto invalid_kind;
13361 kind = OMP_CLAUSE_DEFAULT_SHARED;
13362 break;
13363
13364 default:
13365 goto invalid_kind;
13366 }
13367
13368 c_parser_consume_token (parser);
13369 }
13370 else
13371 {
13372 invalid_kind:
7a5e4956 13373 if (is_oacc)
7fd549d2 13374 c_parser_error (parser, "expected %<none%> or %<present%>");
7a5e4956
CP
13375 else
13376 c_parser_error (parser, "expected %<none%> or %<shared%>");
953ff289 13377 }
32129a17 13378 parens.skip_until_found_close (parser);
953ff289
DN
13379
13380 if (kind == OMP_CLAUSE_DEFAULT_UNSPECIFIED)
13381 return list;
13382
13383 check_no_duplicate_clause (list, OMP_CLAUSE_DEFAULT, "default");
c2255bc4 13384 c = build_omp_clause (loc, OMP_CLAUSE_DEFAULT);
953ff289
DN
13385 OMP_CLAUSE_CHAIN (c) = list;
13386 OMP_CLAUSE_DEFAULT_KIND (c) = kind;
13387
13388 return c;
13389}
13390
13391/* OpenMP 2.5:
13392 firstprivate ( variable-list ) */
13393
13394static tree
13395c_parser_omp_clause_firstprivate (c_parser *parser, tree list)
13396{
13397 return c_parser_omp_var_list_parens (parser, OMP_CLAUSE_FIRSTPRIVATE, list);
13398}
13399
20906c66
JJ
13400/* OpenMP 3.1:
13401 final ( expression ) */
13402
13403static tree
13404c_parser_omp_clause_final (c_parser *parser, tree list)
13405{
13406 location_t loc = c_parser_peek_token (parser)->location;
13407 if (c_parser_next_token_is (parser, CPP_OPEN_PAREN))
13408 {
81a227c6
JJ
13409 matching_parens parens;
13410 tree t, c;
13411 if (!parens.require_open (parser))
13412 t = error_mark_node;
13413 else
13414 {
13415 location_t eloc = c_parser_peek_token (parser)->location;
13416 c_expr expr = c_parser_expr_no_commas (parser, NULL);
13417 t = convert_lvalue_to_rvalue (eloc, expr, true, true).value;
13418 t = c_objc_common_truthvalue_conversion (eloc, t);
13419 t = c_fully_fold (t, false, NULL);
13420 parens.skip_until_found_close (parser);
13421 }
20906c66
JJ
13422
13423 check_no_duplicate_clause (list, OMP_CLAUSE_FINAL, "final");
13424
13425 c = build_omp_clause (loc, OMP_CLAUSE_FINAL);
13426 OMP_CLAUSE_FINAL_EXPR (c) = t;
13427 OMP_CLAUSE_CHAIN (c) = list;
13428 list = c;
13429 }
13430 else
13431 c_parser_error (parser, "expected %<(%>");
13432
13433 return list;
13434}
13435
41dbbb37 13436/* OpenACC, OpenMP 2.5:
d9a6bd32
JJ
13437 if ( expression )
13438
13439 OpenMP 4.5:
13440 if ( directive-name-modifier : expression )
13441
13442 directive-name-modifier:
13443 parallel | task | taskloop | target data | target | target update
28567c40
JJ
13444 | target enter data | target exit data
13445
13446 OpenMP 5.0:
13447 directive-name-modifier:
13448 ... | simd | cancel */
953ff289
DN
13449
13450static tree
d9a6bd32 13451c_parser_omp_clause_if (c_parser *parser, tree list, bool is_omp)
953ff289 13452{
d9a6bd32
JJ
13453 location_t location = c_parser_peek_token (parser)->location;
13454 enum tree_code if_modifier = ERROR_MARK;
953ff289 13455
32129a17
DM
13456 matching_parens parens;
13457 if (!parens.require_open (parser))
d9a6bd32 13458 return list;
953ff289 13459
d9a6bd32
JJ
13460 if (is_omp && c_parser_next_token_is (parser, CPP_NAME))
13461 {
13462 const char *p = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
13463 int n = 2;
28567c40
JJ
13464 if (strcmp (p, "cancel") == 0)
13465 if_modifier = VOID_CST;
13466 else if (strcmp (p, "parallel") == 0)
d9a6bd32 13467 if_modifier = OMP_PARALLEL;
28567c40
JJ
13468 else if (strcmp (p, "simd") == 0)
13469 if_modifier = OMP_SIMD;
d9a6bd32
JJ
13470 else if (strcmp (p, "task") == 0)
13471 if_modifier = OMP_TASK;
13472 else if (strcmp (p, "taskloop") == 0)
13473 if_modifier = OMP_TASKLOOP;
13474 else if (strcmp (p, "target") == 0)
13475 {
13476 if_modifier = OMP_TARGET;
13477 if (c_parser_peek_2nd_token (parser)->type == CPP_NAME)
13478 {
13479 p = IDENTIFIER_POINTER (c_parser_peek_2nd_token (parser)->value);
13480 if (strcmp ("data", p) == 0)
13481 if_modifier = OMP_TARGET_DATA;
13482 else if (strcmp ("update", p) == 0)
13483 if_modifier = OMP_TARGET_UPDATE;
13484 else if (strcmp ("enter", p) == 0)
13485 if_modifier = OMP_TARGET_ENTER_DATA;
13486 else if (strcmp ("exit", p) == 0)
13487 if_modifier = OMP_TARGET_EXIT_DATA;
13488 if (if_modifier != OMP_TARGET)
13489 {
13490 n = 3;
13491 c_parser_consume_token (parser);
13492 }
13493 else
13494 {
13495 location_t loc = c_parser_peek_2nd_token (parser)->location;
13496 error_at (loc, "expected %<data%>, %<update%>, %<enter%> "
13497 "or %<exit%>");
13498 if_modifier = ERROR_MARK;
13499 }
13500 if (if_modifier == OMP_TARGET_ENTER_DATA
13501 || if_modifier == OMP_TARGET_EXIT_DATA)
13502 {
13503 if (c_parser_peek_2nd_token (parser)->type == CPP_NAME)
13504 {
13505 p = IDENTIFIER_POINTER
13506 (c_parser_peek_2nd_token (parser)->value);
13507 if (strcmp ("data", p) == 0)
13508 n = 4;
13509 }
13510 if (n == 4)
13511 c_parser_consume_token (parser);
13512 else
13513 {
13514 location_t loc
13515 = c_parser_peek_2nd_token (parser)->location;
13516 error_at (loc, "expected %<data%>");
13517 if_modifier = ERROR_MARK;
13518 }
13519 }
13520 }
13521 }
13522 if (if_modifier != ERROR_MARK)
13523 {
13524 if (c_parser_peek_2nd_token (parser)->type == CPP_COLON)
13525 {
13526 c_parser_consume_token (parser);
13527 c_parser_consume_token (parser);
13528 }
13529 else
13530 {
13531 if (n > 2)
13532 {
13533 location_t loc = c_parser_peek_2nd_token (parser)->location;
13534 error_at (loc, "expected %<:%>");
13535 }
13536 if_modifier = ERROR_MARK;
13537 }
13538 }
953ff289 13539 }
953ff289 13540
81a227c6
JJ
13541 location_t loc = c_parser_peek_token (parser)->location;
13542 c_expr expr = c_parser_expr_no_commas (parser, NULL);
13543 expr = convert_lvalue_to_rvalue (loc, expr, true, true);
13544 tree t = c_objc_common_truthvalue_conversion (loc, expr.value), c;
13545 t = c_fully_fold (t, false, NULL);
32129a17 13546 parens.skip_until_found_close (parser);
d9a6bd32
JJ
13547
13548 for (c = list; c ; c = OMP_CLAUSE_CHAIN (c))
13549 if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_IF)
13550 {
13551 if (if_modifier != ERROR_MARK
13552 && OMP_CLAUSE_IF_MODIFIER (c) == if_modifier)
13553 {
13554 const char *p = NULL;
13555 switch (if_modifier)
13556 {
28567c40 13557 case VOID_CST: p = "cancel"; break;
d9a6bd32 13558 case OMP_PARALLEL: p = "parallel"; break;
28567c40 13559 case OMP_SIMD: p = "simd"; break;
d9a6bd32
JJ
13560 case OMP_TASK: p = "task"; break;
13561 case OMP_TASKLOOP: p = "taskloop"; break;
13562 case OMP_TARGET_DATA: p = "target data"; break;
13563 case OMP_TARGET: p = "target"; break;
13564 case OMP_TARGET_UPDATE: p = "target update"; break;
bb522e2e
JJ
13565 case OMP_TARGET_ENTER_DATA: p = "target enter data"; break;
13566 case OMP_TARGET_EXIT_DATA: p = "target exit data"; break;
d9a6bd32
JJ
13567 default: gcc_unreachable ();
13568 }
13569 error_at (location, "too many %<if%> clauses with %qs modifier",
13570 p);
13571 return list;
13572 }
13573 else if (OMP_CLAUSE_IF_MODIFIER (c) == if_modifier)
13574 {
13575 if (!is_omp)
13576 error_at (location, "too many %<if%> clauses");
13577 else
13578 error_at (location, "too many %<if%> clauses without modifier");
13579 return list;
13580 }
13581 else if (if_modifier == ERROR_MARK
13582 || OMP_CLAUSE_IF_MODIFIER (c) == ERROR_MARK)
13583 {
13584 error_at (location, "if any %<if%> clause has modifier, then all "
13585 "%<if%> clauses have to use modifier");
13586 return list;
13587 }
13588 }
13589
13590 c = build_omp_clause (location, OMP_CLAUSE_IF);
13591 OMP_CLAUSE_IF_MODIFIER (c) = if_modifier;
13592 OMP_CLAUSE_IF_EXPR (c) = t;
13593 OMP_CLAUSE_CHAIN (c) = list;
13594 return c;
953ff289
DN
13595}
13596
13597/* OpenMP 2.5:
28567c40
JJ
13598 lastprivate ( variable-list )
13599
13600 OpenMP 5.0:
13601 lastprivate ( [ lastprivate-modifier : ] variable-list ) */
953ff289
DN
13602
13603static tree
13604c_parser_omp_clause_lastprivate (c_parser *parser, tree list)
13605{
28567c40
JJ
13606 /* The clauses location. */
13607 location_t loc = c_parser_peek_token (parser)->location;
13608
13609 if (c_parser_require (parser, CPP_OPEN_PAREN, "expected %<(%>"))
13610 {
13611 bool conditional = false;
13612 if (c_parser_next_token_is (parser, CPP_NAME)
13613 && c_parser_peek_2nd_token (parser)->type == CPP_COLON)
13614 {
13615 const char *p
13616 = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
13617 if (strcmp (p, "conditional") == 0)
13618 {
13619 conditional = true;
13620 c_parser_consume_token (parser);
13621 c_parser_consume_token (parser);
13622 }
13623 }
13624 tree nlist = c_parser_omp_variable_list (parser, loc,
13625 OMP_CLAUSE_LASTPRIVATE, list);
13626 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN, "expected %<)%>");
13627 if (conditional)
13628 for (tree c = nlist; c != list; c = OMP_CLAUSE_CHAIN (c))
13629 OMP_CLAUSE_LASTPRIVATE_CONDITIONAL (c) = 1;
13630 return nlist;
13631 }
13632 return list;
953ff289
DN
13633}
13634
20906c66
JJ
13635/* OpenMP 3.1:
13636 mergeable */
13637
13638static tree
13639c_parser_omp_clause_mergeable (c_parser *parser ATTRIBUTE_UNUSED, tree list)
13640{
13641 tree c;
13642
13643 /* FIXME: Should we allow duplicates? */
13644 check_no_duplicate_clause (list, OMP_CLAUSE_MERGEABLE, "mergeable");
13645
13646 c = build_omp_clause (c_parser_peek_token (parser)->location,
13647 OMP_CLAUSE_MERGEABLE);
13648 OMP_CLAUSE_CHAIN (c) = list;
13649
13650 return c;
13651}
13652
953ff289
DN
13653/* OpenMP 2.5:
13654 nowait */
13655
13656static tree
13657c_parser_omp_clause_nowait (c_parser *parser ATTRIBUTE_UNUSED, tree list)
13658{
13659 tree c;
c2255bc4 13660 location_t loc = c_parser_peek_token (parser)->location;
953ff289
DN
13661
13662 check_no_duplicate_clause (list, OMP_CLAUSE_NOWAIT, "nowait");
13663
c2255bc4 13664 c = build_omp_clause (loc, OMP_CLAUSE_NOWAIT);
953ff289
DN
13665 OMP_CLAUSE_CHAIN (c) = list;
13666 return c;
13667}
13668
13669/* OpenMP 2.5:
13670 num_threads ( expression ) */
13671
13672static tree
13673c_parser_omp_clause_num_threads (c_parser *parser, tree list)
13674{
c2255bc4 13675 location_t num_threads_loc = c_parser_peek_token (parser)->location;
32129a17
DM
13676 matching_parens parens;
13677 if (parens.require_open (parser))
953ff289 13678 {
c7412148 13679 location_t expr_loc = c_parser_peek_token (parser)->location;
81a227c6 13680 c_expr expr = c_parser_expr_no_commas (parser, NULL);
9dc5773f
JJ
13681 expr = convert_lvalue_to_rvalue (expr_loc, expr, false, true);
13682 tree c, t = expr.value;
928c19bb 13683 t = c_fully_fold (t, false, NULL);
953ff289 13684
32129a17 13685 parens.skip_until_found_close (parser);
953ff289
DN
13686
13687 if (!INTEGRAL_TYPE_P (TREE_TYPE (t)))
13688 {
13689 c_parser_error (parser, "expected integer expression");
13690 return list;
13691 }
13692
13693 /* Attempt to statically determine when the number isn't positive. */
db3927fb 13694 c = fold_build2_loc (expr_loc, LE_EXPR, boolean_type_node, t,
953ff289 13695 build_int_cst (TREE_TYPE (t), 0));
21ba0cea 13696 protected_set_expr_location (c, expr_loc);
953ff289
DN
13697 if (c == boolean_true_node)
13698 {
3ba09659
AH
13699 warning_at (expr_loc, 0,
13700 "%<num_threads%> value must be positive");
953ff289
DN
13701 t = integer_one_node;
13702 }
13703
13704 check_no_duplicate_clause (list, OMP_CLAUSE_NUM_THREADS, "num_threads");
13705
c2255bc4 13706 c = build_omp_clause (num_threads_loc, OMP_CLAUSE_NUM_THREADS);
953ff289
DN
13707 OMP_CLAUSE_NUM_THREADS_EXPR (c) = t;
13708 OMP_CLAUSE_CHAIN (c) = list;
13709 list = c;
13710 }
13711
13712 return list;
13713}
13714
d9a6bd32
JJ
13715/* OpenMP 4.5:
13716 num_tasks ( expression ) */
13717
13718static tree
13719c_parser_omp_clause_num_tasks (c_parser *parser, tree list)
13720{
13721 location_t num_tasks_loc = c_parser_peek_token (parser)->location;
32129a17
DM
13722 matching_parens parens;
13723 if (parens.require_open (parser))
d9a6bd32
JJ
13724 {
13725 location_t expr_loc = c_parser_peek_token (parser)->location;
81a227c6 13726 c_expr expr = c_parser_expr_no_commas (parser, NULL);
9dc5773f
JJ
13727 expr = convert_lvalue_to_rvalue (expr_loc, expr, false, true);
13728 tree c, t = expr.value;
d9a6bd32
JJ
13729 t = c_fully_fold (t, false, NULL);
13730
32129a17 13731 parens.skip_until_found_close (parser);
d9a6bd32
JJ
13732
13733 if (!INTEGRAL_TYPE_P (TREE_TYPE (t)))
13734 {
13735 c_parser_error (parser, "expected integer expression");
13736 return list;
13737 }
13738
13739 /* Attempt to statically determine when the number isn't positive. */
13740 c = fold_build2_loc (expr_loc, LE_EXPR, boolean_type_node, t,
13741 build_int_cst (TREE_TYPE (t), 0));
13742 if (CAN_HAVE_LOCATION_P (c))
13743 SET_EXPR_LOCATION (c, expr_loc);
13744 if (c == boolean_true_node)
13745 {
13746 warning_at (expr_loc, 0, "%<num_tasks%> value must be positive");
13747 t = integer_one_node;
13748 }
13749
13750 check_no_duplicate_clause (list, OMP_CLAUSE_NUM_TASKS, "num_tasks");
13751
13752 c = build_omp_clause (num_tasks_loc, OMP_CLAUSE_NUM_TASKS);
13753 OMP_CLAUSE_NUM_TASKS_EXPR (c) = t;
13754 OMP_CLAUSE_CHAIN (c) = list;
13755 list = c;
13756 }
13757
13758 return list;
13759}
13760
13761/* OpenMP 4.5:
13762 grainsize ( expression ) */
13763
13764static tree
13765c_parser_omp_clause_grainsize (c_parser *parser, tree list)
13766{
13767 location_t grainsize_loc = c_parser_peek_token (parser)->location;
32129a17
DM
13768 matching_parens parens;
13769 if (parens.require_open (parser))
d9a6bd32
JJ
13770 {
13771 location_t expr_loc = c_parser_peek_token (parser)->location;
81a227c6 13772 c_expr expr = c_parser_expr_no_commas (parser, NULL);
9dc5773f
JJ
13773 expr = convert_lvalue_to_rvalue (expr_loc, expr, false, true);
13774 tree c, t = expr.value;
d9a6bd32
JJ
13775 t = c_fully_fold (t, false, NULL);
13776
32129a17 13777 parens.skip_until_found_close (parser);
d9a6bd32
JJ
13778
13779 if (!INTEGRAL_TYPE_P (TREE_TYPE (t)))
13780 {
13781 c_parser_error (parser, "expected integer expression");
13782 return list;
13783 }
13784
13785 /* Attempt to statically determine when the number isn't positive. */
13786 c = fold_build2_loc (expr_loc, LE_EXPR, boolean_type_node, t,
13787 build_int_cst (TREE_TYPE (t), 0));
13788 if (CAN_HAVE_LOCATION_P (c))
13789 SET_EXPR_LOCATION (c, expr_loc);
13790 if (c == boolean_true_node)
13791 {
13792 warning_at (expr_loc, 0, "%<grainsize%> value must be positive");
13793 t = integer_one_node;
13794 }
13795
13796 check_no_duplicate_clause (list, OMP_CLAUSE_GRAINSIZE, "grainsize");
13797
13798 c = build_omp_clause (grainsize_loc, OMP_CLAUSE_GRAINSIZE);
13799 OMP_CLAUSE_GRAINSIZE_EXPR (c) = t;
13800 OMP_CLAUSE_CHAIN (c) = list;
13801 list = c;
13802 }
13803
13804 return list;
13805}
13806
13807/* OpenMP 4.5:
13808 priority ( expression ) */
13809
13810static tree
13811c_parser_omp_clause_priority (c_parser *parser, tree list)
13812{
13813 location_t priority_loc = c_parser_peek_token (parser)->location;
32129a17
DM
13814 matching_parens parens;
13815 if (parens.require_open (parser))
d9a6bd32
JJ
13816 {
13817 location_t expr_loc = c_parser_peek_token (parser)->location;
81a227c6 13818 c_expr expr = c_parser_expr_no_commas (parser, NULL);
9dc5773f
JJ
13819 expr = convert_lvalue_to_rvalue (expr_loc, expr, false, true);
13820 tree c, t = expr.value;
d9a6bd32
JJ
13821 t = c_fully_fold (t, false, NULL);
13822
32129a17 13823 parens.skip_until_found_close (parser);
d9a6bd32
JJ
13824
13825 if (!INTEGRAL_TYPE_P (TREE_TYPE (t)))
13826 {
13827 c_parser_error (parser, "expected integer expression");
13828 return list;
13829 }
13830
13831 /* Attempt to statically determine when the number isn't
13832 non-negative. */
13833 c = fold_build2_loc (expr_loc, LT_EXPR, boolean_type_node, t,
13834 build_int_cst (TREE_TYPE (t), 0));
13835 if (CAN_HAVE_LOCATION_P (c))
13836 SET_EXPR_LOCATION (c, expr_loc);
13837 if (c == boolean_true_node)
13838 {
13839 warning_at (expr_loc, 0, "%<priority%> value must be non-negative");
13840 t = integer_one_node;
13841 }
13842
13843 check_no_duplicate_clause (list, OMP_CLAUSE_PRIORITY, "priority");
13844
13845 c = build_omp_clause (priority_loc, OMP_CLAUSE_PRIORITY);
13846 OMP_CLAUSE_PRIORITY_EXPR (c) = t;
13847 OMP_CLAUSE_CHAIN (c) = list;
13848 list = c;
13849 }
13850
13851 return list;
13852}
13853
13854/* OpenMP 4.5:
13855 hint ( expression ) */
13856
13857static tree
13858c_parser_omp_clause_hint (c_parser *parser, tree list)
13859{
13860 location_t hint_loc = c_parser_peek_token (parser)->location;
32129a17
DM
13861 matching_parens parens;
13862 if (parens.require_open (parser))
d9a6bd32 13863 {
9dc5773f 13864 location_t expr_loc = c_parser_peek_token (parser)->location;
81a227c6 13865 c_expr expr = c_parser_expr_no_commas (parser, NULL);
9dc5773f
JJ
13866 expr = convert_lvalue_to_rvalue (expr_loc, expr, false, true);
13867 tree c, t = expr.value;
d9a6bd32
JJ
13868 t = c_fully_fold (t, false, NULL);
13869
32129a17 13870 parens.skip_until_found_close (parser);
d9a6bd32 13871
28567c40
JJ
13872 if (!INTEGRAL_TYPE_P (TREE_TYPE (t))
13873 || TREE_CODE (t) != INTEGER_CST)
d9a6bd32 13874 {
28567c40 13875 c_parser_error (parser, "expected constant integer expression");
d9a6bd32
JJ
13876 return list;
13877 }
13878
13879 check_no_duplicate_clause (list, OMP_CLAUSE_HINT, "hint");
13880
13881 c = build_omp_clause (hint_loc, OMP_CLAUSE_HINT);
13882 OMP_CLAUSE_HINT_EXPR (c) = t;
13883 OMP_CLAUSE_CHAIN (c) = list;
13884 list = c;
13885 }
13886
13887 return list;
13888}
13889
13890/* OpenMP 4.5:
28567c40
JJ
13891 defaultmap ( tofrom : scalar )
13892
13893 OpenMP 5.0:
13894 defaultmap ( implicit-behavior [ : variable-category ] ) */
d9a6bd32
JJ
13895
13896static tree
13897c_parser_omp_clause_defaultmap (c_parser *parser, tree list)
13898{
13899 location_t loc = c_parser_peek_token (parser)->location;
13900 tree c;
13901 const char *p;
28567c40
JJ
13902 enum omp_clause_defaultmap_kind behavior = OMP_CLAUSE_DEFAULTMAP_DEFAULT;
13903 enum omp_clause_defaultmap_kind category
13904 = OMP_CLAUSE_DEFAULTMAP_CATEGORY_UNSPECIFIED;
d9a6bd32 13905
32129a17
DM
13906 matching_parens parens;
13907 if (!parens.require_open (parser))
d9a6bd32 13908 return list;
28567c40
JJ
13909 if (c_parser_next_token_is_keyword (parser, RID_DEFAULT))
13910 p = "default";
13911 else if (!c_parser_next_token_is (parser, CPP_NAME))
13912 {
13913 invalid_behavior:
13914 c_parser_error (parser, "expected %<alloc%>, %<to%>, %<from%>, "
13915 "%<tofrom%>, %<firstprivate%>, %<none%> "
13916 "or %<default%>");
d9a6bd32
JJ
13917 goto out_err;
13918 }
28567c40
JJ
13919 else
13920 p = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
13921
13922 switch (p[0])
d9a6bd32 13923 {
28567c40
JJ
13924 case 'a':
13925 if (strcmp ("alloc", p) == 0)
13926 behavior = OMP_CLAUSE_DEFAULTMAP_ALLOC;
13927 else
13928 goto invalid_behavior;
13929 break;
13930
13931 case 'd':
13932 if (strcmp ("default", p) == 0)
13933 behavior = OMP_CLAUSE_DEFAULTMAP_DEFAULT;
13934 else
13935 goto invalid_behavior;
13936 break;
13937
13938 case 'f':
13939 if (strcmp ("firstprivate", p) == 0)
13940 behavior = OMP_CLAUSE_DEFAULTMAP_FIRSTPRIVATE;
13941 else if (strcmp ("from", p) == 0)
13942 behavior = OMP_CLAUSE_DEFAULTMAP_FROM;
13943 else
13944 goto invalid_behavior;
13945 break;
13946
13947 case 'n':
13948 if (strcmp ("none", p) == 0)
13949 behavior = OMP_CLAUSE_DEFAULTMAP_NONE;
13950 else
13951 goto invalid_behavior;
13952 break;
13953
13954 case 't':
13955 if (strcmp ("tofrom", p) == 0)
13956 behavior = OMP_CLAUSE_DEFAULTMAP_TOFROM;
13957 else if (strcmp ("to", p) == 0)
13958 behavior = OMP_CLAUSE_DEFAULTMAP_TO;
13959 else
13960 goto invalid_behavior;
13961 break;
13962
13963 default:
13964 goto invalid_behavior;
d9a6bd32
JJ
13965 }
13966 c_parser_consume_token (parser);
28567c40
JJ
13967
13968 if (!c_parser_next_token_is (parser, CPP_CLOSE_PAREN))
d9a6bd32 13969 {
28567c40
JJ
13970 if (!c_parser_require (parser, CPP_COLON, "expected %<:%>"))
13971 goto out_err;
13972 if (!c_parser_next_token_is (parser, CPP_NAME))
13973 {
13974 invalid_category:
13975 c_parser_error (parser, "expected %<scalar%>, %<aggregate%> or "
13976 "%<pointer%>");
13977 goto out_err;
13978 }
13979 p = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
13980 switch (p[0])
13981 {
13982 case 'a':
13983 if (strcmp ("aggregate", p) == 0)
13984 category = OMP_CLAUSE_DEFAULTMAP_CATEGORY_AGGREGATE;
13985 else
13986 goto invalid_category;
13987 break;
13988
13989 case 'p':
13990 if (strcmp ("pointer", p) == 0)
13991 category = OMP_CLAUSE_DEFAULTMAP_CATEGORY_POINTER;
13992 else
13993 goto invalid_category;
13994 break;
13995
13996 case 's':
13997 if (strcmp ("scalar", p) == 0)
13998 category = OMP_CLAUSE_DEFAULTMAP_CATEGORY_SCALAR;
13999 else
14000 goto invalid_category;
14001 break;
14002
14003 default:
14004 goto invalid_category;
14005 }
14006
14007 c_parser_consume_token (parser);
d9a6bd32 14008 }
32129a17 14009 parens.skip_until_found_close (parser);
28567c40
JJ
14010
14011 for (c = list; c ; c = OMP_CLAUSE_CHAIN (c))
14012 if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEFAULTMAP
14013 && (category == OMP_CLAUSE_DEFAULTMAP_CATEGORY_UNSPECIFIED
14014 || OMP_CLAUSE_DEFAULTMAP_CATEGORY (c) == category
14015 || (OMP_CLAUSE_DEFAULTMAP_CATEGORY (c)
14016 == OMP_CLAUSE_DEFAULTMAP_CATEGORY_UNSPECIFIED)))
14017 {
14018 enum omp_clause_defaultmap_kind cat = category;
14019 location_t loc = OMP_CLAUSE_LOCATION (c);
14020 if (cat == OMP_CLAUSE_DEFAULTMAP_CATEGORY_UNSPECIFIED)
14021 cat = OMP_CLAUSE_DEFAULTMAP_CATEGORY (c);
14022 p = NULL;
14023 switch (cat)
14024 {
14025 case OMP_CLAUSE_DEFAULTMAP_CATEGORY_UNSPECIFIED:
14026 p = NULL;
14027 break;
14028 case OMP_CLAUSE_DEFAULTMAP_CATEGORY_AGGREGATE:
14029 p = "aggregate";
14030 break;
14031 case OMP_CLAUSE_DEFAULTMAP_CATEGORY_POINTER:
14032 p = "pointer";
14033 break;
14034 case OMP_CLAUSE_DEFAULTMAP_CATEGORY_SCALAR:
14035 p = "scalar";
14036 break;
14037 default:
14038 gcc_unreachable ();
14039 }
14040 if (p)
14041 error_at (loc, "too many %<defaultmap%> clauses with %qs category",
14042 p);
14043 else
14044 error_at (loc, "too many %<defaultmap%> clauses with unspecified "
14045 "category");
14046 break;
14047 }
14048
d9a6bd32 14049 c = build_omp_clause (loc, OMP_CLAUSE_DEFAULTMAP);
28567c40 14050 OMP_CLAUSE_DEFAULTMAP_SET_KIND (c, behavior, category);
d9a6bd32
JJ
14051 OMP_CLAUSE_CHAIN (c) = list;
14052 return c;
14053
14054 out_err:
32129a17 14055 parens.skip_until_found_close (parser);
d9a6bd32
JJ
14056 return list;
14057}
14058
c7b48c8a
TS
14059/* OpenACC 2.0:
14060 use_device ( variable-list )
14061
14062 OpenMP 4.5:
d9a6bd32
JJ
14063 use_device_ptr ( variable-list ) */
14064
14065static tree
14066c_parser_omp_clause_use_device_ptr (c_parser *parser, tree list)
14067{
14068 return c_parser_omp_var_list_parens (parser, OMP_CLAUSE_USE_DEVICE_PTR,
14069 list);
14070}
14071
398e3feb
JJ
14072/* OpenMP 5.0:
14073 use_device_addr ( variable-list ) */
14074
14075static tree
14076c_parser_omp_clause_use_device_addr (c_parser *parser, tree list)
14077{
14078 return c_parser_omp_var_list_parens (parser, OMP_CLAUSE_USE_DEVICE_ADDR,
14079 list);
14080}
14081
d9a6bd32
JJ
14082/* OpenMP 4.5:
14083 is_device_ptr ( variable-list ) */
14084
14085static tree
14086c_parser_omp_clause_is_device_ptr (c_parser *parser, tree list)
14087{
14088 return c_parser_omp_var_list_parens (parser, OMP_CLAUSE_IS_DEVICE_PTR, list);
14089}
14090
41dbbb37 14091/* OpenACC:
1e47f02b
TS
14092 num_gangs ( expression )
14093 num_workers ( expression )
14094 vector_length ( expression ) */
41dbbb37
TS
14095
14096static tree
1e47f02b
TS
14097c_parser_oacc_single_int_clause (c_parser *parser, omp_clause_code code,
14098 tree list)
41dbbb37 14099{
1e47f02b 14100 location_t loc = c_parser_peek_token (parser)->location;
41dbbb37 14101
32129a17
DM
14102 matching_parens parens;
14103 if (!parens.require_open (parser))
1e47f02b 14104 return list;
41dbbb37 14105
1e47f02b
TS
14106 location_t expr_loc = c_parser_peek_token (parser)->location;
14107 c_expr expr = c_parser_expression (parser);
14108 expr = convert_lvalue_to_rvalue (expr_loc, expr, false, true);
14109 tree c, t = expr.value;
14110 t = c_fully_fold (t, false, NULL);
41dbbb37 14111
32129a17 14112 parens.skip_until_found_close (parser);
41dbbb37 14113
1e47f02b
TS
14114 if (t == error_mark_node)
14115 return list;
14116 else if (!INTEGRAL_TYPE_P (TREE_TYPE (t)))
14117 {
14118 error_at (expr_loc, "%qs expression must be integral",
14119 omp_clause_code_name[code]);
14120 return list;
14121 }
41dbbb37 14122
1e47f02b
TS
14123 /* Attempt to statically determine when the number isn't positive. */
14124 c = fold_build2_loc (expr_loc, LE_EXPR, boolean_type_node, t,
14125 build_int_cst (TREE_TYPE (t), 0));
14126 protected_set_expr_location (c, expr_loc);
14127 if (c == boolean_true_node)
14128 {
14129 warning_at (expr_loc, 0,
14130 "%qs value must be positive",
14131 omp_clause_code_name[code]);
14132 t = integer_one_node;
41dbbb37
TS
14133 }
14134
1e47f02b
TS
14135 check_no_duplicate_clause (list, code, omp_clause_code_name[code]);
14136
14137 c = build_omp_clause (loc, code);
14138 OMP_CLAUSE_OPERAND (c, 0) = t;
14139 OMP_CLAUSE_CHAIN (c) = list;
14140 return c;
41dbbb37
TS
14141}
14142
765dd391
CP
14143/* OpenACC:
14144
14145 gang [( gang-arg-list )]
14146 worker [( [num:] int-expr )]
14147 vector [( [length:] int-expr )]
14148
14149 where gang-arg is one of:
14150
14151 [num:] int-expr
14152 static: size-expr
14153
14154 and size-expr may be:
14155
14156 *
14157 int-expr
14158*/
14159
14160static tree
2263c9f2
TS
14161c_parser_oacc_shape_clause (c_parser *parser, location_t loc,
14162 omp_clause_code kind,
765dd391
CP
14163 const char *str, tree list)
14164{
14165 const char *id = "num";
14166 tree ops[2] = { NULL_TREE, NULL_TREE }, c;
765dd391
CP
14167
14168 if (kind == OMP_CLAUSE_VECTOR)
14169 id = "length";
14170
14171 if (c_parser_next_token_is (parser, CPP_OPEN_PAREN))
14172 {
14173 c_parser_consume_token (parser);
14174
14175 do
14176 {
14177 c_token *next = c_parser_peek_token (parser);
14178 int idx = 0;
14179
14180 /* Gang static argument. */
14181 if (kind == OMP_CLAUSE_GANG
14182 && c_parser_next_token_is_keyword (parser, RID_STATIC))
14183 {
14184 c_parser_consume_token (parser);
14185
14186 if (!c_parser_require (parser, CPP_COLON, "expected %<:%>"))
14187 goto cleanup_error;
14188
14189 idx = 1;
14190 if (ops[idx] != NULL_TREE)
14191 {
14192 c_parser_error (parser, "too many %<static%> arguments");
14193 goto cleanup_error;
14194 }
14195
14196 /* Check for the '*' argument. */
7a5e4956
CP
14197 if (c_parser_next_token_is (parser, CPP_MULT)
14198 && (c_parser_peek_2nd_token (parser)->type == CPP_COMMA
14199 || c_parser_peek_2nd_token (parser)->type
14200 == CPP_CLOSE_PAREN))
765dd391
CP
14201 {
14202 c_parser_consume_token (parser);
14203 ops[idx] = integer_minus_one_node;
14204
14205 if (c_parser_next_token_is (parser, CPP_COMMA))
14206 {
14207 c_parser_consume_token (parser);
14208 continue;
14209 }
14210 else
14211 break;
14212 }
14213 }
14214 /* Worker num: argument and vector length: arguments. */
14215 else if (c_parser_next_token_is (parser, CPP_NAME)
14216 && strcmp (id, IDENTIFIER_POINTER (next->value)) == 0
14217 && c_parser_peek_2nd_token (parser)->type == CPP_COLON)
14218 {
14219 c_parser_consume_token (parser); /* id */
14220 c_parser_consume_token (parser); /* ':' */
14221 }
14222
14223 /* Now collect the actual argument. */
14224 if (ops[idx] != NULL_TREE)
14225 {
14226 c_parser_error (parser, "unexpected argument");
14227 goto cleanup_error;
14228 }
14229
14230 location_t expr_loc = c_parser_peek_token (parser)->location;
9dc5773f
JJ
14231 c_expr cexpr = c_parser_expr_no_commas (parser, NULL);
14232 cexpr = convert_lvalue_to_rvalue (expr_loc, cexpr, false, true);
14233 tree expr = cexpr.value;
765dd391
CP
14234 if (expr == error_mark_node)
14235 goto cleanup_error;
14236
765dd391
CP
14237 expr = c_fully_fold (expr, false, NULL);
14238
14239 /* Attempt to statically determine when the number isn't a
14240 positive integer. */
14241
14242 if (!INTEGRAL_TYPE_P (TREE_TYPE (expr)))
14243 {
14244 c_parser_error (parser, "expected integer expression");
14245 return list;
14246 }
14247
14248 tree c = fold_build2_loc (expr_loc, LE_EXPR, boolean_type_node, expr,
14249 build_int_cst (TREE_TYPE (expr), 0));
14250 if (c == boolean_true_node)
14251 {
14252 warning_at (loc, 0,
2f6f187a 14253 "%qs value must be positive", str);
765dd391
CP
14254 expr = integer_one_node;
14255 }
14256
14257 ops[idx] = expr;
14258
14259 if (kind == OMP_CLAUSE_GANG
14260 && c_parser_next_token_is (parser, CPP_COMMA))
14261 {
14262 c_parser_consume_token (parser);
14263 continue;
14264 }
14265 break;
14266 }
14267 while (1);
14268
14269 if (!c_parser_require (parser, CPP_CLOSE_PAREN, "expected %<)%>"))
14270 goto cleanup_error;
14271 }
14272
14273 check_no_duplicate_clause (list, kind, str);
14274
14275 c = build_omp_clause (loc, kind);
14276
14277 if (ops[1])
14278 OMP_CLAUSE_OPERAND (c, 1) = ops[1];
14279
14280 OMP_CLAUSE_OPERAND (c, 0) = ops[0];
14281 OMP_CLAUSE_CHAIN (c) = list;
14282
14283 return c;
14284
14285 cleanup_error:
14286 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN, 0);
14287 return list;
14288}
14289
829c6349 14290/* OpenACC 2.5:
765dd391 14291 auto
829c6349 14292 finalize
765dd391
CP
14293 independent
14294 nohost
14295 seq */
14296
14297static tree
2263c9f2 14298c_parser_oacc_simple_clause (location_t loc, enum omp_clause_code code,
765dd391
CP
14299 tree list)
14300{
14301 check_no_duplicate_clause (list, code, omp_clause_code_name[code]);
14302
2263c9f2 14303 tree c = build_omp_clause (loc, code);
765dd391
CP
14304 OMP_CLAUSE_CHAIN (c) = list;
14305
14306 return c;
14307}
14308
41dbbb37
TS
14309/* OpenACC:
14310 async [( int-expr )] */
14311
14312static tree
14313c_parser_oacc_clause_async (c_parser *parser, tree list)
14314{
14315 tree c, t;
14316 location_t loc = c_parser_peek_token (parser)->location;
14317
14318 t = build_int_cst (integer_type_node, GOMP_ASYNC_NOVAL);
14319
14320 if (c_parser_peek_token (parser)->type == CPP_OPEN_PAREN)
14321 {
14322 c_parser_consume_token (parser);
14323
14324 t = c_parser_expression (parser).value;
14325 if (!INTEGRAL_TYPE_P (TREE_TYPE (t)))
14326 c_parser_error (parser, "expected integer expression");
14327 else if (t == error_mark_node
14328 || !c_parser_require (parser, CPP_CLOSE_PAREN, "expected %<)%>"))
14329 return list;
14330 }
14331 else
14332 t = c_fully_fold (t, false, NULL);
14333
14334 check_no_duplicate_clause (list, OMP_CLAUSE_ASYNC, "async");
14335
14336 c = build_omp_clause (loc, OMP_CLAUSE_ASYNC);
14337 OMP_CLAUSE_ASYNC_EXPR (c) = t;
14338 OMP_CLAUSE_CHAIN (c) = list;
14339 list = c;
14340
14341 return list;
14342}
14343
7a5e4956
CP
14344/* OpenACC 2.0:
14345 tile ( size-expr-list ) */
14346
14347static tree
14348c_parser_oacc_clause_tile (c_parser *parser, tree list)
14349{
14350 tree c, expr = error_mark_node;
02889d23 14351 location_t loc;
7a5e4956
CP
14352 tree tile = NULL_TREE;
14353
14354 check_no_duplicate_clause (list, OMP_CLAUSE_TILE, "tile");
02889d23 14355 check_no_duplicate_clause (list, OMP_CLAUSE_COLLAPSE, "collapse");
7a5e4956
CP
14356
14357 loc = c_parser_peek_token (parser)->location;
14358 if (!c_parser_require (parser, CPP_OPEN_PAREN, "expected %<(%>"))
14359 return list;
14360
14361 do
14362 {
02889d23
CLT
14363 if (tile && !c_parser_require (parser, CPP_COMMA, "expected %<,%>"))
14364 return list;
14365
7a5e4956
CP
14366 if (c_parser_next_token_is (parser, CPP_MULT)
14367 && (c_parser_peek_2nd_token (parser)->type == CPP_COMMA
14368 || c_parser_peek_2nd_token (parser)->type == CPP_CLOSE_PAREN))
14369 {
14370 c_parser_consume_token (parser);
02889d23 14371 expr = integer_zero_node;
7a5e4956
CP
14372 }
14373 else
14374 {
02889d23 14375 location_t expr_loc = c_parser_peek_token (parser)->location;
9dc5773f
JJ
14376 c_expr cexpr = c_parser_expr_no_commas (parser, NULL);
14377 cexpr = convert_lvalue_to_rvalue (expr_loc, cexpr, false, true);
14378 expr = cexpr.value;
7a5e4956
CP
14379
14380 if (expr == error_mark_node)
14381 {
14382 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN,
14383 "expected %<)%>");
14384 return list;
14385 }
14386
7a5e4956
CP
14387 expr = c_fully_fold (expr, false, NULL);
14388
02889d23
CLT
14389 if (!INTEGRAL_TYPE_P (TREE_TYPE (expr))
14390 || !tree_fits_shwi_p (expr)
14391 || tree_to_shwi (expr) <= 0)
7a5e4956 14392 {
02889d23
CLT
14393 error_at (expr_loc, "%<tile%> argument needs positive"
14394 " integral constant");
14395 expr = integer_zero_node;
7a5e4956
CP
14396 }
14397 }
14398
14399 tile = tree_cons (NULL_TREE, expr, tile);
7a5e4956
CP
14400 }
14401 while (c_parser_next_token_is_not (parser, CPP_CLOSE_PAREN));
14402
14403 /* Consume the trailing ')'. */
14404 c_parser_consume_token (parser);
14405
14406 c = build_omp_clause (loc, OMP_CLAUSE_TILE);
14407 tile = nreverse (tile);
14408 OMP_CLAUSE_TILE_LIST (c) = tile;
14409 OMP_CLAUSE_CHAIN (c) = list;
14410 return c;
14411}
14412
41dbbb37 14413/* OpenACC:
19695f4d 14414 wait [( int-expr-list )] */
41dbbb37
TS
14415
14416static tree
14417c_parser_oacc_clause_wait (c_parser *parser, tree list)
14418{
14419 location_t clause_loc = c_parser_peek_token (parser)->location;
14420
14421 if (c_parser_peek_token (parser)->type == CPP_OPEN_PAREN)
14422 list = c_parser_oacc_wait_list (parser, clause_loc, list);
19695f4d
CLT
14423 else
14424 {
14425 tree c = build_omp_clause (clause_loc, OMP_CLAUSE_WAIT);
14426
14427 OMP_CLAUSE_DECL (c) = build_int_cst (integer_type_node, GOMP_ASYNC_NOVAL);
14428 OMP_CLAUSE_CHAIN (c) = list;
14429 list = c;
14430 }
41dbbb37
TS
14431
14432 return list;
14433}
14434
1fdd6f04
JJ
14435
14436/* OpenMP 5.0:
14437 order ( concurrent ) */
14438
14439static tree
14440c_parser_omp_clause_order (c_parser *parser, tree list)
14441{
14442 location_t loc = c_parser_peek_token (parser)->location;
14443 tree c;
14444 const char *p;
14445
14446 matching_parens parens;
14447 if (!parens.require_open (parser))
14448 return list;
14449 if (!c_parser_next_token_is (parser, CPP_NAME))
14450 {
14451 c_parser_error (parser, "expected %<concurrent%>");
14452 goto out_err;
14453 }
14454 p = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
14455 if (strcmp (p, "concurrent") != 0)
14456 {
14457 c_parser_error (parser, "expected %<concurrent%>");
14458 goto out_err;
14459 }
14460 c_parser_consume_token (parser);
14461 parens.skip_until_found_close (parser);
14462 /* check_no_duplicate_clause (list, OMP_CLAUSE_ORDER, "order"); */
14463 c = build_omp_clause (loc, OMP_CLAUSE_ORDER);
14464 OMP_CLAUSE_CHAIN (c) = list;
14465 return c;
14466
14467 out_err:
14468 parens.skip_until_found_close (parser);
14469 return list;
14470}
14471
14472
554a530f
JJ
14473/* OpenMP 5.0:
14474 bind ( teams | parallel | thread ) */
14475
14476static tree
14477c_parser_omp_clause_bind (c_parser *parser, tree list)
14478{
14479 location_t loc = c_parser_peek_token (parser)->location;
14480 tree c;
14481 const char *p;
14482 enum omp_clause_bind_kind kind = OMP_CLAUSE_BIND_THREAD;
14483
14484 matching_parens parens;
14485 if (!parens.require_open (parser))
14486 return list;
14487 if (!c_parser_next_token_is (parser, CPP_NAME))
14488 {
14489 invalid:
14490 c_parser_error (parser,
14491 "expected %<teams%>, %<parallel%> or %<thread%>");
14492 parens.skip_until_found_close (parser);
14493 return list;
14494 }
14495 p = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
14496 if (strcmp (p, "teams") == 0)
14497 kind = OMP_CLAUSE_BIND_TEAMS;
14498 else if (strcmp (p, "parallel") == 0)
14499 kind = OMP_CLAUSE_BIND_PARALLEL;
14500 else if (strcmp (p, "thread") != 0)
14501 goto invalid;
14502 c_parser_consume_token (parser);
14503 parens.skip_until_found_close (parser);
14504 /* check_no_duplicate_clause (list, OMP_CLAUSE_BIND, "bind"); */
14505 c = build_omp_clause (loc, OMP_CLAUSE_BIND);
14506 OMP_CLAUSE_BIND_KIND (c) = kind;
14507 OMP_CLAUSE_CHAIN (c) = list;
14508 return c;
14509}
14510
14511
953ff289 14512/* OpenMP 2.5:
d9a6bd32
JJ
14513 ordered
14514
14515 OpenMP 4.5:
14516 ordered ( constant-expression ) */
953ff289
DN
14517
14518static tree
c2255bc4 14519c_parser_omp_clause_ordered (c_parser *parser, tree list)
953ff289 14520{
953ff289
DN
14521 check_no_duplicate_clause (list, OMP_CLAUSE_ORDERED, "ordered");
14522
d9a6bd32
JJ
14523 tree c, num = NULL_TREE;
14524 HOST_WIDE_INT n;
14525 location_t loc = c_parser_peek_token (parser)->location;
14526 if (c_parser_next_token_is (parser, CPP_OPEN_PAREN))
14527 {
32129a17
DM
14528 matching_parens parens;
14529 parens.consume_open (parser);
d9a6bd32 14530 num = c_parser_expr_no_commas (parser, NULL).value;
32129a17 14531 parens.skip_until_found_close (parser);
d9a6bd32
JJ
14532 }
14533 if (num == error_mark_node)
14534 return list;
14535 if (num)
14536 {
14537 mark_exp_read (num);
14538 num = c_fully_fold (num, false, NULL);
14539 if (!INTEGRAL_TYPE_P (TREE_TYPE (num))
14540 || !tree_fits_shwi_p (num)
14541 || (n = tree_to_shwi (num)) <= 0
14542 || (int) n != n)
14543 {
14544 error_at (loc, "ordered argument needs positive "
14545 "constant integer expression");
14546 return list;
14547 }
14548 }
14549 c = build_omp_clause (loc, OMP_CLAUSE_ORDERED);
14550 OMP_CLAUSE_ORDERED_EXPR (c) = num;
953ff289
DN
14551 OMP_CLAUSE_CHAIN (c) = list;
14552 return c;
14553}
14554
14555/* OpenMP 2.5:
14556 private ( variable-list ) */
14557
14558static tree
14559c_parser_omp_clause_private (c_parser *parser, tree list)
14560{
14561 return c_parser_omp_var_list_parens (parser, OMP_CLAUSE_PRIVATE, list);
14562}
14563
14564/* OpenMP 2.5:
14565 reduction ( reduction-operator : variable-list )
14566
14567 reduction-operator:
20906c66 14568 One of: + * - & ^ | && ||
acf0174b 14569
20906c66
JJ
14570 OpenMP 3.1:
14571
14572 reduction-operator:
acf0174b
JJ
14573 One of: + * - & ^ | && || max min
14574
14575 OpenMP 4.0:
14576
14577 reduction-operator:
14578 One of: + * - & ^ | && ||
28567c40
JJ
14579 identifier
14580
14581 OpenMP 5.0:
14582 reduction ( reduction-modifier, reduction-operator : variable-list )
14583 in_reduction ( reduction-operator : variable-list )
14584 task_reduction ( reduction-operator : variable-list ) */
953ff289
DN
14585
14586static tree
28567c40
JJ
14587c_parser_omp_clause_reduction (c_parser *parser, enum omp_clause_code kind,
14588 bool is_omp, tree list)
953ff289 14589{
c2255bc4 14590 location_t clause_loc = c_parser_peek_token (parser)->location;
32129a17
DM
14591 matching_parens parens;
14592 if (parens.require_open (parser))
953ff289 14593 {
28567c40
JJ
14594 bool task = false;
14595 bool inscan = false;
acf0174b
JJ
14596 enum tree_code code = ERROR_MARK;
14597 tree reduc_id = NULL_TREE;
953ff289 14598
28567c40
JJ
14599 if (kind == OMP_CLAUSE_REDUCTION && is_omp)
14600 {
14601 if (c_parser_next_token_is_keyword (parser, RID_DEFAULT)
14602 && c_parser_peek_2nd_token (parser)->type == CPP_COMMA)
14603 {
14604 c_parser_consume_token (parser);
14605 c_parser_consume_token (parser);
14606 }
14607 else if (c_parser_next_token_is (parser, CPP_NAME)
14608 && c_parser_peek_2nd_token (parser)->type == CPP_COMMA)
14609 {
14610 const char *p
14611 = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
14612 if (strcmp (p, "task") == 0)
14613 task = true;
14614 else if (strcmp (p, "inscan") == 0)
bf38f7e9 14615 inscan = true;
28567c40
JJ
14616 if (task || inscan)
14617 {
14618 c_parser_consume_token (parser);
14619 c_parser_consume_token (parser);
14620 }
14621 }
14622 }
14623
953ff289
DN
14624 switch (c_parser_peek_token (parser)->type)
14625 {
14626 case CPP_PLUS:
14627 code = PLUS_EXPR;
14628 break;
14629 case CPP_MULT:
14630 code = MULT_EXPR;
14631 break;
14632 case CPP_MINUS:
14633 code = MINUS_EXPR;
14634 break;
14635 case CPP_AND:
14636 code = BIT_AND_EXPR;
14637 break;
14638 case CPP_XOR:
14639 code = BIT_XOR_EXPR;
14640 break;
14641 case CPP_OR:
14642 code = BIT_IOR_EXPR;
14643 break;
14644 case CPP_AND_AND:
14645 code = TRUTH_ANDIF_EXPR;
14646 break;
14647 case CPP_OR_OR:
14648 code = TRUTH_ORIF_EXPR;
14649 break;
20906c66
JJ
14650 case CPP_NAME:
14651 {
14652 const char *p
14653 = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
14654 if (strcmp (p, "min") == 0)
14655 {
14656 code = MIN_EXPR;
14657 break;
14658 }
14659 if (strcmp (p, "max") == 0)
14660 {
14661 code = MAX_EXPR;
14662 break;
14663 }
acf0174b
JJ
14664 reduc_id = c_parser_peek_token (parser)->value;
14665 break;
20906c66 14666 }
953ff289
DN
14667 default:
14668 c_parser_error (parser,
14669 "expected %<+%>, %<*%>, %<-%>, %<&%>, "
79c9b7a8 14670 "%<^%>, %<|%>, %<&&%>, %<||%> or identifier");
953ff289
DN
14671 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN, 0);
14672 return list;
14673 }
14674 c_parser_consume_token (parser);
acf0174b 14675 reduc_id = c_omp_reduction_id (code, reduc_id);
953ff289
DN
14676 if (c_parser_require (parser, CPP_COLON, "expected %<:%>"))
14677 {
14678 tree nl, c;
14679
28567c40 14680 nl = c_parser_omp_variable_list (parser, clause_loc, kind, list);
953ff289 14681 for (c = nl; c != list; c = OMP_CLAUSE_CHAIN (c))
acf0174b 14682 {
d9a6bd32
JJ
14683 tree d = OMP_CLAUSE_DECL (c), type;
14684 if (TREE_CODE (d) != TREE_LIST)
14685 type = TREE_TYPE (d);
14686 else
14687 {
14688 int cnt = 0;
14689 tree t;
14690 for (t = d; TREE_CODE (t) == TREE_LIST; t = TREE_CHAIN (t))
14691 cnt++;
14692 type = TREE_TYPE (t);
14693 while (cnt > 0)
14694 {
14695 if (TREE_CODE (type) != POINTER_TYPE
14696 && TREE_CODE (type) != ARRAY_TYPE)
14697 break;
14698 type = TREE_TYPE (type);
14699 cnt--;
14700 }
14701 }
14702 while (TREE_CODE (type) == ARRAY_TYPE)
14703 type = TREE_TYPE (type);
acf0174b 14704 OMP_CLAUSE_REDUCTION_CODE (c) = code;
28567c40
JJ
14705 if (task)
14706 OMP_CLAUSE_REDUCTION_TASK (c) = 1;
14707 else if (inscan)
14708 OMP_CLAUSE_REDUCTION_INSCAN (c) = 1;
acf0174b
JJ
14709 if (code == ERROR_MARK
14710 || !(INTEGRAL_TYPE_P (type)
14711 || TREE_CODE (type) == REAL_TYPE
14712 || TREE_CODE (type) == COMPLEX_TYPE))
14713 OMP_CLAUSE_REDUCTION_PLACEHOLDER (c)
14714 = c_omp_reduction_lookup (reduc_id,
14715 TYPE_MAIN_VARIANT (type));
14716 }
953ff289
DN
14717
14718 list = nl;
14719 }
32129a17 14720 parens.skip_until_found_close (parser);
953ff289
DN
14721 }
14722 return list;
14723}
14724
14725/* OpenMP 2.5:
14726 schedule ( schedule-kind )
14727 schedule ( schedule-kind , expression )
14728
14729 schedule-kind:
a68ab351 14730 static | dynamic | guided | runtime | auto
d9a6bd32
JJ
14731
14732 OpenMP 4.5:
14733 schedule ( schedule-modifier : schedule-kind )
e01d41e5 14734 schedule ( schedule-modifier [ , schedule-modifier ] : schedule-kind , expression )
d9a6bd32
JJ
14735
14736 schedule-modifier:
e01d41e5
JJ
14737 simd
14738 monotonic
14739 nonmonotonic */
953ff289
DN
14740
14741static tree
14742c_parser_omp_clause_schedule (c_parser *parser, tree list)
14743{
14744 tree c, t;
c2255bc4 14745 location_t loc = c_parser_peek_token (parser)->location;
e01d41e5 14746 int modifiers = 0, nmodifiers = 0;
953ff289 14747
32129a17
DM
14748 matching_parens parens;
14749 if (!parens.require_open (parser))
953ff289
DN
14750 return list;
14751
c2255bc4 14752 c = build_omp_clause (loc, OMP_CLAUSE_SCHEDULE);
953ff289 14753
e01d41e5 14754 while (c_parser_next_token_is (parser, CPP_NAME))
d9a6bd32
JJ
14755 {
14756 tree kind = c_parser_peek_token (parser)->value;
14757 const char *p = IDENTIFIER_POINTER (kind);
e01d41e5
JJ
14758 if (strcmp ("simd", p) == 0)
14759 OMP_CLAUSE_SCHEDULE_SIMD (c) = 1;
14760 else if (strcmp ("monotonic", p) == 0)
14761 modifiers |= OMP_CLAUSE_SCHEDULE_MONOTONIC;
14762 else if (strcmp ("nonmonotonic", p) == 0)
14763 modifiers |= OMP_CLAUSE_SCHEDULE_NONMONOTONIC;
14764 else
14765 break;
14766 c_parser_consume_token (parser);
14767 if (nmodifiers++ == 0
14768 && c_parser_next_token_is (parser, CPP_COMMA))
14769 c_parser_consume_token (parser);
14770 else
d9a6bd32 14771 {
e01d41e5
JJ
14772 c_parser_require (parser, CPP_COLON, "expected %<:%>");
14773 break;
d9a6bd32
JJ
14774 }
14775 }
14776
e01d41e5
JJ
14777 if ((modifiers & (OMP_CLAUSE_SCHEDULE_MONOTONIC
14778 | OMP_CLAUSE_SCHEDULE_NONMONOTONIC))
14779 == (OMP_CLAUSE_SCHEDULE_MONOTONIC
14780 | OMP_CLAUSE_SCHEDULE_NONMONOTONIC))
14781 {
14782 error_at (loc, "both %<monotonic%> and %<nonmonotonic%> modifiers "
14783 "specified");
14784 modifiers = 0;
14785 }
14786
953ff289
DN
14787 if (c_parser_next_token_is (parser, CPP_NAME))
14788 {
14789 tree kind = c_parser_peek_token (parser)->value;
14790 const char *p = IDENTIFIER_POINTER (kind);
14791
14792 switch (p[0])
14793 {
14794 case 'd':
14795 if (strcmp ("dynamic", p) != 0)
14796 goto invalid_kind;
14797 OMP_CLAUSE_SCHEDULE_KIND (c) = OMP_CLAUSE_SCHEDULE_DYNAMIC;
14798 break;
14799
14800 case 'g':
14801 if (strcmp ("guided", p) != 0)
14802 goto invalid_kind;
14803 OMP_CLAUSE_SCHEDULE_KIND (c) = OMP_CLAUSE_SCHEDULE_GUIDED;
14804 break;
14805
14806 case 'r':
14807 if (strcmp ("runtime", p) != 0)
14808 goto invalid_kind;
14809 OMP_CLAUSE_SCHEDULE_KIND (c) = OMP_CLAUSE_SCHEDULE_RUNTIME;
14810 break;
14811
14812 default:
14813 goto invalid_kind;
14814 }
14815 }
14816 else if (c_parser_next_token_is_keyword (parser, RID_STATIC))
14817 OMP_CLAUSE_SCHEDULE_KIND (c) = OMP_CLAUSE_SCHEDULE_STATIC;
a68ab351
JJ
14818 else if (c_parser_next_token_is_keyword (parser, RID_AUTO))
14819 OMP_CLAUSE_SCHEDULE_KIND (c) = OMP_CLAUSE_SCHEDULE_AUTO;
953ff289
DN
14820 else
14821 goto invalid_kind;
14822
14823 c_parser_consume_token (parser);
14824 if (c_parser_next_token_is (parser, CPP_COMMA))
14825 {
c7412148 14826 location_t here;
953ff289
DN
14827 c_parser_consume_token (parser);
14828
c7412148 14829 here = c_parser_peek_token (parser)->location;
9dc5773f
JJ
14830 c_expr expr = c_parser_expr_no_commas (parser, NULL);
14831 expr = convert_lvalue_to_rvalue (here, expr, false, true);
14832 t = expr.value;
928c19bb 14833 t = c_fully_fold (t, false, NULL);
953ff289
DN
14834
14835 if (OMP_CLAUSE_SCHEDULE_KIND (c) == OMP_CLAUSE_SCHEDULE_RUNTIME)
3ba09659
AH
14836 error_at (here, "schedule %<runtime%> does not take "
14837 "a %<chunk_size%> parameter");
a68ab351 14838 else if (OMP_CLAUSE_SCHEDULE_KIND (c) == OMP_CLAUSE_SCHEDULE_AUTO)
3ba09659
AH
14839 error_at (here,
14840 "schedule %<auto%> does not take "
14841 "a %<chunk_size%> parameter");
953ff289 14842 else if (TREE_CODE (TREE_TYPE (t)) == INTEGER_TYPE)
7211a097
JJ
14843 {
14844 /* Attempt to statically determine when the number isn't
14845 positive. */
14846 tree s = fold_build2_loc (loc, LE_EXPR, boolean_type_node, t,
14847 build_int_cst (TREE_TYPE (t), 0));
14848 protected_set_expr_location (s, loc);
14849 if (s == boolean_true_node)
14850 {
14851 warning_at (loc, 0,
14852 "chunk size value must be positive");
14853 t = integer_one_node;
14854 }
14855 OMP_CLAUSE_SCHEDULE_CHUNK_EXPR (c) = t;
14856 }
953ff289
DN
14857 else
14858 c_parser_error (parser, "expected integer expression");
14859
32129a17 14860 parens.skip_until_found_close (parser);
953ff289
DN
14861 }
14862 else
14863 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN,
14864 "expected %<,%> or %<)%>");
14865
e01d41e5
JJ
14866 OMP_CLAUSE_SCHEDULE_KIND (c)
14867 = (enum omp_clause_schedule_kind)
14868 (OMP_CLAUSE_SCHEDULE_KIND (c) | modifiers);
14869
953ff289
DN
14870 check_no_duplicate_clause (list, OMP_CLAUSE_SCHEDULE, "schedule");
14871 OMP_CLAUSE_CHAIN (c) = list;
14872 return c;
14873
14874 invalid_kind:
14875 c_parser_error (parser, "invalid schedule kind");
14876 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN, 0);
14877 return list;
14878}
14879
14880/* OpenMP 2.5:
14881 shared ( variable-list ) */
14882
14883static tree
14884c_parser_omp_clause_shared (c_parser *parser, tree list)
14885{
14886 return c_parser_omp_var_list_parens (parser, OMP_CLAUSE_SHARED, list);
14887}
14888
a68ab351
JJ
14889/* OpenMP 3.0:
14890 untied */
14891
14892static tree
14893c_parser_omp_clause_untied (c_parser *parser ATTRIBUTE_UNUSED, tree list)
14894{
14895 tree c;
14896
14897 /* FIXME: Should we allow duplicates? */
14898 check_no_duplicate_clause (list, OMP_CLAUSE_UNTIED, "untied");
14899
c2255bc4
AH
14900 c = build_omp_clause (c_parser_peek_token (parser)->location,
14901 OMP_CLAUSE_UNTIED);
a68ab351 14902 OMP_CLAUSE_CHAIN (c) = list;
c2255bc4 14903
a68ab351
JJ
14904 return c;
14905}
14906
41dbbb37
TS
14907/* OpenMP 4.0:
14908 inbranch
14909 notinbranch */
14910
14911static tree
14912c_parser_omp_clause_branch (c_parser *parser ATTRIBUTE_UNUSED,
14913 enum omp_clause_code code, tree list)
14914{
14915 check_no_duplicate_clause (list, code, omp_clause_code_name[code]);
14916
14917 tree c = build_omp_clause (c_parser_peek_token (parser)->location, code);
14918 OMP_CLAUSE_CHAIN (c) = list;
14919
14920 return c;
14921}
14922
14923/* OpenMP 4.0:
14924 parallel
14925 for
14926 sections
14927 taskgroup */
14928
14929static tree
14930c_parser_omp_clause_cancelkind (c_parser *parser ATTRIBUTE_UNUSED,
14931 enum omp_clause_code code, tree list)
14932{
14933 tree c = build_omp_clause (c_parser_peek_token (parser)->location, code);
14934 OMP_CLAUSE_CHAIN (c) = list;
acf0174b
JJ
14935
14936 return c;
14937}
14938
d9a6bd32
JJ
14939/* OpenMP 4.5:
14940 nogroup */
14941
14942static tree
14943c_parser_omp_clause_nogroup (c_parser *parser ATTRIBUTE_UNUSED, tree list)
14944{
14945 check_no_duplicate_clause (list, OMP_CLAUSE_NOGROUP, "nogroup");
14946 tree c = build_omp_clause (c_parser_peek_token (parser)->location,
14947 OMP_CLAUSE_NOGROUP);
14948 OMP_CLAUSE_CHAIN (c) = list;
14949 return c;
14950}
14951
14952/* OpenMP 4.5:
14953 simd
14954 threads */
14955
14956static tree
14957c_parser_omp_clause_orderedkind (c_parser *parser ATTRIBUTE_UNUSED,
14958 enum omp_clause_code code, tree list)
14959{
14960 check_no_duplicate_clause (list, code, omp_clause_code_name[code]);
14961 tree c = build_omp_clause (c_parser_peek_token (parser)->location, code);
14962 OMP_CLAUSE_CHAIN (c) = list;
14963 return c;
14964}
14965
acf0174b
JJ
14966/* OpenMP 4.0:
14967 num_teams ( expression ) */
14968
14969static tree
14970c_parser_omp_clause_num_teams (c_parser *parser, tree list)
14971{
14972 location_t num_teams_loc = c_parser_peek_token (parser)->location;
32129a17
DM
14973 matching_parens parens;
14974 if (parens.require_open (parser))
acf0174b
JJ
14975 {
14976 location_t expr_loc = c_parser_peek_token (parser)->location;
81a227c6 14977 c_expr expr = c_parser_expr_no_commas (parser, NULL);
9dc5773f
JJ
14978 expr = convert_lvalue_to_rvalue (expr_loc, expr, false, true);
14979 tree c, t = expr.value;
acf0174b
JJ
14980 t = c_fully_fold (t, false, NULL);
14981
32129a17 14982 parens.skip_until_found_close (parser);
acf0174b
JJ
14983
14984 if (!INTEGRAL_TYPE_P (TREE_TYPE (t)))
953ff289 14985 {
acf0174b
JJ
14986 c_parser_error (parser, "expected integer expression");
14987 return list;
953ff289
DN
14988 }
14989
acf0174b
JJ
14990 /* Attempt to statically determine when the number isn't positive. */
14991 c = fold_build2_loc (expr_loc, LE_EXPR, boolean_type_node, t,
14992 build_int_cst (TREE_TYPE (t), 0));
21ba0cea 14993 protected_set_expr_location (c, expr_loc);
acf0174b 14994 if (c == boolean_true_node)
953ff289 14995 {
acf0174b
JJ
14996 warning_at (expr_loc, 0, "%<num_teams%> value must be positive");
14997 t = integer_one_node;
953ff289 14998 }
953ff289 14999
acf0174b 15000 check_no_duplicate_clause (list, OMP_CLAUSE_NUM_TEAMS, "num_teams");
953ff289 15001
acf0174b
JJ
15002 c = build_omp_clause (num_teams_loc, OMP_CLAUSE_NUM_TEAMS);
15003 OMP_CLAUSE_NUM_TEAMS_EXPR (c) = t;
15004 OMP_CLAUSE_CHAIN (c) = list;
15005 list = c;
15006 }
953ff289 15007
acf0174b
JJ
15008 return list;
15009}
953ff289 15010
acf0174b
JJ
15011/* OpenMP 4.0:
15012 thread_limit ( expression ) */
953ff289
DN
15013
15014static tree
acf0174b 15015c_parser_omp_clause_thread_limit (c_parser *parser, tree list)
953ff289 15016{
68c81f24 15017 location_t num_thread_limit_loc = c_parser_peek_token (parser)->location;
32129a17
DM
15018 matching_parens parens;
15019 if (parens.require_open (parser))
acf0174b
JJ
15020 {
15021 location_t expr_loc = c_parser_peek_token (parser)->location;
81a227c6 15022 c_expr expr = c_parser_expr_no_commas (parser, NULL);
9dc5773f
JJ
15023 expr = convert_lvalue_to_rvalue (expr_loc, expr, false, true);
15024 tree c, t = expr.value;
acf0174b 15025 t = c_fully_fold (t, false, NULL);
953ff289 15026
32129a17 15027 parens.skip_until_found_close (parser);
953ff289 15028
acf0174b
JJ
15029 if (!INTEGRAL_TYPE_P (TREE_TYPE (t)))
15030 {
15031 c_parser_error (parser, "expected integer expression");
15032 return list;
15033 }
c2255bc4 15034
acf0174b
JJ
15035 /* Attempt to statically determine when the number isn't positive. */
15036 c = fold_build2_loc (expr_loc, LE_EXPR, boolean_type_node, t,
15037 build_int_cst (TREE_TYPE (t), 0));
21ba0cea 15038 protected_set_expr_location (c, expr_loc);
acf0174b
JJ
15039 if (c == boolean_true_node)
15040 {
15041 warning_at (expr_loc, 0, "%<thread_limit%> value must be positive");
15042 t = integer_one_node;
15043 }
20906c66 15044
acf0174b
JJ
15045 check_no_duplicate_clause (list, OMP_CLAUSE_THREAD_LIMIT,
15046 "thread_limit");
20906c66 15047
68c81f24 15048 c = build_omp_clause (num_thread_limit_loc, OMP_CLAUSE_THREAD_LIMIT);
acf0174b
JJ
15049 OMP_CLAUSE_THREAD_LIMIT_EXPR (c) = t;
15050 OMP_CLAUSE_CHAIN (c) = list;
15051 list = c;
15052 }
20906c66 15053
acf0174b
JJ
15054 return list;
15055}
20906c66 15056
acf0174b
JJ
15057/* OpenMP 4.0:
15058 aligned ( variable-list )
15059 aligned ( variable-list : constant-expression ) */
20906c66 15060
acf0174b
JJ
15061static tree
15062c_parser_omp_clause_aligned (c_parser *parser, tree list)
15063{
15064 location_t clause_loc = c_parser_peek_token (parser)->location;
15065 tree nl, c;
20906c66 15066
32129a17
DM
15067 matching_parens parens;
15068 if (!parens.require_open (parser))
acf0174b 15069 return list;
20906c66 15070
acf0174b
JJ
15071 nl = c_parser_omp_variable_list (parser, clause_loc,
15072 OMP_CLAUSE_ALIGNED, list);
20906c66 15073
acf0174b
JJ
15074 if (c_parser_next_token_is (parser, CPP_COLON))
15075 {
15076 c_parser_consume_token (parser);
9dc5773f
JJ
15077 location_t expr_loc = c_parser_peek_token (parser)->location;
15078 c_expr expr = c_parser_expr_no_commas (parser, NULL);
15079 expr = convert_lvalue_to_rvalue (expr_loc, expr, false, true);
15080 tree alignment = expr.value;
acf0174b 15081 alignment = c_fully_fold (alignment, false, NULL);
fce5e5e3
JJ
15082 if (TREE_CODE (alignment) != INTEGER_CST
15083 || !INTEGRAL_TYPE_P (TREE_TYPE (alignment))
15084 || tree_int_cst_sgn (alignment) != 1)
acf0174b
JJ
15085 {
15086 error_at (clause_loc, "%<aligned%> clause alignment expression must "
15087 "be positive constant integer expression");
15088 alignment = NULL_TREE;
15089 }
953ff289 15090
acf0174b
JJ
15091 for (c = nl; c != list; c = OMP_CLAUSE_CHAIN (c))
15092 OMP_CLAUSE_ALIGNED_ALIGNMENT (c) = alignment;
15093 }
15094
32129a17 15095 parens.skip_until_found_close (parser);
acf0174b
JJ
15096 return nl;
15097}
15098
15099/* OpenMP 4.0:
15100 linear ( variable-list )
d9a6bd32
JJ
15101 linear ( variable-list : expression )
15102
15103 OpenMP 4.5:
15104 linear ( modifier ( variable-list ) )
15105 linear ( modifier ( variable-list ) : expression ) */
acf0174b
JJ
15106
15107static tree
5e9d6aa4 15108c_parser_omp_clause_linear (c_parser *parser, tree list)
953ff289 15109{
acf0174b
JJ
15110 location_t clause_loc = c_parser_peek_token (parser)->location;
15111 tree nl, c, step;
d9a6bd32 15112 enum omp_clause_linear_kind kind = OMP_CLAUSE_LINEAR_DEFAULT;
acf0174b 15113
32129a17
DM
15114 matching_parens parens;
15115 if (!parens.require_open (parser))
acf0174b
JJ
15116 return list;
15117
5e9d6aa4 15118 if (c_parser_next_token_is (parser, CPP_NAME))
d9a6bd32
JJ
15119 {
15120 c_token *tok = c_parser_peek_token (parser);
15121 const char *p = IDENTIFIER_POINTER (tok->value);
15122 if (strcmp ("val", p) == 0)
15123 kind = OMP_CLAUSE_LINEAR_VAL;
15124 if (c_parser_peek_2nd_token (parser)->type != CPP_OPEN_PAREN)
15125 kind = OMP_CLAUSE_LINEAR_DEFAULT;
15126 if (kind != OMP_CLAUSE_LINEAR_DEFAULT)
15127 {
15128 c_parser_consume_token (parser);
15129 c_parser_consume_token (parser);
15130 }
15131 }
15132
acf0174b
JJ
15133 nl = c_parser_omp_variable_list (parser, clause_loc,
15134 OMP_CLAUSE_LINEAR, list);
15135
d9a6bd32 15136 if (kind != OMP_CLAUSE_LINEAR_DEFAULT)
32129a17 15137 parens.skip_until_found_close (parser);
d9a6bd32 15138
acf0174b
JJ
15139 if (c_parser_next_token_is (parser, CPP_COLON))
15140 {
15141 c_parser_consume_token (parser);
9dc5773f 15142 location_t expr_loc = c_parser_peek_token (parser)->location;
81a227c6 15143 c_expr expr = c_parser_expr_no_commas (parser, NULL);
9dc5773f
JJ
15144 expr = convert_lvalue_to_rvalue (expr_loc, expr, false, true);
15145 step = expr.value;
acf0174b
JJ
15146 step = c_fully_fold (step, false, NULL);
15147 if (!INTEGRAL_TYPE_P (TREE_TYPE (step)))
15148 {
15149 error_at (clause_loc, "%<linear%> clause step expression must "
15150 "be integral");
15151 step = integer_one_node;
15152 }
15153
15154 }
15155 else
15156 step = integer_one_node;
15157
15158 for (c = nl; c != list; c = OMP_CLAUSE_CHAIN (c))
15159 {
15160 OMP_CLAUSE_LINEAR_STEP (c) = step;
d9a6bd32 15161 OMP_CLAUSE_LINEAR_KIND (c) = kind;
acf0174b
JJ
15162 }
15163
32129a17 15164 parens.skip_until_found_close (parser);
acf0174b
JJ
15165 return nl;
15166}
15167
28567c40
JJ
15168/* OpenMP 5.0:
15169 nontemporal ( variable-list ) */
15170
15171static tree
15172c_parser_omp_clause_nontemporal (c_parser *parser, tree list)
15173{
15174 return c_parser_omp_var_list_parens (parser, OMP_CLAUSE_NONTEMPORAL, list);
15175}
15176
acf0174b
JJ
15177/* OpenMP 4.0:
15178 safelen ( constant-expression ) */
15179
15180static tree
15181c_parser_omp_clause_safelen (c_parser *parser, tree list)
15182{
15183 location_t clause_loc = c_parser_peek_token (parser)->location;
15184 tree c, t;
15185
32129a17
DM
15186 matching_parens parens;
15187 if (!parens.require_open (parser))
acf0174b
JJ
15188 return list;
15189
9dc5773f
JJ
15190 location_t expr_loc = c_parser_peek_token (parser)->location;
15191 c_expr expr = c_parser_expr_no_commas (parser, NULL);
15192 expr = convert_lvalue_to_rvalue (expr_loc, expr, false, true);
15193 t = expr.value;
acf0174b 15194 t = c_fully_fold (t, false, NULL);
fce5e5e3
JJ
15195 if (TREE_CODE (t) != INTEGER_CST
15196 || !INTEGRAL_TYPE_P (TREE_TYPE (t))
15197 || tree_int_cst_sgn (t) != 1)
acf0174b
JJ
15198 {
15199 error_at (clause_loc, "%<safelen%> clause expression must "
15200 "be positive constant integer expression");
15201 t = NULL_TREE;
15202 }
15203
32129a17 15204 parens.skip_until_found_close (parser);
acf0174b
JJ
15205 if (t == NULL_TREE || t == error_mark_node)
15206 return list;
15207
15208 check_no_duplicate_clause (list, OMP_CLAUSE_SAFELEN, "safelen");
15209
15210 c = build_omp_clause (clause_loc, OMP_CLAUSE_SAFELEN);
15211 OMP_CLAUSE_SAFELEN_EXPR (c) = t;
15212 OMP_CLAUSE_CHAIN (c) = list;
15213 return c;
15214}
15215
15216/* OpenMP 4.0:
15217 simdlen ( constant-expression ) */
15218
15219static tree
15220c_parser_omp_clause_simdlen (c_parser *parser, tree list)
15221{
15222 location_t clause_loc = c_parser_peek_token (parser)->location;
15223 tree c, t;
15224
32129a17
DM
15225 matching_parens parens;
15226 if (!parens.require_open (parser))
acf0174b
JJ
15227 return list;
15228
9dc5773f
JJ
15229 location_t expr_loc = c_parser_peek_token (parser)->location;
15230 c_expr expr = c_parser_expr_no_commas (parser, NULL);
15231 expr = convert_lvalue_to_rvalue (expr_loc, expr, false, true);
15232 t = expr.value;
acf0174b 15233 t = c_fully_fold (t, false, NULL);
fce5e5e3
JJ
15234 if (TREE_CODE (t) != INTEGER_CST
15235 || !INTEGRAL_TYPE_P (TREE_TYPE (t))
15236 || tree_int_cst_sgn (t) != 1)
acf0174b
JJ
15237 {
15238 error_at (clause_loc, "%<simdlen%> clause expression must "
15239 "be positive constant integer expression");
15240 t = NULL_TREE;
15241 }
15242
32129a17 15243 parens.skip_until_found_close (parser);
acf0174b
JJ
15244 if (t == NULL_TREE || t == error_mark_node)
15245 return list;
15246
15247 check_no_duplicate_clause (list, OMP_CLAUSE_SIMDLEN, "simdlen");
15248
15249 c = build_omp_clause (clause_loc, OMP_CLAUSE_SIMDLEN);
15250 OMP_CLAUSE_SIMDLEN_EXPR (c) = t;
15251 OMP_CLAUSE_CHAIN (c) = list;
15252 return c;
15253}
15254
d9a6bd32
JJ
15255/* OpenMP 4.5:
15256 vec:
15257 identifier [+/- integer]
15258 vec , identifier [+/- integer]
15259*/
15260
15261static tree
15262c_parser_omp_clause_depend_sink (c_parser *parser, location_t clause_loc,
15263 tree list)
15264{
15265 tree vec = NULL;
15266 if (c_parser_next_token_is_not (parser, CPP_NAME)
15267 || c_parser_peek_token (parser)->id_kind != C_ID_ID)
15268 {
15269 c_parser_error (parser, "expected identifier");
15270 return list;
15271 }
15272
15273 while (c_parser_next_token_is (parser, CPP_NAME)
15274 && c_parser_peek_token (parser)->id_kind == C_ID_ID)
15275 {
15276 tree t = lookup_name (c_parser_peek_token (parser)->value);
15277 tree addend = NULL;
15278
15279 if (t == NULL_TREE)
15280 {
15281 undeclared_variable (c_parser_peek_token (parser)->location,
15282 c_parser_peek_token (parser)->value);
15283 t = error_mark_node;
15284 }
15285
15286 c_parser_consume_token (parser);
15287
15288 bool neg = false;
15289 if (c_parser_next_token_is (parser, CPP_MINUS))
15290 neg = true;
15291 else if (!c_parser_next_token_is (parser, CPP_PLUS))
15292 {
15293 addend = integer_zero_node;
15294 neg = false;
15295 goto add_to_vector;
15296 }
15297 c_parser_consume_token (parser);
15298
15299 if (c_parser_next_token_is_not (parser, CPP_NUMBER))
15300 {
15301 c_parser_error (parser, "expected integer");
15302 return list;
15303 }
15304
15305 addend = c_parser_peek_token (parser)->value;
15306 if (TREE_CODE (addend) != INTEGER_CST)
15307 {
15308 c_parser_error (parser, "expected integer");
15309 return list;
15310 }
15311 c_parser_consume_token (parser);
15312
15313 add_to_vector:
15314 if (t != error_mark_node)
15315 {
15316 vec = tree_cons (addend, t, vec);
15317 if (neg)
15318 OMP_CLAUSE_DEPEND_SINK_NEGATIVE (vec) = 1;
15319 }
15320
15321 if (c_parser_next_token_is_not (parser, CPP_COMMA))
15322 break;
15323
15324 c_parser_consume_token (parser);
15325 }
15326
15327 if (vec == NULL_TREE)
15328 return list;
15329
15330 tree u = build_omp_clause (clause_loc, OMP_CLAUSE_DEPEND);
15331 OMP_CLAUSE_DEPEND_KIND (u) = OMP_CLAUSE_DEPEND_SINK;
15332 OMP_CLAUSE_DECL (u) = nreverse (vec);
15333 OMP_CLAUSE_CHAIN (u) = list;
15334 return u;
15335}
15336
28567c40
JJ
15337/* OpenMP 5.0:
15338 iterators ( iterators-definition )
15339
15340 iterators-definition:
15341 iterator-specifier
15342 iterator-specifier , iterators-definition
15343
15344 iterator-specifier:
15345 identifier = range-specification
15346 iterator-type identifier = range-specification
15347
15348 range-specification:
15349 begin : end
15350 begin : end : step */
15351
15352static tree
15353c_parser_omp_iterators (c_parser *parser)
15354{
15355 tree ret = NULL_TREE, *last = &ret;
15356 c_parser_consume_token (parser);
15357
15358 push_scope ();
15359
15360 matching_parens parens;
15361 if (!parens.require_open (parser))
15362 return error_mark_node;
15363
15364 do
15365 {
15366 tree iter_type = NULL_TREE, type_expr = NULL_TREE;
15367 if (c_parser_next_tokens_start_typename (parser, cla_prefer_id))
15368 {
15369 struct c_type_name *type = c_parser_type_name (parser);
15370 if (type != NULL)
15371 iter_type = groktypename (type, &type_expr, NULL);
15372 }
15373 if (iter_type == NULL_TREE)
15374 iter_type = integer_type_node;
15375
15376 location_t loc = c_parser_peek_token (parser)->location;
15377 if (!c_parser_next_token_is (parser, CPP_NAME))
15378 {
15379 c_parser_error (parser, "expected identifier");
15380 break;
15381 }
15382
15383 tree id = c_parser_peek_token (parser)->value;
15384 c_parser_consume_token (parser);
15385
15386 if (!c_parser_require (parser, CPP_EQ, "expected %<=%>"))
15387 break;
15388
15389 location_t eloc = c_parser_peek_token (parser)->location;
15390 c_expr expr = c_parser_expr_no_commas (parser, NULL);
15391 expr = convert_lvalue_to_rvalue (eloc, expr, true, false);
15392 tree begin = expr.value;
15393
15394 if (!c_parser_require (parser, CPP_COLON, "expected %<:%>"))
15395 break;
15396
15397 eloc = c_parser_peek_token (parser)->location;
15398 expr = c_parser_expr_no_commas (parser, NULL);
15399 expr = convert_lvalue_to_rvalue (eloc, expr, true, false);
15400 tree end = expr.value;
15401
15402 tree step = integer_one_node;
15403 if (c_parser_next_token_is (parser, CPP_COLON))
15404 {
15405 c_parser_consume_token (parser);
15406 eloc = c_parser_peek_token (parser)->location;
15407 expr = c_parser_expr_no_commas (parser, NULL);
15408 expr = convert_lvalue_to_rvalue (eloc, expr, true, false);
15409 step = expr.value;
15410 }
15411
15412 tree iter_var = build_decl (loc, VAR_DECL, id, iter_type);
15413 DECL_ARTIFICIAL (iter_var) = 1;
15414 DECL_CONTEXT (iter_var) = current_function_decl;
15415 pushdecl (iter_var);
15416
15417 *last = make_tree_vec (6);
15418 TREE_VEC_ELT (*last, 0) = iter_var;
15419 TREE_VEC_ELT (*last, 1) = begin;
15420 TREE_VEC_ELT (*last, 2) = end;
15421 TREE_VEC_ELT (*last, 3) = step;
15422 last = &TREE_CHAIN (*last);
15423
15424 if (c_parser_next_token_is (parser, CPP_COMMA))
15425 {
15426 c_parser_consume_token (parser);
15427 continue;
15428 }
15429 break;
15430 }
15431 while (1);
15432
15433 parens.skip_until_found_close (parser);
15434 return ret ? ret : error_mark_node;
15435}
15436
acf0174b
JJ
15437/* OpenMP 4.0:
15438 depend ( depend-kind: variable-list )
15439
15440 depend-kind:
d9a6bd32
JJ
15441 in | out | inout
15442
15443 OpenMP 4.5:
15444 depend ( source )
15445
28567c40
JJ
15446 depend ( sink : vec )
15447
15448 OpenMP 5.0:
15449 depend ( depend-modifier , depend-kind: variable-list )
15450
15451 depend-kind:
15452 in | out | inout | mutexinoutset | depobj
15453
15454 depend-modifier:
15455 iterator ( iterators-definition ) */
acf0174b
JJ
15456
15457static tree
15458c_parser_omp_clause_depend (c_parser *parser, tree list)
15459{
15460 location_t clause_loc = c_parser_peek_token (parser)->location;
28567c40
JJ
15461 enum omp_clause_depend_kind kind = OMP_CLAUSE_DEPEND_LAST;
15462 tree nl, c, iterators = NULL_TREE;
acf0174b 15463
32129a17
DM
15464 matching_parens parens;
15465 if (!parens.require_open (parser))
acf0174b 15466 return list;
953ff289 15467
28567c40 15468 do
20906c66 15469 {
28567c40
JJ
15470 if (c_parser_next_token_is_not (parser, CPP_NAME))
15471 goto invalid_kind;
15472
20906c66 15473 const char *p = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
28567c40
JJ
15474 if (strcmp ("iterator", p) == 0 && iterators == NULL_TREE)
15475 {
15476 iterators = c_parser_omp_iterators (parser);
15477 c_parser_require (parser, CPP_COMMA, "expected %<,%>");
15478 continue;
15479 }
acf0174b
JJ
15480 if (strcmp ("in", p) == 0)
15481 kind = OMP_CLAUSE_DEPEND_IN;
15482 else if (strcmp ("inout", p) == 0)
15483 kind = OMP_CLAUSE_DEPEND_INOUT;
28567c40
JJ
15484 else if (strcmp ("mutexinoutset", p) == 0)
15485 kind = OMP_CLAUSE_DEPEND_MUTEXINOUTSET;
acf0174b
JJ
15486 else if (strcmp ("out", p) == 0)
15487 kind = OMP_CLAUSE_DEPEND_OUT;
28567c40
JJ
15488 else if (strcmp ("depobj", p) == 0)
15489 kind = OMP_CLAUSE_DEPEND_DEPOBJ;
d9a6bd32
JJ
15490 else if (strcmp ("sink", p) == 0)
15491 kind = OMP_CLAUSE_DEPEND_SINK;
28567c40
JJ
15492 else if (strcmp ("source", p) == 0)
15493 kind = OMP_CLAUSE_DEPEND_SOURCE;
20906c66 15494 else
acf0174b 15495 goto invalid_kind;
28567c40 15496 break;
20906c66 15497 }
28567c40 15498 while (1);
953ff289 15499
acf0174b 15500 c_parser_consume_token (parser);
d9a6bd32 15501
28567c40
JJ
15502 if (iterators
15503 && (kind == OMP_CLAUSE_DEPEND_SOURCE || kind == OMP_CLAUSE_DEPEND_SINK))
15504 {
15505 pop_scope ();
15506 error_at (clause_loc, "%<iterator%> modifier incompatible with %qs",
15507 kind == OMP_CLAUSE_DEPEND_SOURCE ? "source" : "sink");
15508 iterators = NULL_TREE;
15509 }
15510
d9a6bd32
JJ
15511 if (kind == OMP_CLAUSE_DEPEND_SOURCE)
15512 {
15513 c = build_omp_clause (clause_loc, OMP_CLAUSE_DEPEND);
15514 OMP_CLAUSE_DEPEND_KIND (c) = kind;
15515 OMP_CLAUSE_DECL (c) = NULL_TREE;
15516 OMP_CLAUSE_CHAIN (c) = list;
32129a17 15517 parens.skip_until_found_close (parser);
d9a6bd32
JJ
15518 return c;
15519 }
15520
acf0174b
JJ
15521 if (!c_parser_require (parser, CPP_COLON, "expected %<:%>"))
15522 goto resync_fail;
15523
d9a6bd32
JJ
15524 if (kind == OMP_CLAUSE_DEPEND_SINK)
15525 nl = c_parser_omp_clause_depend_sink (parser, clause_loc, list);
15526 else
15527 {
15528 nl = c_parser_omp_variable_list (parser, clause_loc,
15529 OMP_CLAUSE_DEPEND, list);
acf0174b 15530
28567c40
JJ
15531 if (iterators)
15532 {
15533 tree block = pop_scope ();
15534 if (iterators == error_mark_node)
15535 iterators = NULL_TREE;
15536 else
15537 TREE_VEC_ELT (iterators, 5) = block;
15538 }
15539
d9a6bd32 15540 for (c = nl; c != list; c = OMP_CLAUSE_CHAIN (c))
28567c40
JJ
15541 {
15542 OMP_CLAUSE_DEPEND_KIND (c) = kind;
15543 if (iterators)
15544 OMP_CLAUSE_DECL (c)
15545 = build_tree_list (iterators, OMP_CLAUSE_DECL (c));
15546 }
d9a6bd32 15547 }
acf0174b 15548
32129a17 15549 parens.skip_until_found_close (parser);
acf0174b
JJ
15550 return nl;
15551
15552 invalid_kind:
15553 c_parser_error (parser, "invalid depend kind");
15554 resync_fail:
32129a17 15555 parens.skip_until_found_close (parser);
28567c40
JJ
15556 if (iterators)
15557 pop_scope ();
acf0174b
JJ
15558 return list;
15559}
15560
15561/* OpenMP 4.0:
15562 map ( map-kind: variable-list )
15563 map ( variable-list )
15564
15565 map-kind:
d9a6bd32
JJ
15566 alloc | to | from | tofrom
15567
15568 OpenMP 4.5:
15569 map-kind:
15570 alloc | to | from | tofrom | release | delete
15571
15572 map ( always [,] map-kind: variable-list ) */
acf0174b
JJ
15573
15574static tree
15575c_parser_omp_clause_map (c_parser *parser, tree list)
15576{
15577 location_t clause_loc = c_parser_peek_token (parser)->location;
41dbbb37 15578 enum gomp_map_kind kind = GOMP_MAP_TOFROM;
d9a6bd32
JJ
15579 int always = 0;
15580 enum c_id_kind always_id_kind = C_ID_NONE;
15581 location_t always_loc = UNKNOWN_LOCATION;
15582 tree always_id = NULL_TREE;
acf0174b
JJ
15583 tree nl, c;
15584
32129a17
DM
15585 matching_parens parens;
15586 if (!parens.require_open (parser))
acf0174b
JJ
15587 return list;
15588
d9a6bd32
JJ
15589 if (c_parser_next_token_is (parser, CPP_NAME))
15590 {
15591 c_token *tok = c_parser_peek_token (parser);
15592 const char *p = IDENTIFIER_POINTER (tok->value);
15593 always_id_kind = tok->id_kind;
15594 always_loc = tok->location;
15595 always_id = tok->value;
15596 if (strcmp ("always", p) == 0)
15597 {
15598 c_token *sectok = c_parser_peek_2nd_token (parser);
15599 if (sectok->type == CPP_COMMA)
15600 {
15601 c_parser_consume_token (parser);
15602 c_parser_consume_token (parser);
15603 always = 2;
15604 }
15605 else if (sectok->type == CPP_NAME)
15606 {
15607 p = IDENTIFIER_POINTER (sectok->value);
15608 if (strcmp ("alloc", p) == 0
15609 || strcmp ("to", p) == 0
15610 || strcmp ("from", p) == 0
15611 || strcmp ("tofrom", p) == 0
15612 || strcmp ("release", p) == 0
15613 || strcmp ("delete", p) == 0)
15614 {
15615 c_parser_consume_token (parser);
15616 always = 1;
15617 }
15618 }
15619 }
15620 }
15621
acf0174b
JJ
15622 if (c_parser_next_token_is (parser, CPP_NAME)
15623 && c_parser_peek_2nd_token (parser)->type == CPP_COLON)
20906c66 15624 {
acf0174b
JJ
15625 const char *p = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
15626 if (strcmp ("alloc", p) == 0)
41dbbb37 15627 kind = GOMP_MAP_ALLOC;
acf0174b 15628 else if (strcmp ("to", p) == 0)
d9a6bd32 15629 kind = always ? GOMP_MAP_ALWAYS_TO : GOMP_MAP_TO;
acf0174b 15630 else if (strcmp ("from", p) == 0)
d9a6bd32 15631 kind = always ? GOMP_MAP_ALWAYS_FROM : GOMP_MAP_FROM;
acf0174b 15632 else if (strcmp ("tofrom", p) == 0)
d9a6bd32
JJ
15633 kind = always ? GOMP_MAP_ALWAYS_TOFROM : GOMP_MAP_TOFROM;
15634 else if (strcmp ("release", p) == 0)
15635 kind = GOMP_MAP_RELEASE;
15636 else if (strcmp ("delete", p) == 0)
15637 kind = GOMP_MAP_DELETE;
20906c66
JJ
15638 else
15639 {
acf0174b
JJ
15640 c_parser_error (parser, "invalid map kind");
15641 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN,
15642 "expected %<)%>");
15643 return list;
20906c66 15644 }
acf0174b
JJ
15645 c_parser_consume_token (parser);
15646 c_parser_consume_token (parser);
20906c66 15647 }
d9a6bd32
JJ
15648 else if (always)
15649 {
15650 if (always_id_kind != C_ID_ID)
15651 {
15652 c_parser_error (parser, "expected identifier");
32129a17 15653 parens.skip_until_found_close (parser);
d9a6bd32
JJ
15654 return list;
15655 }
15656
15657 tree t = lookup_name (always_id);
15658 if (t == NULL_TREE)
15659 {
15660 undeclared_variable (always_loc, always_id);
15661 t = error_mark_node;
15662 }
15663 if (t != error_mark_node)
15664 {
15665 tree u = build_omp_clause (clause_loc, OMP_CLAUSE_MAP);
15666 OMP_CLAUSE_DECL (u) = t;
15667 OMP_CLAUSE_CHAIN (u) = list;
15668 OMP_CLAUSE_SET_MAP_KIND (u, kind);
15669 list = u;
15670 }
15671 if (always == 1)
15672 {
32129a17 15673 parens.skip_until_found_close (parser);
d9a6bd32
JJ
15674 return list;
15675 }
15676 }
20906c66 15677
acf0174b
JJ
15678 nl = c_parser_omp_variable_list (parser, clause_loc, OMP_CLAUSE_MAP, list);
15679
15680 for (c = nl; c != list; c = OMP_CLAUSE_CHAIN (c))
41dbbb37 15681 OMP_CLAUSE_SET_MAP_KIND (c, kind);
acf0174b 15682
32129a17 15683 parens.skip_until_found_close (parser);
acf0174b
JJ
15684 return nl;
15685}
15686
15687/* OpenMP 4.0:
15688 device ( expression ) */
15689
15690static tree
15691c_parser_omp_clause_device (c_parser *parser, tree list)
15692{
15693 location_t clause_loc = c_parser_peek_token (parser)->location;
32129a17
DM
15694 matching_parens parens;
15695 if (parens.require_open (parser))
953ff289 15696 {
9dc5773f
JJ
15697 location_t expr_loc = c_parser_peek_token (parser)->location;
15698 c_expr expr = c_parser_expr_no_commas (parser, NULL);
15699 expr = convert_lvalue_to_rvalue (expr_loc, expr, false, true);
15700 tree c, t = expr.value;
acf0174b
JJ
15701 t = c_fully_fold (t, false, NULL);
15702
32129a17 15703 parens.skip_until_found_close (parser);
acf0174b
JJ
15704
15705 if (!INTEGRAL_TYPE_P (TREE_TYPE (t)))
20906c66 15706 {
acf0174b
JJ
15707 c_parser_error (parser, "expected integer expression");
15708 return list;
20906c66 15709 }
953ff289 15710
acf0174b 15711 check_no_duplicate_clause (list, OMP_CLAUSE_DEVICE, "device");
953ff289 15712
acf0174b
JJ
15713 c = build_omp_clause (clause_loc, OMP_CLAUSE_DEVICE);
15714 OMP_CLAUSE_DEVICE_ID (c) = t;
15715 OMP_CLAUSE_CHAIN (c) = list;
15716 list = c;
15717 }
953ff289 15718
acf0174b
JJ
15719 return list;
15720}
15721
15722/* OpenMP 4.0:
15723 dist_schedule ( static )
15724 dist_schedule ( static , expression ) */
15725
15726static tree
15727c_parser_omp_clause_dist_schedule (c_parser *parser, tree list)
15728{
15729 tree c, t = NULL_TREE;
15730 location_t loc = c_parser_peek_token (parser)->location;
15731
32129a17
DM
15732 matching_parens parens;
15733 if (!parens.require_open (parser))
acf0174b
JJ
15734 return list;
15735
15736 if (!c_parser_next_token_is_keyword (parser, RID_STATIC))
15737 {
15738 c_parser_error (parser, "invalid dist_schedule kind");
15739 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN,
15740 "expected %<)%>");
15741 return list;
15742 }
15743
15744 c_parser_consume_token (parser);
15745 if (c_parser_next_token_is (parser, CPP_COMMA))
15746 {
15747 c_parser_consume_token (parser);
15748
9dc5773f
JJ
15749 location_t expr_loc = c_parser_peek_token (parser)->location;
15750 c_expr expr = c_parser_expr_no_commas (parser, NULL);
15751 expr = convert_lvalue_to_rvalue (expr_loc, expr, false, true);
15752 t = expr.value;
acf0174b 15753 t = c_fully_fold (t, false, NULL);
32129a17 15754 parens.skip_until_found_close (parser);
acf0174b
JJ
15755 }
15756 else
15757 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN,
15758 "expected %<,%> or %<)%>");
15759
2c3b8bad
JJ
15760 /* check_no_duplicate_clause (list, OMP_CLAUSE_DIST_SCHEDULE,
15761 "dist_schedule"); */
15762 if (omp_find_clause (list, OMP_CLAUSE_DIST_SCHEDULE))
15763 warning_at (loc, 0, "too many %qs clauses", "dist_schedule");
acf0174b
JJ
15764 if (t == error_mark_node)
15765 return list;
15766
15767 c = build_omp_clause (loc, OMP_CLAUSE_DIST_SCHEDULE);
15768 OMP_CLAUSE_DIST_SCHEDULE_CHUNK_EXPR (c) = t;
15769 OMP_CLAUSE_CHAIN (c) = list;
15770 return c;
15771}
15772
15773/* OpenMP 4.0:
15774 proc_bind ( proc-bind-kind )
15775
15776 proc-bind-kind:
15777 master | close | spread */
15778
15779static tree
15780c_parser_omp_clause_proc_bind (c_parser *parser, tree list)
15781{
15782 location_t clause_loc = c_parser_peek_token (parser)->location;
15783 enum omp_clause_proc_bind_kind kind;
15784 tree c;
15785
32129a17
DM
15786 matching_parens parens;
15787 if (!parens.require_open (parser))
acf0174b
JJ
15788 return list;
15789
15790 if (c_parser_next_token_is (parser, CPP_NAME))
15791 {
15792 const char *p = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
15793 if (strcmp ("master", p) == 0)
15794 kind = OMP_CLAUSE_PROC_BIND_MASTER;
15795 else if (strcmp ("close", p) == 0)
15796 kind = OMP_CLAUSE_PROC_BIND_CLOSE;
15797 else if (strcmp ("spread", p) == 0)
15798 kind = OMP_CLAUSE_PROC_BIND_SPREAD;
15799 else
15800 goto invalid_kind;
15801 }
15802 else
15803 goto invalid_kind;
15804
bb522e2e 15805 check_no_duplicate_clause (list, OMP_CLAUSE_PROC_BIND, "proc_bind");
acf0174b 15806 c_parser_consume_token (parser);
32129a17 15807 parens.skip_until_found_close (parser);
acf0174b
JJ
15808 c = build_omp_clause (clause_loc, OMP_CLAUSE_PROC_BIND);
15809 OMP_CLAUSE_PROC_BIND_KIND (c) = kind;
15810 OMP_CLAUSE_CHAIN (c) = list;
15811 return c;
15812
15813 invalid_kind:
15814 c_parser_error (parser, "invalid proc_bind kind");
32129a17 15815 parens.skip_until_found_close (parser);
acf0174b
JJ
15816 return list;
15817}
15818
77eb117f
JJ
15819/* OpenMP 5.0:
15820 device_type ( host | nohost | any ) */
15821
15822static tree
15823c_parser_omp_clause_device_type (c_parser *parser, tree list)
15824{
15825 location_t clause_loc = c_parser_peek_token (parser)->location;
15826 enum omp_clause_device_type_kind kind;
15827 tree c;
15828
15829 matching_parens parens;
15830 if (!parens.require_open (parser))
15831 return list;
15832
15833 if (c_parser_next_token_is (parser, CPP_NAME))
15834 {
15835 const char *p = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
15836 if (strcmp ("host", p) == 0)
15837 kind = OMP_CLAUSE_DEVICE_TYPE_HOST;
15838 else if (strcmp ("nohost", p) == 0)
15839 kind = OMP_CLAUSE_DEVICE_TYPE_NOHOST;
15840 else if (strcmp ("any", p) == 0)
15841 kind = OMP_CLAUSE_DEVICE_TYPE_ANY;
15842 else
15843 goto invalid_kind;
15844 }
15845 else
15846 goto invalid_kind;
15847
15848 /* check_no_duplicate_clause (list, OMP_CLAUSE_DEVICE_TYPE,
15849 "device_type"); */
15850 c_parser_consume_token (parser);
15851 parens.skip_until_found_close (parser);
15852 c = build_omp_clause (clause_loc, OMP_CLAUSE_DEVICE_TYPE);
15853 OMP_CLAUSE_DEVICE_TYPE_KIND (c) = kind;
15854 OMP_CLAUSE_CHAIN (c) = list;
15855 return c;
15856
15857 invalid_kind:
15858 c_parser_error (parser, "expected %<host%>, %<nohost%> or %<any%>");
15859 parens.skip_until_found_close (parser);
15860 return list;
15861}
15862
acf0174b
JJ
15863/* OpenMP 4.0:
15864 to ( variable-list ) */
15865
15866static tree
15867c_parser_omp_clause_to (c_parser *parser, tree list)
15868{
15869 return c_parser_omp_var_list_parens (parser, OMP_CLAUSE_TO, list);
15870}
15871
15872/* OpenMP 4.0:
15873 from ( variable-list ) */
15874
15875static tree
15876c_parser_omp_clause_from (c_parser *parser, tree list)
15877{
15878 return c_parser_omp_var_list_parens (parser, OMP_CLAUSE_FROM, list);
15879}
15880
15881/* OpenMP 4.0:
15882 uniform ( variable-list ) */
15883
15884static tree
15885c_parser_omp_clause_uniform (c_parser *parser, tree list)
15886{
15887 /* The clauses location. */
15888 location_t loc = c_parser_peek_token (parser)->location;
15889
32129a17
DM
15890 matching_parens parens;
15891 if (parens.require_open (parser))
acf0174b
JJ
15892 {
15893 list = c_parser_omp_variable_list (parser, loc, OMP_CLAUSE_UNIFORM,
15894 list);
32129a17 15895 parens.skip_until_found_close (parser);
acf0174b
JJ
15896 }
15897 return list;
15898}
15899
41dbbb37
TS
15900/* Parse all OpenACC clauses. The set clauses allowed by the directive
15901 is a bitmask in MASK. Return the list of clauses found. */
15902
15903static tree
15904c_parser_oacc_all_clauses (c_parser *parser, omp_clause_mask mask,
15905 const char *where, bool finish_p = true)
15906{
15907 tree clauses = NULL;
15908 bool first = true;
15909
15910 while (c_parser_next_token_is_not (parser, CPP_PRAGMA_EOL))
15911 {
15912 location_t here;
15913 pragma_omp_clause c_kind;
15914 const char *c_name;
15915 tree prev = clauses;
15916
15917 if (!first && c_parser_next_token_is (parser, CPP_COMMA))
15918 c_parser_consume_token (parser);
15919
15920 here = c_parser_peek_token (parser)->location;
15921 c_kind = c_parser_omp_clause_name (parser);
15922
15923 switch (c_kind)
15924 {
15925 case PRAGMA_OACC_CLAUSE_ASYNC:
15926 clauses = c_parser_oacc_clause_async (parser, clauses);
15927 c_name = "async";
15928 break;
765dd391 15929 case PRAGMA_OACC_CLAUSE_AUTO:
2263c9f2
TS
15930 clauses = c_parser_oacc_simple_clause (here, OMP_CLAUSE_AUTO,
15931 clauses);
765dd391
CP
15932 c_name = "auto";
15933 break;
519d7496
JB
15934 case PRAGMA_OACC_CLAUSE_ATTACH:
15935 clauses = c_parser_oacc_data_clause (parser, c_kind, clauses);
15936 c_name = "attach";
15937 break;
41dbbb37
TS
15938 case PRAGMA_OACC_CLAUSE_COLLAPSE:
15939 clauses = c_parser_omp_clause_collapse (parser, clauses);
15940 c_name = "collapse";
15941 break;
15942 case PRAGMA_OACC_CLAUSE_COPY:
15943 clauses = c_parser_oacc_data_clause (parser, c_kind, clauses);
15944 c_name = "copy";
15945 break;
15946 case PRAGMA_OACC_CLAUSE_COPYIN:
15947 clauses = c_parser_oacc_data_clause (parser, c_kind, clauses);
15948 c_name = "copyin";
15949 break;
15950 case PRAGMA_OACC_CLAUSE_COPYOUT:
15951 clauses = c_parser_oacc_data_clause (parser, c_kind, clauses);
15952 c_name = "copyout";
15953 break;
15954 case PRAGMA_OACC_CLAUSE_CREATE:
15955 clauses = c_parser_oacc_data_clause (parser, c_kind, clauses);
15956 c_name = "create";
15957 break;
15958 case PRAGMA_OACC_CLAUSE_DELETE:
15959 clauses = c_parser_oacc_data_clause (parser, c_kind, clauses);
15960 c_name = "delete";
15961 break;
7a5e4956
CP
15962 case PRAGMA_OMP_CLAUSE_DEFAULT:
15963 clauses = c_parser_omp_clause_default (parser, clauses, true);
15964 c_name = "default";
15965 break;
519d7496
JB
15966 case PRAGMA_OACC_CLAUSE_DETACH:
15967 clauses = c_parser_oacc_data_clause (parser, c_kind, clauses);
15968 c_name = "detach";
15969 break;
41dbbb37
TS
15970 case PRAGMA_OACC_CLAUSE_DEVICE:
15971 clauses = c_parser_oacc_data_clause (parser, c_kind, clauses);
15972 c_name = "device";
15973 break;
15974 case PRAGMA_OACC_CLAUSE_DEVICEPTR:
15975 clauses = c_parser_oacc_data_clause_deviceptr (parser, clauses);
15976 c_name = "deviceptr";
15977 break;
6e232ba4
JN
15978 case PRAGMA_OACC_CLAUSE_DEVICE_RESIDENT:
15979 clauses = c_parser_oacc_data_clause (parser, c_kind, clauses);
15980 c_name = "device_resident";
15981 break;
829c6349 15982 case PRAGMA_OACC_CLAUSE_FINALIZE:
2263c9f2 15983 clauses = c_parser_oacc_simple_clause (here, OMP_CLAUSE_FINALIZE,
829c6349
CLT
15984 clauses);
15985 c_name = "finalize";
15986 break;
41dbbb37
TS
15987 case PRAGMA_OACC_CLAUSE_FIRSTPRIVATE:
15988 clauses = c_parser_omp_clause_firstprivate (parser, clauses);
15989 c_name = "firstprivate";
15990 break;
765dd391
CP
15991 case PRAGMA_OACC_CLAUSE_GANG:
15992 c_name = "gang";
2263c9f2 15993 clauses = c_parser_oacc_shape_clause (parser, here, OMP_CLAUSE_GANG,
765dd391
CP
15994 c_name, clauses);
15995 break;
41dbbb37
TS
15996 case PRAGMA_OACC_CLAUSE_HOST:
15997 clauses = c_parser_oacc_data_clause (parser, c_kind, clauses);
15998 c_name = "host";
15999 break;
16000 case PRAGMA_OACC_CLAUSE_IF:
d9a6bd32 16001 clauses = c_parser_omp_clause_if (parser, clauses, false);
41dbbb37
TS
16002 c_name = "if";
16003 break;
829c6349 16004 case PRAGMA_OACC_CLAUSE_IF_PRESENT:
2263c9f2 16005 clauses = c_parser_oacc_simple_clause (here, OMP_CLAUSE_IF_PRESENT,
829c6349
CLT
16006 clauses);
16007 c_name = "if_present";
16008 break;
7a5e4956 16009 case PRAGMA_OACC_CLAUSE_INDEPENDENT:
2263c9f2
TS
16010 clauses = c_parser_oacc_simple_clause (here, OMP_CLAUSE_INDEPENDENT,
16011 clauses);
7a5e4956
CP
16012 c_name = "independent";
16013 break;
6e232ba4
JN
16014 case PRAGMA_OACC_CLAUSE_LINK:
16015 clauses = c_parser_oacc_data_clause (parser, c_kind, clauses);
16016 c_name = "link";
16017 break;
a6163563
JB
16018 case PRAGMA_OACC_CLAUSE_NO_CREATE:
16019 clauses = c_parser_oacc_data_clause (parser, c_kind, clauses);
16020 c_name = "no_create";
16021 break;
41dbbb37 16022 case PRAGMA_OACC_CLAUSE_NUM_GANGS:
1e47f02b
TS
16023 clauses = c_parser_oacc_single_int_clause (parser,
16024 OMP_CLAUSE_NUM_GANGS,
16025 clauses);
41dbbb37
TS
16026 c_name = "num_gangs";
16027 break;
16028 case PRAGMA_OACC_CLAUSE_NUM_WORKERS:
1e47f02b
TS
16029 clauses = c_parser_oacc_single_int_clause (parser,
16030 OMP_CLAUSE_NUM_WORKERS,
16031 clauses);
41dbbb37
TS
16032 c_name = "num_workers";
16033 break;
16034 case PRAGMA_OACC_CLAUSE_PRESENT:
16035 clauses = c_parser_oacc_data_clause (parser, c_kind, clauses);
16036 c_name = "present";
16037 break;
41dbbb37
TS
16038 case PRAGMA_OACC_CLAUSE_PRIVATE:
16039 clauses = c_parser_omp_clause_private (parser, clauses);
16040 c_name = "private";
16041 break;
16042 case PRAGMA_OACC_CLAUSE_REDUCTION:
28567c40
JJ
16043 clauses
16044 = c_parser_omp_clause_reduction (parser, OMP_CLAUSE_REDUCTION,
16045 false, clauses);
41dbbb37
TS
16046 c_name = "reduction";
16047 break;
765dd391 16048 case PRAGMA_OACC_CLAUSE_SEQ:
2263c9f2 16049 clauses = c_parser_oacc_simple_clause (here, OMP_CLAUSE_SEQ,
28567c40 16050 clauses);
765dd391
CP
16051 c_name = "seq";
16052 break;
7a5e4956
CP
16053 case PRAGMA_OACC_CLAUSE_TILE:
16054 clauses = c_parser_oacc_clause_tile (parser, clauses);
16055 c_name = "tile";
16056 break;
ff7a55bf 16057 case PRAGMA_OACC_CLAUSE_USE_DEVICE:
c7b48c8a 16058 clauses = c_parser_omp_clause_use_device_ptr (parser, clauses);
ff7a55bf
TS
16059 c_name = "use_device";
16060 break;
765dd391
CP
16061 case PRAGMA_OACC_CLAUSE_VECTOR:
16062 c_name = "vector";
2263c9f2 16063 clauses = c_parser_oacc_shape_clause (parser, here, OMP_CLAUSE_VECTOR,
765dd391
CP
16064 c_name, clauses);
16065 break;
41dbbb37 16066 case PRAGMA_OACC_CLAUSE_VECTOR_LENGTH:
1e47f02b
TS
16067 clauses = c_parser_oacc_single_int_clause (parser,
16068 OMP_CLAUSE_VECTOR_LENGTH,
16069 clauses);
41dbbb37
TS
16070 c_name = "vector_length";
16071 break;
16072 case PRAGMA_OACC_CLAUSE_WAIT:
16073 clauses = c_parser_oacc_clause_wait (parser, clauses);
16074 c_name = "wait";
16075 break;
765dd391
CP
16076 case PRAGMA_OACC_CLAUSE_WORKER:
16077 c_name = "worker";
2263c9f2 16078 clauses = c_parser_oacc_shape_clause (parser, here, OMP_CLAUSE_WORKER,
765dd391
CP
16079 c_name, clauses);
16080 break;
41dbbb37
TS
16081 default:
16082 c_parser_error (parser, "expected %<#pragma acc%> clause");
16083 goto saw_error;
16084 }
16085
16086 first = false;
16087
0bb99c11 16088 if (((mask >> c_kind) & 1) == 0)
41dbbb37
TS
16089 {
16090 /* Remove the invalid clause(s) from the list to avoid
16091 confusing the rest of the compiler. */
16092 clauses = prev;
16093 error_at (here, "%qs is not valid for %qs", c_name, where);
16094 }
16095 }
16096
16097 saw_error:
16098 c_parser_skip_to_pragma_eol (parser);
16099
16100 if (finish_p)
77886428 16101 return c_finish_omp_clauses (clauses, C_ORT_ACC);
41dbbb37
TS
16102
16103 return clauses;
16104}
16105
acf0174b 16106/* Parse all OpenMP clauses. The set clauses allowed by the directive
94e7f906
JJ
16107 is a bitmask in MASK. Return the list of clauses found.
16108 FINISH_P set if c_finish_omp_clauses should be called.
b9424661
JJ
16109 NESTED non-zero if clauses should be terminated by closing paren instead
16110 of end of pragma. If it is 2, additionally commas are required in between
16111 the clauses. */
acf0174b
JJ
16112
16113static tree
16114c_parser_omp_all_clauses (c_parser *parser, omp_clause_mask mask,
94e7f906 16115 const char *where, bool finish_p = true,
b9424661 16116 int nested = 0)
acf0174b
JJ
16117{
16118 tree clauses = NULL;
5e9d6aa4 16119 bool first = true;
acf0174b
JJ
16120
16121 while (c_parser_next_token_is_not (parser, CPP_PRAGMA_EOL))
16122 {
16123 location_t here;
16124 pragma_omp_clause c_kind;
16125 const char *c_name;
16126 tree prev = clauses;
16127
b9424661 16128 if (nested && c_parser_next_token_is (parser, CPP_CLOSE_PAREN))
94e7f906
JJ
16129 break;
16130
b9424661
JJ
16131 if (!first)
16132 {
16133 if (c_parser_next_token_is (parser, CPP_COMMA))
16134 c_parser_consume_token (parser);
16135 else if (nested == 2)
16136 error_at (c_parser_peek_token (parser)->location,
16137 "clauses in %<simd%> trait should be separated "
16138 "by %<,%>");
16139 }
acf0174b
JJ
16140
16141 here = c_parser_peek_token (parser)->location;
16142 c_kind = c_parser_omp_clause_name (parser);
16143
16144 switch (c_kind)
953ff289 16145 {
554a530f
JJ
16146 case PRAGMA_OMP_CLAUSE_BIND:
16147 clauses = c_parser_omp_clause_bind (parser, clauses);
16148 c_name = "bind";
16149 break;
acf0174b
JJ
16150 case PRAGMA_OMP_CLAUSE_COLLAPSE:
16151 clauses = c_parser_omp_clause_collapse (parser, clauses);
16152 c_name = "collapse";
953ff289 16153 break;
acf0174b
JJ
16154 case PRAGMA_OMP_CLAUSE_COPYIN:
16155 clauses = c_parser_omp_clause_copyin (parser, clauses);
16156 c_name = "copyin";
953ff289 16157 break;
acf0174b
JJ
16158 case PRAGMA_OMP_CLAUSE_COPYPRIVATE:
16159 clauses = c_parser_omp_clause_copyprivate (parser, clauses);
16160 c_name = "copyprivate";
953ff289 16161 break;
acf0174b 16162 case PRAGMA_OMP_CLAUSE_DEFAULT:
7a5e4956 16163 clauses = c_parser_omp_clause_default (parser, clauses, false);
acf0174b 16164 c_name = "default";
953ff289 16165 break;
acf0174b
JJ
16166 case PRAGMA_OMP_CLAUSE_FIRSTPRIVATE:
16167 clauses = c_parser_omp_clause_firstprivate (parser, clauses);
16168 c_name = "firstprivate";
953ff289 16169 break;
acf0174b
JJ
16170 case PRAGMA_OMP_CLAUSE_FINAL:
16171 clauses = c_parser_omp_clause_final (parser, clauses);
16172 c_name = "final";
953ff289 16173 break;
d9a6bd32
JJ
16174 case PRAGMA_OMP_CLAUSE_GRAINSIZE:
16175 clauses = c_parser_omp_clause_grainsize (parser, clauses);
16176 c_name = "grainsize";
16177 break;
16178 case PRAGMA_OMP_CLAUSE_HINT:
16179 clauses = c_parser_omp_clause_hint (parser, clauses);
16180 c_name = "hint";
16181 break;
16182 case PRAGMA_OMP_CLAUSE_DEFAULTMAP:
16183 clauses = c_parser_omp_clause_defaultmap (parser, clauses);
16184 c_name = "defaultmap";
16185 break;
acf0174b 16186 case PRAGMA_OMP_CLAUSE_IF:
d9a6bd32 16187 clauses = c_parser_omp_clause_if (parser, clauses, true);
acf0174b 16188 c_name = "if";
953ff289 16189 break;
28567c40
JJ
16190 case PRAGMA_OMP_CLAUSE_IN_REDUCTION:
16191 clauses
16192 = c_parser_omp_clause_reduction (parser, OMP_CLAUSE_IN_REDUCTION,
16193 true, clauses);
16194 c_name = "in_reduction";
16195 break;
acf0174b
JJ
16196 case PRAGMA_OMP_CLAUSE_LASTPRIVATE:
16197 clauses = c_parser_omp_clause_lastprivate (parser, clauses);
16198 c_name = "lastprivate";
953ff289 16199 break;
acf0174b
JJ
16200 case PRAGMA_OMP_CLAUSE_MERGEABLE:
16201 clauses = c_parser_omp_clause_mergeable (parser, clauses);
16202 c_name = "mergeable";
953ff289 16203 break;
acf0174b
JJ
16204 case PRAGMA_OMP_CLAUSE_NOWAIT:
16205 clauses = c_parser_omp_clause_nowait (parser, clauses);
16206 c_name = "nowait";
16207 break;
d9a6bd32
JJ
16208 case PRAGMA_OMP_CLAUSE_NUM_TASKS:
16209 clauses = c_parser_omp_clause_num_tasks (parser, clauses);
16210 c_name = "num_tasks";
16211 break;
acf0174b
JJ
16212 case PRAGMA_OMP_CLAUSE_NUM_THREADS:
16213 clauses = c_parser_omp_clause_num_threads (parser, clauses);
16214 c_name = "num_threads";
16215 break;
1fdd6f04
JJ
16216 case PRAGMA_OMP_CLAUSE_ORDER:
16217 clauses = c_parser_omp_clause_order (parser, clauses);
16218 c_name = "order";
16219 break;
acf0174b
JJ
16220 case PRAGMA_OMP_CLAUSE_ORDERED:
16221 clauses = c_parser_omp_clause_ordered (parser, clauses);
16222 c_name = "ordered";
16223 break;
d9a6bd32
JJ
16224 case PRAGMA_OMP_CLAUSE_PRIORITY:
16225 clauses = c_parser_omp_clause_priority (parser, clauses);
16226 c_name = "priority";
16227 break;
acf0174b
JJ
16228 case PRAGMA_OMP_CLAUSE_PRIVATE:
16229 clauses = c_parser_omp_clause_private (parser, clauses);
16230 c_name = "private";
16231 break;
16232 case PRAGMA_OMP_CLAUSE_REDUCTION:
28567c40
JJ
16233 clauses
16234 = c_parser_omp_clause_reduction (parser, OMP_CLAUSE_REDUCTION,
16235 true, clauses);
acf0174b
JJ
16236 c_name = "reduction";
16237 break;
16238 case PRAGMA_OMP_CLAUSE_SCHEDULE:
16239 clauses = c_parser_omp_clause_schedule (parser, clauses);
16240 c_name = "schedule";
16241 break;
16242 case PRAGMA_OMP_CLAUSE_SHARED:
16243 clauses = c_parser_omp_clause_shared (parser, clauses);
16244 c_name = "shared";
16245 break;
28567c40
JJ
16246 case PRAGMA_OMP_CLAUSE_TASK_REDUCTION:
16247 clauses
16248 = c_parser_omp_clause_reduction (parser, OMP_CLAUSE_TASK_REDUCTION,
16249 true, clauses);
16250 c_name = "task_reduction";
16251 break;
acf0174b
JJ
16252 case PRAGMA_OMP_CLAUSE_UNTIED:
16253 clauses = c_parser_omp_clause_untied (parser, clauses);
16254 c_name = "untied";
16255 break;
16256 case PRAGMA_OMP_CLAUSE_INBRANCH:
16257 clauses = c_parser_omp_clause_branch (parser, OMP_CLAUSE_INBRANCH,
16258 clauses);
16259 c_name = "inbranch";
16260 break;
28567c40
JJ
16261 case PRAGMA_OMP_CLAUSE_NONTEMPORAL:
16262 clauses = c_parser_omp_clause_nontemporal (parser, clauses);
16263 c_name = "nontemporal";
16264 break;
acf0174b
JJ
16265 case PRAGMA_OMP_CLAUSE_NOTINBRANCH:
16266 clauses = c_parser_omp_clause_branch (parser, OMP_CLAUSE_NOTINBRANCH,
16267 clauses);
16268 c_name = "notinbranch";
16269 break;
16270 case PRAGMA_OMP_CLAUSE_PARALLEL:
16271 clauses
16272 = c_parser_omp_clause_cancelkind (parser, OMP_CLAUSE_PARALLEL,
16273 clauses);
16274 c_name = "parallel";
16275 if (!first)
20906c66 16276 {
acf0174b
JJ
16277 clause_not_first:
16278 error_at (here, "%qs must be the first clause of %qs",
16279 c_name, where);
16280 clauses = prev;
16281 }
16282 break;
16283 case PRAGMA_OMP_CLAUSE_FOR:
16284 clauses
16285 = c_parser_omp_clause_cancelkind (parser, OMP_CLAUSE_FOR,
16286 clauses);
16287 c_name = "for";
16288 if (!first)
16289 goto clause_not_first;
16290 break;
16291 case PRAGMA_OMP_CLAUSE_SECTIONS:
16292 clauses
16293 = c_parser_omp_clause_cancelkind (parser, OMP_CLAUSE_SECTIONS,
16294 clauses);
16295 c_name = "sections";
16296 if (!first)
16297 goto clause_not_first;
16298 break;
16299 case PRAGMA_OMP_CLAUSE_TASKGROUP:
16300 clauses
16301 = c_parser_omp_clause_cancelkind (parser, OMP_CLAUSE_TASKGROUP,
16302 clauses);
16303 c_name = "taskgroup";
16304 if (!first)
16305 goto clause_not_first;
16306 break;
d9a6bd32
JJ
16307 case PRAGMA_OMP_CLAUSE_LINK:
16308 clauses
16309 = c_parser_omp_var_list_parens (parser, OMP_CLAUSE_LINK, clauses);
16310 c_name = "link";
16311 break;
acf0174b 16312 case PRAGMA_OMP_CLAUSE_TO:
d9a6bd32
JJ
16313 if ((mask & (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_LINK)) != 0)
16314 clauses
16315 = c_parser_omp_var_list_parens (parser, OMP_CLAUSE_TO_DECLARE,
16316 clauses);
16317 else
16318 clauses = c_parser_omp_clause_to (parser, clauses);
acf0174b
JJ
16319 c_name = "to";
16320 break;
16321 case PRAGMA_OMP_CLAUSE_FROM:
16322 clauses = c_parser_omp_clause_from (parser, clauses);
16323 c_name = "from";
16324 break;
16325 case PRAGMA_OMP_CLAUSE_UNIFORM:
16326 clauses = c_parser_omp_clause_uniform (parser, clauses);
16327 c_name = "uniform";
16328 break;
16329 case PRAGMA_OMP_CLAUSE_NUM_TEAMS:
16330 clauses = c_parser_omp_clause_num_teams (parser, clauses);
16331 c_name = "num_teams";
16332 break;
16333 case PRAGMA_OMP_CLAUSE_THREAD_LIMIT:
16334 clauses = c_parser_omp_clause_thread_limit (parser, clauses);
16335 c_name = "thread_limit";
16336 break;
16337 case PRAGMA_OMP_CLAUSE_ALIGNED:
16338 clauses = c_parser_omp_clause_aligned (parser, clauses);
16339 c_name = "aligned";
16340 break;
41958c28 16341 case PRAGMA_OMP_CLAUSE_LINEAR:
5e9d6aa4 16342 clauses = c_parser_omp_clause_linear (parser, clauses);
acf0174b
JJ
16343 c_name = "linear";
16344 break;
16345 case PRAGMA_OMP_CLAUSE_DEPEND:
16346 clauses = c_parser_omp_clause_depend (parser, clauses);
16347 c_name = "depend";
16348 break;
16349 case PRAGMA_OMP_CLAUSE_MAP:
16350 clauses = c_parser_omp_clause_map (parser, clauses);
16351 c_name = "map";
16352 break;
d9a6bd32
JJ
16353 case PRAGMA_OMP_CLAUSE_USE_DEVICE_PTR:
16354 clauses = c_parser_omp_clause_use_device_ptr (parser, clauses);
16355 c_name = "use_device_ptr";
16356 break;
398e3feb
JJ
16357 case PRAGMA_OMP_CLAUSE_USE_DEVICE_ADDR:
16358 clauses = c_parser_omp_clause_use_device_addr (parser, clauses);
16359 c_name = "use_device_addr";
16360 break;
d9a6bd32
JJ
16361 case PRAGMA_OMP_CLAUSE_IS_DEVICE_PTR:
16362 clauses = c_parser_omp_clause_is_device_ptr (parser, clauses);
16363 c_name = "is_device_ptr";
16364 break;
acf0174b
JJ
16365 case PRAGMA_OMP_CLAUSE_DEVICE:
16366 clauses = c_parser_omp_clause_device (parser, clauses);
16367 c_name = "device";
16368 break;
16369 case PRAGMA_OMP_CLAUSE_DIST_SCHEDULE:
16370 clauses = c_parser_omp_clause_dist_schedule (parser, clauses);
16371 c_name = "dist_schedule";
16372 break;
16373 case PRAGMA_OMP_CLAUSE_PROC_BIND:
16374 clauses = c_parser_omp_clause_proc_bind (parser, clauses);
16375 c_name = "proc_bind";
16376 break;
77eb117f
JJ
16377 case PRAGMA_OMP_CLAUSE_DEVICE_TYPE:
16378 clauses = c_parser_omp_clause_device_type (parser, clauses);
16379 c_name = "device_type";
16380 break;
acf0174b
JJ
16381 case PRAGMA_OMP_CLAUSE_SAFELEN:
16382 clauses = c_parser_omp_clause_safelen (parser, clauses);
16383 c_name = "safelen";
16384 break;
16385 case PRAGMA_OMP_CLAUSE_SIMDLEN:
16386 clauses = c_parser_omp_clause_simdlen (parser, clauses);
16387 c_name = "simdlen";
16388 break;
d9a6bd32
JJ
16389 case PRAGMA_OMP_CLAUSE_NOGROUP:
16390 clauses = c_parser_omp_clause_nogroup (parser, clauses);
16391 c_name = "nogroup";
16392 break;
16393 case PRAGMA_OMP_CLAUSE_THREADS:
16394 clauses
16395 = c_parser_omp_clause_orderedkind (parser, OMP_CLAUSE_THREADS,
16396 clauses);
16397 c_name = "threads";
16398 break;
16399 case PRAGMA_OMP_CLAUSE_SIMD:
16400 clauses
16401 = c_parser_omp_clause_orderedkind (parser, OMP_CLAUSE_SIMD,
16402 clauses);
16403 c_name = "simd";
16404 break;
953ff289 16405 default:
acf0174b 16406 c_parser_error (parser, "expected %<#pragma omp%> clause");
953ff289
DN
16407 goto saw_error;
16408 }
16409
acf0174b
JJ
16410 first = false;
16411
0bb99c11 16412 if (((mask >> c_kind) & 1) == 0)
acf0174b
JJ
16413 {
16414 /* Remove the invalid clause(s) from the list to avoid
16415 confusing the rest of the compiler. */
16416 clauses = prev;
16417 error_at (here, "%qs is not valid for %qs", c_name, where);
16418 }
16419 }
16420
16421 saw_error:
b9424661 16422 if (!nested)
94e7f906 16423 c_parser_skip_to_pragma_eol (parser);
acf0174b
JJ
16424
16425 if (finish_p)
d9a6bd32
JJ
16426 {
16427 if ((mask & (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_UNIFORM)) != 0)
77886428
CP
16428 return c_finish_omp_clauses (clauses, C_ORT_OMP_DECLARE_SIMD);
16429 return c_finish_omp_clauses (clauses, C_ORT_OMP);
d9a6bd32 16430 }
acf0174b
JJ
16431
16432 return clauses;
16433}
16434
41dbbb37 16435/* OpenACC 2.0, OpenMP 2.5:
acf0174b
JJ
16436 structured-block:
16437 statement
16438
16439 In practice, we're also interested in adding the statement to an
16440 outer node. So it is convenient if we work around the fact that
16441 c_parser_statement calls add_stmt. */
16442
16443static tree
dda1bf61 16444c_parser_omp_structured_block (c_parser *parser, bool *if_p)
acf0174b
JJ
16445{
16446 tree stmt = push_stmt_list ();
dda1bf61 16447 c_parser_statement (parser, if_p);
acf0174b
JJ
16448 return pop_stmt_list (stmt);
16449}
16450
41dbbb37
TS
16451/* OpenACC 2.0:
16452 # pragma acc cache (variable-list) new-line
16453
16454 LOC is the location of the #pragma token.
16455*/
16456
16457static tree
16458c_parser_oacc_cache (location_t loc, c_parser *parser)
16459{
16460 tree stmt, clauses;
16461
16462 clauses = c_parser_omp_var_list_parens (parser, OMP_CLAUSE__CACHE_, NULL);
77886428 16463 clauses = c_finish_omp_clauses (clauses, C_ORT_ACC);
41dbbb37
TS
16464
16465 c_parser_skip_to_pragma_eol (parser);
16466
16467 stmt = make_node (OACC_CACHE);
16468 TREE_TYPE (stmt) = void_type_node;
16469 OACC_CACHE_CLAUSES (stmt) = clauses;
16470 SET_EXPR_LOCATION (stmt, loc);
16471 add_stmt (stmt);
16472
16473 return stmt;
16474}
16475
16476/* OpenACC 2.0:
16477 # pragma acc data oacc-data-clause[optseq] new-line
16478 structured-block
16479
16480 LOC is the location of the #pragma token.
16481*/
16482
16483#define OACC_DATA_CLAUSE_MASK \
519d7496
JB
16484 ( (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_ATTACH) \
16485 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_COPY) \
41dbbb37
TS
16486 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_COPYIN) \
16487 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_COPYOUT) \
16488 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_CREATE) \
16489 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_DEVICEPTR) \
16490 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_IF) \
a6163563 16491 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_NO_CREATE) \
829c6349 16492 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_PRESENT))
41dbbb37
TS
16493
16494static tree
dda1bf61 16495c_parser_oacc_data (location_t loc, c_parser *parser, bool *if_p)
41dbbb37
TS
16496{
16497 tree stmt, clauses, block;
16498
16499 clauses = c_parser_oacc_all_clauses (parser, OACC_DATA_CLAUSE_MASK,
16500 "#pragma acc data");
16501
16502 block = c_begin_omp_parallel ();
dda1bf61 16503 add_stmt (c_parser_omp_structured_block (parser, if_p));
41dbbb37
TS
16504
16505 stmt = c_finish_oacc_data (loc, clauses, block);
16506
16507 return stmt;
16508}
16509
6e232ba4
JN
16510/* OpenACC 2.0:
16511 # pragma acc declare oacc-data-clause[optseq] new-line
16512*/
16513
16514#define OACC_DECLARE_CLAUSE_MASK \
16515 ( (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_COPY) \
16516 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_COPYIN) \
16517 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_COPYOUT) \
16518 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_CREATE) \
16519 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_DEVICEPTR) \
16520 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_DEVICE_RESIDENT) \
16521 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_LINK) \
829c6349 16522 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_PRESENT))
6e232ba4
JN
16523
16524static void
16525c_parser_oacc_declare (c_parser *parser)
16526{
16527 location_t pragma_loc = c_parser_peek_token (parser)->location;
16528 tree clauses, stmt, t, decl;
16529
16530 bool error = false;
16531
16532 c_parser_consume_pragma (parser);
16533
16534 clauses = c_parser_oacc_all_clauses (parser, OACC_DECLARE_CLAUSE_MASK,
16535 "#pragma acc declare");
16536 if (!clauses)
16537 {
16538 error_at (pragma_loc,
16539 "no valid clauses specified in %<#pragma acc declare%>");
16540 return;
16541 }
16542
16543 for (t = clauses; t; t = OMP_CLAUSE_CHAIN (t))
16544 {
16545 location_t loc = OMP_CLAUSE_LOCATION (t);
16546 decl = OMP_CLAUSE_DECL (t);
16547 if (!DECL_P (decl))
16548 {
16549 error_at (loc, "array section in %<#pragma acc declare%>");
16550 error = true;
16551 continue;
16552 }
16553
16554 switch (OMP_CLAUSE_MAP_KIND (t))
16555 {
e46c7770 16556 case GOMP_MAP_FIRSTPRIVATE_POINTER:
829c6349
CLT
16557 case GOMP_MAP_ALLOC:
16558 case GOMP_MAP_TO:
6e232ba4
JN
16559 case GOMP_MAP_FORCE_DEVICEPTR:
16560 case GOMP_MAP_DEVICE_RESIDENT:
16561 break;
16562
6e232ba4
JN
16563 case GOMP_MAP_LINK:
16564 if (!global_bindings_p ()
16565 && (TREE_STATIC (decl)
16566 || !DECL_EXTERNAL (decl)))
16567 {
16568 error_at (loc,
aa326bfb 16569 "%qD must be a global variable in "
6e232ba4
JN
16570 "%<#pragma acc declare link%>",
16571 decl);
16572 error = true;
16573 continue;
16574 }
16575 break;
16576
16577 default:
16578 if (global_bindings_p ())
16579 {
16580 error_at (loc, "invalid OpenACC clause at file scope");
16581 error = true;
16582 continue;
16583 }
16584 if (DECL_EXTERNAL (decl))
16585 {
16586 error_at (loc,
16587 "invalid use of %<extern%> variable %qD "
16588 "in %<#pragma acc declare%>", decl);
16589 error = true;
16590 continue;
16591 }
16592 else if (TREE_PUBLIC (decl))
16593 {
16594 error_at (loc,
16595 "invalid use of %<global%> variable %qD "
16596 "in %<#pragma acc declare%>", decl);
16597 error = true;
16598 continue;
16599 }
16600 break;
16601 }
16602
13e41d8b
TB
16603 if (!c_check_in_current_scope (decl))
16604 {
16605 error_at (loc,
16606 "%qD must be a variable declared in the same scope as "
16607 "%<#pragma acc declare%>", decl);
16608 error = true;
16609 continue;
16610 }
16611
6e232ba4
JN
16612 if (lookup_attribute ("omp declare target", DECL_ATTRIBUTES (decl))
16613 || lookup_attribute ("omp declare target link",
16614 DECL_ATTRIBUTES (decl)))
16615 {
16616 error_at (loc, "variable %qD used more than once with "
16617 "%<#pragma acc declare%>", decl);
16618 error = true;
16619 continue;
16620 }
16621
16622 if (!error)
16623 {
16624 tree id;
16625
16626 if (OMP_CLAUSE_MAP_KIND (t) == GOMP_MAP_LINK)
16627 id = get_identifier ("omp declare target link");
16628 else
16629 id = get_identifier ("omp declare target");
16630
16631 DECL_ATTRIBUTES (decl)
16632 = tree_cons (id, NULL_TREE, DECL_ATTRIBUTES (decl));
16633
16634 if (global_bindings_p ())
16635 {
16636 symtab_node *node = symtab_node::get (decl);
16637 if (node != NULL)
16638 {
16639 node->offloadable = 1;
688c4de0 16640 if (ENABLE_OFFLOADING)
6e232ba4 16641 {
688c4de0
IV
16642 g->have_offload = true;
16643 if (is_a <varpool_node *> (node))
e6d6ec9e 16644 vec_safe_push (offload_vars, decl);
6e232ba4 16645 }
6e232ba4
JN
16646 }
16647 }
16648 }
16649 }
16650
16651 if (error || global_bindings_p ())
16652 return;
16653
16654 stmt = make_node (OACC_DECLARE);
16655 TREE_TYPE (stmt) = void_type_node;
16656 OACC_DECLARE_CLAUSES (stmt) = clauses;
16657 SET_EXPR_LOCATION (stmt, pragma_loc);
16658
16659 add_stmt (stmt);
16660
16661 return;
16662}
16663
41dbbb37
TS
16664/* OpenACC 2.0:
16665 # pragma acc enter data oacc-enter-data-clause[optseq] new-line
16666
16667 or
16668
16669 # pragma acc exit data oacc-exit-data-clause[optseq] new-line
16670
16671
16672 LOC is the location of the #pragma token.
16673*/
16674
16675#define OACC_ENTER_DATA_CLAUSE_MASK \
16676 ( (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_IF) \
16677 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_ASYNC) \
519d7496 16678 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_ATTACH) \
41dbbb37
TS
16679 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_COPYIN) \
16680 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_CREATE) \
41dbbb37
TS
16681 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_WAIT) )
16682
16683#define OACC_EXIT_DATA_CLAUSE_MASK \
16684 ( (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_IF) \
16685 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_ASYNC) \
16686 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_COPYOUT) \
16687 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_DELETE) \
519d7496 16688 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_DETACH) \
829c6349 16689 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_FINALIZE) \
41dbbb37
TS
16690 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_WAIT) )
16691
16692static void
16693c_parser_oacc_enter_exit_data (c_parser *parser, bool enter)
16694{
16695 location_t loc = c_parser_peek_token (parser)->location;
16696 tree clauses, stmt;
c5af52eb 16697 const char *p = "";
41dbbb37
TS
16698
16699 c_parser_consume_pragma (parser);
16700
c5af52eb 16701 if (c_parser_next_token_is (parser, CPP_NAME))
41dbbb37 16702 {
c5af52eb
CP
16703 p = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
16704 c_parser_consume_token (parser);
41dbbb37
TS
16705 }
16706
41dbbb37
TS
16707 if (strcmp (p, "data") != 0)
16708 {
324ff1a0
JJ
16709 error_at (loc, "expected %<data%> after %<#pragma acc %s%>",
16710 enter ? "enter" : "exit");
c5af52eb 16711 parser->error = true;
41dbbb37
TS
16712 c_parser_skip_to_pragma_eol (parser);
16713 return;
16714 }
16715
41dbbb37
TS
16716 if (enter)
16717 clauses = c_parser_oacc_all_clauses (parser, OACC_ENTER_DATA_CLAUSE_MASK,
16718 "#pragma acc enter data");
16719 else
16720 clauses = c_parser_oacc_all_clauses (parser, OACC_EXIT_DATA_CLAUSE_MASK,
16721 "#pragma acc exit data");
16722
629b3d75 16723 if (omp_find_clause (clauses, OMP_CLAUSE_MAP) == NULL_TREE)
41dbbb37 16724 {
324ff1a0
JJ
16725 error_at (loc, "%<#pragma acc %s data%> has no data movement clause",
16726 enter ? "enter" : "exit");
41dbbb37
TS
16727 return;
16728 }
16729
06aca1d5 16730 stmt = enter ? make_node (OACC_ENTER_DATA) : make_node (OACC_EXIT_DATA);
41dbbb37 16731 TREE_TYPE (stmt) = void_type_node;
b811915d 16732 OMP_STANDALONE_CLAUSES (stmt) = clauses;
41dbbb37
TS
16733 SET_EXPR_LOCATION (stmt, loc);
16734 add_stmt (stmt);
16735}
16736
16737
37d5ad46
JB
16738/* OpenACC 2.0:
16739 # pragma acc host_data oacc-data-clause[optseq] new-line
16740 structured-block
16741*/
16742
16743#define OACC_HOST_DATA_CLAUSE_MASK \
d5c23c6c
TB
16744 ( (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_USE_DEVICE) \
16745 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_IF) \
16746 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_IF_PRESENT) )
37d5ad46
JB
16747
16748static tree
dda1bf61 16749c_parser_oacc_host_data (location_t loc, c_parser *parser, bool *if_p)
37d5ad46
JB
16750{
16751 tree stmt, clauses, block;
16752
16753 clauses = c_parser_oacc_all_clauses (parser, OACC_HOST_DATA_CLAUSE_MASK,
16754 "#pragma acc host_data");
16755
16756 block = c_begin_omp_parallel ();
dda1bf61 16757 add_stmt (c_parser_omp_structured_block (parser, if_p));
37d5ad46
JB
16758 stmt = c_finish_oacc_host_data (loc, clauses, block);
16759 return stmt;
16760}
16761
16762
41dbbb37
TS
16763/* OpenACC 2.0:
16764
16765 # pragma acc loop oacc-loop-clause[optseq] new-line
16766 structured-block
16767
16768 LOC is the location of the #pragma token.
16769*/
16770
16771#define OACC_LOOP_CLAUSE_MASK \
16772 ( (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_COLLAPSE) \
7a5e4956
CP
16773 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_PRIVATE) \
16774 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_REDUCTION) \
765dd391
CP
16775 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_GANG) \
16776 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_WORKER) \
16777 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_VECTOR) \
16778 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_AUTO) \
7a5e4956 16779 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_INDEPENDENT) \
765dd391 16780 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_SEQ) \
7a5e4956 16781 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_TILE) )
41dbbb37 16782static tree
88bae6f4 16783c_parser_oacc_loop (location_t loc, c_parser *parser, char *p_name,
dda1bf61 16784 omp_clause_mask mask, tree *cclauses, bool *if_p)
41dbbb37 16785{
e7ff0319
CP
16786 bool is_parallel = ((mask >> PRAGMA_OACC_CLAUSE_REDUCTION) & 1) == 1;
16787
41dbbb37 16788 strcat (p_name, " loop");
88bae6f4 16789 mask |= OACC_LOOP_CLAUSE_MASK;
41dbbb37 16790
88bae6f4
TS
16791 tree clauses = c_parser_oacc_all_clauses (parser, mask, p_name,
16792 cclauses == NULL);
16793 if (cclauses)
16794 {
e7ff0319 16795 clauses = c_oacc_split_loop_clauses (clauses, cclauses, is_parallel);
88bae6f4 16796 if (*cclauses)
77886428 16797 *cclauses = c_finish_omp_clauses (*cclauses, C_ORT_ACC);
88bae6f4 16798 if (clauses)
77886428 16799 clauses = c_finish_omp_clauses (clauses, C_ORT_ACC);
88bae6f4 16800 }
41dbbb37 16801
88bae6f4 16802 tree block = c_begin_compound_stmt (true);
dda1bf61
JJ
16803 tree stmt = c_parser_omp_for_loop (loc, parser, OACC_LOOP, clauses, NULL,
16804 if_p);
41dbbb37
TS
16805 block = c_end_compound_stmt (loc, block, true);
16806 add_stmt (block);
16807
16808 return stmt;
16809}
16810
16811/* OpenACC 2.0:
88bae6f4
TS
16812 # pragma acc kernels oacc-kernels-clause[optseq] new-line
16813 structured-block
16814
16815 or
16816
41dbbb37
TS
16817 # pragma acc parallel oacc-parallel-clause[optseq] new-line
16818 structured-block
16819
62aee289
MR
16820 OpenACC 2.6:
16821
16822 # pragma acc serial oacc-serial-clause[optseq] new-line
16823 structured-block
16824
41dbbb37
TS
16825 LOC is the location of the #pragma token.
16826*/
16827
88bae6f4
TS
16828#define OACC_KERNELS_CLAUSE_MASK \
16829 ( (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_ASYNC) \
519d7496 16830 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_ATTACH) \
88bae6f4
TS
16831 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_COPY) \
16832 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_COPYIN) \
16833 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_COPYOUT) \
16834 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_CREATE) \
7a5e4956 16835 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_DEFAULT) \
88bae6f4
TS
16836 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_DEVICEPTR) \
16837 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_IF) \
a6163563 16838 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_NO_CREATE) \
fd71a9a2
TS
16839 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_NUM_GANGS) \
16840 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_NUM_WORKERS) \
88bae6f4 16841 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_PRESENT) \
fd71a9a2 16842 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_VECTOR_LENGTH) \
88bae6f4
TS
16843 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_WAIT) )
16844
41dbbb37
TS
16845#define OACC_PARALLEL_CLAUSE_MASK \
16846 ( (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_ASYNC) \
519d7496 16847 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_ATTACH) \
41dbbb37
TS
16848 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_COPY) \
16849 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_COPYIN) \
16850 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_COPYOUT) \
16851 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_CREATE) \
7a5e4956 16852 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_DEFAULT) \
41dbbb37
TS
16853 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_DEVICEPTR) \
16854 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_IF) \
a6163563 16855 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_NO_CREATE) \
7a5e4956
CP
16856 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_PRIVATE) \
16857 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_FIRSTPRIVATE) \
41dbbb37
TS
16858 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_NUM_GANGS) \
16859 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_NUM_WORKERS) \
16860 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_PRESENT) \
41dbbb37
TS
16861 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_REDUCTION) \
16862 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_VECTOR_LENGTH) \
16863 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_WAIT) )
16864
62aee289
MR
16865#define OACC_SERIAL_CLAUSE_MASK \
16866 ( (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_ASYNC) \
519d7496 16867 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_ATTACH) \
62aee289
MR
16868 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_COPY) \
16869 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_COPYIN) \
16870 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_COPYOUT) \
16871 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_CREATE) \
16872 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_DEFAULT) \
16873 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_DEVICEPTR) \
16874 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_IF) \
a6163563 16875 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_NO_CREATE) \
62aee289
MR
16876 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_PRIVATE) \
16877 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_FIRSTPRIVATE) \
16878 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_PRESENT) \
16879 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_REDUCTION) \
16880 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_WAIT) )
16881
41dbbb37 16882static tree
62aee289
MR
16883c_parser_oacc_compute (location_t loc, c_parser *parser,
16884 enum pragma_kind p_kind, char *p_name, bool *if_p)
41dbbb37 16885{
88bae6f4
TS
16886 omp_clause_mask mask;
16887 enum tree_code code;
16888 switch (p_kind)
16889 {
16890 case PRAGMA_OACC_KERNELS:
16891 strcat (p_name, " kernels");
16892 mask = OACC_KERNELS_CLAUSE_MASK;
16893 code = OACC_KERNELS;
16894 break;
16895 case PRAGMA_OACC_PARALLEL:
16896 strcat (p_name, " parallel");
16897 mask = OACC_PARALLEL_CLAUSE_MASK;
16898 code = OACC_PARALLEL;
16899 break;
62aee289
MR
16900 case PRAGMA_OACC_SERIAL:
16901 strcat (p_name, " serial");
16902 mask = OACC_SERIAL_CLAUSE_MASK;
16903 code = OACC_SERIAL;
16904 break;
88bae6f4
TS
16905 default:
16906 gcc_unreachable ();
16907 }
41dbbb37
TS
16908
16909 if (c_parser_next_token_is (parser, CPP_NAME))
16910 {
16911 const char *p = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
16912 if (strcmp (p, "loop") == 0)
16913 {
16914 c_parser_consume_token (parser);
88bae6f4
TS
16915 tree block = c_begin_omp_parallel ();
16916 tree clauses;
dda1bf61 16917 c_parser_oacc_loop (loc, parser, p_name, mask, &clauses, if_p);
88bae6f4 16918 return c_finish_omp_construct (loc, code, block, clauses);
41dbbb37
TS
16919 }
16920 }
16921
88bae6f4 16922 tree clauses = c_parser_oacc_all_clauses (parser, mask, p_name);
41dbbb37 16923
88bae6f4 16924 tree block = c_begin_omp_parallel ();
dda1bf61 16925 add_stmt (c_parser_omp_structured_block (parser, if_p));
41dbbb37 16926
88bae6f4 16927 return c_finish_omp_construct (loc, code, block, clauses);
41dbbb37
TS
16928}
16929
3a40d81d
NS
16930/* OpenACC 2.0:
16931 # pragma acc routine oacc-routine-clause[optseq] new-line
16932 function-definition
16933
16934 # pragma acc routine ( name ) oacc-routine-clause[optseq] new-line
16935*/
16936
16937#define OACC_ROUTINE_CLAUSE_MASK \
16938 ( (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_GANG) \
16939 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_WORKER) \
16940 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_VECTOR) \
16941 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_SEQ) )
16942
16943/* Parse an OpenACC routine directive. For named directives, we apply
16944 immediately to the named function. For unnamed ones we then parse
16945 a declaration or definition, which must be for a function. */
16946
16947static void
16948c_parser_oacc_routine (c_parser *parser, enum pragma_context context)
16949{
ae9281fc
TS
16950 gcc_checking_assert (context == pragma_external);
16951
0b212d8c 16952 oacc_routine_data data;
ae9281fc
TS
16953 data.error_seen = false;
16954 data.fndecl_seen = false;
0b212d8c 16955 data.loc = c_parser_peek_token (parser)->location;
3a40d81d
NS
16956
16957 c_parser_consume_pragma (parser);
16958
ae9281fc
TS
16959 /* Look for optional '( name )'. */
16960 if (c_parser_next_token_is (parser, CPP_OPEN_PAREN))
3a40d81d 16961 {
ae9281fc 16962 c_parser_consume_token (parser); /* '(' */
3a40d81d 16963
ae9281fc
TS
16964 tree decl = NULL_TREE;
16965 c_token *name_token = c_parser_peek_token (parser);
16966 location_t name_loc = name_token->location;
16967 if (name_token->type == CPP_NAME
16968 && (name_token->id_kind == C_ID_ID
16969 || name_token->id_kind == C_ID_TYPENAME))
3a40d81d 16970 {
ae9281fc 16971 decl = lookup_name (name_token->value);
3a40d81d 16972 if (!decl)
ae9281fc
TS
16973 error_at (name_loc,
16974 "%qE has not been declared", name_token->value);
a04e69c0 16975 c_parser_consume_token (parser);
3a40d81d
NS
16976 }
16977 else
16978 c_parser_error (parser, "expected function name");
16979
a04e69c0
TS
16980 if (!decl
16981 || !c_parser_require (parser, CPP_CLOSE_PAREN, "expected %<)%>"))
16982 {
16983 c_parser_skip_to_pragma_eol (parser, false);
16984 return;
16985 }
ae9281fc
TS
16986
16987 data.clauses
16988 = c_parser_oacc_all_clauses (parser, OACC_ROUTINE_CLAUSE_MASK,
16989 "#pragma acc routine");
5bf04509
TS
16990 /* The clauses are in reverse order; fix that to make later diagnostic
16991 emission easier. */
16992 data.clauses = nreverse (data.clauses);
ae9281fc
TS
16993
16994 if (TREE_CODE (decl) != FUNCTION_DECL)
16995 {
16996 error_at (name_loc, "%qD does not refer to a function", decl);
16997 return;
16998 }
16999
17000 c_finish_oacc_routine (&data, decl, false);
3a40d81d 17001 }
ae9281fc
TS
17002 else /* No optional '( name )'. */
17003 {
17004 data.clauses
17005 = c_parser_oacc_all_clauses (parser, OACC_ROUTINE_CLAUSE_MASK,
17006 "#pragma acc routine");
5bf04509
TS
17007 /* The clauses are in reverse order; fix that to make later diagnostic
17008 emission easier. */
17009 data.clauses = nreverse (data.clauses);
3a40d81d 17010
ae9281fc
TS
17011 /* Emit a helpful diagnostic if there's another pragma following this
17012 one. Also don't allow a static assertion declaration, as in the
17013 following we'll just parse a *single* "declaration or function
17014 definition", and the static assertion counts an one. */
17015 if (c_parser_next_token_is (parser, CPP_PRAGMA)
17016 || c_parser_next_token_is_keyword (parser, RID_STATIC_ASSERT))
17017 {
17018 error_at (data.loc,
17019 "%<#pragma acc routine%> not immediately followed by"
17020 " function declaration or definition");
17021 /* ..., and then just keep going. */
17022 return;
17023 }
17024
17025 /* We only have to consider the pragma_external case here. */
17026 if (c_parser_next_token_is (parser, CPP_KEYWORD)
17027 && c_parser_peek_token (parser)->keyword == RID_EXTENSION)
17028 {
17029 int ext = disable_extension_diagnostics ();
17030 do
17031 c_parser_consume_token (parser);
17032 while (c_parser_next_token_is (parser, CPP_KEYWORD)
17033 && c_parser_peek_token (parser)->keyword == RID_EXTENSION);
17034 c_parser_declaration_or_fndef (parser, true, true, true, false, true,
4e03c3a7 17035 NULL, vNULL, false, NULL, &data);
ae9281fc
TS
17036 restore_extension_diagnostics (ext);
17037 }
17038 else
17039 c_parser_declaration_or_fndef (parser, true, true, true, false, true,
4e03c3a7 17040 NULL, vNULL, false, NULL, &data);
ae9281fc 17041 }
3a40d81d
NS
17042}
17043
0b212d8c
TS
17044/* Finalize an OpenACC routine pragma, applying it to FNDECL.
17045 IS_DEFN is true if we're applying it to the definition. */
3a40d81d
NS
17046
17047static void
0b212d8c 17048c_finish_oacc_routine (struct oacc_routine_data *data, tree fndecl,
ae9281fc 17049 bool is_defn)
3a40d81d 17050{
ae9281fc
TS
17051 /* Keep going if we're in error reporting mode. */
17052 if (data->error_seen
17053 || fndecl == error_mark_node)
17054 return;
17055
17056 if (data->fndecl_seen)
3a40d81d 17057 {
ae9281fc
TS
17058 error_at (data->loc,
17059 "%<#pragma acc routine%> not immediately followed by"
17060 " a single function declaration or definition");
17061 data->error_seen = true;
17062 return;
17063 }
17064 if (fndecl == NULL_TREE || TREE_CODE (fndecl) != FUNCTION_DECL)
17065 {
17066 error_at (data->loc,
17067 "%<#pragma acc routine%> not immediately followed by"
17068 " function declaration or definition");
17069 data->error_seen = true;
3a40d81d
NS
17070 return;
17071 }
17072
b48f44bf
TS
17073 int compatible
17074 = oacc_verify_routine_clauses (fndecl, &data->clauses, data->loc,
17075 "#pragma acc routine");
17076 if (compatible < 0)
ae9281fc 17077 {
ae9281fc
TS
17078 data->error_seen = true;
17079 return;
17080 }
b48f44bf 17081 if (compatible > 0)
ae9281fc 17082 {
ae9281fc 17083 }
b48f44bf
TS
17084 else
17085 {
17086 if (TREE_USED (fndecl) || (!is_defn && DECL_SAVED_TREE (fndecl)))
17087 {
17088 error_at (data->loc,
17089 TREE_USED (fndecl)
17090 ? G_("%<#pragma acc routine%> must be applied before use")
17091 : G_("%<#pragma acc routine%> must be applied before"
17092 " definition"));
17093 data->error_seen = true;
17094 return;
17095 }
3a40d81d 17096
b48f44bf
TS
17097 /* Set the routine's level of parallelism. */
17098 tree dims = oacc_build_routine_dims (data->clauses);
17099 oacc_replace_fn_attrib (fndecl, dims);
3a40d81d 17100
b48f44bf
TS
17101 /* Add an "omp declare target" attribute. */
17102 DECL_ATTRIBUTES (fndecl)
17103 = tree_cons (get_identifier ("omp declare target"),
17104 data->clauses, DECL_ATTRIBUTES (fndecl));
17105 }
ae9281fc
TS
17106
17107 /* Remember that we've used this "#pragma acc routine". */
17108 data->fndecl_seen = true;
3a40d81d
NS
17109}
17110
41dbbb37
TS
17111/* OpenACC 2.0:
17112 # pragma acc update oacc-update-clause[optseq] new-line
17113*/
17114
17115#define OACC_UPDATE_CLAUSE_MASK \
17116 ( (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_ASYNC) \
17117 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_DEVICE) \
17118 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_HOST) \
17119 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_IF) \
829c6349 17120 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_IF_PRESENT) \
41dbbb37
TS
17121 | (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_WAIT) )
17122
17123static void
17124c_parser_oacc_update (c_parser *parser)
17125{
17126 location_t loc = c_parser_peek_token (parser)->location;
17127
17128 c_parser_consume_pragma (parser);
17129
17130 tree clauses = c_parser_oacc_all_clauses (parser, OACC_UPDATE_CLAUSE_MASK,
17131 "#pragma acc update");
629b3d75 17132 if (omp_find_clause (clauses, OMP_CLAUSE_MAP) == NULL_TREE)
41dbbb37
TS
17133 {
17134 error_at (loc,
17135 "%<#pragma acc update%> must contain at least one "
7a5e4956 17136 "%<device%> or %<host%> or %<self%> clause");
41dbbb37
TS
17137 return;
17138 }
17139
17140 if (parser->error)
17141 return;
17142
17143 tree stmt = make_node (OACC_UPDATE);
17144 TREE_TYPE (stmt) = void_type_node;
17145 OACC_UPDATE_CLAUSES (stmt) = clauses;
17146 SET_EXPR_LOCATION (stmt, loc);
17147 add_stmt (stmt);
17148}
17149
17150/* OpenACC 2.0:
17151 # pragma acc wait [(intseq)] oacc-wait-clause[optseq] new-line
17152
17153 LOC is the location of the #pragma token.
17154*/
17155
17156#define OACC_WAIT_CLAUSE_MASK \
17157 ( (OMP_CLAUSE_MASK_1 << PRAGMA_OACC_CLAUSE_ASYNC) )
17158
17159static tree
17160c_parser_oacc_wait (location_t loc, c_parser *parser, char *p_name)
17161{
17162 tree clauses, list = NULL_TREE, stmt = NULL_TREE;
17163
17164 if (c_parser_peek_token (parser)->type == CPP_OPEN_PAREN)
17165 list = c_parser_oacc_wait_list (parser, loc, list);
17166
17167 strcpy (p_name, " wait");
17168 clauses = c_parser_oacc_all_clauses (parser, OACC_WAIT_CLAUSE_MASK, p_name);
17169 stmt = c_finish_oacc_wait (loc, list, clauses);
04d2fbcc 17170 add_stmt (stmt);
41dbbb37
TS
17171
17172 return stmt;
17173}
17174
acf0174b
JJ
17175/* OpenMP 2.5:
17176 # pragma omp atomic new-line
17177 expression-stmt
17178
17179 expression-stmt:
17180 x binop= expr | x++ | ++x | x-- | --x
17181 binop:
17182 +, *, -, /, &, ^, |, <<, >>
17183
17184 where x is an lvalue expression with scalar type.
17185
17186 OpenMP 3.1:
17187 # pragma omp atomic new-line
17188 update-stmt
17189
17190 # pragma omp atomic read new-line
17191 read-stmt
17192
17193 # pragma omp atomic write new-line
17194 write-stmt
17195
17196 # pragma omp atomic update new-line
17197 update-stmt
17198
17199 # pragma omp atomic capture new-line
17200 capture-stmt
17201
17202 # pragma omp atomic capture new-line
17203 capture-block
17204
17205 read-stmt:
17206 v = x
17207 write-stmt:
17208 x = expr
17209 update-stmt:
17210 expression-stmt | x = x binop expr
17211 capture-stmt:
17212 v = expression-stmt
17213 capture-block:
17214 { v = x; update-stmt; } | { update-stmt; v = x; }
17215
17216 OpenMP 4.0:
17217 update-stmt:
17218 expression-stmt | x = x binop expr | x = expr binop x
17219 capture-stmt:
17220 v = update-stmt
17221 capture-block:
17222 { v = x; update-stmt; } | { update-stmt; v = x; } | { v = x; x = expr; }
17223
17224 where x and v are lvalue expressions with scalar type.
17225
17226 LOC is the location of the #pragma token. */
17227
17228static void
17229c_parser_omp_atomic (location_t loc, c_parser *parser)
17230{
17231 tree lhs = NULL_TREE, rhs = NULL_TREE, v = NULL_TREE;
17232 tree lhs1 = NULL_TREE, rhs1 = NULL_TREE;
17233 tree stmt, orig_lhs, unfolded_lhs = NULL_TREE, unfolded_lhs1 = NULL_TREE;
28567c40
JJ
17234 enum tree_code code = ERROR_MARK, opcode = NOP_EXPR;
17235 enum omp_memory_order memory_order = OMP_MEMORY_ORDER_UNSPECIFIED;
acf0174b
JJ
17236 struct c_expr expr;
17237 location_t eloc;
17238 bool structured_block = false;
17239 bool swapped = false;
f4b189d5 17240 bool non_lvalue_p;
28567c40
JJ
17241 bool first = true;
17242 tree clauses = NULL_TREE;
acf0174b 17243
28567c40 17244 while (c_parser_next_token_is_not (parser, CPP_PRAGMA_EOL))
acf0174b 17245 {
28567c40 17246 if (!first && c_parser_next_token_is (parser, CPP_COMMA))
42056eac
JJ
17247 c_parser_consume_token (parser);
17248
28567c40
JJ
17249 first = false;
17250
42056eac 17251 if (c_parser_next_token_is (parser, CPP_NAME))
acf0174b 17252 {
42056eac
JJ
17253 const char *p
17254 = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
28567c40
JJ
17255 location_t cloc = c_parser_peek_token (parser)->location;
17256 enum tree_code new_code = ERROR_MARK;
17257 enum omp_memory_order new_memory_order
17258 = OMP_MEMORY_ORDER_UNSPECIFIED;
17259
17260 if (!strcmp (p, "read"))
17261 new_code = OMP_ATOMIC_READ;
17262 else if (!strcmp (p, "write"))
17263 new_code = NOP_EXPR;
17264 else if (!strcmp (p, "update"))
17265 new_code = OMP_ATOMIC;
17266 else if (!strcmp (p, "capture"))
17267 new_code = OMP_ATOMIC_CAPTURE_NEW;
17268 else if (!strcmp (p, "seq_cst"))
17269 new_memory_order = OMP_MEMORY_ORDER_SEQ_CST;
17270 else if (!strcmp (p, "acq_rel"))
17271 new_memory_order = OMP_MEMORY_ORDER_ACQ_REL;
17272 else if (!strcmp (p, "release"))
17273 new_memory_order = OMP_MEMORY_ORDER_RELEASE;
17274 else if (!strcmp (p, "acquire"))
17275 new_memory_order = OMP_MEMORY_ORDER_ACQUIRE;
17276 else if (!strcmp (p, "relaxed"))
17277 new_memory_order = OMP_MEMORY_ORDER_RELAXED;
17278 else if (!strcmp (p, "hint"))
42056eac 17279 {
42056eac 17280 c_parser_consume_token (parser);
28567c40
JJ
17281 clauses = c_parser_omp_clause_hint (parser, clauses);
17282 continue;
17283 }
17284 else
17285 {
17286 p = NULL;
17287 error_at (cloc, "expected %<read%>, %<write%>, %<update%>, "
17288 "%<capture%>, %<seq_cst%>, %<acq_rel%>, "
17289 "%<release%>, %<relaxed%> or %<hint%> clause");
17290 }
17291 if (p)
17292 {
17293 if (new_code != ERROR_MARK)
17294 {
17295 if (code != ERROR_MARK)
17296 error_at (cloc, "too many atomic clauses");
17297 else
17298 code = new_code;
17299 }
17300 else if (new_memory_order != OMP_MEMORY_ORDER_UNSPECIFIED)
17301 {
17302 if (memory_order != OMP_MEMORY_ORDER_UNSPECIFIED)
17303 error_at (cloc, "too many memory order clauses");
17304 else
17305 memory_order = new_memory_order;
17306 }
17307 c_parser_consume_token (parser);
17308 continue;
17309 }
17310 }
17311 break;
17312 }
17313 c_parser_skip_to_pragma_eol (parser);
17314
17315 if (code == ERROR_MARK)
17316 code = OMP_ATOMIC;
17317 if (memory_order == OMP_MEMORY_ORDER_UNSPECIFIED)
17318 {
17319 omp_requires_mask
17320 = (enum omp_requires) (omp_requires_mask
17321 | OMP_REQUIRES_ATOMIC_DEFAULT_MEM_ORDER_USED);
17322 switch ((enum omp_memory_order)
17323 (omp_requires_mask & OMP_REQUIRES_ATOMIC_DEFAULT_MEM_ORDER))
17324 {
17325 case OMP_MEMORY_ORDER_UNSPECIFIED:
17326 case OMP_MEMORY_ORDER_RELAXED:
17327 memory_order = OMP_MEMORY_ORDER_RELAXED;
17328 break;
17329 case OMP_MEMORY_ORDER_SEQ_CST:
17330 memory_order = OMP_MEMORY_ORDER_SEQ_CST;
17331 break;
17332 case OMP_MEMORY_ORDER_ACQ_REL:
17333 switch (code)
17334 {
17335 case OMP_ATOMIC_READ:
17336 memory_order = OMP_MEMORY_ORDER_ACQUIRE;
17337 break;
17338 case NOP_EXPR: /* atomic write */
17339 case OMP_ATOMIC:
17340 memory_order = OMP_MEMORY_ORDER_RELEASE;
17341 break;
17342 default:
17343 memory_order = OMP_MEMORY_ORDER_ACQ_REL;
17344 break;
42056eac 17345 }
28567c40
JJ
17346 break;
17347 default:
17348 gcc_unreachable ();
acf0174b
JJ
17349 }
17350 }
28567c40
JJ
17351 else
17352 switch (code)
17353 {
17354 case OMP_ATOMIC_READ:
17355 if (memory_order == OMP_MEMORY_ORDER_ACQ_REL
17356 || memory_order == OMP_MEMORY_ORDER_RELEASE)
17357 {
17358 error_at (loc, "%<#pragma omp atomic read%> incompatible with "
17359 "%<acq_rel%> or %<release%> clauses");
17360 memory_order = OMP_MEMORY_ORDER_SEQ_CST;
17361 }
17362 break;
17363 case NOP_EXPR: /* atomic write */
17364 if (memory_order == OMP_MEMORY_ORDER_ACQ_REL
17365 || memory_order == OMP_MEMORY_ORDER_ACQUIRE)
17366 {
17367 error_at (loc, "%<#pragma omp atomic write%> incompatible with "
17368 "%<acq_rel%> or %<acquire%> clauses");
17369 memory_order = OMP_MEMORY_ORDER_SEQ_CST;
17370 }
17371 break;
17372 case OMP_ATOMIC:
17373 if (memory_order == OMP_MEMORY_ORDER_ACQ_REL
17374 || memory_order == OMP_MEMORY_ORDER_ACQUIRE)
17375 {
17376 error_at (loc, "%<#pragma omp atomic update%> incompatible with "
17377 "%<acq_rel%> or %<acquire%> clauses");
17378 memory_order = OMP_MEMORY_ORDER_SEQ_CST;
17379 }
17380 break;
17381 default:
17382 break;
17383 }
acf0174b
JJ
17384
17385 switch (code)
17386 {
17387 case OMP_ATOMIC_READ:
17388 case NOP_EXPR: /* atomic write */
f4b189d5
JJ
17389 v = c_parser_cast_expression (parser, NULL).value;
17390 non_lvalue_p = !lvalue_p (v);
f9c59f7e 17391 v = c_fully_fold (v, false, NULL, true);
acf0174b
JJ
17392 if (v == error_mark_node)
17393 goto saw_error;
f4b189d5
JJ
17394 if (non_lvalue_p)
17395 v = non_lvalue (v);
acf0174b
JJ
17396 loc = c_parser_peek_token (parser)->location;
17397 if (!c_parser_require (parser, CPP_EQ, "expected %<=%>"))
17398 goto saw_error;
17399 if (code == NOP_EXPR)
f4b189d5
JJ
17400 {
17401 lhs = c_parser_expression (parser).value;
17402 lhs = c_fully_fold (lhs, false, NULL);
17403 if (lhs == error_mark_node)
17404 goto saw_error;
17405 }
acf0174b 17406 else
f4b189d5
JJ
17407 {
17408 lhs = c_parser_cast_expression (parser, NULL).value;
17409 non_lvalue_p = !lvalue_p (lhs);
f9c59f7e 17410 lhs = c_fully_fold (lhs, false, NULL, true);
f4b189d5
JJ
17411 if (lhs == error_mark_node)
17412 goto saw_error;
17413 if (non_lvalue_p)
17414 lhs = non_lvalue (lhs);
17415 }
acf0174b
JJ
17416 if (code == NOP_EXPR)
17417 {
17418 /* atomic write is represented by OMP_ATOMIC with NOP_EXPR
17419 opcode. */
17420 code = OMP_ATOMIC;
17421 rhs = lhs;
17422 lhs = v;
17423 v = NULL_TREE;
17424 }
17425 goto done;
17426 case OMP_ATOMIC_CAPTURE_NEW:
17427 if (c_parser_next_token_is (parser, CPP_OPEN_BRACE))
17428 {
17429 c_parser_consume_token (parser);
17430 structured_block = true;
17431 }
17432 else
17433 {
f4b189d5
JJ
17434 v = c_parser_cast_expression (parser, NULL).value;
17435 non_lvalue_p = !lvalue_p (v);
f9c59f7e 17436 v = c_fully_fold (v, false, NULL, true);
acf0174b
JJ
17437 if (v == error_mark_node)
17438 goto saw_error;
f4b189d5
JJ
17439 if (non_lvalue_p)
17440 v = non_lvalue (v);
acf0174b
JJ
17441 if (!c_parser_require (parser, CPP_EQ, "expected %<=%>"))
17442 goto saw_error;
17443 }
17444 break;
17445 default:
17446 break;
17447 }
17448
17449 /* For structured_block case we don't know yet whether
17450 old or new x should be captured. */
17451restart:
17452 eloc = c_parser_peek_token (parser)->location;
f4b189d5 17453 expr = c_parser_cast_expression (parser, NULL);
acf0174b
JJ
17454 lhs = expr.value;
17455 expr = default_function_array_conversion (eloc, expr);
17456 unfolded_lhs = expr.value;
f9c59f7e 17457 lhs = c_fully_fold (lhs, false, NULL, true);
acf0174b
JJ
17458 orig_lhs = lhs;
17459 switch (TREE_CODE (lhs))
17460 {
17461 case ERROR_MARK:
17462 saw_error:
17463 c_parser_skip_to_end_of_block_or_statement (parser);
17464 if (structured_block)
17465 {
17466 if (c_parser_next_token_is (parser, CPP_CLOSE_BRACE))
17467 c_parser_consume_token (parser);
17468 else if (code == OMP_ATOMIC_CAPTURE_NEW)
17469 {
17470 c_parser_skip_to_end_of_block_or_statement (parser);
17471 if (c_parser_next_token_is (parser, CPP_CLOSE_BRACE))
17472 c_parser_consume_token (parser);
17473 }
17474 }
17475 return;
17476
17477 case POSTINCREMENT_EXPR:
17478 if (code == OMP_ATOMIC_CAPTURE_NEW && !structured_block)
17479 code = OMP_ATOMIC_CAPTURE_OLD;
17480 /* FALLTHROUGH */
17481 case PREINCREMENT_EXPR:
17482 lhs = TREE_OPERAND (lhs, 0);
17483 unfolded_lhs = NULL_TREE;
17484 opcode = PLUS_EXPR;
17485 rhs = integer_one_node;
17486 break;
17487
17488 case POSTDECREMENT_EXPR:
17489 if (code == OMP_ATOMIC_CAPTURE_NEW && !structured_block)
17490 code = OMP_ATOMIC_CAPTURE_OLD;
17491 /* FALLTHROUGH */
17492 case PREDECREMENT_EXPR:
17493 lhs = TREE_OPERAND (lhs, 0);
17494 unfolded_lhs = NULL_TREE;
17495 opcode = MINUS_EXPR;
17496 rhs = integer_one_node;
17497 break;
17498
17499 case COMPOUND_EXPR:
17500 if (TREE_CODE (TREE_OPERAND (lhs, 0)) == SAVE_EXPR
17501 && TREE_CODE (TREE_OPERAND (lhs, 1)) == COMPOUND_EXPR
17502 && TREE_CODE (TREE_OPERAND (TREE_OPERAND (lhs, 1), 0)) == MODIFY_EXPR
17503 && TREE_OPERAND (TREE_OPERAND (lhs, 1), 1) == TREE_OPERAND (lhs, 0)
17504 && TREE_CODE (TREE_TYPE (TREE_OPERAND (TREE_OPERAND
17505 (TREE_OPERAND (lhs, 1), 0), 0)))
17506 == BOOLEAN_TYPE)
17507 /* Undo effects of boolean_increment for post {in,de}crement. */
17508 lhs = TREE_OPERAND (TREE_OPERAND (lhs, 1), 0);
17509 /* FALLTHRU */
17510 case MODIFY_EXPR:
17511 if (TREE_CODE (lhs) == MODIFY_EXPR
17512 && TREE_CODE (TREE_TYPE (TREE_OPERAND (lhs, 0))) == BOOLEAN_TYPE)
17513 {
17514 /* Undo effects of boolean_increment. */
17515 if (integer_onep (TREE_OPERAND (lhs, 1)))
17516 {
17517 /* This is pre or post increment. */
17518 rhs = TREE_OPERAND (lhs, 1);
17519 lhs = TREE_OPERAND (lhs, 0);
17520 unfolded_lhs = NULL_TREE;
17521 opcode = NOP_EXPR;
17522 if (code == OMP_ATOMIC_CAPTURE_NEW
17523 && !structured_block
17524 && TREE_CODE (orig_lhs) == COMPOUND_EXPR)
17525 code = OMP_ATOMIC_CAPTURE_OLD;
17526 break;
17527 }
17528 if (TREE_CODE (TREE_OPERAND (lhs, 1)) == TRUTH_NOT_EXPR
17529 && TREE_OPERAND (lhs, 0)
17530 == TREE_OPERAND (TREE_OPERAND (lhs, 1), 0))
17531 {
17532 /* This is pre or post decrement. */
17533 rhs = TREE_OPERAND (lhs, 1);
17534 lhs = TREE_OPERAND (lhs, 0);
17535 unfolded_lhs = NULL_TREE;
17536 opcode = NOP_EXPR;
17537 if (code == OMP_ATOMIC_CAPTURE_NEW
17538 && !structured_block
17539 && TREE_CODE (orig_lhs) == COMPOUND_EXPR)
17540 code = OMP_ATOMIC_CAPTURE_OLD;
17541 break;
17542 }
17543 }
17544 /* FALLTHRU */
17545 default:
f4b189d5
JJ
17546 if (!lvalue_p (unfolded_lhs))
17547 lhs = non_lvalue (lhs);
acf0174b
JJ
17548 switch (c_parser_peek_token (parser)->type)
17549 {
17550 case CPP_MULT_EQ:
17551 opcode = MULT_EXPR;
17552 break;
17553 case CPP_DIV_EQ:
17554 opcode = TRUNC_DIV_EXPR;
17555 break;
17556 case CPP_PLUS_EQ:
17557 opcode = PLUS_EXPR;
17558 break;
17559 case CPP_MINUS_EQ:
17560 opcode = MINUS_EXPR;
17561 break;
17562 case CPP_LSHIFT_EQ:
17563 opcode = LSHIFT_EXPR;
17564 break;
17565 case CPP_RSHIFT_EQ:
17566 opcode = RSHIFT_EXPR;
17567 break;
17568 case CPP_AND_EQ:
17569 opcode = BIT_AND_EXPR;
17570 break;
17571 case CPP_OR_EQ:
17572 opcode = BIT_IOR_EXPR;
17573 break;
17574 case CPP_XOR_EQ:
17575 opcode = BIT_XOR_EXPR;
17576 break;
17577 case CPP_EQ:
17578 c_parser_consume_token (parser);
17579 eloc = c_parser_peek_token (parser)->location;
17580 expr = c_parser_expr_no_commas (parser, NULL, unfolded_lhs);
17581 rhs1 = expr.value;
17582 switch (TREE_CODE (rhs1))
17583 {
17584 case MULT_EXPR:
17585 case TRUNC_DIV_EXPR:
4886ec8e 17586 case RDIV_EXPR:
acf0174b
JJ
17587 case PLUS_EXPR:
17588 case MINUS_EXPR:
17589 case LSHIFT_EXPR:
17590 case RSHIFT_EXPR:
17591 case BIT_AND_EXPR:
17592 case BIT_IOR_EXPR:
17593 case BIT_XOR_EXPR:
17594 if (c_tree_equal (TREE_OPERAND (rhs1, 0), unfolded_lhs))
17595 {
17596 opcode = TREE_CODE (rhs1);
f9c59f7e
JJ
17597 rhs = c_fully_fold (TREE_OPERAND (rhs1, 1), false, NULL,
17598 true);
17599 rhs1 = c_fully_fold (TREE_OPERAND (rhs1, 0), false, NULL,
17600 true);
acf0174b
JJ
17601 goto stmt_done;
17602 }
17603 if (c_tree_equal (TREE_OPERAND (rhs1, 1), unfolded_lhs))
17604 {
17605 opcode = TREE_CODE (rhs1);
f9c59f7e
JJ
17606 rhs = c_fully_fold (TREE_OPERAND (rhs1, 0), false, NULL,
17607 true);
17608 rhs1 = c_fully_fold (TREE_OPERAND (rhs1, 1), false, NULL,
17609 true);
acf0174b
JJ
17610 swapped = !commutative_tree_code (opcode);
17611 goto stmt_done;
17612 }
17613 break;
17614 case ERROR_MARK:
17615 goto saw_error;
17616 default:
17617 break;
17618 }
17619 if (c_parser_peek_token (parser)->type == CPP_SEMICOLON)
17620 {
17621 if (structured_block && code == OMP_ATOMIC_CAPTURE_NEW)
17622 {
17623 code = OMP_ATOMIC_CAPTURE_OLD;
17624 v = lhs;
17625 lhs = NULL_TREE;
17626 expr = default_function_array_read_conversion (eloc, expr);
17627 unfolded_lhs1 = expr.value;
f9c59f7e 17628 lhs1 = c_fully_fold (unfolded_lhs1, false, NULL, true);
acf0174b
JJ
17629 rhs1 = NULL_TREE;
17630 c_parser_consume_token (parser);
17631 goto restart;
17632 }
17633 if (structured_block)
17634 {
17635 opcode = NOP_EXPR;
17636 expr = default_function_array_read_conversion (eloc, expr);
f9c59f7e 17637 rhs = c_fully_fold (expr.value, false, NULL, true);
acf0174b
JJ
17638 rhs1 = NULL_TREE;
17639 goto stmt_done;
17640 }
17641 }
17642 c_parser_error (parser, "invalid form of %<#pragma omp atomic%>");
17643 goto saw_error;
17644 default:
17645 c_parser_error (parser,
17646 "invalid operator for %<#pragma omp atomic%>");
17647 goto saw_error;
17648 }
17649
17650 /* Arrange to pass the location of the assignment operator to
17651 c_finish_omp_atomic. */
17652 loc = c_parser_peek_token (parser)->location;
17653 c_parser_consume_token (parser);
17654 eloc = c_parser_peek_token (parser)->location;
17655 expr = c_parser_expression (parser);
17656 expr = default_function_array_read_conversion (eloc, expr);
17657 rhs = expr.value;
f9c59f7e 17658 rhs = c_fully_fold (rhs, false, NULL, true);
acf0174b
JJ
17659 break;
17660 }
17661stmt_done:
17662 if (structured_block && code == OMP_ATOMIC_CAPTURE_NEW)
17663 {
17664 if (!c_parser_require (parser, CPP_SEMICOLON, "expected %<;%>"))
17665 goto saw_error;
f4b189d5
JJ
17666 v = c_parser_cast_expression (parser, NULL).value;
17667 non_lvalue_p = !lvalue_p (v);
f9c59f7e 17668 v = c_fully_fold (v, false, NULL, true);
acf0174b
JJ
17669 if (v == error_mark_node)
17670 goto saw_error;
f4b189d5
JJ
17671 if (non_lvalue_p)
17672 v = non_lvalue (v);
acf0174b
JJ
17673 if (!c_parser_require (parser, CPP_EQ, "expected %<=%>"))
17674 goto saw_error;
17675 eloc = c_parser_peek_token (parser)->location;
f4b189d5 17676 expr = c_parser_cast_expression (parser, NULL);
acf0174b
JJ
17677 lhs1 = expr.value;
17678 expr = default_function_array_read_conversion (eloc, expr);
17679 unfolded_lhs1 = expr.value;
f9c59f7e 17680 lhs1 = c_fully_fold (lhs1, false, NULL, true);
acf0174b
JJ
17681 if (lhs1 == error_mark_node)
17682 goto saw_error;
f4b189d5
JJ
17683 if (!lvalue_p (unfolded_lhs1))
17684 lhs1 = non_lvalue (lhs1);
acf0174b
JJ
17685 }
17686 if (structured_block)
17687 {
17688 c_parser_skip_until_found (parser, CPP_SEMICOLON, "expected %<;%>");
17689 c_parser_require (parser, CPP_CLOSE_BRACE, "expected %<}%>");
17690 }
17691done:
17692 if (unfolded_lhs && unfolded_lhs1
17693 && !c_tree_equal (unfolded_lhs, unfolded_lhs1))
17694 {
17695 error ("%<#pragma omp atomic capture%> uses two different "
17696 "expressions for memory");
17697 stmt = error_mark_node;
17698 }
17699 else
17700 stmt = c_finish_omp_atomic (loc, code, opcode, lhs, rhs, v, lhs1, rhs1,
28567c40 17701 swapped, memory_order);
acf0174b
JJ
17702 if (stmt != error_mark_node)
17703 add_stmt (stmt);
17704
17705 if (!structured_block)
17706 c_parser_skip_until_found (parser, CPP_SEMICOLON, "expected %<;%>");
17707}
17708
17709
17710/* OpenMP 2.5:
17711 # pragma omp barrier new-line
17712*/
17713
17714static void
17715c_parser_omp_barrier (c_parser *parser)
17716{
17717 location_t loc = c_parser_peek_token (parser)->location;
17718 c_parser_consume_pragma (parser);
17719 c_parser_skip_to_pragma_eol (parser);
17720
17721 c_finish_omp_barrier (loc);
17722}
17723
17724/* OpenMP 2.5:
17725 # pragma omp critical [(name)] new-line
17726 structured-block
17727
d9a6bd32
JJ
17728 OpenMP 4.5:
17729 # pragma omp critical [(name) [hint(expression)]] new-line
17730
acf0174b
JJ
17731 LOC is the location of the #pragma itself. */
17732
d9a6bd32
JJ
17733#define OMP_CRITICAL_CLAUSE_MASK \
17734 ( (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_HINT) )
17735
acf0174b 17736static tree
dda1bf61 17737c_parser_omp_critical (location_t loc, c_parser *parser, bool *if_p)
acf0174b 17738{
d9a6bd32 17739 tree stmt, name = NULL_TREE, clauses = NULL_TREE;
acf0174b
JJ
17740
17741 if (c_parser_next_token_is (parser, CPP_OPEN_PAREN))
17742 {
17743 c_parser_consume_token (parser);
17744 if (c_parser_next_token_is (parser, CPP_NAME))
17745 {
17746 name = c_parser_peek_token (parser)->value;
17747 c_parser_consume_token (parser);
17748 c_parser_require (parser, CPP_CLOSE_PAREN, "expected %<)%>");
17749 }
17750 else
17751 c_parser_error (parser, "expected identifier");
d9a6bd32 17752
28567c40
JJ
17753 if (c_parser_next_token_is (parser, CPP_COMMA)
17754 && c_parser_peek_2nd_token (parser)->type == CPP_NAME)
17755 c_parser_consume_token (parser);
17756
d9a6bd32
JJ
17757 clauses = c_parser_omp_all_clauses (parser,
17758 OMP_CRITICAL_CLAUSE_MASK,
17759 "#pragma omp critical");
17760 }
17761 else
17762 {
17763 if (c_parser_next_token_is_not (parser, CPP_PRAGMA_EOL))
17764 c_parser_error (parser, "expected %<(%> or end of line");
17765 c_parser_skip_to_pragma_eol (parser);
acf0174b 17766 }
acf0174b 17767
dda1bf61 17768 stmt = c_parser_omp_structured_block (parser, if_p);
d9a6bd32 17769 return c_finish_omp_critical (loc, stmt, name, clauses);
acf0174b
JJ
17770}
17771
28567c40
JJ
17772/* OpenMP 5.0:
17773 # pragma omp depobj ( depobj ) depobj-clause new-line
17774
17775 depobj-clause:
17776 depend (dependence-type : locator)
17777 destroy
17778 update (dependence-type)
17779
17780 dependence-type:
17781 in
17782 out
17783 inout
17784 mutexinout */
17785
17786static void
17787c_parser_omp_depobj (c_parser *parser)
17788{
17789 location_t loc = c_parser_peek_token (parser)->location;
17790 c_parser_consume_pragma (parser);
17791 matching_parens parens;
17792 if (!parens.require_open (parser))
17793 {
17794 c_parser_skip_to_pragma_eol (parser);
17795 return;
17796 }
17797
17798 tree depobj = c_parser_expr_no_commas (parser, NULL).value;
17799 if (depobj != error_mark_node)
17800 {
17801 if (!lvalue_p (depobj))
17802 {
17803 error_at (EXPR_LOC_OR_LOC (depobj, loc),
17804 "%<depobj%> expression is not lvalue expression");
17805 depobj = error_mark_node;
17806 }
17807 else
17808 {
17809 tree addr = build_unary_op (EXPR_LOC_OR_LOC (depobj, loc), ADDR_EXPR,
17810 depobj, false);
17811 if (addr == error_mark_node)
17812 depobj = error_mark_node;
17813 else
17814 depobj = build_indirect_ref (EXPR_LOC_OR_LOC (depobj, loc),
17815 addr, RO_UNARY_STAR);
17816 }
17817 }
17818
17819 parens.skip_until_found_close (parser);
17820 tree clause = NULL_TREE;
17821 enum omp_clause_depend_kind kind = OMP_CLAUSE_DEPEND_SOURCE;
17822 location_t c_loc = c_parser_peek_token (parser)->location;
17823 if (c_parser_next_token_is (parser, CPP_NAME))
17824 {
17825 const char *p = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
17826
17827 c_parser_consume_token (parser);
17828 if (!strcmp ("depend", p))
17829 {
17830 clause = c_parser_omp_clause_depend (parser, NULL_TREE);
17831 clause = c_finish_omp_clauses (clause, C_ORT_OMP);
17832 if (!clause)
17833 clause = error_mark_node;
17834 }
17835 else if (!strcmp ("destroy", p))
17836 kind = OMP_CLAUSE_DEPEND_LAST;
17837 else if (!strcmp ("update", p))
17838 {
17839 matching_parens c_parens;
17840 if (c_parens.require_open (parser))
17841 {
17842 location_t c2_loc = c_parser_peek_token (parser)->location;
17843 if (c_parser_next_token_is (parser, CPP_NAME))
17844 {
17845 const char *p2
17846 = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
17847
17848 c_parser_consume_token (parser);
17849 if (!strcmp ("in", p2))
17850 kind = OMP_CLAUSE_DEPEND_IN;
17851 else if (!strcmp ("out", p2))
17852 kind = OMP_CLAUSE_DEPEND_OUT;
17853 else if (!strcmp ("inout", p2))
17854 kind = OMP_CLAUSE_DEPEND_INOUT;
17855 else if (!strcmp ("mutexinoutset", p2))
17856 kind = OMP_CLAUSE_DEPEND_MUTEXINOUTSET;
17857 }
17858 if (kind == OMP_CLAUSE_DEPEND_SOURCE)
17859 {
17860 clause = error_mark_node;
17861 error_at (c2_loc, "expected %<in%>, %<out%>, %<inout%> or "
17862 "%<mutexinoutset%>");
17863 }
17864 c_parens.skip_until_found_close (parser);
17865 }
17866 else
17867 clause = error_mark_node;
17868 }
17869 }
17870 if (!clause && kind == OMP_CLAUSE_DEPEND_SOURCE)
17871 {
17872 clause = error_mark_node;
17873 error_at (c_loc, "expected %<depend%>, %<destroy%> or %<update%> clause");
17874 }
17875 c_parser_skip_to_pragma_eol (parser);
17876
17877 c_finish_omp_depobj (loc, depobj, kind, clause);
17878}
17879
17880
acf0174b
JJ
17881/* OpenMP 2.5:
17882 # pragma omp flush flush-vars[opt] new-line
17883
17884 flush-vars:
28567c40
JJ
17885 ( variable-list )
17886
17887 OpenMP 5.0:
17888 # pragma omp flush memory-order-clause new-line */
acf0174b
JJ
17889
17890static void
17891c_parser_omp_flush (c_parser *parser)
17892{
17893 location_t loc = c_parser_peek_token (parser)->location;
17894 c_parser_consume_pragma (parser);
28567c40
JJ
17895 enum memmodel mo = MEMMODEL_LAST;
17896 if (c_parser_next_token_is (parser, CPP_NAME))
17897 {
17898 const char *p
17899 = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
17900
17901 if (!strcmp (p, "acq_rel"))
17902 mo = MEMMODEL_ACQ_REL;
17903 else if (!strcmp (p, "release"))
17904 mo = MEMMODEL_RELEASE;
17905 else if (!strcmp (p, "acquire"))
17906 mo = MEMMODEL_ACQUIRE;
17907 else
17908 error_at (c_parser_peek_token (parser)->location,
17909 "expected %<acq_rel%>, %<release%> or %<acquire%>");
17910 c_parser_consume_token (parser);
17911 }
acf0174b 17912 if (c_parser_next_token_is (parser, CPP_OPEN_PAREN))
28567c40
JJ
17913 {
17914 if (mo != MEMMODEL_LAST)
17915 error_at (c_parser_peek_token (parser)->location,
17916 "%<flush%> list specified together with memory order "
17917 "clause");
17918 c_parser_omp_var_list_parens (parser, OMP_CLAUSE_ERROR, NULL);
17919 }
acf0174b
JJ
17920 else if (c_parser_next_token_is_not (parser, CPP_PRAGMA_EOL))
17921 c_parser_error (parser, "expected %<(%> or end of line");
17922 c_parser_skip_to_pragma_eol (parser);
17923
28567c40 17924 c_finish_omp_flush (loc, mo);
acf0174b
JJ
17925}
17926
bf38f7e9
JJ
17927/* OpenMP 5.0:
17928
17929 scan-loop-body:
17930 { structured-block scan-directive structured-block } */
17931
17932static void
17933c_parser_omp_scan_loop_body (c_parser *parser, bool open_brace_parsed)
17934{
17935 tree substmt;
17936 location_t loc;
17937 tree clauses = NULL_TREE;
17938
17939 loc = c_parser_peek_token (parser)->location;
17940 if (!open_brace_parsed
17941 && !c_parser_require (parser, CPP_OPEN_BRACE, "expected %<{%>"))
17942 {
17943 /* Avoid skipping until the end of the block. */
17944 parser->error = false;
17945 return;
17946 }
17947
17948 substmt = c_parser_omp_structured_block (parser, NULL);
17949 substmt = build2 (OMP_SCAN, void_type_node, substmt, NULL_TREE);
17950 SET_EXPR_LOCATION (substmt, loc);
17951 add_stmt (substmt);
17952
17953 loc = c_parser_peek_token (parser)->location;
17954 if (c_parser_peek_token (parser)->pragma_kind == PRAGMA_OMP_SCAN)
17955 {
17956 enum omp_clause_code clause = OMP_CLAUSE_ERROR;
17957
17958 c_parser_consume_pragma (parser);
17959
17960 if (c_parser_next_token_is (parser, CPP_NAME))
17961 {
17962 const char *p
17963 = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
17964 if (strcmp (p, "inclusive") == 0)
17965 clause = OMP_CLAUSE_INCLUSIVE;
17966 else if (strcmp (p, "exclusive") == 0)
17967 clause = OMP_CLAUSE_EXCLUSIVE;
17968 }
17969 if (clause != OMP_CLAUSE_ERROR)
17970 {
17971 c_parser_consume_token (parser);
17972 clauses = c_parser_omp_var_list_parens (parser, clause, NULL_TREE);
17973 }
17974 else
17975 c_parser_error (parser, "expected %<inclusive%> or "
17976 "%<exclusive%> clause");
17977 c_parser_skip_to_pragma_eol (parser);
17978 }
17979 else
17980 error ("expected %<#pragma omp scan%>");
17981
17982 clauses = c_finish_omp_clauses (clauses, C_ORT_OMP);
17983 substmt = c_parser_omp_structured_block (parser, NULL);
17984 substmt = build2 (OMP_SCAN, void_type_node, substmt, clauses);
17985 SET_EXPR_LOCATION (substmt, loc);
17986 add_stmt (substmt);
17987
17988 c_parser_skip_until_found (parser, CPP_CLOSE_BRACE,
17989 "expected %<}%>");
17990}
17991
41dbbb37 17992/* Parse the restricted form of loop statements allowed by OpenACC and OpenMP.
acf0174b
JJ
17993 The real trick here is to determine the loop control variable early
17994 so that we can push a new decl if necessary to make it private.
41dbbb37
TS
17995 LOC is the location of the "acc" or "omp" in "#pragma acc" or "#pragma omp",
17996 respectively. */
acf0174b
JJ
17997
17998static tree
17999c_parser_omp_for_loop (location_t loc, c_parser *parser, enum tree_code code,
dda1bf61 18000 tree clauses, tree *cclauses, bool *if_p)
acf0174b
JJ
18001{
18002 tree decl, cond, incr, save_break, save_cont, body, init, stmt, cl;
a8a098ac
JJ
18003 tree declv, condv, incrv, initv, ret = NULL_TREE;
18004 tree pre_body = NULL_TREE, this_pre_body;
d9a6bd32 18005 tree ordered_cl = NULL_TREE;
acf0174b 18006 bool fail = false, open_brace_parsed = false;
d9a6bd32 18007 int i, collapse = 1, ordered = 0, count, nbraces = 0;
acf0174b 18008 location_t for_loc;
02889d23 18009 bool tiling = false;
bf38f7e9 18010 bool inscan = false;
acf0174b
JJ
18011 vec<tree, va_gc> *for_block = make_tree_vector ();
18012
18013 for (cl = clauses; cl; cl = OMP_CLAUSE_CHAIN (cl))
18014 if (OMP_CLAUSE_CODE (cl) == OMP_CLAUSE_COLLAPSE)
9439e9a1 18015 collapse = tree_to_shwi (OMP_CLAUSE_COLLAPSE_EXPR (cl));
02889d23
CLT
18016 else if (OMP_CLAUSE_CODE (cl) == OMP_CLAUSE_TILE)
18017 {
18018 tiling = true;
18019 collapse = list_length (OMP_CLAUSE_TILE_LIST (cl));
18020 }
d9a6bd32
JJ
18021 else if (OMP_CLAUSE_CODE (cl) == OMP_CLAUSE_ORDERED
18022 && OMP_CLAUSE_ORDERED_EXPR (cl))
18023 {
18024 ordered_cl = cl;
18025 ordered = tree_to_shwi (OMP_CLAUSE_ORDERED_EXPR (cl));
18026 }
bf38f7e9
JJ
18027 else if (OMP_CLAUSE_CODE (cl) == OMP_CLAUSE_REDUCTION
18028 && OMP_CLAUSE_REDUCTION_INSCAN (cl)
18029 && (code == OMP_SIMD || code == OMP_FOR))
18030 inscan = true;
d9a6bd32
JJ
18031
18032 if (ordered && ordered < collapse)
18033 {
18034 error_at (OMP_CLAUSE_LOCATION (ordered_cl),
18035 "%<ordered%> clause parameter is less than %<collapse%>");
18036 OMP_CLAUSE_ORDERED_EXPR (ordered_cl)
18037 = build_int_cst (NULL_TREE, collapse);
18038 ordered = collapse;
18039 }
18040 if (ordered)
18041 {
18042 for (tree *pc = &clauses; *pc; )
18043 if (OMP_CLAUSE_CODE (*pc) == OMP_CLAUSE_LINEAR)
18044 {
18045 error_at (OMP_CLAUSE_LOCATION (*pc),
18046 "%<linear%> clause may not be specified together "
18047 "with %<ordered%> clause with a parameter");
18048 *pc = OMP_CLAUSE_CHAIN (*pc);
18049 }
18050 else
18051 pc = &OMP_CLAUSE_CHAIN (*pc);
18052 }
acf0174b 18053
02889d23 18054 gcc_assert (tiling || (collapse >= 1 && ordered >= 0));
d9a6bd32 18055 count = ordered ? ordered : collapse;
acf0174b 18056
d9a6bd32
JJ
18057 declv = make_tree_vec (count);
18058 initv = make_tree_vec (count);
18059 condv = make_tree_vec (count);
18060 incrv = make_tree_vec (count);
acf0174b 18061
5e9d6aa4 18062 if (!c_parser_next_token_is_keyword (parser, RID_FOR))
acf0174b
JJ
18063 {
18064 c_parser_error (parser, "for statement expected");
18065 return NULL;
18066 }
18067 for_loc = c_parser_peek_token (parser)->location;
18068 c_parser_consume_token (parser);
18069
d9a6bd32 18070 for (i = 0; i < count; i++)
acf0174b
JJ
18071 {
18072 int bracecount = 0;
18073
32129a17
DM
18074 matching_parens parens;
18075 if (!parens.require_open (parser))
acf0174b
JJ
18076 goto pop_scopes;
18077
18078 /* Parse the initialization declaration or expression. */
18079 if (c_parser_next_tokens_start_declaration (parser))
18080 {
18081 if (i > 0)
18082 vec_safe_push (for_block, c_begin_compound_stmt (true));
a8a098ac 18083 this_pre_body = push_stmt_list ();
acf0174b
JJ
18084 c_parser_declaration_or_fndef (parser, true, true, true, true, true,
18085 NULL, vNULL);
a8a098ac
JJ
18086 if (this_pre_body)
18087 {
18088 this_pre_body = pop_stmt_list (this_pre_body);
18089 if (pre_body)
18090 {
18091 tree t = pre_body;
18092 pre_body = push_stmt_list ();
18093 add_stmt (t);
18094 add_stmt (this_pre_body);
18095 pre_body = pop_stmt_list (pre_body);
18096 }
18097 else
18098 pre_body = this_pre_body;
18099 }
acf0174b
JJ
18100 decl = check_for_loop_decls (for_loc, flag_isoc99);
18101 if (decl == NULL)
18102 goto error_init;
18103 if (DECL_INITIAL (decl) == error_mark_node)
18104 decl = error_mark_node;
18105 init = decl;
18106 }
18107 else if (c_parser_next_token_is (parser, CPP_NAME)
18108 && c_parser_peek_2nd_token (parser)->type == CPP_EQ)
18109 {
18110 struct c_expr decl_exp;
18111 struct c_expr init_exp;
18112 location_t init_loc;
18113
18114 decl_exp = c_parser_postfix_expression (parser);
18115 decl = decl_exp.value;
18116
18117 c_parser_require (parser, CPP_EQ, "expected %<=%>");
18118
18119 init_loc = c_parser_peek_token (parser)->location;
18120 init_exp = c_parser_expr_no_commas (parser, NULL);
18121 init_exp = default_function_array_read_conversion (init_loc,
18122 init_exp);
18123 init = build_modify_expr (init_loc, decl, decl_exp.original_type,
18124 NOP_EXPR, init_loc, init_exp.value,
18125 init_exp.original_type);
18126 init = c_process_expr_stmt (init_loc, init);
18127
18128 c_parser_skip_until_found (parser, CPP_SEMICOLON, "expected %<;%>");
18129 }
18130 else
18131 {
18132 error_init:
18133 c_parser_error (parser,
18134 "expected iteration declaration or initialization");
18135 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN,
18136 "expected %<)%>");
18137 fail = true;
18138 goto parse_next;
18139 }
18140
18141 /* Parse the loop condition. */
18142 cond = NULL_TREE;
18143 if (c_parser_next_token_is_not (parser, CPP_SEMICOLON))
18144 {
18145 location_t cond_loc = c_parser_peek_token (parser)->location;
18146 struct c_expr cond_expr
18147 = c_parser_binary_expression (parser, NULL, NULL_TREE);
18148
18149 cond = cond_expr.value;
18150 cond = c_objc_common_truthvalue_conversion (cond_loc, cond);
ebc6a85e
TV
18151 if (COMPARISON_CLASS_P (cond))
18152 {
18153 tree op0 = TREE_OPERAND (cond, 0), op1 = TREE_OPERAND (cond, 1);
18154 op0 = c_fully_fold (op0, false, NULL);
18155 op1 = c_fully_fold (op1, false, NULL);
18156 TREE_OPERAND (cond, 0) = op0;
18157 TREE_OPERAND (cond, 1) = op1;
18158 }
acf0174b
JJ
18159 switch (cond_expr.original_code)
18160 {
18161 case GT_EXPR:
18162 case GE_EXPR:
18163 case LT_EXPR:
18164 case LE_EXPR:
18165 break;
28567c40
JJ
18166 case NE_EXPR:
18167 if (code != OACC_LOOP)
18168 break;
18169 /* FALLTHRU. */
acf0174b
JJ
18170 default:
18171 /* Can't be cond = error_mark_node, because we want to preserve
18172 the location until c_finish_omp_for. */
18173 cond = build1 (NOP_EXPR, boolean_type_node, error_mark_node);
18174 break;
18175 }
18176 protected_set_expr_location (cond, cond_loc);
18177 }
18178 c_parser_skip_until_found (parser, CPP_SEMICOLON, "expected %<;%>");
18179
18180 /* Parse the increment expression. */
18181 incr = NULL_TREE;
18182 if (c_parser_next_token_is_not (parser, CPP_CLOSE_PAREN))
18183 {
18184 location_t incr_loc = c_parser_peek_token (parser)->location;
18185
18186 incr = c_process_expr_stmt (incr_loc,
18187 c_parser_expression (parser).value);
18188 }
32129a17 18189 parens.skip_until_found_close (parser);
acf0174b
JJ
18190
18191 if (decl == NULL || decl == error_mark_node || init == error_mark_node)
18192 fail = true;
18193 else
18194 {
18195 TREE_VEC_ELT (declv, i) = decl;
18196 TREE_VEC_ELT (initv, i) = init;
18197 TREE_VEC_ELT (condv, i) = cond;
18198 TREE_VEC_ELT (incrv, i) = incr;
18199 }
18200
18201 parse_next:
d9a6bd32 18202 if (i == count - 1)
acf0174b
JJ
18203 break;
18204
18205 /* FIXME: OpenMP 3.0 draft isn't very clear on what exactly is allowed
18206 in between the collapsed for loops to be still considered perfectly
18207 nested. Hopefully the final version clarifies this.
18208 For now handle (multiple) {'s and empty statements. */
18209 do
18210 {
18211 if (c_parser_next_token_is_keyword (parser, RID_FOR))
18212 {
18213 c_parser_consume_token (parser);
18214 break;
18215 }
18216 else if (c_parser_next_token_is (parser, CPP_OPEN_BRACE))
18217 {
18218 c_parser_consume_token (parser);
18219 bracecount++;
18220 }
18221 else if (bracecount
18222 && c_parser_next_token_is (parser, CPP_SEMICOLON))
18223 c_parser_consume_token (parser);
18224 else
18225 {
18226 c_parser_error (parser, "not enough perfectly nested loops");
18227 if (bracecount)
18228 {
18229 open_brace_parsed = true;
18230 bracecount--;
18231 }
18232 fail = true;
d9a6bd32 18233 count = 0;
acf0174b
JJ
18234 break;
18235 }
18236 }
18237 while (1);
18238
18239 nbraces += bracecount;
18240 }
18241
dda1bf61
JJ
18242 if (nbraces)
18243 if_p = NULL;
18244
acf0174b 18245 save_break = c_break_label;
5e9d6aa4 18246 c_break_label = size_one_node;
acf0174b
JJ
18247 save_cont = c_cont_label;
18248 c_cont_label = NULL_TREE;
18249 body = push_stmt_list ();
18250
bf38f7e9
JJ
18251 if (inscan)
18252 c_parser_omp_scan_loop_body (parser, open_brace_parsed);
18253 else if (open_brace_parsed)
acf0174b
JJ
18254 {
18255 location_t here = c_parser_peek_token (parser)->location;
18256 stmt = c_begin_compound_stmt (true);
18257 c_parser_compound_statement_nostart (parser);
18258 add_stmt (c_end_compound_stmt (here, stmt, true));
18259 }
18260 else
dda1bf61 18261 add_stmt (c_parser_c99_block_statement (parser, if_p));
acf0174b
JJ
18262 if (c_cont_label)
18263 {
18264 tree t = build1 (LABEL_EXPR, void_type_node, c_cont_label);
18265 SET_EXPR_LOCATION (t, loc);
18266 add_stmt (t);
18267 }
18268
18269 body = pop_stmt_list (body);
18270 c_break_label = save_break;
18271 c_cont_label = save_cont;
18272
18273 while (nbraces)
18274 {
18275 if (c_parser_next_token_is (parser, CPP_CLOSE_BRACE))
18276 {
18277 c_parser_consume_token (parser);
18278 nbraces--;
18279 }
18280 else if (c_parser_next_token_is (parser, CPP_SEMICOLON))
18281 c_parser_consume_token (parser);
18282 else
18283 {
18284 c_parser_error (parser, "collapsed loops not perfectly nested");
18285 while (nbraces)
18286 {
18287 location_t here = c_parser_peek_token (parser)->location;
18288 stmt = c_begin_compound_stmt (true);
18289 add_stmt (body);
18290 c_parser_compound_statement_nostart (parser);
18291 body = c_end_compound_stmt (here, stmt, true);
18292 nbraces--;
18293 }
18294 goto pop_scopes;
18295 }
18296 }
18297
18298 /* Only bother calling c_finish_omp_for if we haven't already generated
18299 an error from the initialization parsing. */
18300 if (!fail)
18301 {
d9a6bd32 18302 stmt = c_finish_omp_for (loc, code, declv, NULL, initv, condv,
28567c40 18303 incrv, body, pre_body, true);
e01d41e5
JJ
18304
18305 /* Check for iterators appearing in lb, b or incr expressions. */
18306 if (stmt && !c_omp_check_loop_iv (stmt, declv, NULL))
18307 stmt = NULL_TREE;
18308
acf0174b
JJ
18309 if (stmt)
18310 {
e01d41e5
JJ
18311 add_stmt (stmt);
18312
acf0174b
JJ
18313 if (cclauses != NULL
18314 && cclauses[C_OMP_CLAUSE_SPLIT_PARALLEL] != NULL)
18315 {
18316 tree *c;
18317 for (c = &cclauses[C_OMP_CLAUSE_SPLIT_PARALLEL]; *c ; )
18318 if (OMP_CLAUSE_CODE (*c) != OMP_CLAUSE_FIRSTPRIVATE
18319 && OMP_CLAUSE_CODE (*c) != OMP_CLAUSE_LASTPRIVATE)
18320 c = &OMP_CLAUSE_CHAIN (*c);
18321 else
18322 {
d9a6bd32 18323 for (i = 0; i < count; i++)
acf0174b
JJ
18324 if (TREE_VEC_ELT (declv, i) == OMP_CLAUSE_DECL (*c))
18325 break;
d9a6bd32 18326 if (i == count)
acf0174b
JJ
18327 c = &OMP_CLAUSE_CHAIN (*c);
18328 else if (OMP_CLAUSE_CODE (*c) == OMP_CLAUSE_FIRSTPRIVATE)
18329 {
18330 error_at (loc,
18331 "iteration variable %qD should not be firstprivate",
18332 OMP_CLAUSE_DECL (*c));
18333 *c = OMP_CLAUSE_CHAIN (*c);
18334 }
18335 else
18336 {
41b37d5e
JJ
18337 /* Move lastprivate (decl) clause to OMP_FOR_CLAUSES. */
18338 tree l = *c;
18339 *c = OMP_CLAUSE_CHAIN (*c);
56ad0e38
JJ
18340 if (code == OMP_SIMD)
18341 {
18342 OMP_CLAUSE_CHAIN (l)
18343 = cclauses[C_OMP_CLAUSE_SPLIT_FOR];
18344 cclauses[C_OMP_CLAUSE_SPLIT_FOR] = l;
18345 }
18346 else
18347 {
18348 OMP_CLAUSE_CHAIN (l) = clauses;
18349 clauses = l;
18350 }
acf0174b
JJ
18351 }
18352 }
18353 }
18354 OMP_FOR_CLAUSES (stmt) = clauses;
18355 }
18356 ret = stmt;
18357 }
18358pop_scopes:
18359 while (!for_block->is_empty ())
18360 {
18361 /* FIXME diagnostics: LOC below should be the actual location of
18362 this particular for block. We need to build a list of
18363 locations to go along with FOR_BLOCK. */
18364 stmt = c_end_compound_stmt (loc, for_block->pop (), true);
18365 add_stmt (stmt);
18366 }
18367 release_tree_vector (for_block);
18368 return ret;
18369}
18370
18371/* Helper function for OpenMP parsing, split clauses and call
18372 finish_omp_clauses on each of the set of clauses afterwards. */
18373
18374static void
18375omp_split_clauses (location_t loc, enum tree_code code,
18376 omp_clause_mask mask, tree clauses, tree *cclauses)
18377{
18378 int i;
18379 c_omp_split_clauses (loc, code, mask, clauses, cclauses);
18380 for (i = 0; i < C_OMP_CLAUSE_SPLIT_COUNT; i++)
18381 if (cclauses[i])
77886428 18382 cclauses[i] = c_finish_omp_clauses (cclauses[i], C_ORT_OMP);
acf0174b
JJ
18383}
18384
554a530f
JJ
18385/* OpenMP 5.0:
18386 #pragma omp loop loop-clause[optseq] new-line
18387 for-loop
18388
18389 LOC is the location of the #pragma token.
18390*/
18391
18392#define OMP_LOOP_CLAUSE_MASK \
18393 ( (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_PRIVATE) \
18394 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_LASTPRIVATE) \
18395 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_REDUCTION) \
18396 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_COLLAPSE) \
18397 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_BIND) \
18398 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_ORDER))
18399
18400static tree
18401c_parser_omp_loop (location_t loc, c_parser *parser,
18402 char *p_name, omp_clause_mask mask, tree *cclauses,
18403 bool *if_p)
18404{
18405 tree block, clauses, ret;
18406
18407 strcat (p_name, " loop");
18408 mask |= OMP_LOOP_CLAUSE_MASK;
18409
18410 clauses = c_parser_omp_all_clauses (parser, mask, p_name, cclauses == NULL);
18411 if (cclauses)
18412 {
18413 omp_split_clauses (loc, OMP_LOOP, mask, clauses, cclauses);
18414 clauses = cclauses[C_OMP_CLAUSE_SPLIT_LOOP];
18415 }
18416
18417 block = c_begin_compound_stmt (true);
18418 ret = c_parser_omp_for_loop (loc, parser, OMP_LOOP, clauses, cclauses, if_p);
18419 block = c_end_compound_stmt (loc, block, true);
18420 add_stmt (block);
18421
18422 return ret;
18423}
18424
acf0174b
JJ
18425/* OpenMP 4.0:
18426 #pragma omp simd simd-clause[optseq] new-line
18427 for-loop
18428
18429 LOC is the location of the #pragma token.
18430*/
18431
18432#define OMP_SIMD_CLAUSE_MASK \
18433 ( (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_SAFELEN) \
d9a6bd32 18434 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_SIMDLEN) \
acf0174b
JJ
18435 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_LINEAR) \
18436 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_ALIGNED) \
18437 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_PRIVATE) \
18438 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_LASTPRIVATE) \
18439 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_REDUCTION) \
28567c40
JJ
18440 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_COLLAPSE) \
18441 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_IF) \
1fdd6f04
JJ
18442 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_NONTEMPORAL) \
18443 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_ORDER))
acf0174b
JJ
18444
18445static tree
18446c_parser_omp_simd (location_t loc, c_parser *parser,
dda1bf61
JJ
18447 char *p_name, omp_clause_mask mask, tree *cclauses,
18448 bool *if_p)
acf0174b
JJ
18449{
18450 tree block, clauses, ret;
18451
18452 strcat (p_name, " simd");
18453 mask |= OMP_SIMD_CLAUSE_MASK;
acf0174b
JJ
18454
18455 clauses = c_parser_omp_all_clauses (parser, mask, p_name, cclauses == NULL);
18456 if (cclauses)
18457 {
18458 omp_split_clauses (loc, OMP_SIMD, mask, clauses, cclauses);
18459 clauses = cclauses[C_OMP_CLAUSE_SPLIT_SIMD];
629b3d75 18460 tree c = omp_find_clause (cclauses[C_OMP_CLAUSE_SPLIT_FOR],
d9a6bd32
JJ
18461 OMP_CLAUSE_ORDERED);
18462 if (c && OMP_CLAUSE_ORDERED_EXPR (c))
18463 {
18464 error_at (OMP_CLAUSE_LOCATION (c),
18465 "%<ordered%> clause with parameter may not be specified "
18466 "on %qs construct", p_name);
18467 OMP_CLAUSE_ORDERED_EXPR (c) = NULL_TREE;
18468 }
acf0174b
JJ
18469 }
18470
18471 block = c_begin_compound_stmt (true);
dda1bf61 18472 ret = c_parser_omp_for_loop (loc, parser, OMP_SIMD, clauses, cclauses, if_p);
acf0174b
JJ
18473 block = c_end_compound_stmt (loc, block, true);
18474 add_stmt (block);
18475
18476 return ret;
18477}
18478
18479/* OpenMP 2.5:
18480 #pragma omp for for-clause[optseq] new-line
18481 for-loop
18482
18483 OpenMP 4.0:
18484 #pragma omp for simd for-simd-clause[optseq] new-line
18485 for-loop
18486
18487 LOC is the location of the #pragma token.
18488*/
18489
18490#define OMP_FOR_CLAUSE_MASK \
18491 ( (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_PRIVATE) \
18492 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_FIRSTPRIVATE) \
18493 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_LASTPRIVATE) \
d9a6bd32 18494 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_LINEAR) \
acf0174b
JJ
18495 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_REDUCTION) \
18496 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_ORDERED) \
18497 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_SCHEDULE) \
18498 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_COLLAPSE) \
1fdd6f04
JJ
18499 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_NOWAIT) \
18500 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_ORDER))
acf0174b
JJ
18501
18502static tree
18503c_parser_omp_for (location_t loc, c_parser *parser,
dda1bf61
JJ
18504 char *p_name, omp_clause_mask mask, tree *cclauses,
18505 bool *if_p)
acf0174b
JJ
18506{
18507 tree block, clauses, ret;
18508
18509 strcat (p_name, " for");
18510 mask |= OMP_FOR_CLAUSE_MASK;
00631022
JJ
18511 /* parallel for{, simd} disallows nowait clause, but for
18512 target {teams distribute ,}parallel for{, simd} it should be accepted. */
18513 if (cclauses && (mask & (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_MAP)) == 0)
acf0174b 18514 mask &= ~(OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_NOWAIT);
d9a6bd32
JJ
18515 /* Composite distribute parallel for{, simd} disallows ordered clause. */
18516 if ((mask & (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_DIST_SCHEDULE)) != 0)
18517 mask &= ~(OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_ORDERED);
acf0174b
JJ
18518
18519 if (c_parser_next_token_is (parser, CPP_NAME))
20906c66 18520 {
acf0174b
JJ
18521 const char *p = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
18522
18523 if (strcmp (p, "simd") == 0)
18524 {
18525 tree cclauses_buf[C_OMP_CLAUSE_SPLIT_COUNT];
18526 if (cclauses == NULL)
18527 cclauses = cclauses_buf;
18528
18529 c_parser_consume_token (parser);
6d7f7e0a 18530 if (!flag_openmp) /* flag_openmp_simd */
dda1bf61
JJ
18531 return c_parser_omp_simd (loc, parser, p_name, mask, cclauses,
18532 if_p);
acf0174b 18533 block = c_begin_compound_stmt (true);
dda1bf61 18534 ret = c_parser_omp_simd (loc, parser, p_name, mask, cclauses, if_p);
acf0174b
JJ
18535 block = c_end_compound_stmt (loc, block, true);
18536 if (ret == NULL_TREE)
18537 return ret;
18538 ret = make_node (OMP_FOR);
18539 TREE_TYPE (ret) = void_type_node;
18540 OMP_FOR_BODY (ret) = block;
18541 OMP_FOR_CLAUSES (ret) = cclauses[C_OMP_CLAUSE_SPLIT_FOR];
18542 SET_EXPR_LOCATION (ret, loc);
18543 add_stmt (ret);
18544 return ret;
18545 }
20906c66 18546 }
6d7f7e0a
TB
18547 if (!flag_openmp) /* flag_openmp_simd */
18548 {
62021f64 18549 c_parser_skip_to_pragma_eol (parser, false);
6d7f7e0a
TB
18550 return NULL_TREE;
18551 }
acf0174b 18552
d9a6bd32
JJ
18553 /* Composite distribute parallel for disallows linear clause. */
18554 if ((mask & (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_DIST_SCHEDULE)) != 0)
18555 mask &= ~(OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_LINEAR);
18556
acf0174b
JJ
18557 clauses = c_parser_omp_all_clauses (parser, mask, p_name, cclauses == NULL);
18558 if (cclauses)
20906c66 18559 {
acf0174b
JJ
18560 omp_split_clauses (loc, OMP_FOR, mask, clauses, cclauses);
18561 clauses = cclauses[C_OMP_CLAUSE_SPLIT_FOR];
20906c66 18562 }
20906c66 18563
acf0174b 18564 block = c_begin_compound_stmt (true);
dda1bf61 18565 ret = c_parser_omp_for_loop (loc, parser, OMP_FOR, clauses, cclauses, if_p);
acf0174b
JJ
18566 block = c_end_compound_stmt (loc, block, true);
18567 add_stmt (block);
18568
18569 return ret;
953ff289
DN
18570}
18571
28567c40
JJ
18572static tree c_parser_omp_taskloop (location_t, c_parser *, char *,
18573 omp_clause_mask, tree *, bool *);
18574
acf0174b
JJ
18575/* OpenMP 2.5:
18576 # pragma omp master new-line
18577 structured-block
18578
18579 LOC is the location of the #pragma token.
18580*/
18581
18582static tree
28567c40
JJ
18583c_parser_omp_master (location_t loc, c_parser *parser,
18584 char *p_name, omp_clause_mask mask, tree *cclauses,
18585 bool *if_p)
acf0174b 18586{
28567c40
JJ
18587 tree block, clauses, ret;
18588
18589 strcat (p_name, " master");
18590
18591 if (c_parser_next_token_is (parser, CPP_NAME))
18592 {
18593 const char *p = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
18594
18595 if (strcmp (p, "taskloop") == 0)
18596 {
18597 tree cclauses_buf[C_OMP_CLAUSE_SPLIT_COUNT];
18598 if (cclauses == NULL)
18599 cclauses = cclauses_buf;
18600
18601 c_parser_consume_token (parser);
18602 if (!flag_openmp) /* flag_openmp_simd */
18603 return c_parser_omp_taskloop (loc, parser, p_name, mask, cclauses,
18604 if_p);
18605 block = c_begin_compound_stmt (true);
18606 ret = c_parser_omp_taskloop (loc, parser, p_name, mask, cclauses,
18607 if_p);
18608 block = c_end_compound_stmt (loc, block, true);
18609 if (ret == NULL_TREE)
18610 return ret;
18611 ret = c_finish_omp_master (loc, block);
18612 return ret;
18613 }
18614 }
18615 if (!flag_openmp) /* flag_openmp_simd */
18616 {
18617 c_parser_skip_to_pragma_eol (parser, false);
18618 return NULL_TREE;
18619 }
18620
18621 if (cclauses)
18622 {
18623 clauses = c_parser_omp_all_clauses (parser, mask, p_name, false);
18624 omp_split_clauses (loc, OMP_MASTER, mask, clauses, cclauses);
18625 }
18626 else
18627 c_parser_skip_to_pragma_eol (parser);
18628
dda1bf61
JJ
18629 return c_finish_omp_master (loc, c_parser_omp_structured_block (parser,
18630 if_p));
acf0174b 18631}
953ff289
DN
18632
18633/* OpenMP 2.5:
acf0174b
JJ
18634 # pragma omp ordered new-line
18635 structured-block
18636
d9a6bd32
JJ
18637 OpenMP 4.5:
18638 # pragma omp ordered ordered-clauses new-line
18639 structured-block
18640
18641 # pragma omp ordered depend-clauses new-line */
18642
18643#define OMP_ORDERED_CLAUSE_MASK \
18644 ( (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_THREADS) \
18645 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_SIMD))
18646
18647#define OMP_ORDERED_DEPEND_CLAUSE_MASK \
18648 (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_DEPEND)
18649
18650static bool
dda1bf61
JJ
18651c_parser_omp_ordered (c_parser *parser, enum pragma_context context,
18652 bool *if_p)
d9a6bd32
JJ
18653{
18654 location_t loc = c_parser_peek_token (parser)->location;
18655 c_parser_consume_pragma (parser);
18656
18657 if (context != pragma_stmt && context != pragma_compound)
18658 {
18659 c_parser_error (parser, "expected declaration specifiers");
192b048b 18660 c_parser_skip_to_pragma_eol (parser, false);
d9a6bd32
JJ
18661 return false;
18662 }
18663
18664 if (c_parser_next_token_is (parser, CPP_NAME))
18665 {
18666 const char *p = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
18667
18668 if (!strcmp ("depend", p))
18669 {
d2e05fcb
JJ
18670 if (!flag_openmp) /* flag_openmp_simd */
18671 {
18672 c_parser_skip_to_pragma_eol (parser, false);
18673 return false;
18674 }
d9a6bd32
JJ
18675 if (context == pragma_stmt)
18676 {
18677 error_at (loc,
883c8f06 18678 "%<#pragma omp ordered%> with %<depend%> clause may "
d9a6bd32 18679 "only be used in compound statements");
aec17bfe 18680 c_parser_skip_to_pragma_eol (parser, false);
d9a6bd32
JJ
18681 return false;
18682 }
18683
18684 tree clauses
18685 = c_parser_omp_all_clauses (parser,
18686 OMP_ORDERED_DEPEND_CLAUSE_MASK,
18687 "#pragma omp ordered");
18688 c_finish_omp_ordered (loc, clauses, NULL_TREE);
18689 return false;
18690 }
18691 }
953ff289 18692
d9a6bd32
JJ
18693 tree clauses = c_parser_omp_all_clauses (parser, OMP_ORDERED_CLAUSE_MASK,
18694 "#pragma omp ordered");
d2e05fcb
JJ
18695
18696 if (!flag_openmp /* flag_openmp_simd */
18697 && omp_find_clause (clauses, OMP_CLAUSE_SIMD) == NULL_TREE)
18698 return false;
18699
d9a6bd32 18700 c_finish_omp_ordered (loc, clauses,
dda1bf61 18701 c_parser_omp_structured_block (parser, if_p));
d9a6bd32 18702 return true;
acf0174b 18703}
953ff289 18704
acf0174b
JJ
18705/* OpenMP 2.5:
18706
18707 section-scope:
18708 { section-sequence }
18709
18710 section-sequence:
18711 section-directive[opt] structured-block
18712 section-sequence section-directive structured-block
18713
18714 SECTIONS_LOC is the location of the #pragma omp sections. */
18715
18716static tree
18717c_parser_omp_sections_scope (location_t sections_loc, c_parser *parser)
18718{
18719 tree stmt, substmt;
18720 bool error_suppress = false;
18721 location_t loc;
18722
18723 loc = c_parser_peek_token (parser)->location;
18724 if (!c_parser_require (parser, CPP_OPEN_BRACE, "expected %<{%>"))
18725 {
18726 /* Avoid skipping until the end of the block. */
18727 parser->error = false;
18728 return NULL_TREE;
18729 }
18730
18731 stmt = push_stmt_list ();
18732
18733 if (c_parser_peek_token (parser)->pragma_kind != PRAGMA_OMP_SECTION)
18734 {
dda1bf61 18735 substmt = c_parser_omp_structured_block (parser, NULL);
acf0174b
JJ
18736 substmt = build1 (OMP_SECTION, void_type_node, substmt);
18737 SET_EXPR_LOCATION (substmt, loc);
18738 add_stmt (substmt);
18739 }
18740
18741 while (1)
18742 {
18743 if (c_parser_next_token_is (parser, CPP_CLOSE_BRACE))
18744 break;
18745 if (c_parser_next_token_is (parser, CPP_EOF))
18746 break;
18747
18748 loc = c_parser_peek_token (parser)->location;
18749 if (c_parser_peek_token (parser)->pragma_kind == PRAGMA_OMP_SECTION)
18750 {
18751 c_parser_consume_pragma (parser);
18752 c_parser_skip_to_pragma_eol (parser);
18753 error_suppress = false;
18754 }
18755 else if (!error_suppress)
18756 {
18757 error_at (loc, "expected %<#pragma omp section%> or %<}%>");
18758 error_suppress = true;
18759 }
18760
dda1bf61 18761 substmt = c_parser_omp_structured_block (parser, NULL);
acf0174b
JJ
18762 substmt = build1 (OMP_SECTION, void_type_node, substmt);
18763 SET_EXPR_LOCATION (substmt, loc);
18764 add_stmt (substmt);
18765 }
18766 c_parser_skip_until_found (parser, CPP_CLOSE_BRACE,
18767 "expected %<#pragma omp section%> or %<}%>");
18768
18769 substmt = pop_stmt_list (stmt);
18770
18771 stmt = make_node (OMP_SECTIONS);
18772 SET_EXPR_LOCATION (stmt, sections_loc);
18773 TREE_TYPE (stmt) = void_type_node;
18774 OMP_SECTIONS_BODY (stmt) = substmt;
18775
18776 return add_stmt (stmt);
953ff289
DN
18777}
18778
18779/* OpenMP 2.5:
acf0174b
JJ
18780 # pragma omp sections sections-clause[optseq] newline
18781 sections-scope
c2255bc4 18782
acf0174b
JJ
18783 LOC is the location of the #pragma token.
18784*/
18785
18786#define OMP_SECTIONS_CLAUSE_MASK \
18787 ( (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_PRIVATE) \
18788 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_FIRSTPRIVATE) \
18789 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_LASTPRIVATE) \
18790 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_REDUCTION) \
18791 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_NOWAIT))
953ff289
DN
18792
18793static tree
acf0174b
JJ
18794c_parser_omp_sections (location_t loc, c_parser *parser,
18795 char *p_name, omp_clause_mask mask, tree *cclauses)
953ff289 18796{
acf0174b 18797 tree block, clauses, ret;
953ff289 18798
acf0174b
JJ
18799 strcat (p_name, " sections");
18800 mask |= OMP_SECTIONS_CLAUSE_MASK;
18801 if (cclauses)
18802 mask &= ~(OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_NOWAIT);
18803
18804 clauses = c_parser_omp_all_clauses (parser, mask, p_name, cclauses == NULL);
18805 if (cclauses)
18806 {
18807 omp_split_clauses (loc, OMP_SECTIONS, mask, clauses, cclauses);
18808 clauses = cclauses[C_OMP_CLAUSE_SPLIT_SECTIONS];
18809 }
18810
18811 block = c_begin_compound_stmt (true);
18812 ret = c_parser_omp_sections_scope (loc, parser);
18813 if (ret)
18814 OMP_SECTIONS_CLAUSES (ret) = clauses;
18815 block = c_end_compound_stmt (loc, block, true);
18816 add_stmt (block);
18817
18818 return ret;
18819}
18820
18821/* OpenMP 2.5:
cef0fd0e
TS
18822 # pragma omp parallel parallel-clause[optseq] new-line
18823 structured-block
18824 # pragma omp parallel for parallel-for-clause[optseq] new-line
18825 structured-block
18826 # pragma omp parallel sections parallel-sections-clause[optseq] new-line
18827 structured-block
18828
18829 OpenMP 4.0:
18830 # pragma omp parallel for simd parallel-for-simd-clause[optseq] new-line
18831 structured-block
acf0174b
JJ
18832
18833 LOC is the location of the #pragma token.
18834*/
18835
18836#define OMP_PARALLEL_CLAUSE_MASK \
18837 ( (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_IF) \
18838 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_PRIVATE) \
18839 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_FIRSTPRIVATE) \
18840 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_DEFAULT) \
18841 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_SHARED) \
18842 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_COPYIN) \
18843 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_REDUCTION) \
18844 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_NUM_THREADS) \
18845 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_PROC_BIND))
18846
18847static tree
18848c_parser_omp_parallel (location_t loc, c_parser *parser,
dda1bf61
JJ
18849 char *p_name, omp_clause_mask mask, tree *cclauses,
18850 bool *if_p)
acf0174b
JJ
18851{
18852 tree stmt, clauses, block;
18853
18854 strcat (p_name, " parallel");
18855 mask |= OMP_PARALLEL_CLAUSE_MASK;
d9a6bd32
JJ
18856 /* #pragma omp target parallel{, for, for simd} disallow copyin clause. */
18857 if ((mask & (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_MAP)) != 0
18858 && (mask & (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_DIST_SCHEDULE)) == 0)
18859 mask &= ~(OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_COPYIN);
acf0174b
JJ
18860
18861 if (c_parser_next_token_is_keyword (parser, RID_FOR))
953ff289 18862 {
acf0174b
JJ
18863 tree cclauses_buf[C_OMP_CLAUSE_SPLIT_COUNT];
18864 if (cclauses == NULL)
18865 cclauses = cclauses_buf;
18866
953ff289 18867 c_parser_consume_token (parser);
6d7f7e0a 18868 if (!flag_openmp) /* flag_openmp_simd */
dda1bf61 18869 return c_parser_omp_for (loc, parser, p_name, mask, cclauses, if_p);
acf0174b 18870 block = c_begin_omp_parallel ();
dda1bf61 18871 tree ret = c_parser_omp_for (loc, parser, p_name, mask, cclauses, if_p);
acf0174b
JJ
18872 stmt
18873 = c_finish_omp_parallel (loc, cclauses[C_OMP_CLAUSE_SPLIT_PARALLEL],
18874 block);
e162a134
JJ
18875 if (ret == NULL_TREE)
18876 return ret;
acf0174b
JJ
18877 OMP_PARALLEL_COMBINED (stmt) = 1;
18878 return stmt;
18879 }
d9a6bd32
JJ
18880 /* When combined with distribute, parallel has to be followed by for.
18881 #pragma omp target parallel is allowed though. */
18882 else if (cclauses
18883 && (mask & (OMP_CLAUSE_MASK_1
18884 << PRAGMA_OMP_CLAUSE_DIST_SCHEDULE)) != 0)
acf0174b
JJ
18885 {
18886 error_at (loc, "expected %<for%> after %qs", p_name);
18887 c_parser_skip_to_pragma_eol (parser);
18888 return NULL_TREE;
18889 }
554a530f 18890 else if (c_parser_next_token_is (parser, CPP_NAME))
acf0174b
JJ
18891 {
18892 const char *p = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
554a530f 18893 if (cclauses == NULL && strcmp (p, "master") == 0)
953ff289 18894 {
acf0174b 18895 tree cclauses_buf[C_OMP_CLAUSE_SPLIT_COUNT];
28567c40
JJ
18896 cclauses = cclauses_buf;
18897
18898 c_parser_consume_token (parser);
18899 if (!flag_openmp) /* flag_openmp_simd */
18900 return c_parser_omp_master (loc, parser, p_name, mask, cclauses,
18901 if_p);
18902 block = c_begin_omp_parallel ();
18903 tree ret = c_parser_omp_master (loc, parser, p_name, mask, cclauses,
18904 if_p);
18905 stmt = c_finish_omp_parallel (loc,
18906 cclauses[C_OMP_CLAUSE_SPLIT_PARALLEL],
18907 block);
28567c40
JJ
18908 if (ret == NULL)
18909 return ret;
4df50a05 18910 OMP_PARALLEL_COMBINED (stmt) = 1;
28567c40
JJ
18911 return stmt;
18912 }
554a530f
JJ
18913 else if (strcmp (p, "loop") == 0)
18914 {
18915 tree cclauses_buf[C_OMP_CLAUSE_SPLIT_COUNT];
18916 if (cclauses == NULL)
18917 cclauses = cclauses_buf;
18918
18919 c_parser_consume_token (parser);
18920 if (!flag_openmp) /* flag_openmp_simd */
18921 return c_parser_omp_loop (loc, parser, p_name, mask, cclauses,
18922 if_p);
18923 block = c_begin_omp_parallel ();
18924 tree ret = c_parser_omp_loop (loc, parser, p_name, mask, cclauses,
18925 if_p);
18926 stmt
18927 = c_finish_omp_parallel (loc,
18928 cclauses[C_OMP_CLAUSE_SPLIT_PARALLEL],
18929 block);
18930 if (ret == NULL_TREE)
18931 return ret;
18932 OMP_PARALLEL_COMBINED (stmt) = 1;
18933 return stmt;
18934 }
28567c40
JJ
18935 else if (!flag_openmp) /* flag_openmp_simd */
18936 {
18937 c_parser_skip_to_pragma_eol (parser, false);
18938 return NULL_TREE;
18939 }
554a530f 18940 else if (cclauses == NULL && strcmp (p, "sections") == 0)
28567c40
JJ
18941 {
18942 tree cclauses_buf[C_OMP_CLAUSE_SPLIT_COUNT];
18943 cclauses = cclauses_buf;
acf0174b 18944
953ff289 18945 c_parser_consume_token (parser);
acf0174b
JJ
18946 block = c_begin_omp_parallel ();
18947 c_parser_omp_sections (loc, parser, p_name, mask, cclauses);
18948 stmt = c_finish_omp_parallel (loc,
18949 cclauses[C_OMP_CLAUSE_SPLIT_PARALLEL],
18950 block);
18951 OMP_PARALLEL_COMBINED (stmt) = 1;
18952 return stmt;
953ff289 18953 }
953ff289 18954 }
28567c40
JJ
18955 else if (!flag_openmp) /* flag_openmp_simd */
18956 {
18957 c_parser_skip_to_pragma_eol (parser, false);
18958 return NULL_TREE;
18959 }
953ff289 18960
acf0174b 18961 clauses = c_parser_omp_all_clauses (parser, mask, p_name, cclauses == NULL);
d9a6bd32
JJ
18962 if (cclauses)
18963 {
18964 omp_split_clauses (loc, OMP_PARALLEL, mask, clauses, cclauses);
18965 clauses = cclauses[C_OMP_CLAUSE_SPLIT_PARALLEL];
18966 }
acf0174b
JJ
18967
18968 block = c_begin_omp_parallel ();
dda1bf61 18969 c_parser_statement (parser, if_p);
acf0174b
JJ
18970 stmt = c_finish_omp_parallel (loc, clauses, block);
18971
18972 return stmt;
18973}
18974
18975/* OpenMP 2.5:
18976 # pragma omp single single-clause[optseq] new-line
18977 structured-block
18978
18979 LOC is the location of the #pragma.
18980*/
18981
18982#define OMP_SINGLE_CLAUSE_MASK \
18983 ( (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_PRIVATE) \
18984 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_FIRSTPRIVATE) \
18985 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_COPYPRIVATE) \
18986 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_NOWAIT))
18987
18988static tree
dda1bf61 18989c_parser_omp_single (location_t loc, c_parser *parser, bool *if_p)
acf0174b
JJ
18990{
18991 tree stmt = make_node (OMP_SINGLE);
18992 SET_EXPR_LOCATION (stmt, loc);
18993 TREE_TYPE (stmt) = void_type_node;
18994
18995 OMP_SINGLE_CLAUSES (stmt)
18996 = c_parser_omp_all_clauses (parser, OMP_SINGLE_CLAUSE_MASK,
18997 "#pragma omp single");
dda1bf61 18998 OMP_SINGLE_BODY (stmt) = c_parser_omp_structured_block (parser, if_p);
acf0174b
JJ
18999
19000 return add_stmt (stmt);
19001}
19002
19003/* OpenMP 3.0:
19004 # pragma omp task task-clause[optseq] new-line
19005
19006 LOC is the location of the #pragma.
19007*/
19008
19009#define OMP_TASK_CLAUSE_MASK \
19010 ( (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_IF) \
19011 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_UNTIED) \
19012 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_DEFAULT) \
19013 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_PRIVATE) \
19014 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_FIRSTPRIVATE) \
19015 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_SHARED) \
19016 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_FINAL) \
19017 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_MERGEABLE) \
d9a6bd32 19018 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_DEPEND) \
28567c40
JJ
19019 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_PRIORITY) \
19020 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_IN_REDUCTION))
acf0174b
JJ
19021
19022static tree
dda1bf61 19023c_parser_omp_task (location_t loc, c_parser *parser, bool *if_p)
acf0174b
JJ
19024{
19025 tree clauses, block;
19026
19027 clauses = c_parser_omp_all_clauses (parser, OMP_TASK_CLAUSE_MASK,
19028 "#pragma omp task");
19029
19030 block = c_begin_omp_task ();
dda1bf61 19031 c_parser_statement (parser, if_p);
acf0174b 19032 return c_finish_omp_task (loc, clauses, block);
953ff289
DN
19033}
19034
acf0174b
JJ
19035/* OpenMP 3.0:
19036 # pragma omp taskwait new-line
28567c40
JJ
19037
19038 OpenMP 5.0:
19039 # pragma omp taskwait taskwait-clause[optseq] new-line
acf0174b 19040*/
953ff289 19041
28567c40
JJ
19042#define OMP_TASKWAIT_CLAUSE_MASK \
19043 (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_DEPEND)
19044
953ff289 19045static void
acf0174b 19046c_parser_omp_taskwait (c_parser *parser)
953ff289 19047{
c2255bc4 19048 location_t loc = c_parser_peek_token (parser)->location;
953ff289 19049 c_parser_consume_pragma (parser);
953ff289 19050
28567c40
JJ
19051 tree clauses
19052 = c_parser_omp_all_clauses (parser, OMP_TASKWAIT_CLAUSE_MASK,
19053 "#pragma omp taskwait");
19054
19055 if (clauses)
19056 {
19057 tree stmt = make_node (OMP_TASK);
19058 TREE_TYPE (stmt) = void_node;
19059 OMP_TASK_CLAUSES (stmt) = clauses;
19060 OMP_TASK_BODY (stmt) = NULL_TREE;
19061 SET_EXPR_LOCATION (stmt, loc);
19062 add_stmt (stmt);
19063 }
19064 else
19065 c_finish_omp_taskwait (loc);
953ff289
DN
19066}
19067
acf0174b
JJ
19068/* OpenMP 3.1:
19069 # pragma omp taskyield new-line
19070*/
953ff289 19071
acf0174b
JJ
19072static void
19073c_parser_omp_taskyield (c_parser *parser)
953ff289 19074{
acf0174b
JJ
19075 location_t loc = c_parser_peek_token (parser)->location;
19076 c_parser_consume_pragma (parser);
19077 c_parser_skip_to_pragma_eol (parser);
a68ab351 19078
acf0174b
JJ
19079 c_finish_omp_taskyield (loc);
19080}
3ba09659 19081
acf0174b
JJ
19082/* OpenMP 4.0:
19083 # pragma omp taskgroup new-line
28567c40
JJ
19084
19085 OpenMP 5.0:
19086 # pragma omp taskgroup taskgroup-clause[optseq] new-line
acf0174b 19087*/
953ff289 19088
28567c40
JJ
19089#define OMP_TASKGROUP_CLAUSE_MASK \
19090 ( (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_TASK_REDUCTION))
19091
acf0174b 19092static tree
28567c40 19093c_parser_omp_taskgroup (location_t loc, c_parser *parser, bool *if_p)
acf0174b 19094{
28567c40
JJ
19095 tree clauses = c_parser_omp_all_clauses (parser, OMP_TASKGROUP_CLAUSE_MASK,
19096 "#pragma omp taskgroup");
19097
19098 tree body = c_parser_omp_structured_block (parser, if_p);
19099 return c_finish_omp_taskgroup (loc, body, clauses);
acf0174b 19100}
c9f9eb5d 19101
acf0174b
JJ
19102/* OpenMP 4.0:
19103 # pragma omp cancel cancel-clause[optseq] new-line
953ff289 19104
acf0174b
JJ
19105 LOC is the location of the #pragma.
19106*/
a68ab351 19107
acf0174b
JJ
19108#define OMP_CANCEL_CLAUSE_MASK \
19109 ( (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_PARALLEL) \
19110 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_FOR) \
19111 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_SECTIONS) \
19112 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_TASKGROUP) \
19113 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_IF))
a68ab351 19114
acf0174b
JJ
19115static void
19116c_parser_omp_cancel (c_parser *parser)
19117{
19118 location_t loc = c_parser_peek_token (parser)->location;
a68ab351 19119
acf0174b
JJ
19120 c_parser_consume_pragma (parser);
19121 tree clauses = c_parser_omp_all_clauses (parser, OMP_CANCEL_CLAUSE_MASK,
19122 "#pragma omp cancel");
953ff289 19123
acf0174b
JJ
19124 c_finish_omp_cancel (loc, clauses);
19125}
953ff289 19126
acf0174b
JJ
19127/* OpenMP 4.0:
19128 # pragma omp cancellation point cancelpt-clause[optseq] new-line
953ff289 19129
acf0174b
JJ
19130 LOC is the location of the #pragma.
19131*/
953ff289 19132
acf0174b
JJ
19133#define OMP_CANCELLATION_POINT_CLAUSE_MASK \
19134 ( (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_PARALLEL) \
19135 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_FOR) \
19136 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_SECTIONS) \
19137 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_TASKGROUP))
a68ab351 19138
acf0174b 19139static void
54d19c3b 19140c_parser_omp_cancellation_point (c_parser *parser, enum pragma_context context)
acf0174b
JJ
19141{
19142 location_t loc = c_parser_peek_token (parser)->location;
19143 tree clauses;
19144 bool point_seen = false;
19145
19146 c_parser_consume_pragma (parser);
19147 if (c_parser_next_token_is (parser, CPP_NAME))
a68ab351 19148 {
acf0174b
JJ
19149 const char *p = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
19150 if (strcmp (p, "point") == 0)
a68ab351 19151 {
acf0174b
JJ
19152 c_parser_consume_token (parser);
19153 point_seen = true;
a68ab351 19154 }
a68ab351 19155 }
acf0174b 19156 if (!point_seen)
a68ab351 19157 {
acf0174b
JJ
19158 c_parser_error (parser, "expected %<point%>");
19159 c_parser_skip_to_pragma_eol (parser);
19160 return;
a68ab351 19161 }
953ff289 19162
54d19c3b
TS
19163 if (context != pragma_compound)
19164 {
19165 if (context == pragma_stmt)
a71dbc63
JJ
19166 error_at (loc,
19167 "%<#pragma %s%> may only be used in compound statements",
19168 "omp cancellation point");
54d19c3b
TS
19169 else
19170 c_parser_error (parser, "expected declaration specifiers");
19171 c_parser_skip_to_pragma_eol (parser, false);
19172 return;
19173 }
19174
acf0174b
JJ
19175 clauses
19176 = c_parser_omp_all_clauses (parser, OMP_CANCELLATION_POINT_CLAUSE_MASK,
19177 "#pragma omp cancellation point");
c2255bc4 19178
acf0174b
JJ
19179 c_finish_omp_cancellation_point (loc, clauses);
19180}
953ff289 19181
acf0174b
JJ
19182/* OpenMP 4.0:
19183 #pragma omp distribute distribute-clause[optseq] new-line
19184 for-loop */
19185
19186#define OMP_DISTRIBUTE_CLAUSE_MASK \
19187 ( (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_PRIVATE) \
19188 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_FIRSTPRIVATE) \
e01d41e5 19189 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_LASTPRIVATE) \
acf0174b
JJ
19190 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_DIST_SCHEDULE)\
19191 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_COLLAPSE))
953ff289
DN
19192
19193static tree
acf0174b 19194c_parser_omp_distribute (location_t loc, c_parser *parser,
dda1bf61
JJ
19195 char *p_name, omp_clause_mask mask, tree *cclauses,
19196 bool *if_p)
953ff289 19197{
acf0174b
JJ
19198 tree clauses, block, ret;
19199
19200 strcat (p_name, " distribute");
19201 mask |= OMP_DISTRIBUTE_CLAUSE_MASK;
19202
19203 if (c_parser_next_token_is (parser, CPP_NAME))
19204 {
19205 const char *p = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
19206 bool simd = false;
19207 bool parallel = false;
19208
19209 if (strcmp (p, "simd") == 0)
19210 simd = true;
19211 else
19212 parallel = strcmp (p, "parallel") == 0;
19213 if (parallel || simd)
19214 {
19215 tree cclauses_buf[C_OMP_CLAUSE_SPLIT_COUNT];
19216 if (cclauses == NULL)
19217 cclauses = cclauses_buf;
19218 c_parser_consume_token (parser);
6d7f7e0a
TB
19219 if (!flag_openmp) /* flag_openmp_simd */
19220 {
19221 if (simd)
dda1bf61
JJ
19222 return c_parser_omp_simd (loc, parser, p_name, mask, cclauses,
19223 if_p);
6d7f7e0a
TB
19224 else
19225 return c_parser_omp_parallel (loc, parser, p_name, mask,
dda1bf61 19226 cclauses, if_p);
6d7f7e0a 19227 }
acf0174b
JJ
19228 block = c_begin_compound_stmt (true);
19229 if (simd)
dda1bf61
JJ
19230 ret = c_parser_omp_simd (loc, parser, p_name, mask, cclauses,
19231 if_p);
acf0174b 19232 else
dda1bf61
JJ
19233 ret = c_parser_omp_parallel (loc, parser, p_name, mask, cclauses,
19234 if_p);
acf0174b
JJ
19235 block = c_end_compound_stmt (loc, block, true);
19236 if (ret == NULL)
19237 return ret;
19238 ret = make_node (OMP_DISTRIBUTE);
19239 TREE_TYPE (ret) = void_type_node;
19240 OMP_FOR_BODY (ret) = block;
19241 OMP_FOR_CLAUSES (ret) = cclauses[C_OMP_CLAUSE_SPLIT_DISTRIBUTE];
19242 SET_EXPR_LOCATION (ret, loc);
19243 add_stmt (ret);
19244 return ret;
19245 }
19246 }
6d7f7e0a
TB
19247 if (!flag_openmp) /* flag_openmp_simd */
19248 {
62021f64 19249 c_parser_skip_to_pragma_eol (parser, false);
6d7f7e0a
TB
19250 return NULL_TREE;
19251 }
953ff289 19252
acf0174b
JJ
19253 clauses = c_parser_omp_all_clauses (parser, mask, p_name, cclauses == NULL);
19254 if (cclauses)
19255 {
19256 omp_split_clauses (loc, OMP_DISTRIBUTE, mask, clauses, cclauses);
19257 clauses = cclauses[C_OMP_CLAUSE_SPLIT_DISTRIBUTE];
19258 }
953ff289
DN
19259
19260 block = c_begin_compound_stmt (true);
dda1bf61
JJ
19261 ret = c_parser_omp_for_loop (loc, parser, OMP_DISTRIBUTE, clauses, NULL,
19262 if_p);
c2255bc4 19263 block = c_end_compound_stmt (loc, block, true);
953ff289
DN
19264 add_stmt (block);
19265
19266 return ret;
19267}
19268
acf0174b
JJ
19269/* OpenMP 4.0:
19270 # pragma omp teams teams-clause[optseq] new-line
19271 structured-block */
c2255bc4 19272
acf0174b
JJ
19273#define OMP_TEAMS_CLAUSE_MASK \
19274 ( (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_PRIVATE) \
19275 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_FIRSTPRIVATE) \
19276 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_SHARED) \
19277 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_REDUCTION) \
19278 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_NUM_TEAMS) \
19279 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_THREAD_LIMIT) \
19280 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_DEFAULT))
953ff289
DN
19281
19282static tree
acf0174b 19283c_parser_omp_teams (location_t loc, c_parser *parser,
dda1bf61
JJ
19284 char *p_name, omp_clause_mask mask, tree *cclauses,
19285 bool *if_p)
953ff289 19286{
acf0174b
JJ
19287 tree clauses, block, ret;
19288
19289 strcat (p_name, " teams");
19290 mask |= OMP_TEAMS_CLAUSE_MASK;
19291
19292 if (c_parser_next_token_is (parser, CPP_NAME))
19293 {
19294 const char *p = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
19295 if (strcmp (p, "distribute") == 0)
19296 {
19297 tree cclauses_buf[C_OMP_CLAUSE_SPLIT_COUNT];
19298 if (cclauses == NULL)
19299 cclauses = cclauses_buf;
19300
19301 c_parser_consume_token (parser);
6d7f7e0a 19302 if (!flag_openmp) /* flag_openmp_simd */
dda1bf61
JJ
19303 return c_parser_omp_distribute (loc, parser, p_name, mask,
19304 cclauses, if_p);
28567c40 19305 block = c_begin_omp_parallel ();
dda1bf61
JJ
19306 ret = c_parser_omp_distribute (loc, parser, p_name, mask, cclauses,
19307 if_p);
acf0174b
JJ
19308 block = c_end_compound_stmt (loc, block, true);
19309 if (ret == NULL)
19310 return ret;
19311 clauses = cclauses[C_OMP_CLAUSE_SPLIT_TEAMS];
19312 ret = make_node (OMP_TEAMS);
19313 TREE_TYPE (ret) = void_type_node;
19314 OMP_TEAMS_CLAUSES (ret) = clauses;
19315 OMP_TEAMS_BODY (ret) = block;
41b37d5e 19316 OMP_TEAMS_COMBINED (ret) = 1;
28567c40 19317 SET_EXPR_LOCATION (ret, loc);
acf0174b
JJ
19318 return add_stmt (ret);
19319 }
554a530f
JJ
19320 else if (strcmp (p, "loop") == 0)
19321 {
19322 tree cclauses_buf[C_OMP_CLAUSE_SPLIT_COUNT];
19323 if (cclauses == NULL)
19324 cclauses = cclauses_buf;
19325
19326 c_parser_consume_token (parser);
19327 if (!flag_openmp) /* flag_openmp_simd */
19328 return c_parser_omp_loop (loc, parser, p_name, mask, cclauses,
19329 if_p);
19330 block = c_begin_omp_parallel ();
19331 ret = c_parser_omp_loop (loc, parser, p_name, mask, cclauses, if_p);
19332 block = c_end_compound_stmt (loc, block, true);
19333 if (ret == NULL)
19334 return ret;
19335 clauses = cclauses[C_OMP_CLAUSE_SPLIT_TEAMS];
19336 ret = make_node (OMP_TEAMS);
19337 TREE_TYPE (ret) = void_type_node;
19338 OMP_TEAMS_CLAUSES (ret) = clauses;
19339 OMP_TEAMS_BODY (ret) = block;
19340 OMP_TEAMS_COMBINED (ret) = 1;
19341 SET_EXPR_LOCATION (ret, loc);
19342 return add_stmt (ret);
19343 }
acf0174b 19344 }
6d7f7e0a
TB
19345 if (!flag_openmp) /* flag_openmp_simd */
19346 {
62021f64 19347 c_parser_skip_to_pragma_eol (parser, false);
6d7f7e0a
TB
19348 return NULL_TREE;
19349 }
acf0174b
JJ
19350
19351 clauses = c_parser_omp_all_clauses (parser, mask, p_name, cclauses == NULL);
19352 if (cclauses)
19353 {
19354 omp_split_clauses (loc, OMP_TEAMS, mask, clauses, cclauses);
19355 clauses = cclauses[C_OMP_CLAUSE_SPLIT_TEAMS];
19356 }
19357
19358 tree stmt = make_node (OMP_TEAMS);
19359 TREE_TYPE (stmt) = void_type_node;
19360 OMP_TEAMS_CLAUSES (stmt) = clauses;
28567c40
JJ
19361 block = c_begin_omp_parallel ();
19362 add_stmt (c_parser_omp_structured_block (parser, if_p));
19363 OMP_TEAMS_BODY (stmt) = c_end_compound_stmt (loc, block, true);
19364 SET_EXPR_LOCATION (stmt, loc);
acf0174b
JJ
19365
19366 return add_stmt (stmt);
953ff289
DN
19367}
19368
acf0174b
JJ
19369/* OpenMP 4.0:
19370 # pragma omp target data target-data-clause[optseq] new-line
19371 structured-block */
c2255bc4 19372
acf0174b
JJ
19373#define OMP_TARGET_DATA_CLAUSE_MASK \
19374 ( (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_DEVICE) \
19375 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_MAP) \
d9a6bd32 19376 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_IF) \
398e3feb
JJ
19377 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_USE_DEVICE_PTR) \
19378 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_USE_DEVICE_ADDR))
953ff289
DN
19379
19380static tree
dda1bf61 19381c_parser_omp_target_data (location_t loc, c_parser *parser, bool *if_p)
953ff289 19382{
d9a6bd32 19383 tree clauses
acf0174b
JJ
19384 = c_parser_omp_all_clauses (parser, OMP_TARGET_DATA_CLAUSE_MASK,
19385 "#pragma omp target data");
d9a6bd32
JJ
19386 int map_seen = 0;
19387 for (tree *pc = &clauses; *pc;)
19388 {
19389 if (OMP_CLAUSE_CODE (*pc) == OMP_CLAUSE_MAP)
19390 switch (OMP_CLAUSE_MAP_KIND (*pc))
19391 {
19392 case GOMP_MAP_TO:
19393 case GOMP_MAP_ALWAYS_TO:
19394 case GOMP_MAP_FROM:
19395 case GOMP_MAP_ALWAYS_FROM:
19396 case GOMP_MAP_TOFROM:
19397 case GOMP_MAP_ALWAYS_TOFROM:
19398 case GOMP_MAP_ALLOC:
19399 map_seen = 3;
19400 break;
19401 case GOMP_MAP_FIRSTPRIVATE_POINTER:
e01d41e5 19402 case GOMP_MAP_ALWAYS_POINTER:
d9a6bd32
JJ
19403 break;
19404 default:
19405 map_seen |= 1;
19406 error_at (OMP_CLAUSE_LOCATION (*pc),
19407 "%<#pragma omp target data%> with map-type other "
19408 "than %<to%>, %<from%>, %<tofrom%> or %<alloc%> "
19409 "on %<map%> clause");
19410 *pc = OMP_CLAUSE_CHAIN (*pc);
19411 continue;
19412 }
398e3feb
JJ
19413 else if (OMP_CLAUSE_CODE (*pc) == OMP_CLAUSE_USE_DEVICE_PTR
19414 || OMP_CLAUSE_CODE (*pc) == OMP_CLAUSE_USE_DEVICE_ADDR)
28567c40 19415 map_seen = 3;
d9a6bd32
JJ
19416 pc = &OMP_CLAUSE_CHAIN (*pc);
19417 }
19418
19419 if (map_seen != 3)
19420 {
19421 if (map_seen == 0)
19422 error_at (loc,
19423 "%<#pragma omp target data%> must contain at least "
398e3feb
JJ
19424 "one %<map%>, %<use_device_ptr%> or %<use_device_addr%> "
19425 "clause");
d9a6bd32
JJ
19426 return NULL_TREE;
19427 }
19428
19429 tree stmt = make_node (OMP_TARGET_DATA);
19430 TREE_TYPE (stmt) = void_type_node;
19431 OMP_TARGET_DATA_CLAUSES (stmt) = clauses;
acf0174b
JJ
19432 keep_next_level ();
19433 tree block = c_begin_compound_stmt (true);
dda1bf61 19434 add_stmt (c_parser_omp_structured_block (parser, if_p));
acf0174b 19435 OMP_TARGET_DATA_BODY (stmt) = c_end_compound_stmt (loc, block, true);
953ff289 19436
acf0174b
JJ
19437 SET_EXPR_LOCATION (stmt, loc);
19438 return add_stmt (stmt);
19439}
953ff289 19440
acf0174b
JJ
19441/* OpenMP 4.0:
19442 # pragma omp target update target-update-clause[optseq] new-line */
c2255bc4 19443
acf0174b
JJ
19444#define OMP_TARGET_UPDATE_CLAUSE_MASK \
19445 ( (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_FROM) \
19446 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_TO) \
19447 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_DEVICE) \
d9a6bd32
JJ
19448 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_IF) \
19449 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_DEPEND) \
19450 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_NOWAIT))
953ff289 19451
acf0174b
JJ
19452static bool
19453c_parser_omp_target_update (location_t loc, c_parser *parser,
19454 enum pragma_context context)
953ff289 19455{
acf0174b
JJ
19456 if (context == pragma_stmt)
19457 {
a71dbc63
JJ
19458 error_at (loc, "%<#pragma %s%> may only be used in compound statements",
19459 "omp target update");
aec17bfe 19460 c_parser_skip_to_pragma_eol (parser, false);
acf0174b
JJ
19461 return false;
19462 }
953ff289 19463
acf0174b
JJ
19464 tree clauses
19465 = c_parser_omp_all_clauses (parser, OMP_TARGET_UPDATE_CLAUSE_MASK,
19466 "#pragma omp target update");
629b3d75
MJ
19467 if (omp_find_clause (clauses, OMP_CLAUSE_TO) == NULL_TREE
19468 && omp_find_clause (clauses, OMP_CLAUSE_FROM) == NULL_TREE)
953ff289 19469 {
acf0174b 19470 error_at (loc,
06aca1d5 19471 "%<#pragma omp target update%> must contain at least one "
acf0174b
JJ
19472 "%<from%> or %<to%> clauses");
19473 return false;
953ff289
DN
19474 }
19475
acf0174b
JJ
19476 tree stmt = make_node (OMP_TARGET_UPDATE);
19477 TREE_TYPE (stmt) = void_type_node;
19478 OMP_TARGET_UPDATE_CLAUSES (stmt) = clauses;
19479 SET_EXPR_LOCATION (stmt, loc);
19480 add_stmt (stmt);
19481 return false;
19482}
953ff289 19483
d9a6bd32
JJ
19484/* OpenMP 4.5:
19485 # pragma omp target enter data target-data-clause[optseq] new-line */
19486
19487#define OMP_TARGET_ENTER_DATA_CLAUSE_MASK \
19488 ( (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_DEVICE) \
19489 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_MAP) \
19490 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_IF) \
19491 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_DEPEND) \
19492 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_NOWAIT))
19493
19494static tree
19495c_parser_omp_target_enter_data (location_t loc, c_parser *parser,
19496 enum pragma_context context)
19497{
19498 bool data_seen = false;
19499 if (c_parser_next_token_is (parser, CPP_NAME))
19500 {
19501 const char *p = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
19502 if (strcmp (p, "data") == 0)
19503 {
19504 c_parser_consume_token (parser);
19505 data_seen = true;
19506 }
19507 }
19508 if (!data_seen)
19509 {
19510 c_parser_error (parser, "expected %<data%>");
19511 c_parser_skip_to_pragma_eol (parser);
19512 return NULL_TREE;
19513 }
19514
19515 if (context == pragma_stmt)
19516 {
a71dbc63
JJ
19517 error_at (loc, "%<#pragma %s%> may only be used in compound statements",
19518 "omp target enter data");
aec17bfe 19519 c_parser_skip_to_pragma_eol (parser, false);
d9a6bd32
JJ
19520 return NULL_TREE;
19521 }
19522
19523 tree clauses
19524 = c_parser_omp_all_clauses (parser, OMP_TARGET_ENTER_DATA_CLAUSE_MASK,
19525 "#pragma omp target enter data");
19526 int map_seen = 0;
19527 for (tree *pc = &clauses; *pc;)
19528 {
19529 if (OMP_CLAUSE_CODE (*pc) == OMP_CLAUSE_MAP)
19530 switch (OMP_CLAUSE_MAP_KIND (*pc))
19531 {
19532 case GOMP_MAP_TO:
19533 case GOMP_MAP_ALWAYS_TO:
19534 case GOMP_MAP_ALLOC:
19535 map_seen = 3;
19536 break;
19537 case GOMP_MAP_FIRSTPRIVATE_POINTER:
e01d41e5 19538 case GOMP_MAP_ALWAYS_POINTER:
d9a6bd32
JJ
19539 break;
19540 default:
19541 map_seen |= 1;
19542 error_at (OMP_CLAUSE_LOCATION (*pc),
19543 "%<#pragma omp target enter data%> with map-type other "
19544 "than %<to%> or %<alloc%> on %<map%> clause");
19545 *pc = OMP_CLAUSE_CHAIN (*pc);
19546 continue;
19547 }
19548 pc = &OMP_CLAUSE_CHAIN (*pc);
19549 }
19550
19551 if (map_seen != 3)
19552 {
19553 if (map_seen == 0)
19554 error_at (loc,
19555 "%<#pragma omp target enter data%> must contain at least "
19556 "one %<map%> clause");
19557 return NULL_TREE;
19558 }
19559
19560 tree stmt = make_node (OMP_TARGET_ENTER_DATA);
19561 TREE_TYPE (stmt) = void_type_node;
19562 OMP_TARGET_ENTER_DATA_CLAUSES (stmt) = clauses;
19563 SET_EXPR_LOCATION (stmt, loc);
19564 add_stmt (stmt);
19565 return stmt;
19566}
19567
19568/* OpenMP 4.5:
19569 # pragma omp target exit data target-data-clause[optseq] new-line */
19570
19571#define OMP_TARGET_EXIT_DATA_CLAUSE_MASK \
19572 ( (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_DEVICE) \
19573 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_MAP) \
19574 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_IF) \
19575 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_DEPEND) \
19576 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_NOWAIT))
19577
19578static tree
19579c_parser_omp_target_exit_data (location_t loc, c_parser *parser,
19580 enum pragma_context context)
19581{
19582 bool data_seen = false;
19583 if (c_parser_next_token_is (parser, CPP_NAME))
19584 {
19585 const char *p = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
19586 if (strcmp (p, "data") == 0)
19587 {
19588 c_parser_consume_token (parser);
19589 data_seen = true;
19590 }
19591 }
19592 if (!data_seen)
19593 {
19594 c_parser_error (parser, "expected %<data%>");
19595 c_parser_skip_to_pragma_eol (parser);
19596 return NULL_TREE;
19597 }
19598
19599 if (context == pragma_stmt)
19600 {
a71dbc63
JJ
19601 error_at (loc, "%<#pragma %s%> may only be used in compound statements",
19602 "omp target exit data");
aec17bfe 19603 c_parser_skip_to_pragma_eol (parser, false);
d9a6bd32
JJ
19604 return NULL_TREE;
19605 }
19606
19607 tree clauses
19608 = c_parser_omp_all_clauses (parser, OMP_TARGET_EXIT_DATA_CLAUSE_MASK,
19609 "#pragma omp target exit data");
19610
19611 int map_seen = 0;
19612 for (tree *pc = &clauses; *pc;)
19613 {
19614 if (OMP_CLAUSE_CODE (*pc) == OMP_CLAUSE_MAP)
19615 switch (OMP_CLAUSE_MAP_KIND (*pc))
19616 {
19617 case GOMP_MAP_FROM:
19618 case GOMP_MAP_ALWAYS_FROM:
19619 case GOMP_MAP_RELEASE:
19620 case GOMP_MAP_DELETE:
19621 map_seen = 3;
19622 break;
19623 case GOMP_MAP_FIRSTPRIVATE_POINTER:
e01d41e5 19624 case GOMP_MAP_ALWAYS_POINTER:
d9a6bd32
JJ
19625 break;
19626 default:
19627 map_seen |= 1;
19628 error_at (OMP_CLAUSE_LOCATION (*pc),
19629 "%<#pragma omp target exit data%> with map-type other "
883c8f06 19630 "than %<from%>, %<release%> or %<delete%> on %<map%>"
d9a6bd32
JJ
19631 " clause");
19632 *pc = OMP_CLAUSE_CHAIN (*pc);
19633 continue;
19634 }
19635 pc = &OMP_CLAUSE_CHAIN (*pc);
19636 }
19637
19638 if (map_seen != 3)
19639 {
19640 if (map_seen == 0)
19641 error_at (loc,
19642 "%<#pragma omp target exit data%> must contain at least one "
19643 "%<map%> clause");
19644 return NULL_TREE;
19645 }
19646
19647 tree stmt = make_node (OMP_TARGET_EXIT_DATA);
19648 TREE_TYPE (stmt) = void_type_node;
19649 OMP_TARGET_EXIT_DATA_CLAUSES (stmt) = clauses;
19650 SET_EXPR_LOCATION (stmt, loc);
19651 add_stmt (stmt);
19652 return stmt;
19653}
19654
acf0174b
JJ
19655/* OpenMP 4.0:
19656 # pragma omp target target-clause[optseq] new-line
19657 structured-block */
953ff289 19658
acf0174b
JJ
19659#define OMP_TARGET_CLAUSE_MASK \
19660 ( (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_DEVICE) \
19661 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_MAP) \
d9a6bd32
JJ
19662 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_IF) \
19663 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_DEPEND) \
19664 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_NOWAIT) \
19665 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_PRIVATE) \
19666 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_FIRSTPRIVATE) \
19667 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_DEFAULTMAP) \
19668 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_IS_DEVICE_PTR))
953ff289 19669
acf0174b 19670static bool
dda1bf61 19671c_parser_omp_target (c_parser *parser, enum pragma_context context, bool *if_p)
acf0174b
JJ
19672{
19673 location_t loc = c_parser_peek_token (parser)->location;
19674 c_parser_consume_pragma (parser);
d9a6bd32 19675 tree *pc = NULL, stmt, block;
953ff289 19676
acf0174b
JJ
19677 if (context != pragma_stmt && context != pragma_compound)
19678 {
19679 c_parser_error (parser, "expected declaration specifiers");
19680 c_parser_skip_to_pragma_eol (parser);
19681 return false;
953ff289
DN
19682 }
19683
28567c40
JJ
19684 if (flag_openmp)
19685 omp_requires_mask
19686 = (enum omp_requires) (omp_requires_mask | OMP_REQUIRES_TARGET_USED);
19687
acf0174b 19688 if (c_parser_next_token_is (parser, CPP_NAME))
953ff289 19689 {
acf0174b 19690 const char *p = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
d9a6bd32 19691 enum tree_code ccode = ERROR_MARK;
953ff289 19692
6d7f7e0a 19693 if (strcmp (p, "teams") == 0)
d9a6bd32
JJ
19694 ccode = OMP_TEAMS;
19695 else if (strcmp (p, "parallel") == 0)
19696 ccode = OMP_PARALLEL;
19697 else if (strcmp (p, "simd") == 0)
19698 ccode = OMP_SIMD;
19699 if (ccode != ERROR_MARK)
acf0174b
JJ
19700 {
19701 tree cclauses[C_OMP_CLAUSE_SPLIT_COUNT];
19702 char p_name[sizeof ("#pragma omp target teams distribute "
19703 "parallel for simd")];
953ff289 19704
acf0174b 19705 c_parser_consume_token (parser);
e7bd1de1 19706 strcpy (p_name, "#pragma omp target");
6d7f7e0a 19707 if (!flag_openmp) /* flag_openmp_simd */
edbba2ce 19708 {
d9a6bd32
JJ
19709 tree stmt;
19710 switch (ccode)
19711 {
19712 case OMP_TEAMS:
19713 stmt = c_parser_omp_teams (loc, parser, p_name,
19714 OMP_TARGET_CLAUSE_MASK,
dda1bf61 19715 cclauses, if_p);
d9a6bd32
JJ
19716 break;
19717 case OMP_PARALLEL:
19718 stmt = c_parser_omp_parallel (loc, parser, p_name,
19719 OMP_TARGET_CLAUSE_MASK,
dda1bf61 19720 cclauses, if_p);
d9a6bd32
JJ
19721 break;
19722 case OMP_SIMD:
19723 stmt = c_parser_omp_simd (loc, parser, p_name,
19724 OMP_TARGET_CLAUSE_MASK,
dda1bf61 19725 cclauses, if_p);
d9a6bd32
JJ
19726 break;
19727 default:
19728 gcc_unreachable ();
19729 }
edbba2ce
TS
19730 return stmt != NULL_TREE;
19731 }
acf0174b 19732 keep_next_level ();
d9a6bd32
JJ
19733 tree block = c_begin_compound_stmt (true), ret;
19734 switch (ccode)
19735 {
19736 case OMP_TEAMS:
19737 ret = c_parser_omp_teams (loc, parser, p_name,
dda1bf61
JJ
19738 OMP_TARGET_CLAUSE_MASK, cclauses,
19739 if_p);
d9a6bd32
JJ
19740 break;
19741 case OMP_PARALLEL:
19742 ret = c_parser_omp_parallel (loc, parser, p_name,
dda1bf61
JJ
19743 OMP_TARGET_CLAUSE_MASK, cclauses,
19744 if_p);
d9a6bd32
JJ
19745 break;
19746 case OMP_SIMD:
19747 ret = c_parser_omp_simd (loc, parser, p_name,
dda1bf61
JJ
19748 OMP_TARGET_CLAUSE_MASK, cclauses,
19749 if_p);
d9a6bd32
JJ
19750 break;
19751 default:
19752 gcc_unreachable ();
19753 }
acf0174b 19754 block = c_end_compound_stmt (loc, block, true);
edbba2ce
TS
19755 if (ret == NULL_TREE)
19756 return false;
e01d41e5
JJ
19757 if (ccode == OMP_TEAMS)
19758 {
19759 /* For combined target teams, ensure the num_teams and
19760 thread_limit clause expressions are evaluated on the host,
19761 before entering the target construct. */
19762 tree c;
19763 for (c = cclauses[C_OMP_CLAUSE_SPLIT_TEAMS];
19764 c; c = OMP_CLAUSE_CHAIN (c))
19765 if ((OMP_CLAUSE_CODE (c) == OMP_CLAUSE_NUM_TEAMS
19766 || OMP_CLAUSE_CODE (c) == OMP_CLAUSE_THREAD_LIMIT)
19767 && TREE_CODE (OMP_CLAUSE_OPERAND (c, 0)) != INTEGER_CST)
19768 {
19769 tree expr = OMP_CLAUSE_OPERAND (c, 0);
19770 tree tmp = create_tmp_var_raw (TREE_TYPE (expr));
19771 expr = build4 (TARGET_EXPR, TREE_TYPE (expr), tmp,
19772 expr, NULL_TREE, NULL_TREE);
19773 add_stmt (expr);
19774 OMP_CLAUSE_OPERAND (c, 0) = expr;
19775 tree tc = build_omp_clause (OMP_CLAUSE_LOCATION (c),
19776 OMP_CLAUSE_FIRSTPRIVATE);
19777 OMP_CLAUSE_DECL (tc) = tmp;
19778 OMP_CLAUSE_CHAIN (tc)
19779 = cclauses[C_OMP_CLAUSE_SPLIT_TARGET];
19780 cclauses[C_OMP_CLAUSE_SPLIT_TARGET] = tc;
19781 }
19782 }
acf0174b
JJ
19783 tree stmt = make_node (OMP_TARGET);
19784 TREE_TYPE (stmt) = void_type_node;
19785 OMP_TARGET_CLAUSES (stmt) = cclauses[C_OMP_CLAUSE_SPLIT_TARGET];
19786 OMP_TARGET_BODY (stmt) = block;
d9a6bd32 19787 OMP_TARGET_COMBINED (stmt) = 1;
28567c40 19788 SET_EXPR_LOCATION (stmt, loc);
acf0174b 19789 add_stmt (stmt);
d9a6bd32
JJ
19790 pc = &OMP_TARGET_CLAUSES (stmt);
19791 goto check_clauses;
acf0174b 19792 }
6d7f7e0a
TB
19793 else if (!flag_openmp) /* flag_openmp_simd */
19794 {
62021f64 19795 c_parser_skip_to_pragma_eol (parser, false);
edbba2ce 19796 return false;
6d7f7e0a
TB
19797 }
19798 else if (strcmp (p, "data") == 0)
19799 {
19800 c_parser_consume_token (parser);
dda1bf61 19801 c_parser_omp_target_data (loc, parser, if_p);
6d7f7e0a
TB
19802 return true;
19803 }
d9a6bd32
JJ
19804 else if (strcmp (p, "enter") == 0)
19805 {
19806 c_parser_consume_token (parser);
19807 c_parser_omp_target_enter_data (loc, parser, context);
19808 return false;
19809 }
19810 else if (strcmp (p, "exit") == 0)
19811 {
19812 c_parser_consume_token (parser);
19813 c_parser_omp_target_exit_data (loc, parser, context);
19814 return false;
19815 }
6d7f7e0a
TB
19816 else if (strcmp (p, "update") == 0)
19817 {
19818 c_parser_consume_token (parser);
19819 return c_parser_omp_target_update (loc, parser, context);
19820 }
953ff289 19821 }
bcac0b4d
JJ
19822 if (!flag_openmp) /* flag_openmp_simd */
19823 {
19824 c_parser_skip_to_pragma_eol (parser, false);
19825 return false;
19826 }
953ff289 19827
d9a6bd32 19828 stmt = make_node (OMP_TARGET);
953ff289 19829 TREE_TYPE (stmt) = void_type_node;
953ff289 19830
acf0174b
JJ
19831 OMP_TARGET_CLAUSES (stmt)
19832 = c_parser_omp_all_clauses (parser, OMP_TARGET_CLAUSE_MASK,
19833 "#pragma omp target");
d9a6bd32 19834 pc = &OMP_TARGET_CLAUSES (stmt);
acf0174b 19835 keep_next_level ();
d9a6bd32 19836 block = c_begin_compound_stmt (true);
dda1bf61 19837 add_stmt (c_parser_omp_structured_block (parser, if_p));
acf0174b
JJ
19838 OMP_TARGET_BODY (stmt) = c_end_compound_stmt (loc, block, true);
19839
19840 SET_EXPR_LOCATION (stmt, loc);
19841 add_stmt (stmt);
d9a6bd32
JJ
19842
19843check_clauses:
19844 while (*pc)
19845 {
19846 if (OMP_CLAUSE_CODE (*pc) == OMP_CLAUSE_MAP)
19847 switch (OMP_CLAUSE_MAP_KIND (*pc))
19848 {
19849 case GOMP_MAP_TO:
19850 case GOMP_MAP_ALWAYS_TO:
19851 case GOMP_MAP_FROM:
19852 case GOMP_MAP_ALWAYS_FROM:
19853 case GOMP_MAP_TOFROM:
19854 case GOMP_MAP_ALWAYS_TOFROM:
19855 case GOMP_MAP_ALLOC:
19856 case GOMP_MAP_FIRSTPRIVATE_POINTER:
e01d41e5 19857 case GOMP_MAP_ALWAYS_POINTER:
d9a6bd32
JJ
19858 break;
19859 default:
19860 error_at (OMP_CLAUSE_LOCATION (*pc),
19861 "%<#pragma omp target%> with map-type other "
19862 "than %<to%>, %<from%>, %<tofrom%> or %<alloc%> "
19863 "on %<map%> clause");
19864 *pc = OMP_CLAUSE_CHAIN (*pc);
19865 continue;
19866 }
19867 pc = &OMP_CLAUSE_CHAIN (*pc);
19868 }
49ddde69 19869 cfun->has_omp_target = true;
acf0174b
JJ
19870 return true;
19871}
19872
19873/* OpenMP 4.0:
94e7f906
JJ
19874 # pragma omp declare simd declare-simd-clauses[optseq] new-line
19875
19876 OpenMP 5.0:
19877 # pragma omp declare variant (identifier) match(context-selector) new-line
19878 */
acf0174b
JJ
19879
19880#define OMP_DECLARE_SIMD_CLAUSE_MASK \
19881 ( (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_SIMDLEN) \
19882 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_LINEAR) \
19883 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_ALIGNED) \
19884 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_UNIFORM) \
19885 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_INBRANCH) \
19886 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_NOTINBRANCH))
19887
19888static void
19889c_parser_omp_declare_simd (c_parser *parser, enum pragma_context context)
19890{
94e7f906
JJ
19891 c_token *token = c_parser_peek_token (parser);
19892 gcc_assert (token->type == CPP_NAME);
19893 tree kind = token->value;
19894 gcc_assert (strcmp (IDENTIFIER_POINTER (kind), "simd") == 0
19895 || strcmp (IDENTIFIER_POINTER (kind), "variant") == 0);
19896
8c681247 19897 auto_vec<c_token> clauses;
acf0174b
JJ
19898 while (c_parser_next_token_is_not (parser, CPP_PRAGMA_EOL))
19899 {
19900 c_token *token = c_parser_peek_token (parser);
19901 if (token->type == CPP_EOF)
19902 {
19903 c_parser_skip_to_pragma_eol (parser);
acf0174b
JJ
19904 return;
19905 }
19906 clauses.safe_push (*token);
19907 c_parser_consume_token (parser);
19908 }
19909 clauses.safe_push (*c_parser_peek_token (parser));
19910 c_parser_skip_to_pragma_eol (parser);
19911
19912 while (c_parser_next_token_is (parser, CPP_PRAGMA))
19913 {
94e7f906 19914 if (c_parser_peek_token (parser)->pragma_kind != PRAGMA_OMP_DECLARE
acf0174b 19915 || c_parser_peek_2nd_token (parser)->type != CPP_NAME
94e7f906 19916 || c_parser_peek_2nd_token (parser)->value != kind)
acf0174b 19917 {
94e7f906
JJ
19918 error ("%<#pragma omp declare %s%> must be followed by "
19919 "function declaration or definition or another "
19920 "%<#pragma omp declare %s%>",
19921 IDENTIFIER_POINTER (kind), IDENTIFIER_POINTER (kind));
acf0174b
JJ
19922 return;
19923 }
19924 c_parser_consume_pragma (parser);
19925 while (c_parser_next_token_is_not (parser, CPP_PRAGMA_EOL))
19926 {
19927 c_token *token = c_parser_peek_token (parser);
19928 if (token->type == CPP_EOF)
19929 {
19930 c_parser_skip_to_pragma_eol (parser);
acf0174b
JJ
19931 return;
19932 }
19933 clauses.safe_push (*token);
19934 c_parser_consume_token (parser);
19935 }
19936 clauses.safe_push (*c_parser_peek_token (parser));
19937 c_parser_skip_to_pragma_eol (parser);
19938 }
19939
19940 /* Make sure nothing tries to read past the end of the tokens. */
19941 c_token eof_token;
19942 memset (&eof_token, 0, sizeof (eof_token));
19943 eof_token.type = CPP_EOF;
19944 clauses.safe_push (eof_token);
19945 clauses.safe_push (eof_token);
19946
19947 switch (context)
19948 {
19949 case pragma_external:
19950 if (c_parser_next_token_is (parser, CPP_KEYWORD)
19951 && c_parser_peek_token (parser)->keyword == RID_EXTENSION)
19952 {
19953 int ext = disable_extension_diagnostics ();
19954 do
19955 c_parser_consume_token (parser);
19956 while (c_parser_next_token_is (parser, CPP_KEYWORD)
19957 && c_parser_peek_token (parser)->keyword == RID_EXTENSION);
19958 c_parser_declaration_or_fndef (parser, true, true, true, false, true,
19959 NULL, clauses);
19960 restore_extension_diagnostics (ext);
19961 }
19962 else
19963 c_parser_declaration_or_fndef (parser, true, true, true, false, true,
19964 NULL, clauses);
19965 break;
19966 case pragma_struct:
19967 case pragma_param:
41521dee 19968 case pragma_stmt:
94e7f906
JJ
19969 error ("%<#pragma omp declare %s%> must be followed by "
19970 "function declaration or definition",
19971 IDENTIFIER_POINTER (kind));
acf0174b
JJ
19972 break;
19973 case pragma_compound:
acf0174b
JJ
19974 if (c_parser_next_token_is (parser, CPP_KEYWORD)
19975 && c_parser_peek_token (parser)->keyword == RID_EXTENSION)
19976 {
19977 int ext = disable_extension_diagnostics ();
19978 do
19979 c_parser_consume_token (parser);
19980 while (c_parser_next_token_is (parser, CPP_KEYWORD)
19981 && c_parser_peek_token (parser)->keyword == RID_EXTENSION);
19982 if (c_parser_next_tokens_start_declaration (parser))
19983 {
19984 c_parser_declaration_or_fndef (parser, true, true, true, true,
19985 true, NULL, clauses);
19986 restore_extension_diagnostics (ext);
19987 break;
19988 }
19989 restore_extension_diagnostics (ext);
19990 }
19991 else if (c_parser_next_tokens_start_declaration (parser))
19992 {
19993 c_parser_declaration_or_fndef (parser, true, true, true, true, true,
19994 NULL, clauses);
19995 break;
19996 }
94e7f906
JJ
19997 error ("%<#pragma omp declare %s%> must be followed by "
19998 "function declaration or definition",
19999 IDENTIFIER_POINTER (kind));
acf0174b
JJ
20000 break;
20001 default:
20002 gcc_unreachable ();
20003 }
953ff289
DN
20004}
20005
94e7f906
JJ
20006static const char *const omp_construct_selectors[] = {
20007 "simd", "target", "teams", "parallel", "for", NULL };
20008static const char *const omp_device_selectors[] = {
20009 "kind", "isa", "arch", NULL };
20010static const char *const omp_implementation_selectors[] = {
20011 "vendor", "extension", "atomic_default_mem_order", "unified_address",
20012 "unified_shared_memory", "dynamic_allocators", "reverse_offload", NULL };
20013static const char *const omp_user_selectors[] = {
20014 "condition", NULL };
20015
20016/* OpenMP 5.0:
20017
20018 trait-selector:
20019 trait-selector-name[([trait-score:]trait-property[,trait-property[,...]])]
20020
20021 trait-score:
20022 score(score-expression) */
20023
20024static tree
20025c_parser_omp_context_selector (c_parser *parser, tree set, tree parms)
20026{
20027 tree ret = NULL_TREE;
20028 do
20029 {
20030 tree selector;
20031 if (c_parser_next_token_is (parser, CPP_KEYWORD)
20032 || c_parser_next_token_is (parser, CPP_NAME))
20033 selector = c_parser_peek_token (parser)->value;
20034 else
20035 {
20036 c_parser_error (parser, "expected trait selector name");
20037 return error_mark_node;
20038 }
20039
20040 tree properties = NULL_TREE;
20041 const char *const *selectors = NULL;
20042 bool allow_score = true;
20043 bool allow_user = false;
20044 int property_limit = 0;
b2417b59
JJ
20045 enum { CTX_PROPERTY_NONE, CTX_PROPERTY_USER, CTX_PROPERTY_NAME_LIST,
20046 CTX_PROPERTY_ID, CTX_PROPERTY_EXPR,
20047 CTX_PROPERTY_SIMD } property_kind = CTX_PROPERTY_NONE;
94e7f906
JJ
20048 switch (IDENTIFIER_POINTER (set)[0])
20049 {
20050 case 'c': /* construct */
20051 selectors = omp_construct_selectors;
20052 allow_score = false;
20053 property_limit = 1;
20054 property_kind = CTX_PROPERTY_SIMD;
20055 break;
20056 case 'd': /* device */
20057 selectors = omp_device_selectors;
20058 allow_score = false;
20059 allow_user = true;
20060 property_limit = 3;
b2417b59 20061 property_kind = CTX_PROPERTY_NAME_LIST;
94e7f906
JJ
20062 break;
20063 case 'i': /* implementation */
20064 selectors = omp_implementation_selectors;
20065 allow_user = true;
20066 property_limit = 3;
b2417b59 20067 property_kind = CTX_PROPERTY_NAME_LIST;
94e7f906
JJ
20068 break;
20069 case 'u': /* user */
20070 selectors = omp_user_selectors;
20071 property_limit = 1;
20072 property_kind = CTX_PROPERTY_EXPR;
20073 break;
20074 default:
20075 gcc_unreachable ();
20076 }
20077 for (int i = 0; ; i++)
20078 {
20079 if (selectors[i] == NULL)
20080 {
20081 if (allow_user)
20082 {
20083 property_kind = CTX_PROPERTY_USER;
20084 break;
20085 }
20086 else
20087 {
20088 error_at (c_parser_peek_token (parser)->location,
20089 "selector %qs not allowed for context selector "
20090 "set %qs", IDENTIFIER_POINTER (selector),
20091 IDENTIFIER_POINTER (set));
20092 c_parser_consume_token (parser);
20093 return error_mark_node;
20094 }
20095 }
20096 if (i == property_limit)
20097 property_kind = CTX_PROPERTY_NONE;
20098 if (strcmp (selectors[i], IDENTIFIER_POINTER (selector)) == 0)
20099 break;
20100 }
b2417b59
JJ
20101 if (property_kind == CTX_PROPERTY_NAME_LIST
20102 && IDENTIFIER_POINTER (set)[0] == 'i'
20103 && strcmp (IDENTIFIER_POINTER (selector),
20104 "atomic_default_mem_order") == 0)
20105 property_kind = CTX_PROPERTY_ID;
94e7f906
JJ
20106
20107 c_parser_consume_token (parser);
20108
20109 if (c_parser_next_token_is (parser, CPP_OPEN_PAREN))
20110 {
20111 if (property_kind == CTX_PROPERTY_NONE)
20112 {
20113 error_at (c_parser_peek_token (parser)->location,
20114 "selector %qs does not accept any properties",
20115 IDENTIFIER_POINTER (selector));
20116 return error_mark_node;
20117 }
20118
20119 matching_parens parens;
20120 parens.require_open (parser);
20121
20122 c_token *token = c_parser_peek_token (parser);
20123 if (allow_score
20124 && c_parser_next_token_is (parser, CPP_NAME)
20125 && strcmp (IDENTIFIER_POINTER (token->value), "score") == 0
20126 && c_parser_peek_2nd_token (parser)->type == CPP_OPEN_PAREN)
20127 {
20128 c_parser_consume_token (parser);
20129
20130 matching_parens parens2;
20131 parens2.require_open (parser);
20132 tree score = c_parser_expr_no_commas (parser, NULL).value;
20133 parens2.skip_until_found_close (parser);
20134 c_parser_require (parser, CPP_COLON, "expected %<:%>");
20135 if (score != error_mark_node)
20136 {
20137 mark_exp_read (score);
20138 score = c_fully_fold (score, false, NULL);
20139 if (!INTEGRAL_TYPE_P (TREE_TYPE (score))
bedb7f04 20140 || TREE_CODE (score) != INTEGER_CST)
94e7f906
JJ
20141 error_at (token->location, "score argument must be "
20142 "constant integer expression");
bedb7f04
JJ
20143 else if (tree_int_cst_sgn (score) < 0)
20144 error_at (token->location, "score argument must be "
20145 "non-negative");
94e7f906
JJ
20146 else
20147 properties = tree_cons (get_identifier (" score"),
20148 score, properties);
20149 }
20150 token = c_parser_peek_token (parser);
20151 }
20152
20153 switch (property_kind)
20154 {
20155 tree t;
20156 case CTX_PROPERTY_USER:
20157 do
20158 {
20159 t = c_parser_expr_no_commas (parser, NULL).value;
20160 if (TREE_CODE (t) == STRING_CST)
20161 properties = tree_cons (NULL_TREE, t, properties);
20162 else if (t != error_mark_node)
20163 {
20164 mark_exp_read (t);
20165 t = c_fully_fold (t, false, NULL);
20166 if (!INTEGRAL_TYPE_P (TREE_TYPE (t))
20167 || !tree_fits_shwi_p (t))
20168 error_at (token->location, "property must be "
20169 "constant integer expression or string "
20170 "literal");
20171 else
20172 properties = tree_cons (NULL_TREE, t, properties);
20173 }
20de9568
JJ
20174 else
20175 return error_mark_node;
94e7f906
JJ
20176
20177 if (c_parser_next_token_is (parser, CPP_COMMA))
20178 c_parser_consume_token (parser);
20179 else
20180 break;
20181 }
20182 while (1);
20183 break;
b2417b59
JJ
20184 case CTX_PROPERTY_ID:
20185 if (c_parser_next_token_is (parser, CPP_KEYWORD)
20186 || c_parser_next_token_is (parser, CPP_NAME))
20187 {
20188 tree prop = c_parser_peek_token (parser)->value;
20189 c_parser_consume_token (parser);
20190 properties = tree_cons (prop, NULL_TREE, properties);
20191 }
20192 else
20193 {
20194 c_parser_error (parser, "expected identifier");
20195 return error_mark_node;
20196 }
20197 break;
20198 case CTX_PROPERTY_NAME_LIST:
94e7f906
JJ
20199 do
20200 {
b2417b59 20201 tree prop = NULL_TREE, value = NULL_TREE;
94e7f906
JJ
20202 if (c_parser_next_token_is (parser, CPP_KEYWORD)
20203 || c_parser_next_token_is (parser, CPP_NAME))
b2417b59
JJ
20204 {
20205 prop = c_parser_peek_token (parser)->value;
20206 c_parser_consume_token (parser);
20207 }
20208 else if (c_parser_next_token_is (parser, CPP_STRING))
20209 value = c_parser_string_literal (parser, false,
20210 false).value;
94e7f906
JJ
20211 else
20212 {
b2417b59
JJ
20213 c_parser_error (parser, "expected identifier or "
20214 "string literal");
94e7f906
JJ
20215 return error_mark_node;
20216 }
94e7f906 20217
b2417b59 20218 properties = tree_cons (prop, value, properties);
94e7f906
JJ
20219
20220 if (c_parser_next_token_is (parser, CPP_COMMA))
20221 c_parser_consume_token (parser);
20222 else
20223 break;
20224 }
20225 while (1);
20226 break;
20227 case CTX_PROPERTY_EXPR:
20228 t = c_parser_expr_no_commas (parser, NULL).value;
20229 if (t != error_mark_node)
20230 {
20231 mark_exp_read (t);
20232 t = c_fully_fold (t, false, NULL);
20233 if (!INTEGRAL_TYPE_P (TREE_TYPE (t))
20234 || !tree_fits_shwi_p (t))
20235 error_at (token->location, "property must be "
20236 "constant integer expression");
20237 else
20238 properties = tree_cons (NULL_TREE, t, properties);
20239 }
20de9568
JJ
20240 else
20241 return error_mark_node;
94e7f906
JJ
20242 break;
20243 case CTX_PROPERTY_SIMD:
20244 if (parms == NULL_TREE)
20245 {
20246 error_at (token->location, "properties for %<simd%> "
20247 "selector may not be specified in "
20248 "%<metadirective%>");
20249 return error_mark_node;
20250 }
20251 tree c;
20252 c = c_parser_omp_all_clauses (parser,
20253 OMP_DECLARE_SIMD_CLAUSE_MASK,
b9424661 20254 "simd", true, 2);
94e7f906
JJ
20255 c = c_omp_declare_simd_clauses_to_numbers (parms
20256 == error_mark_node
20257 ? NULL_TREE : parms,
20258 c);
20de9568 20259 properties = c;
94e7f906
JJ
20260 break;
20261 default:
20262 gcc_unreachable ();
20263 }
20264
20265 parens.skip_until_found_close (parser);
20266 properties = nreverse (properties);
20267 }
b2417b59
JJ
20268 else if (property_kind == CTX_PROPERTY_NAME_LIST
20269 || property_kind == CTX_PROPERTY_ID
94e7f906
JJ
20270 || property_kind == CTX_PROPERTY_EXPR)
20271 {
20272 c_parser_require (parser, CPP_OPEN_PAREN, "expected %<(%>");
20273 return error_mark_node;
20274 }
20275
20276 ret = tree_cons (selector, properties, ret);
20277
20278 if (c_parser_next_token_is (parser, CPP_COMMA))
20279 c_parser_consume_token (parser);
20280 else
20281 break;
20282 }
20283 while (1);
20284
20285 return nreverse (ret);
20286}
20287
20288/* OpenMP 5.0:
20289
20290 trait-set-selector[,trait-set-selector[,...]]
20291
20292 trait-set-selector:
20293 trait-set-selector-name = { trait-selector[, trait-selector[, ...]] }
20294
20295 trait-set-selector-name:
20296 constructor
20297 device
20298 implementation
20299 user */
20300
20301static tree
20302c_parser_omp_context_selector_specification (c_parser *parser, tree parms)
20303{
20304 tree ret = NULL_TREE;
20305 do
20306 {
20307 const char *setp = "";
20308 if (c_parser_next_token_is (parser, CPP_NAME))
20309 setp = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
20310 switch (setp[0])
20311 {
20312 case 'c':
20313 if (strcmp (setp, "construct") == 0)
20314 setp = NULL;
20315 break;
20316 case 'd':
20317 if (strcmp (setp, "device") == 0)
20318 setp = NULL;
20319 break;
20320 case 'i':
20321 if (strcmp (setp, "implementation") == 0)
20322 setp = NULL;
20323 break;
20324 case 'u':
20325 if (strcmp (setp, "user") == 0)
20326 setp = NULL;
20327 break;
20328 default:
20329 break;
20330 }
20331 if (setp)
20332 {
20333 c_parser_error (parser, "expected %<construct%>, %<device%>, "
20334 "%<implementation%> or %<user%>");
20335 return error_mark_node;
20336 }
20337
20338 tree set = c_parser_peek_token (parser)->value;
20339 c_parser_consume_token (parser);
20340
20341 if (!c_parser_require (parser, CPP_EQ, "expected %<=%>"))
20342 return error_mark_node;
20343
20344 matching_braces braces;
20345 if (!braces.require_open (parser))
20346 return error_mark_node;
20347
20348 tree selectors = c_parser_omp_context_selector (parser, set, parms);
20349 if (selectors == error_mark_node)
20350 ret = error_mark_node;
20351 else if (ret != error_mark_node)
20352 ret = tree_cons (set, selectors, ret);
20353
20354 braces.skip_until_found_close (parser);
20355
20356 if (c_parser_next_token_is (parser, CPP_COMMA))
20357 c_parser_consume_token (parser);
20358 else
20359 break;
20360 }
20361 while (1);
20362
20363 if (ret == error_mark_node)
20364 return ret;
20365 return nreverse (ret);
20366}
20367
20368/* Finalize #pragma omp declare variant after FNDECL has been parsed, and put
20de9568 20369 that into "omp declare variant base" attribute. */
94e7f906
JJ
20370
20371static void
20372c_finish_omp_declare_variant (c_parser *parser, tree fndecl, tree parms)
20373{
20374 matching_parens parens;
20375 if (!parens.require_open (parser))
20376 {
20377 fail:
20378 c_parser_skip_to_pragma_eol (parser, false);
20379 return;
20380 }
20381
20382 if (c_parser_next_token_is_not (parser, CPP_NAME)
20383 || c_parser_peek_token (parser)->id_kind != C_ID_ID)
20384 {
20385 c_parser_error (parser, "expected identifier");
20386 goto fail;
20387 }
20388
20389 c_token *token = c_parser_peek_token (parser);
20390 tree variant = lookup_name (token->value);
20391
20392 if (variant == NULL_TREE)
20393 {
20394 undeclared_variable (token->location, token->value);
20395 variant = error_mark_node;
20396 }
20397
20398 c_parser_consume_token (parser);
20399
20400 parens.require_close (parser);
20401
20402 const char *clause = "";
20403 location_t match_loc = c_parser_peek_token (parser)->location;
20404 if (c_parser_next_token_is (parser, CPP_NAME))
20405 clause = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
20406 if (strcmp (clause, "match"))
20407 {
20408 c_parser_error (parser, "expected %<match%>");
20409 goto fail;
20410 }
20411
20412 c_parser_consume_token (parser);
20413
20414 if (!parens.require_open (parser))
20415 goto fail;
20416
20417 if (parms == NULL_TREE)
20418 parms = error_mark_node;
20419
20420 tree ctx = c_parser_omp_context_selector_specification (parser, parms);
20421 if (ctx == error_mark_node)
20422 goto fail;
20423 ctx = c_omp_check_context_selector (match_loc, ctx);
20424 if (ctx != error_mark_node && variant != error_mark_node)
20425 {
20426 if (TREE_CODE (variant) != FUNCTION_DECL)
20427 {
20428 error_at (token->location, "variant %qD is not a function", variant);
20429 variant = error_mark_node;
20430 }
d0c464d2 20431 else if (omp_get_context_selector (ctx, "construct", "simd") == NULL_TREE
94e7f906
JJ
20432 && !comptypes (TREE_TYPE (fndecl), TREE_TYPE (variant)))
20433 {
20434 error_at (token->location, "variant %qD and base %qD have "
20435 "incompatible types", variant, fndecl);
20436 variant = error_mark_node;
20437 }
20438 else if (fndecl_built_in_p (variant)
20439 && (strncmp (IDENTIFIER_POINTER (DECL_NAME (variant)),
20440 "__builtin_", strlen ("__builtin_")) == 0
20441 || strncmp (IDENTIFIER_POINTER (DECL_NAME (variant)),
20442 "__sync_", strlen ("__sync_")) == 0
20443 || strncmp (IDENTIFIER_POINTER (DECL_NAME (variant)),
20444 "__atomic_", strlen ("__atomic_")) == 0))
20445 {
20446 error_at (token->location, "variant %qD is a built-in", variant);
20447 variant = error_mark_node;
20448 }
20449 if (variant != error_mark_node)
20450 {
20451 C_DECL_USED (variant) = 1;
d0c464d2 20452 tree construct = omp_get_context_selector (ctx, "construct", NULL);
20de9568 20453 c_omp_mark_declare_variant (match_loc, variant, construct);
135df52c 20454 if (omp_context_selector_matches (ctx))
20de9568
JJ
20455 {
20456 tree attr
20457 = tree_cons (get_identifier ("omp declare variant base"),
20458 build_tree_list (variant, ctx),
20459 DECL_ATTRIBUTES (fndecl));
20460 DECL_ATTRIBUTES (fndecl) = attr;
20461 }
94e7f906
JJ
20462 }
20463 }
20464
20465 parens.require_close (parser);
20466 c_parser_skip_to_pragma_eol (parser);
20467}
20468
20469/* Finalize #pragma omp declare simd or #pragma omp declare variant
20470 clauses after FNDECL has been parsed, and put that into "omp declare simd"
20de9568 20471 or "omp declare variant base" attribute. */
c2255bc4 20472
acf0174b
JJ
20473static void
20474c_finish_omp_declare_simd (c_parser *parser, tree fndecl, tree parms,
20475 vec<c_token> clauses)
20476{
94e7f906
JJ
20477 /* Normally first token is CPP_NAME "simd" or "variant". CPP_EOF there
20478 indicates error has been reported and CPP_PRAGMA that
20479 c_finish_omp_declare_simd has already processed the tokens. */
41958c28 20480 if (clauses.exists () && clauses[0].type == CPP_EOF)
acf0174b 20481 return;
94e7f906
JJ
20482 const char *kind = "simd";
20483 if (clauses.exists ()
20484 && (clauses[0].type == CPP_NAME || clauses[0].type == CPP_PRAGMA))
20485 kind = IDENTIFIER_POINTER (clauses[0].value);
20486 gcc_assert (strcmp (kind, "simd") == 0 || strcmp (kind, "variant") == 0);
acf0174b
JJ
20487 if (fndecl == NULL_TREE || TREE_CODE (fndecl) != FUNCTION_DECL)
20488 {
94e7f906
JJ
20489 error ("%<#pragma omp declare %s%> not immediately followed by "
20490 "a function declaration or definition", kind);
acf0174b
JJ
20491 clauses[0].type = CPP_EOF;
20492 return;
20493 }
41958c28 20494 if (clauses.exists () && clauses[0].type != CPP_NAME)
acf0174b
JJ
20495 {
20496 error_at (DECL_SOURCE_LOCATION (fndecl),
94e7f906
JJ
20497 "%<#pragma omp declare %s%> not immediately followed by "
20498 "a single function declaration or definition", kind);
acf0174b
JJ
20499 clauses[0].type = CPP_EOF;
20500 return;
20501 }
953ff289 20502
acf0174b
JJ
20503 if (parms == NULL_TREE)
20504 parms = DECL_ARGUMENTS (fndecl);
953ff289 20505
acf0174b
JJ
20506 unsigned int tokens_avail = parser->tokens_avail;
20507 gcc_assert (parser->tokens == &parser->tokens_buf[0]);
fff77217 20508
5e9d6aa4
JK
20509 parser->tokens = clauses.address ();
20510 parser->tokens_avail = clauses.length ();
41958c28 20511
acf0174b
JJ
20512 /* c_parser_omp_declare_simd pushed 2 extra CPP_EOF tokens at the end. */
20513 while (parser->tokens_avail > 3)
20514 {
20515 c_token *token = c_parser_peek_token (parser);
5e9d6aa4 20516 gcc_assert (token->type == CPP_NAME
94e7f906 20517 && strcmp (IDENTIFIER_POINTER (token->value), kind) == 0);
acf0174b
JJ
20518 c_parser_consume_token (parser);
20519 parser->in_pragma = true;
953ff289 20520
94e7f906
JJ
20521 if (strcmp (kind, "simd") == 0)
20522 {
20523 tree c;
20524 c = c_parser_omp_all_clauses (parser, OMP_DECLARE_SIMD_CLAUSE_MASK,
20525 "#pragma omp declare simd");
20526 c = c_omp_declare_simd_clauses_to_numbers (parms, c);
20527 if (c != NULL_TREE)
20528 c = tree_cons (NULL_TREE, c, NULL_TREE);
20529 c = build_tree_list (get_identifier ("omp declare simd"), c);
20530 TREE_CHAIN (c) = DECL_ATTRIBUTES (fndecl);
20531 DECL_ATTRIBUTES (fndecl) = c;
20532 }
20533 else
20534 {
20535 gcc_assert (strcmp (kind, "variant") == 0);
20536 c_finish_omp_declare_variant (parser, fndecl, parms);
20537 }
acf0174b 20538 }
953ff289 20539
acf0174b
JJ
20540 parser->tokens = &parser->tokens_buf[0];
20541 parser->tokens_avail = tokens_avail;
41958c28
BI
20542 if (clauses.exists ())
20543 clauses[0].type = CPP_PRAGMA;
953ff289
DN
20544}
20545
953ff289 20546
acf0174b
JJ
20547/* OpenMP 4.0:
20548 # pragma omp declare target new-line
20549 declarations and definitions
d9a6bd32
JJ
20550 # pragma omp end declare target new-line
20551
20552 OpenMP 4.5:
20553 # pragma omp declare target ( extended-list ) new-line
20554
20555 # pragma omp declare target declare-target-clauses[seq] new-line */
20556
20557#define OMP_DECLARE_TARGET_CLAUSE_MASK \
20558 ( (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_TO) \
77eb117f
JJ
20559 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_LINK) \
20560 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_DEVICE_TYPE))
953ff289 20561
acf0174b
JJ
20562static void
20563c_parser_omp_declare_target (c_parser *parser)
953ff289 20564{
d9a6bd32 20565 tree clauses = NULL_TREE;
77eb117f
JJ
20566 int device_type = 0;
20567 bool only_device_type = true;
d9a6bd32
JJ
20568 if (c_parser_next_token_is (parser, CPP_NAME))
20569 clauses = c_parser_omp_all_clauses (parser, OMP_DECLARE_TARGET_CLAUSE_MASK,
20570 "#pragma omp declare target");
20571 else if (c_parser_next_token_is (parser, CPP_OPEN_PAREN))
20572 {
20573 clauses = c_parser_omp_var_list_parens (parser, OMP_CLAUSE_TO_DECLARE,
20574 clauses);
77886428 20575 clauses = c_finish_omp_clauses (clauses, C_ORT_OMP);
d9a6bd32
JJ
20576 c_parser_skip_to_pragma_eol (parser);
20577 }
20578 else
20579 {
20580 c_parser_skip_to_pragma_eol (parser);
20581 current_omp_declare_target_attribute++;
20582 return;
20583 }
77eb117f
JJ
20584 for (tree c = clauses; c; c = OMP_CLAUSE_CHAIN (c))
20585 if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEVICE_TYPE)
20586 device_type |= OMP_CLAUSE_DEVICE_TYPE_KIND (c);
d9a6bd32
JJ
20587 for (tree c = clauses; c; c = OMP_CLAUSE_CHAIN (c))
20588 {
77eb117f
JJ
20589 if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_DEVICE_TYPE)
20590 continue;
d9a6bd32
JJ
20591 tree t = OMP_CLAUSE_DECL (c), id;
20592 tree at1 = lookup_attribute ("omp declare target", DECL_ATTRIBUTES (t));
20593 tree at2 = lookup_attribute ("omp declare target link",
20594 DECL_ATTRIBUTES (t));
77eb117f 20595 only_device_type = false;
d9a6bd32
JJ
20596 if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_LINK)
20597 {
20598 id = get_identifier ("omp declare target link");
20599 std::swap (at1, at2);
20600 }
20601 else
20602 id = get_identifier ("omp declare target");
20603 if (at2)
20604 {
20605 error_at (OMP_CLAUSE_LOCATION (c),
20606 "%qD specified both in declare target %<link%> and %<to%>"
20607 " clauses", t);
20608 continue;
20609 }
20610 if (!at1)
e01d41e5 20611 {
e01d41e5 20612 DECL_ATTRIBUTES (t) = tree_cons (id, NULL_TREE, DECL_ATTRIBUTES (t));
56f71478
JJ
20613 if (TREE_CODE (t) != FUNCTION_DECL && !is_global_var (t))
20614 continue;
20615
20616 symtab_node *node = symtab_node::get (t);
e01d41e5
JJ
20617 if (node != NULL)
20618 {
20619 node->offloadable = 1;
1d899da2 20620 if (ENABLE_OFFLOADING)
e01d41e5 20621 {
1d899da2
TS
20622 g->have_offload = true;
20623 if (is_a <varpool_node *> (node))
e6d6ec9e 20624 vec_safe_push (offload_vars, t);
e01d41e5 20625 }
e01d41e5
JJ
20626 }
20627 }
77eb117f
JJ
20628 if (TREE_CODE (t) != FUNCTION_DECL)
20629 continue;
20630 if ((device_type & OMP_CLAUSE_DEVICE_TYPE_HOST) != 0)
20631 {
20632 tree at3 = lookup_attribute ("omp declare target host",
20633 DECL_ATTRIBUTES (t));
20634 if (at3 == NULL_TREE)
20635 {
20636 id = get_identifier ("omp declare target host");
20637 DECL_ATTRIBUTES (t)
20638 = tree_cons (id, NULL_TREE, DECL_ATTRIBUTES (t));
20639 }
20640 }
20641 if ((device_type & OMP_CLAUSE_DEVICE_TYPE_NOHOST) != 0)
20642 {
20643 tree at3 = lookup_attribute ("omp declare target nohost",
20644 DECL_ATTRIBUTES (t));
20645 if (at3 == NULL_TREE)
20646 {
20647 id = get_identifier ("omp declare target nohost");
20648 DECL_ATTRIBUTES (t)
20649 = tree_cons (id, NULL_TREE, DECL_ATTRIBUTES (t));
20650 }
20651 }
d9a6bd32 20652 }
77eb117f
JJ
20653 if (device_type && only_device_type)
20654 warning_at (OMP_CLAUSE_LOCATION (clauses), 0,
20655 "directive with only %<device_type%> clauses ignored");
acf0174b 20656}
953ff289 20657
acf0174b
JJ
20658static void
20659c_parser_omp_end_declare_target (c_parser *parser)
20660{
20661 location_t loc = c_parser_peek_token (parser)->location;
20662 c_parser_consume_pragma (parser);
20663 if (c_parser_next_token_is (parser, CPP_NAME)
20664 && strcmp (IDENTIFIER_POINTER (c_parser_peek_token (parser)->value),
20665 "declare") == 0)
953ff289
DN
20666 {
20667 c_parser_consume_token (parser);
acf0174b
JJ
20668 if (c_parser_next_token_is (parser, CPP_NAME)
20669 && strcmp (IDENTIFIER_POINTER (c_parser_peek_token (parser)->value),
20670 "target") == 0)
20671 c_parser_consume_token (parser);
20672 else
953ff289 20673 {
acf0174b
JJ
20674 c_parser_error (parser, "expected %<target%>");
20675 c_parser_skip_to_pragma_eol (parser);
20676 return;
953ff289
DN
20677 }
20678 }
acf0174b
JJ
20679 else
20680 {
20681 c_parser_error (parser, "expected %<declare%>");
20682 c_parser_skip_to_pragma_eol (parser);
20683 return;
20684 }
20685 c_parser_skip_to_pragma_eol (parser);
20686 if (!current_omp_declare_target_attribute)
20687 error_at (loc, "%<#pragma omp end declare target%> without corresponding "
20688 "%<#pragma omp declare target%>");
20689 else
20690 current_omp_declare_target_attribute--;
20691}
953ff289 20692
953ff289 20693
acf0174b
JJ
20694/* OpenMP 4.0
20695 #pragma omp declare reduction (reduction-id : typename-list : expression) \
20696 initializer-clause[opt] new-line
20697
20698 initializer-clause:
20699 initializer (omp_priv = initializer)
20700 initializer (function-name (argument-list)) */
20701
20702static void
20703c_parser_omp_declare_reduction (c_parser *parser, enum pragma_context context)
20704{
20705 unsigned int tokens_avail = 0, i;
20706 vec<tree> types = vNULL;
20707 vec<c_token> clauses = vNULL;
20708 enum tree_code reduc_code = ERROR_MARK;
20709 tree reduc_id = NULL_TREE;
20710 tree type;
20711 location_t rloc = c_parser_peek_token (parser)->location;
20712
20713 if (context == pragma_struct || context == pragma_param)
953ff289 20714 {
acf0174b
JJ
20715 error ("%<#pragma omp declare reduction%> not at file or block scope");
20716 goto fail;
20717 }
953ff289 20718
acf0174b
JJ
20719 if (!c_parser_require (parser, CPP_OPEN_PAREN, "expected %<(%>"))
20720 goto fail;
953ff289 20721
acf0174b
JJ
20722 switch (c_parser_peek_token (parser)->type)
20723 {
20724 case CPP_PLUS:
20725 reduc_code = PLUS_EXPR;
20726 break;
20727 case CPP_MULT:
20728 reduc_code = MULT_EXPR;
20729 break;
20730 case CPP_MINUS:
20731 reduc_code = MINUS_EXPR;
20732 break;
20733 case CPP_AND:
20734 reduc_code = BIT_AND_EXPR;
20735 break;
20736 case CPP_XOR:
20737 reduc_code = BIT_XOR_EXPR;
20738 break;
20739 case CPP_OR:
20740 reduc_code = BIT_IOR_EXPR;
20741 break;
20742 case CPP_AND_AND:
20743 reduc_code = TRUTH_ANDIF_EXPR;
20744 break;
20745 case CPP_OR_OR:
20746 reduc_code = TRUTH_ORIF_EXPR;
20747 break;
20748 case CPP_NAME:
20749 const char *p;
20750 p = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
20751 if (strcmp (p, "min") == 0)
20752 {
20753 reduc_code = MIN_EXPR;
20754 break;
20755 }
20756 if (strcmp (p, "max") == 0)
20757 {
20758 reduc_code = MAX_EXPR;
20759 break;
20760 }
20761 reduc_id = c_parser_peek_token (parser)->value;
953ff289 20762 break;
953ff289 20763 default:
acf0174b
JJ
20764 c_parser_error (parser,
20765 "expected %<+%>, %<*%>, %<-%>, %<&%>, "
79c9b7a8 20766 "%<^%>, %<|%>, %<&&%>, %<||%> or identifier");
acf0174b 20767 goto fail;
953ff289
DN
20768 }
20769
acf0174b
JJ
20770 tree orig_reduc_id, reduc_decl;
20771 orig_reduc_id = reduc_id;
20772 reduc_id = c_omp_reduction_id (reduc_code, reduc_id);
20773 reduc_decl = c_omp_reduction_decl (reduc_id);
20774 c_parser_consume_token (parser);
953ff289 20775
acf0174b
JJ
20776 if (!c_parser_require (parser, CPP_COLON, "expected %<:%>"))
20777 goto fail;
c2255bc4 20778
acf0174b
JJ
20779 while (true)
20780 {
20781 location_t loc = c_parser_peek_token (parser)->location;
20782 struct c_type_name *ctype = c_parser_type_name (parser);
20783 if (ctype != NULL)
20784 {
20785 type = groktypename (ctype, NULL, NULL);
20786 if (type == error_mark_node)
20787 ;
20788 else if ((INTEGRAL_TYPE_P (type)
20789 || TREE_CODE (type) == REAL_TYPE
20790 || TREE_CODE (type) == COMPLEX_TYPE)
20791 && orig_reduc_id == NULL_TREE)
20792 error_at (loc, "predeclared arithmetic type in "
20793 "%<#pragma omp declare reduction%>");
20794 else if (TREE_CODE (type) == FUNCTION_TYPE
20795 || TREE_CODE (type) == ARRAY_TYPE)
20796 error_at (loc, "function or array type in "
20797 "%<#pragma omp declare reduction%>");
9dc5773f
JJ
20798 else if (TYPE_ATOMIC (type))
20799 error_at (loc, "%<_Atomic%> qualified type in "
20800 "%<#pragma omp declare reduction%>");
acf0174b
JJ
20801 else if (TYPE_QUALS_NO_ADDR_SPACE (type))
20802 error_at (loc, "const, volatile or restrict qualified type in "
20803 "%<#pragma omp declare reduction%>");
20804 else
20805 {
20806 tree t;
20807 for (t = DECL_INITIAL (reduc_decl); t; t = TREE_CHAIN (t))
20808 if (comptypes (TREE_PURPOSE (t), type))
20809 {
20810 error_at (loc, "redeclaration of %qs "
20811 "%<#pragma omp declare reduction%> for "
20812 "type %qT",
20813 IDENTIFIER_POINTER (reduc_id)
20814 + sizeof ("omp declare reduction ") - 1,
20815 type);
20816 location_t ploc
20817 = DECL_SOURCE_LOCATION (TREE_VEC_ELT (TREE_VALUE (t),
20818 0));
20819 error_at (ploc, "previous %<#pragma omp declare "
20820 "reduction%>");
20821 break;
20822 }
20823 if (t == NULL_TREE)
20824 types.safe_push (type);
20825 }
20826 if (c_parser_next_token_is (parser, CPP_COMMA))
20827 c_parser_consume_token (parser);
20828 else
20829 break;
20830 }
20831 else
20832 break;
20833 }
953ff289 20834
acf0174b
JJ
20835 if (!c_parser_require (parser, CPP_COLON, "expected %<:%>")
20836 || types.is_empty ())
20837 {
20838 fail:
20839 clauses.release ();
20840 types.release ();
20841 while (true)
20842 {
20843 c_token *token = c_parser_peek_token (parser);
20844 if (token->type == CPP_EOF || token->type == CPP_PRAGMA_EOL)
20845 break;
20846 c_parser_consume_token (parser);
20847 }
20848 c_parser_skip_to_pragma_eol (parser);
20849 return;
20850 }
953ff289 20851
acf0174b
JJ
20852 if (types.length () > 1)
20853 {
20854 while (c_parser_next_token_is_not (parser, CPP_PRAGMA_EOL))
20855 {
20856 c_token *token = c_parser_peek_token (parser);
20857 if (token->type == CPP_EOF)
20858 goto fail;
20859 clauses.safe_push (*token);
20860 c_parser_consume_token (parser);
20861 }
20862 clauses.safe_push (*c_parser_peek_token (parser));
20863 c_parser_skip_to_pragma_eol (parser);
953ff289 20864
acf0174b
JJ
20865 /* Make sure nothing tries to read past the end of the tokens. */
20866 c_token eof_token;
20867 memset (&eof_token, 0, sizeof (eof_token));
20868 eof_token.type = CPP_EOF;
20869 clauses.safe_push (eof_token);
20870 clauses.safe_push (eof_token);
20871 }
953ff289 20872
acf0174b
JJ
20873 int errs = errorcount;
20874 FOR_EACH_VEC_ELT (types, i, type)
20875 {
20876 tokens_avail = parser->tokens_avail;
20877 gcc_assert (parser->tokens == &parser->tokens_buf[0]);
20878 if (!clauses.is_empty ())
20879 {
20880 parser->tokens = clauses.address ();
20881 parser->tokens_avail = clauses.length ();
20882 parser->in_pragma = true;
20883 }
953ff289 20884
acf0174b
JJ
20885 bool nested = current_function_decl != NULL_TREE;
20886 if (nested)
20887 c_push_function_context ();
20888 tree fndecl = build_decl (BUILTINS_LOCATION, FUNCTION_DECL,
20889 reduc_id, default_function_type);
20890 current_function_decl = fndecl;
20891 allocate_struct_function (fndecl, true);
20892 push_scope ();
20893 tree stmt = push_stmt_list ();
20894 /* Intentionally BUILTINS_LOCATION, so that -Wshadow doesn't
20895 warn about these. */
20896 tree omp_out = build_decl (BUILTINS_LOCATION, VAR_DECL,
20897 get_identifier ("omp_out"), type);
20898 DECL_ARTIFICIAL (omp_out) = 1;
20899 DECL_CONTEXT (omp_out) = fndecl;
20900 pushdecl (omp_out);
20901 tree omp_in = build_decl (BUILTINS_LOCATION, VAR_DECL,
20902 get_identifier ("omp_in"), type);
20903 DECL_ARTIFICIAL (omp_in) = 1;
20904 DECL_CONTEXT (omp_in) = fndecl;
20905 pushdecl (omp_in);
20906 struct c_expr combiner = c_parser_expression (parser);
20907 struct c_expr initializer;
20908 tree omp_priv = NULL_TREE, omp_orig = NULL_TREE;
20909 bool bad = false;
913884f7 20910 initializer.set_error ();
acf0174b
JJ
20911 if (!c_parser_require (parser, CPP_CLOSE_PAREN, "expected %<)%>"))
20912 bad = true;
20913 else if (c_parser_next_token_is (parser, CPP_NAME)
20914 && strcmp (IDENTIFIER_POINTER
20915 (c_parser_peek_token (parser)->value),
20916 "initializer") == 0)
20917 {
20918 c_parser_consume_token (parser);
20919 pop_scope ();
20920 push_scope ();
20921 omp_priv = build_decl (BUILTINS_LOCATION, VAR_DECL,
20922 get_identifier ("omp_priv"), type);
20923 DECL_ARTIFICIAL (omp_priv) = 1;
20924 DECL_INITIAL (omp_priv) = error_mark_node;
20925 DECL_CONTEXT (omp_priv) = fndecl;
20926 pushdecl (omp_priv);
20927 omp_orig = build_decl (BUILTINS_LOCATION, VAR_DECL,
20928 get_identifier ("omp_orig"), type);
20929 DECL_ARTIFICIAL (omp_orig) = 1;
20930 DECL_CONTEXT (omp_orig) = fndecl;
20931 pushdecl (omp_orig);
20932 if (!c_parser_require (parser, CPP_OPEN_PAREN, "expected %<(%>"))
20933 bad = true;
20934 else if (!c_parser_next_token_is (parser, CPP_NAME))
20935 {
20936 c_parser_error (parser, "expected %<omp_priv%> or "
20937 "function-name");
20938 bad = true;
20939 }
20940 else if (strcmp (IDENTIFIER_POINTER
20941 (c_parser_peek_token (parser)->value),
20942 "omp_priv") != 0)
20943 {
20944 if (c_parser_peek_2nd_token (parser)->type != CPP_OPEN_PAREN
20945 || c_parser_peek_token (parser)->id_kind != C_ID_ID)
20946 {
20947 c_parser_error (parser, "expected function-name %<(%>");
20948 bad = true;
20949 }
20950 else
20951 initializer = c_parser_postfix_expression (parser);
20952 if (initializer.value
20953 && TREE_CODE (initializer.value) == CALL_EXPR)
20954 {
20955 int j;
20956 tree c = initializer.value;
20957 for (j = 0; j < call_expr_nargs (c); j++)
d9a6bd32
JJ
20958 {
20959 tree a = CALL_EXPR_ARG (c, j);
20960 STRIP_NOPS (a);
20961 if (TREE_CODE (a) == ADDR_EXPR
20962 && TREE_OPERAND (a, 0) == omp_priv)
20963 break;
20964 }
acf0174b
JJ
20965 if (j == call_expr_nargs (c))
20966 error ("one of the initializer call arguments should be "
20967 "%<&omp_priv%>");
20968 }
20969 }
20970 else
20971 {
20972 c_parser_consume_token (parser);
20973 if (!c_parser_require (parser, CPP_EQ, "expected %<=%>"))
20974 bad = true;
20975 else
20976 {
20977 tree st = push_stmt_list ();
acf0174b 20978 location_t loc = c_parser_peek_token (parser)->location;
5dd9a9d0
DM
20979 rich_location richloc (line_table, loc);
20980 start_init (omp_priv, NULL_TREE, 0, &richloc);
acf0174b
JJ
20981 struct c_expr init = c_parser_initializer (parser);
20982 finish_init ();
20983 finish_decl (omp_priv, loc, init.value,
20984 init.original_type, NULL_TREE);
20985 pop_stmt_list (st);
20986 }
20987 }
20988 if (!bad
20989 && !c_parser_require (parser, CPP_CLOSE_PAREN, "expected %<)%>"))
20990 bad = true;
20991 }
c2255bc4 20992
acf0174b
JJ
20993 if (!bad)
20994 {
20995 c_parser_skip_to_pragma_eol (parser);
a68ab351 20996
acf0174b
JJ
20997 tree t = tree_cons (type, make_tree_vec (omp_priv ? 6 : 3),
20998 DECL_INITIAL (reduc_decl));
20999 DECL_INITIAL (reduc_decl) = t;
21000 DECL_SOURCE_LOCATION (omp_out) = rloc;
21001 TREE_VEC_ELT (TREE_VALUE (t), 0) = omp_out;
21002 TREE_VEC_ELT (TREE_VALUE (t), 1) = omp_in;
21003 TREE_VEC_ELT (TREE_VALUE (t), 2) = combiner.value;
21004 walk_tree (&combiner.value, c_check_omp_declare_reduction_r,
21005 &TREE_VEC_ELT (TREE_VALUE (t), 0), NULL);
21006 if (omp_priv)
21007 {
21008 DECL_SOURCE_LOCATION (omp_priv) = rloc;
21009 TREE_VEC_ELT (TREE_VALUE (t), 3) = omp_priv;
21010 TREE_VEC_ELT (TREE_VALUE (t), 4) = omp_orig;
21011 TREE_VEC_ELT (TREE_VALUE (t), 5) = initializer.value;
21012 walk_tree (&initializer.value, c_check_omp_declare_reduction_r,
21013 &TREE_VEC_ELT (TREE_VALUE (t), 3), NULL);
21014 walk_tree (&DECL_INITIAL (omp_priv),
21015 c_check_omp_declare_reduction_r,
21016 &TREE_VEC_ELT (TREE_VALUE (t), 3), NULL);
21017 }
21018 }
a68ab351 21019
acf0174b
JJ
21020 pop_stmt_list (stmt);
21021 pop_scope ();
21022 if (cfun->language != NULL)
21023 {
21024 ggc_free (cfun->language);
21025 cfun->language = NULL;
21026 }
21027 set_cfun (NULL);
21028 current_function_decl = NULL_TREE;
21029 if (nested)
21030 c_pop_function_context ();
a68ab351 21031
acf0174b
JJ
21032 if (!clauses.is_empty ())
21033 {
21034 parser->tokens = &parser->tokens_buf[0];
21035 parser->tokens_avail = tokens_avail;
21036 }
21037 if (bad)
21038 goto fail;
21039 if (errs != errorcount)
21040 break;
21041 }
a68ab351 21042
acf0174b
JJ
21043 clauses.release ();
21044 types.release ();
a68ab351
JJ
21045}
21046
953ff289 21047
acf0174b
JJ
21048/* OpenMP 4.0
21049 #pragma omp declare simd declare-simd-clauses[optseq] new-line
21050 #pragma omp declare reduction (reduction-id : typename-list : expression) \
21051 initializer-clause[opt] new-line
94e7f906
JJ
21052 #pragma omp declare target new-line
21053
21054 OpenMP 5.0
21055 #pragma omp declare variant (identifier) match (context-selector) */
20906c66
JJ
21056
21057static void
acf0174b 21058c_parser_omp_declare (c_parser *parser, enum pragma_context context)
20906c66 21059{
20906c66 21060 c_parser_consume_pragma (parser);
acf0174b
JJ
21061 if (c_parser_next_token_is (parser, CPP_NAME))
21062 {
21063 const char *p = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
21064 if (strcmp (p, "simd") == 0)
21065 {
21066 /* c_parser_consume_token (parser); done in
21067 c_parser_omp_declare_simd. */
21068 c_parser_omp_declare_simd (parser, context);
21069 return;
21070 }
21071 if (strcmp (p, "reduction") == 0)
21072 {
21073 c_parser_consume_token (parser);
21074 c_parser_omp_declare_reduction (parser, context);
21075 return;
21076 }
6d7f7e0a
TB
21077 if (!flag_openmp) /* flag_openmp_simd */
21078 {
62021f64 21079 c_parser_skip_to_pragma_eol (parser, false);
6d7f7e0a
TB
21080 return;
21081 }
acf0174b
JJ
21082 if (strcmp (p, "target") == 0)
21083 {
21084 c_parser_consume_token (parser);
21085 c_parser_omp_declare_target (parser);
21086 return;
21087 }
94e7f906
JJ
21088 if (strcmp (p, "variant") == 0)
21089 {
21090 /* c_parser_consume_token (parser); done in
21091 c_parser_omp_declare_simd. */
21092 c_parser_omp_declare_simd (parser, context);
21093 return;
21094 }
acf0174b 21095 }
20906c66 21096
94e7f906
JJ
21097 c_parser_error (parser, "expected %<simd%>, %<reduction%>, "
21098 "%<target%> or %<variant%>");
acf0174b 21099 c_parser_skip_to_pragma_eol (parser);
20906c66
JJ
21100}
21101
28567c40
JJ
21102/* OpenMP 5.0
21103 #pragma omp requires clauses[optseq] new-line */
21104
21105static void
21106c_parser_omp_requires (c_parser *parser)
21107{
21108 bool first = true;
21109 enum omp_requires new_req = (enum omp_requires) 0;
21110
21111 c_parser_consume_pragma (parser);
21112
21113 location_t loc = c_parser_peek_token (parser)->location;
21114 while (c_parser_next_token_is_not (parser, CPP_PRAGMA_EOL))
21115 {
21116 if (!first && c_parser_next_token_is (parser, CPP_COMMA))
21117 c_parser_consume_token (parser);
21118
21119 first = false;
21120
21121 if (c_parser_next_token_is (parser, CPP_NAME))
21122 {
21123 const char *p
21124 = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
21125 location_t cloc = c_parser_peek_token (parser)->location;
21126 enum omp_requires this_req = (enum omp_requires) 0;
21127
21128 if (!strcmp (p, "unified_address"))
21129 this_req = OMP_REQUIRES_UNIFIED_ADDRESS;
21130 else if (!strcmp (p, "unified_shared_memory"))
21131 this_req = OMP_REQUIRES_UNIFIED_SHARED_MEMORY;
21132 else if (!strcmp (p, "dynamic_allocators"))
21133 this_req = OMP_REQUIRES_DYNAMIC_ALLOCATORS;
21134 else if (!strcmp (p, "reverse_offload"))
21135 this_req = OMP_REQUIRES_REVERSE_OFFLOAD;
21136 else if (!strcmp (p, "atomic_default_mem_order"))
21137 {
21138 c_parser_consume_token (parser);
21139
21140 matching_parens parens;
21141 if (parens.require_open (parser))
21142 {
21143 if (c_parser_next_token_is (parser, CPP_NAME))
21144 {
21145 tree v = c_parser_peek_token (parser)->value;
21146 p = IDENTIFIER_POINTER (v);
21147
21148 if (!strcmp (p, "seq_cst"))
21149 this_req
21150 = (enum omp_requires) OMP_MEMORY_ORDER_SEQ_CST;
21151 else if (!strcmp (p, "relaxed"))
21152 this_req
21153 = (enum omp_requires) OMP_MEMORY_ORDER_RELAXED;
21154 else if (!strcmp (p, "acq_rel"))
21155 this_req
21156 = (enum omp_requires) OMP_MEMORY_ORDER_ACQ_REL;
21157 }
21158 if (this_req == 0)
21159 {
21160 error_at (c_parser_peek_token (parser)->location,
21161 "expected %<seq_cst%>, %<relaxed%> or "
21162 "%<acq_rel%>");
21163 if (c_parser_peek_2nd_token (parser)->type
21164 == CPP_CLOSE_PAREN)
21165 c_parser_consume_token (parser);
21166 }
21167 else
21168 c_parser_consume_token (parser);
21169
21170 parens.skip_until_found_close (parser);
21171 if (this_req == 0)
21172 {
21173 c_parser_skip_to_pragma_eol (parser, false);
21174 return;
21175 }
21176 }
21177 p = NULL;
21178 }
21179 else
21180 {
21181 error_at (cloc, "expected %<unified_address%>, "
21182 "%<unified_shared_memory%>, "
21183 "%<dynamic_allocators%>, "
21184 "%<reverse_offload%> "
21185 "or %<atomic_default_mem_order%> clause");
21186 c_parser_skip_to_pragma_eol (parser, false);
21187 return;
21188 }
3179ebae
JJ
21189 if (p)
21190 sorry_at (cloc, "%qs clause on %<requires%> directive not "
21191 "supported yet", p);
28567c40
JJ
21192 if (p)
21193 c_parser_consume_token (parser);
21194 if (this_req)
21195 {
21196 if ((this_req & ~OMP_REQUIRES_ATOMIC_DEFAULT_MEM_ORDER) != 0)
21197 {
21198 if ((this_req & new_req) != 0)
21199 error_at (cloc, "too many %qs clauses", p);
21200 if (this_req != OMP_REQUIRES_DYNAMIC_ALLOCATORS
21201 && (omp_requires_mask & OMP_REQUIRES_TARGET_USED) != 0)
21202 error_at (cloc, "%qs clause used lexically after first "
21203 "target construct or offloading API", p);
21204 }
21205 else if ((new_req & OMP_REQUIRES_ATOMIC_DEFAULT_MEM_ORDER) != 0)
21206 {
21207 error_at (cloc, "too many %qs clauses",
21208 "atomic_default_mem_order");
21209 this_req = (enum omp_requires) 0;
21210 }
21211 else if ((omp_requires_mask
21212 & OMP_REQUIRES_ATOMIC_DEFAULT_MEM_ORDER) != 0)
21213 {
21214 error_at (cloc, "more than one %<atomic_default_mem_order%>"
21215 " clause in a single compilation unit");
21216 this_req
21217 = (enum omp_requires)
21218 (omp_requires_mask
21219 & OMP_REQUIRES_ATOMIC_DEFAULT_MEM_ORDER);
21220 }
21221 else if ((omp_requires_mask
21222 & OMP_REQUIRES_ATOMIC_DEFAULT_MEM_ORDER_USED) != 0)
21223 error_at (cloc, "%<atomic_default_mem_order%> clause used "
21224 "lexically after first %<atomic%> construct "
21225 "without memory order clause");
21226 new_req = (enum omp_requires) (new_req | this_req);
21227 omp_requires_mask
21228 = (enum omp_requires) (omp_requires_mask | this_req);
21229 continue;
21230 }
21231 }
21232 break;
21233 }
21234 c_parser_skip_to_pragma_eol (parser);
21235
21236 if (new_req == 0)
21237 error_at (loc, "%<pragma omp requires%> requires at least one clause");
21238}
21239
21240/* Helper function for c_parser_omp_taskloop.
21241 Disallow zero sized or potentially zero sized task reductions. */
21242
21243static tree
21244c_finish_taskloop_clauses (tree clauses)
21245{
21246 tree *pc = &clauses;
21247 for (tree c = clauses; c; c = *pc)
21248 {
21249 bool remove = false;
21250 if (OMP_CLAUSE_CODE (c) == OMP_CLAUSE_REDUCTION)
21251 {
21252 tree type = strip_array_types (TREE_TYPE (OMP_CLAUSE_DECL (c)));
21253 if (integer_zerop (TYPE_SIZE_UNIT (type)))
21254 {
21255 error_at (OMP_CLAUSE_LOCATION (c),
21256 "zero sized type %qT in %<reduction%> clause", type);
21257 remove = true;
21258 }
21259 else if (TREE_CODE (TYPE_SIZE_UNIT (type)) != INTEGER_CST)
21260 {
21261 error_at (OMP_CLAUSE_LOCATION (c),
21262 "variable sized type %qT in %<reduction%> clause",
21263 type);
21264 remove = true;
21265 }
21266 }
21267 if (remove)
21268 *pc = OMP_CLAUSE_CHAIN (c);
21269 else
21270 pc = &OMP_CLAUSE_CHAIN (c);
21271 }
21272 return clauses;
21273}
21274
d9a6bd32
JJ
21275/* OpenMP 4.5:
21276 #pragma omp taskloop taskloop-clause[optseq] new-line
21277 for-loop
21278
21279 #pragma omp taskloop simd taskloop-simd-clause[optseq] new-line
21280 for-loop */
21281
21282#define OMP_TASKLOOP_CLAUSE_MASK \
21283 ( (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_SHARED) \
21284 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_PRIVATE) \
21285 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_FIRSTPRIVATE) \
21286 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_LASTPRIVATE) \
21287 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_DEFAULT) \
21288 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_GRAINSIZE) \
21289 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_NUM_TASKS) \
21290 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_COLLAPSE) \
21291 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_UNTIED) \
21292 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_IF) \
21293 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_FINAL) \
21294 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_MERGEABLE) \
21295 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_NOGROUP) \
28567c40
JJ
21296 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_PRIORITY) \
21297 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_REDUCTION) \
21298 | (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_IN_REDUCTION))
d9a6bd32
JJ
21299
21300static tree
21301c_parser_omp_taskloop (location_t loc, c_parser *parser,
dda1bf61
JJ
21302 char *p_name, omp_clause_mask mask, tree *cclauses,
21303 bool *if_p)
d9a6bd32
JJ
21304{
21305 tree clauses, block, ret;
21306
21307 strcat (p_name, " taskloop");
21308 mask |= OMP_TASKLOOP_CLAUSE_MASK;
28567c40
JJ
21309 /* #pragma omp parallel master taskloop{, simd} disallow in_reduction
21310 clause. */
21311 if ((mask & (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_NUM_THREADS)) != 0)
21312 mask &= ~(OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_IN_REDUCTION);
d9a6bd32
JJ
21313
21314 if (c_parser_next_token_is (parser, CPP_NAME))
21315 {
21316 const char *p = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
21317
21318 if (strcmp (p, "simd") == 0)
21319 {
21320 tree cclauses_buf[C_OMP_CLAUSE_SPLIT_COUNT];
21321 if (cclauses == NULL)
21322 cclauses = cclauses_buf;
d9a6bd32
JJ
21323 c_parser_consume_token (parser);
21324 if (!flag_openmp) /* flag_openmp_simd */
dda1bf61
JJ
21325 return c_parser_omp_simd (loc, parser, p_name, mask, cclauses,
21326 if_p);
d9a6bd32 21327 block = c_begin_compound_stmt (true);
dda1bf61 21328 ret = c_parser_omp_simd (loc, parser, p_name, mask, cclauses, if_p);
d9a6bd32
JJ
21329 block = c_end_compound_stmt (loc, block, true);
21330 if (ret == NULL)
21331 return ret;
21332 ret = make_node (OMP_TASKLOOP);
21333 TREE_TYPE (ret) = void_type_node;
21334 OMP_FOR_BODY (ret) = block;
21335 OMP_FOR_CLAUSES (ret) = cclauses[C_OMP_CLAUSE_SPLIT_TASKLOOP];
28567c40
JJ
21336 OMP_FOR_CLAUSES (ret)
21337 = c_finish_taskloop_clauses (OMP_FOR_CLAUSES (ret));
d9a6bd32
JJ
21338 SET_EXPR_LOCATION (ret, loc);
21339 add_stmt (ret);
21340 return ret;
21341 }
21342 }
21343 if (!flag_openmp) /* flag_openmp_simd */
21344 {
21345 c_parser_skip_to_pragma_eol (parser, false);
21346 return NULL_TREE;
21347 }
21348
21349 clauses = c_parser_omp_all_clauses (parser, mask, p_name, cclauses == NULL);
21350 if (cclauses)
21351 {
21352 omp_split_clauses (loc, OMP_TASKLOOP, mask, clauses, cclauses);
21353 clauses = cclauses[C_OMP_CLAUSE_SPLIT_TASKLOOP];
21354 }
21355
28567c40 21356 clauses = c_finish_taskloop_clauses (clauses);
d9a6bd32 21357 block = c_begin_compound_stmt (true);
dda1bf61 21358 ret = c_parser_omp_for_loop (loc, parser, OMP_TASKLOOP, clauses, NULL, if_p);
d9a6bd32
JJ
21359 block = c_end_compound_stmt (loc, block, true);
21360 add_stmt (block);
21361
21362 return ret;
21363}
21364
953ff289
DN
21365/* Main entry point to parsing most OpenMP pragmas. */
21366
21367static void
dda1bf61 21368c_parser_omp_construct (c_parser *parser, bool *if_p)
953ff289
DN
21369{
21370 enum pragma_kind p_kind;
21371 location_t loc;
21372 tree stmt;
acf0174b
JJ
21373 char p_name[sizeof "#pragma omp teams distribute parallel for simd"];
21374 omp_clause_mask mask (0);
953ff289
DN
21375
21376 loc = c_parser_peek_token (parser)->location;
21377 p_kind = c_parser_peek_token (parser)->pragma_kind;
21378 c_parser_consume_pragma (parser);
21379
21380 switch (p_kind)
21381 {
4bf9e5a8
TS
21382 case PRAGMA_OACC_ATOMIC:
21383 c_parser_omp_atomic (loc, parser);
21384 return;
41dbbb37
TS
21385 case PRAGMA_OACC_CACHE:
21386 strcpy (p_name, "#pragma acc");
21387 stmt = c_parser_oacc_cache (loc, parser);
21388 break;
21389 case PRAGMA_OACC_DATA:
dda1bf61 21390 stmt = c_parser_oacc_data (loc, parser, if_p);
41dbbb37 21391 break;
37d5ad46 21392 case PRAGMA_OACC_HOST_DATA:
dda1bf61 21393 stmt = c_parser_oacc_host_data (loc, parser, if_p);
37d5ad46 21394 break;
41dbbb37 21395 case PRAGMA_OACC_KERNELS:
88bae6f4 21396 case PRAGMA_OACC_PARALLEL:
62aee289 21397 case PRAGMA_OACC_SERIAL:
41dbbb37 21398 strcpy (p_name, "#pragma acc");
62aee289 21399 stmt = c_parser_oacc_compute (loc, parser, p_kind, p_name, if_p);
41dbbb37
TS
21400 break;
21401 case PRAGMA_OACC_LOOP:
21402 strcpy (p_name, "#pragma acc");
dda1bf61 21403 stmt = c_parser_oacc_loop (loc, parser, p_name, mask, NULL, if_p);
41dbbb37
TS
21404 break;
21405 case PRAGMA_OACC_WAIT:
21406 strcpy (p_name, "#pragma wait");
21407 stmt = c_parser_oacc_wait (loc, parser, p_name);
21408 break;
953ff289 21409 case PRAGMA_OMP_ATOMIC:
c2255bc4 21410 c_parser_omp_atomic (loc, parser);
953ff289
DN
21411 return;
21412 case PRAGMA_OMP_CRITICAL:
dda1bf61 21413 stmt = c_parser_omp_critical (loc, parser, if_p);
953ff289 21414 break;
acf0174b
JJ
21415 case PRAGMA_OMP_DISTRIBUTE:
21416 strcpy (p_name, "#pragma omp");
dda1bf61 21417 stmt = c_parser_omp_distribute (loc, parser, p_name, mask, NULL, if_p);
acf0174b 21418 break;
953ff289 21419 case PRAGMA_OMP_FOR:
acf0174b 21420 strcpy (p_name, "#pragma omp");
dda1bf61 21421 stmt = c_parser_omp_for (loc, parser, p_name, mask, NULL, if_p);
953ff289 21422 break;
554a530f
JJ
21423 case PRAGMA_OMP_LOOP:
21424 strcpy (p_name, "#pragma omp");
21425 stmt = c_parser_omp_loop (loc, parser, p_name, mask, NULL, if_p);
21426 break;
953ff289 21427 case PRAGMA_OMP_MASTER:
28567c40
JJ
21428 strcpy (p_name, "#pragma omp");
21429 stmt = c_parser_omp_master (loc, parser, p_name, mask, NULL, if_p);
953ff289 21430 break;
953ff289 21431 case PRAGMA_OMP_PARALLEL:
acf0174b 21432 strcpy (p_name, "#pragma omp");
dda1bf61 21433 stmt = c_parser_omp_parallel (loc, parser, p_name, mask, NULL, if_p);
953ff289
DN
21434 break;
21435 case PRAGMA_OMP_SECTIONS:
acf0174b
JJ
21436 strcpy (p_name, "#pragma omp");
21437 stmt = c_parser_omp_sections (loc, parser, p_name, mask, NULL);
21438 break;
21439 case PRAGMA_OMP_SIMD:
21440 strcpy (p_name, "#pragma omp");
dda1bf61 21441 stmt = c_parser_omp_simd (loc, parser, p_name, mask, NULL, if_p);
953ff289
DN
21442 break;
21443 case PRAGMA_OMP_SINGLE:
dda1bf61 21444 stmt = c_parser_omp_single (loc, parser, if_p);
953ff289 21445 break;
a68ab351 21446 case PRAGMA_OMP_TASK:
dda1bf61 21447 stmt = c_parser_omp_task (loc, parser, if_p);
a68ab351 21448 break;
acf0174b 21449 case PRAGMA_OMP_TASKGROUP:
28567c40 21450 stmt = c_parser_omp_taskgroup (loc, parser, if_p);
acf0174b 21451 break;
d9a6bd32
JJ
21452 case PRAGMA_OMP_TASKLOOP:
21453 strcpy (p_name, "#pragma omp");
dda1bf61 21454 stmt = c_parser_omp_taskloop (loc, parser, p_name, mask, NULL, if_p);
d9a6bd32 21455 break;
acf0174b
JJ
21456 case PRAGMA_OMP_TEAMS:
21457 strcpy (p_name, "#pragma omp");
dda1bf61 21458 stmt = c_parser_omp_teams (loc, parser, p_name, mask, NULL, if_p);
acf0174b 21459 break;
953ff289
DN
21460 default:
21461 gcc_unreachable ();
21462 }
21463
21464 if (stmt)
c2255bc4 21465 gcc_assert (EXPR_LOCATION (stmt) != UNKNOWN_LOCATION);
953ff289
DN
21466}
21467
21468
21469/* OpenMP 2.5:
21470 # pragma omp threadprivate (variable-list) */
21471
21472static void
21473c_parser_omp_threadprivate (c_parser *parser)
21474{
21475 tree vars, t;
c2255bc4 21476 location_t loc;
953ff289
DN
21477
21478 c_parser_consume_pragma (parser);
c2255bc4 21479 loc = c_parser_peek_token (parser)->location;
d75d71e0 21480 vars = c_parser_omp_var_list_parens (parser, OMP_CLAUSE_ERROR, NULL);
953ff289 21481
953ff289
DN
21482 /* Mark every variable in VARS to be assigned thread local storage. */
21483 for (t = vars; t; t = TREE_CHAIN (t))
21484 {
21485 tree v = TREE_PURPOSE (t);
21486
c2255bc4
AH
21487 /* FIXME diagnostics: Ideally we should keep individual
21488 locations for all the variables in the var list to make the
21489 following errors more precise. Perhaps
21490 c_parser_omp_var_list_parens() should construct a list of
21491 locations to go along with the var list. */
21492
953ff289
DN
21493 /* If V had already been marked threadprivate, it doesn't matter
21494 whether it had been used prior to this point. */
0ae9bd27 21495 if (!VAR_P (v))
c2255bc4 21496 error_at (loc, "%qD is not a variable", v);
5df27e4a 21497 else if (TREE_USED (v) && !C_DECL_THREADPRIVATE_P (v))
c2255bc4 21498 error_at (loc, "%qE declared %<threadprivate%> after first use", v);
62f9079a 21499 else if (! is_global_var (v))
c2255bc4 21500 error_at (loc, "automatic variable %qE cannot be %<threadprivate%>", v);
5df27e4a
JJ
21501 else if (TREE_TYPE (v) == error_mark_node)
21502 ;
953ff289 21503 else if (! COMPLETE_TYPE_P (TREE_TYPE (v)))
c2255bc4 21504 error_at (loc, "%<threadprivate%> %qE has incomplete type", v);
953ff289
DN
21505 else
21506 {
21507 if (! DECL_THREAD_LOCAL_P (v))
21508 {
56363ffd 21509 set_decl_tls_model (v, decl_default_tls_model (v));
953ff289
DN
21510 /* If rtl has been already set for this var, call
21511 make_decl_rtl once again, so that encode_section_info
21512 has a chance to look at the new decl flags. */
21513 if (DECL_RTL_SET_P (v))
21514 make_decl_rtl (v);
21515 }
21516 C_DECL_THREADPRIVATE_P (v) = 1;
21517 }
21518 }
21519
21520 c_parser_skip_to_pragma_eol (parser);
21521}
9a771876 21522
0a35513e
AH
21523/* Parse a transaction attribute (GCC Extension).
21524
21525 transaction-attribute:
783bfe5e 21526 gnu-attributes
c01bd174
JM
21527 attribute-specifier
21528*/
0a35513e
AH
21529
21530static tree
21531c_parser_transaction_attributes (c_parser *parser)
21532{
0a35513e 21533 if (c_parser_next_token_is_keyword (parser, RID_ATTRIBUTE))
783bfe5e 21534 return c_parser_gnu_attributes (parser);
0a35513e
AH
21535
21536 if (!c_parser_next_token_is (parser, CPP_OPEN_SQUARE))
21537 return NULL_TREE;
c01bd174 21538 return c_parser_std_attribute_specifier (parser, true);
0a35513e
AH
21539}
21540
21541/* Parse a __transaction_atomic or __transaction_relaxed statement
21542 (GCC Extension).
21543
21544 transaction-statement:
21545 __transaction_atomic transaction-attribute[opt] compound-statement
21546 __transaction_relaxed compound-statement
21547
21548 Note that the only valid attribute is: "outer".
21549*/
21550
21551static tree
21552c_parser_transaction (c_parser *parser, enum rid keyword)
21553{
21554 unsigned int old_in = parser->in_transaction;
21555 unsigned int this_in = 1, new_in;
21556 location_t loc = c_parser_peek_token (parser)->location;
21557 tree stmt, attrs;
21558
21559 gcc_assert ((keyword == RID_TRANSACTION_ATOMIC
21560 || keyword == RID_TRANSACTION_RELAXED)
21561 && c_parser_next_token_is_keyword (parser, keyword));
21562 c_parser_consume_token (parser);
21563
21564 if (keyword == RID_TRANSACTION_RELAXED)
21565 this_in |= TM_STMT_ATTR_RELAXED;
21566 else
21567 {
21568 attrs = c_parser_transaction_attributes (parser);
21569 if (attrs)
21570 this_in |= parse_tm_stmt_attr (attrs, TM_STMT_ATTR_OUTER);
21571 }
21572
21573 /* Keep track if we're in the lexical scope of an outer transaction. */
21574 new_in = this_in | (old_in & TM_STMT_ATTR_OUTER);
21575
21576 parser->in_transaction = new_in;
21577 stmt = c_parser_compound_statement (parser);
21578 parser->in_transaction = old_in;
21579
21580 if (flag_tm)
21581 stmt = c_finish_transaction (loc, stmt, this_in);
21582 else
21583 error_at (loc, (keyword == RID_TRANSACTION_ATOMIC ?
21584 "%<__transaction_atomic%> without transactional memory support enabled"
21585 : "%<__transaction_relaxed %> "
21586 "without transactional memory support enabled"));
21587
21588 return stmt;
21589}
21590
21591/* Parse a __transaction_atomic or __transaction_relaxed expression
21592 (GCC Extension).
21593
21594 transaction-expression:
21595 __transaction_atomic ( expression )
21596 __transaction_relaxed ( expression )
21597*/
21598
21599static struct c_expr
21600c_parser_transaction_expression (c_parser *parser, enum rid keyword)
21601{
21602 struct c_expr ret;
21603 unsigned int old_in = parser->in_transaction;
21604 unsigned int this_in = 1;
21605 location_t loc = c_parser_peek_token (parser)->location;
21606 tree attrs;
21607
21608 gcc_assert ((keyword == RID_TRANSACTION_ATOMIC
21609 || keyword == RID_TRANSACTION_RELAXED)
21610 && c_parser_next_token_is_keyword (parser, keyword));
21611 c_parser_consume_token (parser);
21612
21613 if (keyword == RID_TRANSACTION_RELAXED)
21614 this_in |= TM_STMT_ATTR_RELAXED;
21615 else
21616 {
21617 attrs = c_parser_transaction_attributes (parser);
21618 if (attrs)
21619 this_in |= parse_tm_stmt_attr (attrs, 0);
21620 }
21621
21622 parser->in_transaction = this_in;
32129a17
DM
21623 matching_parens parens;
21624 if (parens.require_open (parser))
0a35513e
AH
21625 {
21626 tree expr = c_parser_expression (parser).value;
21627 ret.original_type = TREE_TYPE (expr);
21628 ret.value = build1 (TRANSACTION_EXPR, ret.original_type, expr);
21629 if (this_in & TM_STMT_ATTR_RELAXED)
21630 TRANSACTION_EXPR_RELAXED (ret.value) = 1;
21631 SET_EXPR_LOCATION (ret.value, loc);
21632 ret.original_code = TRANSACTION_EXPR;
32129a17 21633 if (!parens.require_close (parser))
69b76518
TR
21634 {
21635 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN, NULL);
21636 goto error;
21637 }
0a35513e
AH
21638 }
21639 else
21640 {
69b76518 21641 error:
913884f7 21642 ret.set_error ();
0a35513e
AH
21643 ret.original_code = ERROR_MARK;
21644 ret.original_type = NULL;
21645 }
21646 parser->in_transaction = old_in;
21647
21648 if (!flag_tm)
21649 error_at (loc, (keyword == RID_TRANSACTION_ATOMIC ?
21650 "%<__transaction_atomic%> without transactional memory support enabled"
21651 : "%<__transaction_relaxed %> "
21652 "without transactional memory support enabled"));
21653
bef08b71
DM
21654 set_c_expr_source_range (&ret, loc, loc);
21655
0a35513e
AH
21656 return ret;
21657}
21658
21659/* Parse a __transaction_cancel statement (GCC Extension).
21660
21661 transaction-cancel-statement:
21662 __transaction_cancel transaction-attribute[opt] ;
21663
21664 Note that the only valid attribute is "outer".
21665*/
21666
21667static tree
acf0174b 21668c_parser_transaction_cancel (c_parser *parser)
0a35513e
AH
21669{
21670 location_t loc = c_parser_peek_token (parser)->location;
21671 tree attrs;
21672 bool is_outer = false;
21673
21674 gcc_assert (c_parser_next_token_is_keyword (parser, RID_TRANSACTION_CANCEL));
21675 c_parser_consume_token (parser);
21676
21677 attrs = c_parser_transaction_attributes (parser);
21678 if (attrs)
21679 is_outer = (parse_tm_stmt_attr (attrs, TM_STMT_ATTR_OUTER) != 0);
21680
21681 if (!flag_tm)
21682 {
21683 error_at (loc, "%<__transaction_cancel%> without "
21684 "transactional memory support enabled");
21685 goto ret_error;
21686 }
21687 else if (parser->in_transaction & TM_STMT_ATTR_RELAXED)
21688 {
21689 error_at (loc, "%<__transaction_cancel%> within a "
21690 "%<__transaction_relaxed%>");
21691 goto ret_error;
21692 }
21693 else if (is_outer)
21694 {
21695 if ((parser->in_transaction & TM_STMT_ATTR_OUTER) == 0
21696 && !is_tm_may_cancel_outer (current_function_decl))
21697 {
21698 error_at (loc, "outer %<__transaction_cancel%> not "
a9c697b8
MS
21699 "within outer %<__transaction_atomic%> or "
21700 "a %<transaction_may_cancel_outer%> function");
0a35513e
AH
21701 goto ret_error;
21702 }
21703 }
21704 else if (parser->in_transaction == 0)
21705 {
21706 error_at (loc, "%<__transaction_cancel%> not within "
21707 "%<__transaction_atomic%>");
21708 goto ret_error;
21709 }
21710
21711 return add_stmt (build_tm_abort_call (loc, is_outer));
21712
21713 ret_error:
21714 return build1 (NOP_EXPR, void_type_node, error_mark_node);
21715}
bc4071dd 21716\f
27bf414c
JM
21717/* Parse a single source file. */
21718
21719void
21720c_parse_file (void)
21721{
bc4071dd
RH
21722 /* Use local storage to begin. If the first token is a pragma, parse it.
21723 If it is #pragma GCC pch_preprocess, then this will load a PCH file
21724 which will cause garbage collection. */
21725 c_parser tparser;
21726
21727 memset (&tparser, 0, sizeof tparser);
471c5330 21728 tparser.translate_strings_p = true;
acf0174b 21729 tparser.tokens = &tparser.tokens_buf[0];
bc4071dd
RH
21730 the_parser = &tparser;
21731
21732 if (c_parser_peek_token (&tparser)->pragma_kind == PRAGMA_GCC_PCH_PREPROCESS)
21733 c_parser_pragma_pch_preprocess (&tparser);
22f8849d
IS
21734 else
21735 c_common_no_more_pch ();
bc4071dd 21736
766090c2 21737 the_parser = ggc_alloc<c_parser> ();
bc4071dd 21738 *the_parser = tparser;
acf0174b
JJ
21739 if (tparser.tokens == &tparser.tokens_buf[0])
21740 the_parser->tokens = &the_parser->tokens_buf[0];
bc4071dd 21741
f9417da1
RG
21742 /* Initialize EH, if we've been told to do so. */
21743 if (flag_exceptions)
1d65f45c 21744 using_eh_for_cleanups ();
f9417da1 21745
27bf414c
JM
21746 c_parser_translation_unit (the_parser);
21747 the_parser = NULL;
21748}
21749
c2e84327
DM
21750/* Parse the body of a function declaration marked with "__RTL".
21751
21752 The RTL parser works on the level of characters read from a
21753 FILE *, whereas c_parser works at the level of tokens.
21754 Square this circle by consuming all of the tokens up to and
21755 including the closing brace, recording the start/end of the RTL
21756 fragment, and reopening the file and re-reading the relevant
21757 lines within the RTL parser.
21758
21759 This requires the opening and closing braces of the C function
21760 to be on separate lines from the RTL they wrap.
21761
21762 Take ownership of START_WITH_PASS, if non-NULL. */
21763
9def91e9 21764location_t
c2e84327
DM
21765c_parser_parse_rtl_body (c_parser *parser, char *start_with_pass)
21766{
21767 if (!c_parser_require (parser, CPP_OPEN_BRACE, "expected %<{%>"))
21768 {
21769 free (start_with_pass);
9def91e9 21770 return c_parser_peek_token (parser)->location;
c2e84327
DM
21771 }
21772
21773 location_t start_loc = c_parser_peek_token (parser)->location;
21774
21775 /* Consume all tokens, up to the closing brace, handling
21776 matching pairs of braces in the rtl dump. */
21777 int num_open_braces = 1;
21778 while (1)
21779 {
21780 switch (c_parser_peek_token (parser)->type)
21781 {
21782 case CPP_OPEN_BRACE:
21783 num_open_braces++;
21784 break;
21785 case CPP_CLOSE_BRACE:
21786 if (--num_open_braces == 0)
21787 goto found_closing_brace;
21788 break;
21789 case CPP_EOF:
21790 error_at (start_loc, "no closing brace");
21791 free (start_with_pass);
9def91e9 21792 return c_parser_peek_token (parser)->location;
c2e84327
DM
21793 default:
21794 break;
21795 }
21796 c_parser_consume_token (parser);
21797 }
21798
21799 found_closing_brace:
21800 /* At the closing brace; record its location. */
21801 location_t end_loc = c_parser_peek_token (parser)->location;
21802
21803 /* Consume the closing brace. */
21804 c_parser_consume_token (parser);
21805
21806 /* Invoke the RTL parser. */
21807 if (!read_rtl_function_body_from_file_range (start_loc, end_loc))
21808 {
21809 free (start_with_pass);
9def91e9 21810 return end_loc;
c2e84327
DM
21811 }
21812
20a38017
MM
21813 /* Run the backend on the cfun created above, transferring ownership of
21814 START_WITH_PASS. */
21815 run_rtl_passes (start_with_pass);
9def91e9 21816 return end_loc;
c2e84327
DM
21817}
21818
d4a10d0a 21819#include "gt-c-c-parser.h"