1 /* Parser for GIMPLE.
2 Copyright (C) 2016-2022 Free Software Foundation, Inc.
3
4 This file is part of GCC.
5
6 GCC is free software; you can redistribute it and/or modify it under
7 the terms of the GNU General Public License as published by the Free
8 Software Foundation; either version 3, or (at your option) any later
9 version.
10
11 GCC is distributed in the hope that it will be useful, but WITHOUT ANY
12 WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
14 for more details.
15
16 You should have received a copy of the GNU General Public License
17 along with GCC; see the file COPYING3. If not see
18 <http://www.gnu.org/licenses/>. */
19
20 #include "config.h"
21 #include "system.h"
22 #include "coretypes.h"
23 #include "target.h"
24 #include "function.h"
25 #include "c-tree.h"
26 #include "timevar.h"
27 #include "stringpool.h"
28 #include "cgraph.h"
29 #include "attribs.h"
30 #include "stor-layout.h"
31 #include "varasm.h"
32 #include "trans-mem.h"
33 #include "c-family/c-pragma.h"
34 #include "c-lang.h"
35 #include "c-family/c-objc.h"
36 #include "plugin.h"
37 #include "builtins.h"
38 #include "gomp-constants.h"
39 #include "c-family/c-indentation.h"
40 #include "gimple-expr.h"
41 #include "context.h"
42 #include "gcc-rich-location.h"
43 #include "c-parser.h"
44 #include "tree-vrp.h"
45 #include "tree-pass.h"
46 #include "tree-pretty-print.h"
47 #include "tree.h"
48 #include "basic-block.h"
49 #include "gimple.h"
50 #include "gimple-pretty-print.h"
51 #include "tree-ssa.h"
52 #include "pass_manager.h"
53 #include "tree-ssanames.h"
54 #include "gimple-ssa.h"
55 #include "tree-dfa.h"
56 #include "internal-fn.h"
57 #include "cfg.h"
58 #include "cfghooks.h"
59 #include "bitmap.h"
60 #include "cfganal.h"
61 #include "tree-cfg.h"
62 #include "gimple-iterator.h"
63 #include "cfgloop.h"
64 #include "tree-phinodes.h"
65 #include "tree-into-ssa.h"
66
67
68 /* GIMPLE parser state. */
69
70 class gimple_parser
71 {
72 public:
gimple_parser(c_parser * p)73 gimple_parser (c_parser *p) : parser (p), edges(), current_bb(NULL) {}
74 /* c_parser is not visible here, use composition and fake inheritance
75 via a conversion operator. */
operator c_parser*()76 operator c_parser *() { return parser; }
77 c_parser *parser;
78
79 /* CFG build state. */
80 class gimple_parser_edge
81 {
82 public:
83 int src;
84 int dest;
85 int flags;
86 profile_probability probability;
87 };
88 auto_vec<gimple_parser_edge> edges;
89 basic_block current_bb;
90
91 void push_edge (int, int, int, profile_probability);
92 };
93
94 void
push_edge(int src,int dest,int flags,profile_probability prob)95 gimple_parser::push_edge (int src, int dest, int flags,
96 profile_probability prob)
97 {
98 gimple_parser_edge e;
99 e.src = src;
100 e.dest = dest;
101 e.flags = flags;
102 e.probability = prob;
103 edges.safe_push (e);
104 }
105
106
107 /* Gimple parsing functions. */
108 static bool c_parser_gimple_compound_statement (gimple_parser &, gimple_seq *);
109 static void c_parser_gimple_label (gimple_parser &, gimple_seq *);
110 static void c_parser_gimple_statement (gimple_parser &, gimple_seq *);
111 static struct c_expr c_parser_gimple_binary_expression (gimple_parser &);
112 static struct c_expr c_parser_gimple_unary_expression (gimple_parser &);
113 static struct c_expr c_parser_gimple_postfix_expression (gimple_parser &);
114 static struct c_expr c_parser_gimple_postfix_expression_after_primary
115 (gimple_parser &, location_t, struct c_expr);
116 static void c_parser_gimple_declaration (gimple_parser &);
117 static void c_parser_gimple_goto_stmt (gimple_parser &, location_t,
118 tree, gimple_seq *);
119 static void c_parser_gimple_try_stmt (gimple_parser &, gimple_seq *);
120 static void c_parser_gimple_if_stmt (gimple_parser &, gimple_seq *);
121 static void c_parser_gimple_switch_stmt (gimple_parser &, gimple_seq *);
122 static void c_parser_gimple_return_stmt (gimple_parser &, gimple_seq *);
123 static void c_finish_gimple_return (location_t, tree);
124 static tree c_parser_gimple_paren_condition (gimple_parser &);
125 static void c_parser_gimple_expr_list (gimple_parser &, vec<tree> *);
126
127
128 /* See if VAL is an identifier matching __BB<num> and return <num>
129 in *INDEX. */
130
131 static bool
c_parser_gimple_parse_bb_spec(tree val,int * index)132 c_parser_gimple_parse_bb_spec (tree val, int *index)
133 {
134 if (!startswith (IDENTIFIER_POINTER (val), "__BB"))
135 return false;
136 for (const char *p = IDENTIFIER_POINTER (val) + 4; *p; ++p)
137 if (!ISDIGIT (*p))
138 return false;
139 *index = atoi (IDENTIFIER_POINTER (val) + 4);
140 return *index > 0;
141 }
142
143 /* See if VAL is an identifier matching __BB<num> and return <num>
144 in *INDEX. Return true if so and parse also FREQUENCY of
145 the edge. */
146
147
148 static bool
c_parser_gimple_parse_bb_spec_edge_probability(tree val,gimple_parser & parser,int * index,profile_probability * probability)149 c_parser_gimple_parse_bb_spec_edge_probability (tree val,
150 gimple_parser &parser,
151 int *index,
152 profile_probability
153 *probability)
154 {
155 bool return_p = c_parser_gimple_parse_bb_spec (val, index);
156 if (return_p)
157 {
158 *probability = profile_probability::uninitialized ();
159 /* Parse frequency if provided. */
160 if (c_parser_next_token_is (parser, CPP_OPEN_PAREN))
161 {
162 tree f;
163 c_parser_consume_token (parser);
164 if (!c_parser_next_token_is (parser, CPP_NAME))
165 {
166 c_parser_error (parser, "expected frequency quality");
167 return false;
168 }
169
170 profile_quality quality;
171 const char *v
172 = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
173 if (!parse_profile_quality (v, &quality))
174 {
175 c_parser_error (parser, "unknown profile quality");
176 return false;
177 }
178
179 c_parser_consume_token (parser);
180 if (!c_parser_require (parser, CPP_OPEN_PAREN, "expected %<(%>"))
181 return false;
182
183 if (!c_parser_next_token_is (parser, CPP_NUMBER)
184 || (TREE_CODE (f = c_parser_peek_token (parser)->value)
185 != INTEGER_CST))
186 {
187 c_parser_error (parser, "expected frequency value");
188 return false;
189 }
190
191 unsigned int value = TREE_INT_CST_LOW (f);
192 *probability = profile_probability (value, quality);
193
194 c_parser_consume_token (parser);
195 if (!c_parser_require (parser, CPP_CLOSE_PAREN, "expected %<)%>"))
196 return false;
197
198 if (!c_parser_require (parser, CPP_CLOSE_PAREN, "expected %<)%>"))
199 return false;
200 }
201
202 return true;
203 }
204
205 return false;
206
207 }
208
209 /* Parse the body of a function declaration marked with "__GIMPLE". */
210
211 void
c_parser_parse_gimple_body(c_parser * cparser,char * gimple_pass,enum c_declspec_il cdil,profile_count entry_bb_count)212 c_parser_parse_gimple_body (c_parser *cparser, char *gimple_pass,
213 enum c_declspec_il cdil,
214 profile_count entry_bb_count)
215 {
216 gimple_parser parser (cparser);
217 gimple_seq seq = NULL;
218 gimple_seq body = NULL;
219 tree stmt = push_stmt_list ();
220 push_scope ();
221 location_t loc1 = c_parser_peek_token (parser)->location;
222
223 cfun->pass_startwith = gimple_pass;
224 init_tree_ssa (cfun);
225
226 if (cdil == cdil_gimple)
227 /* While we have SSA names in the IL we do not have a CFG built yet
228 and PHIs are represented using a PHI internal function. We do
229 have lowered control flow and exception handling (well, we do not
230 have parser support for EH yet). But as we still have BINDs
231 we have to go through lowering again. */
232 cfun->curr_properties = PROP_gimple_any;
233 else
234 {
235 /* We have at least cdil_gimple_cfg. */
236 gimple_register_cfg_hooks ();
237 init_empty_tree_cfg ();
238 parser.current_bb = ENTRY_BLOCK_PTR_FOR_FN (cfun);
239 /* Initialize the bare loop structure - we are going to only
240 mark headers and leave the rest to fixup. */
241 set_loops_for_fn (cfun, ggc_cleared_alloc<struct loops> ());
242 init_loops_structure (cfun, loops_for_fn (cfun), 1);
243 loops_state_set (cfun, LOOPS_NEED_FIXUP|LOOPS_MAY_HAVE_MULTIPLE_LATCHES);
244 cfun->curr_properties
245 |= PROP_gimple_lcf | PROP_gimple_leh | PROP_cfg | PROP_loops;
246 if (cdil == cdil_gimple_ssa)
247 {
248 init_ssa_operands (cfun);
249 cfun->curr_properties |= PROP_ssa;
250 }
251 }
252
253 if (! c_parser_gimple_compound_statement (parser, &seq)
254 && cdil == cdil_gimple)
255 {
256 gimple *ret = gimple_build_return (NULL);
257 gimple_seq_add_stmt_without_update (&seq, ret);
258 }
259
260 tree block = pop_scope ();
261 stmt = pop_stmt_list (stmt);
262 stmt = c_build_bind_expr (loc1, block, stmt);
263
264 block = DECL_INITIAL (current_function_decl);
265 BLOCK_SUBBLOCKS (block) = NULL_TREE;
266 BLOCK_CHAIN (block) = NULL_TREE;
267 TREE_ASM_WRITTEN (block) = 1;
268
269 if (cdil == cdil_gimple)
270 {
271 gbind *bind_stmt = gimple_build_bind (BIND_EXPR_VARS (stmt), NULL,
272 BIND_EXPR_BLOCK (stmt));
273 gimple_bind_set_body (bind_stmt, seq);
274 gimple_seq_add_stmt_without_update (&body, bind_stmt);
275 gimple_set_body (current_function_decl, body);
276 }
277 else
278 {
279 /* Control-flow and binds are lowered, record local decls. */
280 for (tree var = BIND_EXPR_VARS (stmt); var; var = DECL_CHAIN (var))
281 if (VAR_P (var)
282 && !DECL_EXTERNAL (var))
283 add_local_decl (cfun, var);
284 /* We have a CFG. Build the edges. */
285 for (unsigned i = 0; i < parser.edges.length (); ++i)
286 {
287 edge e = make_edge (BASIC_BLOCK_FOR_FN (cfun, parser.edges[i].src),
288 BASIC_BLOCK_FOR_FN (cfun, parser.edges[i].dest),
289 parser.edges[i].flags);
290 e->probability = parser.edges[i].probability;
291 }
292 /* Add edges for case labels. */
293 basic_block bb;
294 FOR_EACH_BB_FN (bb, cfun)
295 if (EDGE_COUNT (bb->succs) == 0)
296 {
297 gimple *last = last_stmt (bb);
298 if (gswitch *sw = safe_dyn_cast <gswitch *> (last))
299 for (unsigned i = 0; i < gimple_switch_num_labels (sw); ++i)
300 {
301 basic_block label_bb = gimple_switch_label_bb (cfun, sw, i);
302 make_edge (bb, label_bb, 0);
303 }
304 }
305 /* Need those for loop fixup. */
306 calculate_dominance_info (CDI_DOMINATORS);
307 /* With SSA lower PHIs parsed as internal function calls and
308 update stmts. */
309 if (cdil == cdil_gimple_ssa)
310 {
311 /* Create PHI nodes, they are parsed into __PHI internal calls. */
312 FOR_EACH_BB_FN (bb, cfun)
313 for (gimple_stmt_iterator gsi = gsi_start_bb (bb);
314 !gsi_end_p (gsi);)
315 {
316 gimple *stmt = gsi_stmt (gsi);
317 if (!gimple_call_internal_p (stmt, IFN_PHI))
318 break;
319
320 gphi *phi = create_phi_node (gimple_call_lhs (stmt), bb);
321 for (unsigned i = 0; i < gimple_call_num_args (stmt); i += 2)
322 {
323 int srcidx = TREE_INT_CST_LOW (gimple_call_arg (stmt, i));
324 edge e = find_edge (BASIC_BLOCK_FOR_FN (cfun, srcidx), bb);
325 if (!e)
326 c_parser_error (parser, "edge not found");
327 else
328 add_phi_arg (phi, gimple_call_arg (stmt, i + 1), e,
329 UNKNOWN_LOCATION);
330 }
331 gsi_remove (&gsi, true);
332 }
333 /* Fill SSA name gaps, putting them on the freelist and diagnose
334 SSA names without definition. */
335 for (unsigned i = 1; i < num_ssa_names; ++i)
336 if (!ssa_name (i))
337 {
338 tree name = make_ssa_name_fn (cfun, integer_type_node, NULL, i);
339 release_ssa_name_fn (cfun, name);
340 }
341 else if (!SSA_NAME_DEF_STMT (ssa_name (i)))
342 error ("SSA name %qE with version %d has no definition",
343 ssa_name (i), i);
344 /* No explicit virtual operands (yet). */
345 bitmap_obstack_initialize (NULL);
346 update_ssa (TODO_update_ssa_only_virtuals);
347 bitmap_obstack_release (NULL);
348 /* ??? By flushing the freelist after virtual operand SSA rewrite
349 we keep the gaps available for re-use like needed for the
350 PR89595 testcase but then usually virtual operands would have
351 taken most of them. The fix is obviously to make virtual
352 operands explicit in the SSA IL. */
353 flush_ssaname_freelist ();
354 }
355 fix_loop_structure (NULL);
356 }
357
358 if (cfun->curr_properties & PROP_cfg)
359 {
360 ENTRY_BLOCK_PTR_FOR_FN (cfun)->count = entry_bb_count;
361 gcov_type t = param_gimple_fe_computed_hot_bb_threshold;
362 set_hot_bb_threshold (t);
363 update_max_bb_count ();
364 cgraph_node::get_create (cfun->decl);
365 cgraph_edge::rebuild_edges ();
366 }
367 dump_function (TDI_gimple, current_function_decl);
368 }
369
370 /* Parse a compound statement in gimple function body.
371
372 gimple-statement:
373 gimple-statement
374 gimple-declaration-statement
375 gimple-if-statement
376 gimple-switch-statement
377 gimple-labeled-statement
378 gimple-expression-statement
379 gimple-goto-statement
380 gimple-phi-statement
381 gimple-return-statement
382 */
383
384 static bool
c_parser_gimple_compound_statement(gimple_parser & parser,gimple_seq * seq)385 c_parser_gimple_compound_statement (gimple_parser &parser, gimple_seq *seq)
386 {
387 bool return_p = false;
388
389 if (! c_parser_require (parser, CPP_OPEN_BRACE, "expected %<{%>"))
390 return false;
391
392 /* A compund statement starts with optional declarations. */
393 while (c_parser_next_tokens_start_declaration (parser))
394 {
395 c_parser_gimple_declaration (parser);
396 if (! c_parser_require (parser, CPP_SEMICOLON, "expected %<;%>"))
397 return false;
398 }
399
400 while (c_parser_next_token_is_not (parser, CPP_CLOSE_BRACE))
401 {
402 if (c_parser_error (parser))
403 {
404 c_parser_skip_until_found (parser, CPP_CLOSE_BRACE, NULL);
405 return return_p;
406 }
407 else if (c_parser_next_token_is (parser, CPP_EOF))
408 {
409 c_parser_error (parser, "expected declaration or statement");
410 return return_p;
411 }
412
413 switch (c_parser_peek_token (parser)->type)
414 {
415 case CPP_KEYWORD:
416 switch (c_parser_peek_token (parser)->keyword)
417 {
418 case RID_AT_TRY:
419 c_parser_gimple_try_stmt (parser, seq);
420 break;
421 case RID_IF:
422 c_parser_gimple_if_stmt (parser, seq);
423 break;
424 case RID_SWITCH:
425 c_parser_gimple_switch_stmt (parser, seq);
426 break;
427 case RID_GOTO:
428 {
429 location_t loc = c_parser_peek_token (parser)->location;
430 c_parser_consume_token (parser);
431 if (c_parser_next_token_is (parser, CPP_NAME))
432 {
433 tree label = c_parser_peek_token (parser)->value;
434 c_parser_consume_token (parser);
435 c_parser_gimple_goto_stmt (parser, loc, label, seq);
436 if (! c_parser_require (parser, CPP_SEMICOLON,
437 "expected %<;%>"))
438 return return_p;
439 }
440 }
441 break;
442 case RID_RETURN:
443 return_p = true;
444 c_parser_gimple_return_stmt (parser, seq);
445 if (! c_parser_require (parser, CPP_SEMICOLON,
446 "expected %<;%>"))
447 return return_p;
448 if (cfun->curr_properties & PROP_cfg)
449 parser.push_edge (parser.current_bb->index, EXIT_BLOCK, 0,
450 profile_probability::uninitialized ());
451 break;
452 default:
453 goto expr_stmt;
454 }
455 break;
456 case CPP_NAME:
457 if (c_parser_peek_2nd_token (parser)->type == CPP_COLON)
458 {
459 c_parser_gimple_label (parser, seq);
460 break;
461 }
462 if (c_parser_next_token_is (parser, CPP_NAME)
463 && c_parser_peek_token (parser)->id_kind == C_ID_ID
464 && strcmp (IDENTIFIER_POINTER (c_parser_peek_token (parser)->value),
465 "try") == 0)
466 {
467 c_parser_gimple_try_stmt (parser, seq);
468 break;
469 }
470 /* Basic block specification.
471 __BB (index, ...) */
472 if ((cfun->curr_properties & PROP_cfg)
473 && !strcmp (IDENTIFIER_POINTER
474 (c_parser_peek_token (parser)->value), "__BB"))
475 {
476 c_parser_consume_token (parser);
477 if (! c_parser_require (parser, CPP_OPEN_PAREN,
478 "expected %<(%>"))
479 return return_p;
480 if (c_parser_next_token_is_not (parser, CPP_NUMBER))
481 {
482 c_parser_error (parser, "expected block index");
483 return return_p;
484 }
485 tree tnum = c_parser_peek_token (parser)->value;
486 if (TREE_CODE (tnum) != INTEGER_CST)
487 {
488 c_parser_error (parser, "expected block index");
489 return return_p;
490 }
491 int index = TREE_INT_CST_LOW (tnum);
492 if (index < NUM_FIXED_BLOCKS
493 || (index < last_basic_block_for_fn (cfun)
494 && BASIC_BLOCK_FOR_FN (cfun, index) != NULL))
495 {
496 c_parser_error (parser, "invalid block index");
497 return return_p;
498 }
499 int is_loop_header_of = -1;
500 profile_count bb_count = profile_count::uninitialized ();
501 c_parser_consume_token (parser);
502 while (c_parser_next_token_is (parser, CPP_COMMA))
503 {
504 c_parser_consume_token (parser);
505 if (! c_parser_next_token_is (parser, CPP_NAME))
506 {
507 c_parser_error (parser, "expected block specifier");
508 return return_p;
509 }
510 /* loop_header (NUM) */
511 if (!strcmp (IDENTIFIER_POINTER
512 (c_parser_peek_token (parser)->value),
513 "loop_header"))
514 {
515 c_parser_consume_token (parser);
516 if (! c_parser_require (parser, CPP_OPEN_PAREN,
517 "expected %<(%>"))
518 return return_p;
519 tree loop_num;
520 if (! c_parser_next_token_is (parser, CPP_NUMBER)
521 || TREE_CODE (loop_num
522 = c_parser_peek_token (parser)->value)
523 != INTEGER_CST)
524 {
525 c_parser_error (parser, "expected loop number");
526 return return_p;
527 }
528 c_parser_consume_token (parser);
529 is_loop_header_of = TREE_INT_CST_LOW (loop_num);
530 if (! c_parser_require (parser, CPP_CLOSE_PAREN,
531 "expected %<)%>"))
532 return return_p;
533 }
534 /* Parse profile: quality(value) */
535 else
536 {
537 tree q;
538 profile_quality quality;
539 tree v = c_parser_peek_token (parser)->value;
540 if (!parse_profile_quality (IDENTIFIER_POINTER (v),
541 &quality))
542 {
543 c_parser_error (parser, "unknown block specifier");
544 return false;
545 }
546
547 c_parser_consume_token (parser);
548 if (!c_parser_require (parser, CPP_OPEN_PAREN,
549 "expected %<(%>"))
550 return false;
551
552 if (!c_parser_next_token_is (parser, CPP_NUMBER)
553 || (TREE_CODE (q = c_parser_peek_token (parser)->value)
554 != INTEGER_CST))
555 {
556 c_parser_error (parser, "expected count value");
557 return false;
558 }
559
560 bb_count
561 = profile_count::from_gcov_type (TREE_INT_CST_LOW (q),
562 quality);
563 c_parser_consume_token (parser);
564 if (! c_parser_require (parser, CPP_CLOSE_PAREN,
565 "expected %<)%>"))
566 return return_p;
567 }
568 }
569 if (! c_parser_require (parser, CPP_CLOSE_PAREN,
570 "expected %<)%>")
571 || ! c_parser_require (parser, CPP_COLON,
572 "expected %<:%>"))
573 return return_p;
574
575 /* Put stmts parsed in the current block. */
576 if (!gimple_seq_empty_p (*seq))
577 {
578 if (!parser.current_bb)
579 c_parser_error (parser, "stmts without block");
580 else
581 {
582 gimple_stmt_iterator gsi
583 = gsi_start_bb (parser.current_bb);
584 gsi_insert_seq_after (&gsi, *seq, GSI_CONTINUE_LINKING);
585 }
586 *seq = NULL;
587 }
588
589 /* Build an empty block with specified index, linking them
590 in source order. */
591 basic_block bb = alloc_block ();
592 bb->index = index;
593 link_block (bb, (parser.current_bb ? parser.current_bb
594 : ENTRY_BLOCK_PTR_FOR_FN (cfun)));
595 if (basic_block_info_for_fn (cfun)->length () <= (size_t)index)
596 vec_safe_grow_cleared (basic_block_info_for_fn (cfun),
597 index + 1, true);
598 SET_BASIC_BLOCK_FOR_FN (cfun, index, bb);
599 if (last_basic_block_for_fn (cfun) <= index)
600 last_basic_block_for_fn (cfun) = index + 1;
601 n_basic_blocks_for_fn (cfun)++;
602 if (parser.current_bb->index == ENTRY_BLOCK)
603 parser.push_edge (ENTRY_BLOCK, bb->index, EDGE_FALLTHRU,
604 profile_probability::always ());
605
606 /* We leave the proper setting to fixup. */
607 class loop *loop_father = loops_for_fn (cfun)->tree_root;
608 /* If the new block is a loop header, allocate a loop
609 struct. Fixup will take care of proper placement within
610 the loop tree. */
611 if (is_loop_header_of != -1)
612 {
613 if (number_of_loops (cfun) > (unsigned)is_loop_header_of
614 && get_loop (cfun, is_loop_header_of) != NULL)
615 {
616 c_parser_error (parser, "duplicate loop header");
617 }
618 else
619 {
620 class loop *loop = alloc_loop ();
621 loop->num = is_loop_header_of;
622 loop->header = bb;
623 if (number_of_loops (cfun) <= (unsigned)is_loop_header_of)
624 vec_safe_grow_cleared (loops_for_fn (cfun)->larray,
625 is_loop_header_of + 1, true);
626 (*loops_for_fn (cfun)->larray)[is_loop_header_of] = loop;
627 flow_loop_tree_node_add (loops_for_fn (cfun)->tree_root,
628 loop);
629 }
630 loop_father = get_loop (cfun, is_loop_header_of);
631 }
632 bb->loop_father = loop_father;
633 bb->count = bb_count;
634
635 /* Stmts now go to the new block. */
636 parser.current_bb = bb;
637 break;
638 }
639 goto expr_stmt;
640
641 case CPP_SEMICOLON:
642 {
643 /* Empty stmt. */
644 location_t loc = c_parser_peek_token (parser)->location;
645 c_parser_consume_token (parser);
646 gimple *nop = gimple_build_nop ();
647 gimple_set_location (nop, loc);
648 gimple_seq_add_stmt_without_update (seq, nop);
649 break;
650 }
651
652 default:
653 expr_stmt:
654 c_parser_gimple_statement (parser, seq);
655 if (! c_parser_require (parser, CPP_SEMICOLON, "expected %<;%>"))
656 c_parser_skip_until_found (parser, CPP_SEMICOLON, NULL);
657 }
658 }
659 c_parser_consume_token (parser);
660
661 /* Put stmts parsed in the current block. */
662 if ((cfun->curr_properties & PROP_cfg)
663 && !gimple_seq_empty_p (*seq))
664 {
665 if (!parser.current_bb)
666 c_parser_error (parser, "stmts without block");
667 else
668 {
669 gimple_stmt_iterator gsi = gsi_start_bb (parser.current_bb);
670 gsi_insert_seq_after (&gsi, *seq, GSI_CONTINUE_LINKING);
671 }
672 *seq = NULL;
673 }
674
675 return return_p;
676 }
677
678 /* Parse a gimple statement.
679
680 gimple-statement:
681 gimple-call-expression
682 gimple-assign-statement
683 gimple-phi-statement
684
685 gimple-assign-statement:
686 gimple-unary-expression = gimple-assign-rhs
687
688 gimple-assign-rhs:
689 gimple-cast-expression
690 gimple-unary-expression
691 gimple-binary-expression
692 gimple-call-expression
693
694 gimple-phi-statement:
695 identifier = __PHI ( label : gimple_primary-expression, ... )
696
697 gimple-call-expr:
698 gimple-primary-expression ( argument-list )
699
700 gimple-cast-expression:
701 ( type-name ) gimple-primary-expression
702
703 */
704
705 static void
c_parser_gimple_statement(gimple_parser & parser,gimple_seq * seq)706 c_parser_gimple_statement (gimple_parser &parser, gimple_seq *seq)
707 {
708 struct c_expr lhs, rhs;
709 gimple *assign = NULL;
710 location_t loc;
711 tree arg = NULL_TREE;
712 auto_vec<tree> vargs;
713
714 lhs = c_parser_gimple_unary_expression (parser);
715 loc = EXPR_LOCATION (lhs.value);
716 rhs.set_error ();
717
718 /* GIMPLE call statement without LHS. */
719 if (c_parser_next_token_is (parser, CPP_SEMICOLON)
720 && TREE_CODE (lhs.value) == CALL_EXPR)
721 {
722 gimple *call;
723 call = gimple_build_call_from_tree (lhs.value, NULL);
724 gimple_seq_add_stmt_without_update (seq, call);
725 gimple_set_location (call, loc);
726 return;
727 }
728
729 /* All following cases are statements with LHS. */
730 if (! c_parser_require (parser, CPP_EQ, "expected %<=%>"))
731 return;
732
733 /* Cast expression. */
734 if (c_parser_next_token_is (parser, CPP_OPEN_PAREN)
735 && c_token_starts_typename (c_parser_peek_2nd_token (parser)))
736 {
737 c_parser_consume_token (parser);
738 struct c_type_name *type_name = c_parser_type_name (parser);
739 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN, "expected %<)%>");
740 if (type_name == NULL)
741 return;
742 /* ??? The actual type used in the cast expression is ignored as
743 in GIMPLE it is encoded by the type of the LHS. */
744 rhs = c_parser_gimple_postfix_expression (parser);
745 if (lhs.value != error_mark_node
746 && rhs.value != error_mark_node)
747 {
748 enum tree_code code = NOP_EXPR;
749 if (FLOAT_TYPE_P (TREE_TYPE (lhs.value))
750 && ! FLOAT_TYPE_P (TREE_TYPE (rhs.value)))
751 code = FLOAT_EXPR;
752 else if (! FLOAT_TYPE_P (TREE_TYPE (lhs.value))
753 && FLOAT_TYPE_P (TREE_TYPE (rhs.value)))
754 code = FIX_TRUNC_EXPR;
755 assign = gimple_build_assign (lhs.value, code, rhs.value);
756 gimple_seq_add_stmt_without_update (seq, assign);
757 gimple_set_location (assign, loc);
758 return;
759 }
760 }
761
762 /* Unary expression. */
763 switch (c_parser_peek_token (parser)->type)
764 {
765 case CPP_NAME:
766 {
767 tree id = c_parser_peek_token (parser)->value;
768 if (strcmp (IDENTIFIER_POINTER (id), "__ABS") == 0
769 || strcmp (IDENTIFIER_POINTER (id), "__ABSU") == 0
770 || strcmp (IDENTIFIER_POINTER (id), "__MIN") == 0
771 || strcmp (IDENTIFIER_POINTER (id), "__MAX") == 0
772 || strcmp (IDENTIFIER_POINTER (id), "__BIT_INSERT") == 0
773 || strcmp (IDENTIFIER_POINTER (id), "__VEC_PERM") == 0)
774 goto build_unary_expr;
775 break;
776 }
777 case CPP_KEYWORD:
778 if (c_parser_peek_token (parser)->keyword != RID_REALPART
779 && c_parser_peek_token (parser)->keyword != RID_IMAGPART)
780 break;
781 /* Fallthru. */
782 case CPP_AND:
783 case CPP_PLUS:
784 case CPP_MINUS:
785 case CPP_COMPL:
786 case CPP_NOT:
787 case CPP_MULT: /* pointer deref */
788 build_unary_expr:
789 rhs = c_parser_gimple_unary_expression (parser);
790 if (rhs.value != error_mark_node)
791 {
792 assign = gimple_build_assign (lhs.value, rhs.value);
793 gimple_set_location (assign, loc);
794 gimple_seq_add_stmt_without_update (seq, assign);
795 }
796 return;
797
798 default:;
799 }
800
801 /* GIMPLE PHI statement. */
802 if (c_parser_next_token_is_keyword (parser, RID_PHI))
803 {
804 c_parser_consume_token (parser);
805
806 if (! c_parser_require (parser, CPP_OPEN_PAREN, "expected %<(%>"))
807 return;
808
809 if (c_parser_next_token_is (parser, CPP_OPEN_PAREN))
810 c_parser_consume_token (parser);
811
812 while (c_parser_next_token_is_not (parser, CPP_CLOSE_PAREN))
813 {
814 if (c_parser_next_token_is (parser, CPP_NAME)
815 && c_parser_peek_2nd_token (parser)->type == CPP_COLON)
816 {
817 arg = c_parser_peek_token (parser)->value;
818 c_parser_consume_token (parser);
819 if (c_parser_next_token_is (parser, CPP_COLON))
820 c_parser_consume_token (parser);
821 int src_index = -1;
822 if (!c_parser_gimple_parse_bb_spec (arg, &src_index))
823 c_parser_error (parser, "invalid source block specification");
824 vargs.safe_push (size_int (src_index));
825 }
826 else if (c_parser_next_token_is (parser, CPP_COMMA))
827 c_parser_consume_token (parser);
828 else
829 {
830 arg = c_parser_gimple_unary_expression (parser).value;
831 vargs.safe_push (arg);
832 }
833 }
834
835 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN,
836 "expected %<)%>");
837
838 /* Build internal function for PHI. */
839 gcall *call_stmt = gimple_build_call_internal_vec (IFN_PHI, vargs);
840 gimple_call_set_lhs (call_stmt, lhs.value);
841 gimple_set_location (call_stmt, UNKNOWN_LOCATION);
842 gimple_seq_add_stmt_without_update (seq, call_stmt);
843 return;
844 }
845
846 /* GIMPLE call with lhs. */
847 if (c_parser_next_token_is (parser, CPP_DOT)
848 || (c_parser_next_token_is (parser, CPP_NAME)
849 && c_parser_peek_2nd_token (parser)->type == CPP_OPEN_PAREN
850 && lookup_name (c_parser_peek_token (parser)->value)))
851 {
852 rhs = c_parser_gimple_unary_expression (parser);
853 if (rhs.value != error_mark_node)
854 {
855 gimple *call = gimple_build_call_from_tree (rhs.value, NULL);
856 gimple_call_set_lhs (call, lhs.value);
857 gimple_seq_add_stmt_without_update (seq, call);
858 gimple_set_location (call, loc);
859 }
860 return;
861 }
862
863 rhs = c_parser_gimple_binary_expression (parser);
864 if (lhs.value != error_mark_node
865 && rhs.value != error_mark_node)
866 {
867 /* If we parsed a comparison or an identifier and the next token
868 is a '?' then parse a conditional expression. */
869 if ((COMPARISON_CLASS_P (rhs.value)
870 || SSA_VAR_P (rhs.value))
871 && c_parser_next_token_is (parser, CPP_QUERY))
872 {
873 struct c_expr trueval, falseval;
874 c_parser_consume_token (parser);
875 trueval = c_parser_gimple_postfix_expression (parser);
876 falseval.set_error ();
877 if (c_parser_require (parser, CPP_COLON, "expected %<:%>"))
878 falseval = c_parser_gimple_postfix_expression (parser);
879 if (trueval.value == error_mark_node
880 || falseval.value == error_mark_node)
881 return;
882 rhs.value = build3_loc (loc,
883 VECTOR_TYPE_P (TREE_TYPE (rhs.value))
884 ? VEC_COND_EXPR : COND_EXPR,
885 TREE_TYPE (trueval.value),
886 rhs.value, trueval.value, falseval.value);
887 }
888 if (get_gimple_rhs_class (TREE_CODE (rhs.value)) == GIMPLE_INVALID_RHS)
889 {
890 c_parser_error (parser, "unexpected RHS for assignment");
891 return;
892 }
893 assign = gimple_build_assign (lhs.value, rhs.value);
894 gimple_seq_add_stmt_without_update (seq, assign);
895 gimple_set_location (assign, loc);
896 }
897 return;
898 }
899
900 /* Parse gimple binary expr.
901
902 gimple-binary-expression:
903 gimple-unary-expression * gimple-unary-expression
904 gimple-unary-expression __MULT_HIGHPART gimple-unary-expression
905 gimple-unary-expression / gimple-unary-expression
906 gimple-unary-expression % gimple-unary-expression
907 gimple-unary-expression + gimple-unary-expression
908 gimple-unary-expression - gimple-unary-expression
909 gimple-unary-expression << gimple-unary-expression
910 gimple-unary-expression >> gimple-unary-expression
911 gimple-unary-expression < gimple-unary-expression
912 gimple-unary-expression > gimple-unary-expression
913 gimple-unary-expression <= gimple-unary-expression
914 gimple-unary-expression >= gimple-unary-expression
915 gimple-unary-expression == gimple-unary-expression
916 gimple-unary-expression != gimple-unary-expression
917 gimple-unary-expression & gimple-unary-expression
918 gimple-unary-expression ^ gimple-unary-expression
919 gimple-unary-expression | gimple-unary-expression
920
921 */
922
923 static c_expr
c_parser_gimple_binary_expression(gimple_parser & parser)924 c_parser_gimple_binary_expression (gimple_parser &parser)
925 {
926 /* Location of the binary operator. */
927 struct c_expr ret, lhs, rhs;
928 enum tree_code code = ERROR_MARK;
929 ret.set_error ();
930 lhs = c_parser_gimple_postfix_expression (parser);
931 if (c_parser_error (parser))
932 return ret;
933 tree ret_type = TREE_TYPE (lhs.value);
934 switch (c_parser_peek_token (parser)->type)
935 {
936 case CPP_MULT:
937 code = MULT_EXPR;
938 break;
939 case CPP_DIV:
940 code = TRUNC_DIV_EXPR;
941 break;
942 case CPP_MOD:
943 code = TRUNC_MOD_EXPR;
944 break;
945 case CPP_PLUS:
946 if (POINTER_TYPE_P (TREE_TYPE (lhs.value)))
947 code = POINTER_PLUS_EXPR;
948 else
949 code = PLUS_EXPR;
950 break;
951 case CPP_MINUS:
952 code = MINUS_EXPR;
953 break;
954 case CPP_LSHIFT:
955 code = LSHIFT_EXPR;
956 break;
957 case CPP_RSHIFT:
958 code = RSHIFT_EXPR;
959 break;
960 case CPP_LESS:
961 code = LT_EXPR;
962 ret_type = boolean_type_node;
963 break;
964 case CPP_GREATER:
965 code = GT_EXPR;
966 ret_type = boolean_type_node;
967 break;
968 case CPP_LESS_EQ:
969 code = LE_EXPR;
970 ret_type = boolean_type_node;
971 break;
972 case CPP_GREATER_EQ:
973 code = GE_EXPR;
974 ret_type = boolean_type_node;
975 break;
976 case CPP_EQ_EQ:
977 code = EQ_EXPR;
978 ret_type = boolean_type_node;
979 break;
980 case CPP_NOT_EQ:
981 code = NE_EXPR;
982 ret_type = boolean_type_node;
983 break;
984 case CPP_AND:
985 code = BIT_AND_EXPR;
986 break;
987 case CPP_XOR:
988 code = BIT_XOR_EXPR;
989 break;
990 case CPP_OR:
991 code = BIT_IOR_EXPR;
992 break;
993 case CPP_AND_AND:
994 c_parser_error (parser, "%<&&%> not valid in GIMPLE");
995 return ret;
996 case CPP_OR_OR:
997 c_parser_error (parser, "%<||%> not valid in GIMPLE");
998 return ret;
999 case CPP_NAME:
1000 {
1001 tree id = c_parser_peek_token (parser)->value;
1002 if (strcmp (IDENTIFIER_POINTER (id), "__MULT_HIGHPART") == 0)
1003 {
1004 code = MULT_HIGHPART_EXPR;
1005 break;
1006 }
1007 }
1008 /* Fallthru. */
1009 default:
1010 /* Not a binary expression. */
1011 return lhs;
1012 }
1013 location_t ret_loc = c_parser_peek_token (parser)->location;
1014 c_parser_consume_token (parser);
1015 rhs = c_parser_gimple_postfix_expression (parser);
1016 if (lhs.value != error_mark_node && rhs.value != error_mark_node)
1017 ret.value = build2_loc (ret_loc, code, ret_type, lhs.value, rhs.value);
1018 return ret;
1019 }
1020
1021 /* Parse a gimple parentized binary expression. */
1022
1023 static c_expr
c_parser_gimple_parentized_binary_expression(gimple_parser & parser,location_t op_loc,tree_code code)1024 c_parser_gimple_parentized_binary_expression (gimple_parser &parser,
1025 location_t op_loc,
1026 tree_code code)
1027 {
1028 struct c_expr ret;
1029 ret.set_error ();
1030
1031 c_parser_consume_token (parser);
1032 if (!c_parser_require (parser, CPP_OPEN_PAREN, "expected %<(%>"))
1033 return ret;
1034 c_expr op1 = c_parser_gimple_postfix_expression (parser);
1035 if (!c_parser_require (parser, CPP_COMMA, "expected %<,%>"))
1036 return ret;
1037 c_expr op2 = c_parser_gimple_postfix_expression (parser);
1038 if (!c_parser_require (parser, CPP_CLOSE_PAREN, "expected %<)%>"))
1039 return ret;
1040
1041 if (op1.value != error_mark_node && op2.value != error_mark_node)
1042 ret.value = build2_loc (op_loc,
1043 code, TREE_TYPE (op1.value), op1.value, op2.value);
1044 return ret;
1045 }
1046
1047 /* Parse a gimple parentized binary expression. */
1048
1049 static c_expr
c_parser_gimple_parentized_ternary_expression(gimple_parser & parser,location_t op_loc,tree_code code)1050 c_parser_gimple_parentized_ternary_expression (gimple_parser &parser,
1051 location_t op_loc,
1052 tree_code code)
1053 {
1054 struct c_expr ret;
1055 ret.set_error ();
1056
1057 c_parser_consume_token (parser);
1058 if (!c_parser_require (parser, CPP_OPEN_PAREN, "expected %<(%>"))
1059 return ret;
1060 c_expr op1 = c_parser_gimple_postfix_expression (parser);
1061 if (!c_parser_require (parser, CPP_COMMA, "expected %<,%>"))
1062 return ret;
1063 c_expr op2 = c_parser_gimple_postfix_expression (parser);
1064 if (!c_parser_require (parser, CPP_COMMA, "expected %<)%>"))
1065 return ret;
1066 c_expr op3 = c_parser_gimple_postfix_expression (parser);
1067 if (!c_parser_require (parser, CPP_CLOSE_PAREN, "expected %<)%>"))
1068 return ret;
1069
1070 if (op1.value != error_mark_node
1071 && op2.value != error_mark_node
1072 && op3.value != error_mark_node)
1073 ret.value = build3_loc (op_loc,
1074 code, TREE_TYPE (op1.value),
1075 op1.value, op2.value, op3.value);
1076 return ret;
1077 }
1078
1079 /* Parse gimple unary expression.
1080
1081 gimple-unary-expression:
1082 gimple-postfix-expression
1083 unary-operator gimple-postfix-expression
1084
1085 unary-operator: one of
1086 & * + - ~ abs_expr
1087 */
1088
1089 static c_expr
c_parser_gimple_unary_expression(gimple_parser & parser)1090 c_parser_gimple_unary_expression (gimple_parser &parser)
1091 {
1092 struct c_expr ret, op;
1093 location_t op_loc = c_parser_peek_token (parser)->location;
1094 location_t finish;
1095 ret.set_error ();
1096 switch (c_parser_peek_token (parser)->type)
1097 {
1098 case CPP_AND:
1099 c_parser_consume_token (parser);
1100 op = c_parser_gimple_postfix_expression (parser);
1101 mark_exp_read (op.value);
1102 return parser_build_unary_op (op_loc, ADDR_EXPR, op);
1103 case CPP_MULT:
1104 {
1105 c_parser_consume_token (parser);
1106 op = c_parser_gimple_postfix_expression (parser);
1107 if (op.value == error_mark_node)
1108 return ret;
1109 if (! POINTER_TYPE_P (TREE_TYPE (op.value)))
1110 {
1111 error_at (op_loc, "expected pointer as argument of unary %<*%>");
1112 return ret;
1113 }
1114 finish = op.get_finish ();
1115 location_t combined_loc = make_location (op_loc, op_loc, finish);
1116 ret.value = build_simple_mem_ref_loc (combined_loc, op.value);
1117 TREE_SIDE_EFFECTS (ret.value)
1118 = TREE_THIS_VOLATILE (ret.value)
1119 = TYPE_VOLATILE (TREE_TYPE (TREE_TYPE (op.value)));
1120 ret.src_range.m_start = op_loc;
1121 ret.src_range.m_finish = finish;
1122 return ret;
1123 }
1124 case CPP_PLUS:
1125 c_parser_consume_token (parser);
1126 op = c_parser_gimple_postfix_expression (parser);
1127 return parser_build_unary_op (op_loc, CONVERT_EXPR, op);
1128 case CPP_MINUS:
1129 c_parser_consume_token (parser);
1130 op = c_parser_gimple_postfix_expression (parser);
1131 return parser_build_unary_op (op_loc, NEGATE_EXPR, op);
1132 case CPP_COMPL:
1133 c_parser_consume_token (parser);
1134 op = c_parser_gimple_postfix_expression (parser);
1135 return parser_build_unary_op (op_loc, BIT_NOT_EXPR, op);
1136 case CPP_NOT:
1137 c_parser_error (parser, "%<!%> not valid in GIMPLE");
1138 return ret;
1139 case CPP_KEYWORD:
1140 switch (c_parser_peek_token (parser)->keyword)
1141 {
1142 case RID_REALPART:
1143 c_parser_consume_token (parser);
1144 op = c_parser_gimple_postfix_expression (parser);
1145 return parser_build_unary_op (op_loc, REALPART_EXPR, op);
1146 case RID_IMAGPART:
1147 c_parser_consume_token (parser);
1148 op = c_parser_gimple_postfix_expression (parser);
1149 return parser_build_unary_op (op_loc, IMAGPART_EXPR, op);
1150 default:
1151 return c_parser_gimple_postfix_expression (parser);
1152 }
1153 case CPP_NAME:
1154 {
1155 tree id = c_parser_peek_token (parser)->value;
1156 if (strcmp (IDENTIFIER_POINTER (id), "__ABS") == 0)
1157 {
1158 c_parser_consume_token (parser);
1159 op = c_parser_gimple_postfix_expression (parser);
1160 return parser_build_unary_op (op_loc, ABS_EXPR, op);
1161 }
1162 else if (strcmp (IDENTIFIER_POINTER (id), "__ABSU") == 0)
1163 {
1164 c_parser_consume_token (parser);
1165 op = c_parser_gimple_postfix_expression (parser);
1166 return parser_build_unary_op (op_loc, ABSU_EXPR, op);
1167 }
1168 else if (strcmp (IDENTIFIER_POINTER (id), "__MIN") == 0)
1169 return c_parser_gimple_parentized_binary_expression (parser,
1170 op_loc,
1171 MIN_EXPR);
1172 else if (strcmp (IDENTIFIER_POINTER (id), "__MAX") == 0)
1173 return c_parser_gimple_parentized_binary_expression (parser,
1174 op_loc,
1175 MAX_EXPR);
1176 else if (strcmp (IDENTIFIER_POINTER (id), "__VEC_PERM") == 0)
1177 return c_parser_gimple_parentized_ternary_expression
1178 (parser, op_loc, VEC_PERM_EXPR);
1179 else if (strcmp (IDENTIFIER_POINTER (id), "__BIT_INSERT") == 0)
1180 {
1181 /* __BIT_INSERT '(' postfix-expression, postfix-expression,
1182 integer ')' */
1183 location_t loc = c_parser_peek_token (parser)->location;
1184 c_parser_consume_token (parser);
1185 if (c_parser_require (parser, CPP_OPEN_PAREN, "expected %<(%>"))
1186 {
1187 c_expr op0 = c_parser_gimple_postfix_expression (parser);
1188 c_parser_skip_until_found (parser, CPP_COMMA,
1189 "expected %<,%>");
1190 c_expr op1 = c_parser_gimple_postfix_expression (parser);
1191 c_parser_skip_until_found (parser, CPP_COMMA,
1192 "expected %<,%>");
1193 c_expr op2 = c_parser_gimple_postfix_expression (parser);
1194 if (TREE_CODE (op2.value) != INTEGER_CST
1195 || !int_fits_type_p (op2.value, bitsizetype))
1196 c_parser_error (parser, "expected constant offset");
1197 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN,
1198 "expected %<)%>");
1199 if (op0.value != error_mark_node
1200 && op1.value != error_mark_node
1201 && TREE_CODE (op2.value) == INTEGER_CST)
1202 ret.value = build3_loc (loc, BIT_INSERT_EXPR,
1203 TREE_TYPE (op0.value),
1204 op0.value, op1.value,
1205 fold_convert (bitsizetype,
1206 op2.value));
1207 }
1208 return ret;
1209 }
1210 else
1211 return c_parser_gimple_postfix_expression (parser);
1212 }
1213 default:
1214 return c_parser_gimple_postfix_expression (parser);
1215 }
1216 }
1217
1218 /* Decompose ID into base name (ID until ver_offset) and VERSION. Return
1219 true if ID matches a SSA name. */
1220
1221 static bool
c_parser_parse_ssa_name_id(tree id,unsigned * version,unsigned * ver_offset)1222 c_parser_parse_ssa_name_id (tree id, unsigned *version, unsigned *ver_offset)
1223 {
1224 const char *token = IDENTIFIER_POINTER (id);
1225 const char *var_version = strrchr (token, '_');
1226 if (! var_version)
1227 return false;
1228
1229 *ver_offset = var_version - token;
1230 for (const char *p = var_version + 1; *p; ++p)
1231 if (! ISDIGIT (*p))
1232 return false;
1233 *version = atoi (var_version + 1);
1234 return *version > 0;
1235 }
1236
1237 /* Get at the actual SSA name ID with VERSION starting at VER_OFFSET.
1238 TYPE is the type if the SSA name is being declared. */
1239
1240 static tree
c_parser_parse_ssa_name(gimple_parser & parser,tree id,tree type,unsigned version,unsigned ver_offset)1241 c_parser_parse_ssa_name (gimple_parser &parser,
1242 tree id, tree type, unsigned version,
1243 unsigned ver_offset)
1244 {
1245 tree name = NULL_TREE;
1246 const char *token = IDENTIFIER_POINTER (id);
1247
1248 if (ver_offset == 0)
1249 {
1250 /* Anonymous unnamed SSA name. */
1251 if (version < num_ssa_names)
1252 name = ssa_name (version);
1253 if (! name)
1254 {
1255 if (! type)
1256 {
1257 c_parser_error (parser, "SSA name undeclared");
1258 return error_mark_node;
1259 }
1260 name = make_ssa_name_fn (cfun, type, NULL, version);
1261 }
1262 }
1263 else
1264 {
1265 if (version < num_ssa_names)
1266 name = ssa_name (version);
1267 if (! name)
1268 {
1269 /* Separate var name from version. */
1270 char *var_name = XNEWVEC (char, ver_offset + 1);
1271 memcpy (var_name, token, ver_offset);
1272 var_name[ver_offset] = '\0';
1273 /* lookup for parent decl. */
1274 id = get_identifier (var_name);
1275 tree parent = lookup_name (id);
1276 XDELETEVEC (var_name);
1277 if (! parent || parent == error_mark_node)
1278 {
1279 c_parser_error (parser, "base variable or SSA name undeclared");
1280 return error_mark_node;
1281 }
1282 if (!(VAR_P (parent)
1283 || TREE_CODE (parent) == PARM_DECL
1284 || TREE_CODE (parent) == RESULT_DECL))
1285 {
1286 error ("invalid base %qE for SSA name", parent);
1287 return error_mark_node;
1288 }
1289 name = make_ssa_name_fn (cfun, parent,
1290 gimple_build_nop (), version);
1291 }
1292 }
1293
1294 return name;
1295 }
1296
1297 /* Parse a gimple call to an internal function.
1298
1299 gimple-call-internal:
1300 . identifier ( gimple-argument-expression-list[opt] ) */
1301
1302 static struct c_expr
c_parser_gimple_call_internal(gimple_parser & parser)1303 c_parser_gimple_call_internal (gimple_parser &parser)
1304 {
1305 struct c_expr expr;
1306 expr.set_error ();
1307
1308 gcc_assert (c_parser_next_token_is (parser, CPP_DOT));
1309 c_parser_consume_token (parser);
1310 location_t loc = c_parser_peek_token (parser)->location;
1311 if (!c_parser_next_token_is (parser, CPP_NAME)
1312 || c_parser_peek_token (parser)->id_kind != C_ID_ID)
1313 {
1314 c_parser_error (parser, "expecting internal function name");
1315 return expr;
1316 }
1317 tree id = c_parser_peek_token (parser)->value;
1318 internal_fn ifn = lookup_internal_fn (IDENTIFIER_POINTER (id));
1319 c_parser_consume_token (parser);
1320 if (c_parser_require (parser, CPP_OPEN_PAREN, "expected %<(%>"))
1321 {
1322 auto_vec<tree> exprlist;
1323 if (!c_parser_next_token_is (parser, CPP_CLOSE_PAREN))
1324 c_parser_gimple_expr_list (parser, &exprlist);
1325 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN, "expected %<)%>");
1326 if (ifn == IFN_LAST)
1327 error_at (loc, "unknown internal function %qE", id);
1328 else
1329 {
1330 expr.value = build_call_expr_internal_loc_array
1331 (loc, ifn, void_type_node, exprlist.length (),
1332 exprlist.address ());
1333 expr.original_code = ERROR_MARK;
1334 expr.original_type = NULL;
1335 }
1336 }
1337 return expr;
1338 }
1339
1340 /* Parse '<' type [',' alignment] '>' and return a type on success
1341 and NULL_TREE on error. */
1342
1343 static tree
c_parser_gimple_typespec(gimple_parser & parser)1344 c_parser_gimple_typespec (gimple_parser &parser)
1345 {
1346 struct c_type_name *type_name = NULL;
1347 tree alignment = NULL_TREE;
1348 if (c_parser_require (parser, CPP_LESS, "expected %<<%>"))
1349 {
1350 type_name = c_parser_type_name (parser);
1351 /* Optional alignment. */
1352 if (c_parser_next_token_is (parser, CPP_COMMA))
1353 {
1354 c_parser_consume_token (parser);
1355 alignment
1356 = c_parser_gimple_postfix_expression (parser).value;
1357 }
1358 c_parser_skip_until_found (parser,
1359 CPP_GREATER, "expected %<>%>");
1360 }
1361 if (!type_name)
1362 return NULL_TREE;
1363 tree tem;
1364 tree type = groktypename (type_name, &tem, NULL);
1365 if (alignment)
1366 type = build_aligned_type (type, tree_to_uhwi (alignment));
1367 return type;
1368 }
1369
1370 /* Parse gimple postfix expression.
1371
1372 gimple-postfix-expression:
1373 gimple-primary-expression
1374 gimple-primary-expression [ gimple-primary-expression ]
1375 gimple-primary-expression ( gimple-argument-expression-list[opt] )
1376 gimple-postfix-expression . identifier
1377 gimple-postfix-expression -> identifier
1378
1379 gimple-argument-expression-list:
1380 gimple-unary-expression
1381 gimple-argument-expression-list , gimple-unary-expression
1382
1383 gimple-primary-expression:
1384 identifier
1385 constant
1386 string-literal
1387 constructor
1388 gimple-call-internal
1389
1390 */
1391
1392 static struct c_expr
c_parser_gimple_postfix_expression(gimple_parser & parser)1393 c_parser_gimple_postfix_expression (gimple_parser &parser)
1394 {
1395 location_t loc = c_parser_peek_token (parser)->location;
1396 source_range tok_range = c_parser_peek_token (parser)->get_range ();
1397 struct c_expr expr;
1398 expr.set_error ();
1399 switch (c_parser_peek_token (parser)->type)
1400 {
1401 case CPP_NUMBER:
1402 expr.value = c_parser_peek_token (parser)->value;
1403 set_c_expr_source_range (&expr, tok_range);
1404 loc = c_parser_peek_token (parser)->location;
1405 c_parser_consume_token (parser);
1406 break;
1407 case CPP_CHAR:
1408 case CPP_CHAR16:
1409 case CPP_CHAR32:
1410 case CPP_UTF8CHAR:
1411 case CPP_WCHAR:
1412 expr.value = c_parser_peek_token (parser)->value;
1413 set_c_expr_source_range (&expr, tok_range);
1414 c_parser_consume_token (parser);
1415 break;
1416 case CPP_STRING:
1417 case CPP_STRING16:
1418 case CPP_STRING32:
1419 case CPP_WSTRING:
1420 case CPP_UTF8STRING:
1421 expr = c_parser_string_literal (parser, false, true);
1422 break;
1423 case CPP_DOT:
1424 expr = c_parser_gimple_call_internal (parser);
1425 break;
1426 case CPP_NAME:
1427 if (c_parser_peek_token (parser)->id_kind == C_ID_ID)
1428 {
1429 tree id = c_parser_peek_token (parser)->value;
1430 if (strcmp (IDENTIFIER_POINTER (id), "__MEM") == 0)
1431 {
1432 /* __MEM '<' type-name [ ',' number ] '>'
1433 '(' [ '(' type-name ')' ] unary-expression
1434 [ '+' number ] ')' */
1435 location_t loc = c_parser_peek_token (parser)->location;
1436 c_parser_consume_token (parser);
1437 tree type = c_parser_gimple_typespec (parser);
1438 struct c_expr ptr;
1439 ptr.value = error_mark_node;
1440 tree alias_off = NULL_TREE;
1441 if (c_parser_require (parser, CPP_OPEN_PAREN, "expected %<(%>"))
1442 {
1443 tree alias_type = NULL_TREE;
1444 /* Optional alias-type cast. */
1445 if (c_parser_next_token_is (parser, CPP_OPEN_PAREN))
1446 {
1447 c_parser_consume_token (parser);
1448 struct c_type_name *alias_type_name
1449 = c_parser_type_name (parser);
1450 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN,
1451 "expected %<)%>");
1452 if (alias_type_name)
1453 {
1454 tree tem;
1455 alias_type = groktypename (alias_type_name,
1456 &tem, NULL);
1457 }
1458 }
1459 ptr = c_parser_gimple_unary_expression (parser);
1460 if (ptr.value == error_mark_node
1461 || ! POINTER_TYPE_P (TREE_TYPE (ptr.value)))
1462 {
1463 if (ptr.value != error_mark_node)
1464 error_at (ptr.get_start (),
1465 "invalid type of %<__MEM%> operand");
1466 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN,
1467 "expected %<)%>");
1468 return expr;
1469 }
1470 if (! alias_type)
1471 alias_type = TREE_TYPE (ptr.value);
1472 /* Optional constant offset. */
1473 if (c_parser_next_token_is (parser, CPP_PLUS))
1474 {
1475 c_parser_consume_token (parser);
1476 alias_off
1477 = c_parser_gimple_postfix_expression (parser).value;
1478 alias_off = fold_convert (alias_type, alias_off);
1479 }
1480 if (! alias_off)
1481 alias_off = build_int_cst (alias_type, 0);
1482 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN,
1483 "expected %<)%>");
1484 }
1485 if (! type || c_parser_error (parser))
1486 {
1487 c_parser_set_error (parser, false);
1488 return expr;
1489 }
1490 expr.value = build2_loc (loc, MEM_REF,
1491 type, ptr.value, alias_off);
1492 break;
1493 }
1494 else if (strcmp (IDENTIFIER_POINTER (id), "__VIEW_CONVERT") == 0)
1495 {
1496 /* __VIEW_CONVERT '<' type-name [ ',' number ] '>'
1497 '(' postfix-expression ')' */
1498 location_t loc = c_parser_peek_token (parser)->location;
1499 c_parser_consume_token (parser);
1500 tree type = c_parser_gimple_typespec (parser);
1501 if (c_parser_require (parser, CPP_OPEN_PAREN, "expected %<(%>"))
1502 {
1503 c_expr op = c_parser_gimple_postfix_expression (parser);
1504 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN,
1505 "expected %<)%>");
1506 if (type && op.value != error_mark_node)
1507 expr.value = build1_loc (loc, VIEW_CONVERT_EXPR,
1508 type, op.value);
1509 }
1510 break;
1511 }
1512 else if (strcmp (IDENTIFIER_POINTER (id), "__BIT_FIELD_REF") == 0)
1513 {
1514 /* __BIT_FIELD_REF '<' type-name [ ',' number ] '>'
1515 '(' postfix-expression, integer, integer ')' */
1516 location_t loc = c_parser_peek_token (parser)->location;
1517 c_parser_consume_token (parser);
1518 tree type = c_parser_gimple_typespec (parser);
1519 if (c_parser_require (parser, CPP_OPEN_PAREN, "expected %<(%>"))
1520 {
1521 c_expr op0 = c_parser_gimple_postfix_expression (parser);
1522 c_parser_skip_until_found (parser, CPP_COMMA,
1523 "expected %<,%>");
1524 c_expr op1 = c_parser_gimple_postfix_expression (parser);
1525 if (TREE_CODE (op1.value) != INTEGER_CST
1526 || !int_fits_type_p (op1.value, bitsizetype))
1527 c_parser_error (parser, "expected constant size");
1528 c_parser_skip_until_found (parser, CPP_COMMA,
1529 "expected %<,%>");
1530 c_expr op2 = c_parser_gimple_postfix_expression (parser);
1531 if (TREE_CODE (op2.value) != INTEGER_CST
1532 || !int_fits_type_p (op2.value, bitsizetype))
1533 c_parser_error (parser, "expected constant offset");
1534 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN,
1535 "expected %<)%>");
1536 if (type
1537 && op0.value != error_mark_node
1538 && TREE_CODE (op1.value) == INTEGER_CST
1539 && TREE_CODE (op2.value) == INTEGER_CST)
1540 expr.value = build3_loc (loc, BIT_FIELD_REF, type,
1541 op0.value,
1542 fold_convert (bitsizetype,
1543 op1.value),
1544 fold_convert (bitsizetype,
1545 op2.value));
1546 }
1547 break;
1548 }
1549 else if (strcmp (IDENTIFIER_POINTER (id), "_Literal") == 0)
1550 {
1551 /* _Literal '(' type-name ')' ( [ '-' ] constant | constructor ) */
1552 c_parser_consume_token (parser);
1553 tree type = NULL_TREE;
1554 if (c_parser_require (parser, CPP_OPEN_PAREN, "expected %<(%>"))
1555 {
1556 struct c_type_name *type_name = c_parser_type_name (parser);
1557 tree tem;
1558 if (type_name)
1559 type = groktypename (type_name, &tem, NULL);
1560 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN,
1561 "expected %<)%>");
1562 }
1563 if (! type)
1564 {
1565 c_parser_error (parser, "invalid _Literal");
1566 return expr;
1567 }
1568 if (c_parser_next_token_is (parser, CPP_OPEN_BRACE))
1569 {
1570 c_parser_consume_token (parser);
1571 if (!AGGREGATE_TYPE_P (type)
1572 && !VECTOR_TYPE_P (type))
1573 {
1574 c_parser_error (parser, "invalid type for _Literal with "
1575 "constructor");
1576 c_parser_skip_until_found (parser, CPP_CLOSE_BRACE,
1577 "expected %<}%>");
1578 return expr;
1579 }
1580 vec<constructor_elt, va_gc> *v = NULL;
1581 bool constant_p = true;
1582 if (VECTOR_TYPE_P (type)
1583 && !c_parser_next_token_is (parser, CPP_CLOSE_BRACE))
1584 {
1585 vec_alloc (v, TYPE_VECTOR_SUBPARTS (type).to_constant ());
1586 do
1587 {
1588 tree val
1589 = c_parser_gimple_postfix_expression (parser).value;
1590 if (! val
1591 || val == error_mark_node
1592 || (! CONSTANT_CLASS_P (val)
1593 && ! SSA_VAR_P (val)))
1594 {
1595 c_parser_error (parser, "invalid _Literal");
1596 return expr;
1597 }
1598 CONSTRUCTOR_APPEND_ELT (v, NULL_TREE, val);
1599 if (! CONSTANT_CLASS_P (val))
1600 constant_p = false;
1601 if (c_parser_next_token_is (parser, CPP_COMMA))
1602 c_parser_consume_token (parser);
1603 else
1604 break;
1605 }
1606 while (1);
1607 }
1608 if (c_parser_require (parser, CPP_CLOSE_BRACE,
1609 "expected %<}%>"))
1610 {
1611 if (v && constant_p)
1612 expr.value = build_vector_from_ctor (type, v);
1613 else
1614 expr.value = build_constructor (type, v);
1615 }
1616 else
1617 {
1618 c_parser_skip_until_found (parser, CPP_CLOSE_BRACE,
1619 "expected %<}%>");
1620 return expr;
1621 }
1622 }
1623 else
1624 {
1625 bool neg_p, addr_p;
1626 if ((neg_p = c_parser_next_token_is (parser, CPP_MINUS)))
1627 c_parser_consume_token (parser);
1628 if ((addr_p = c_parser_next_token_is (parser, CPP_AND)))
1629 c_parser_consume_token (parser);
1630 tree val = c_parser_gimple_postfix_expression (parser).value;
1631 if (! val
1632 || val == error_mark_node
1633 || (!CONSTANT_CLASS_P (val) && !addr_p))
1634 {
1635 c_parser_error (parser, "invalid _Literal");
1636 return expr;
1637 }
1638 if (addr_p)
1639 {
1640 val = build1 (ADDR_EXPR, type, val);
1641 if (!is_gimple_invariant_address (val))
1642 {
1643 c_parser_error (parser, "invalid _Literal");
1644 return expr;
1645 }
1646 }
1647 if (neg_p)
1648 {
1649 val = const_unop (NEGATE_EXPR, TREE_TYPE (val), val);
1650 if (! val)
1651 {
1652 c_parser_error (parser, "invalid _Literal");
1653 return expr;
1654 }
1655 }
1656 expr.value = fold_convert (type, val);
1657 }
1658 return expr;
1659 }
1660
1661 /* SSA name. */
1662 unsigned version, ver_offset;
1663 if (! lookup_name (id)
1664 && c_parser_parse_ssa_name_id (id, &version, &ver_offset))
1665 {
1666 c_parser_consume_token (parser);
1667 expr.value = c_parser_parse_ssa_name (parser, id, NULL_TREE,
1668 version, ver_offset);
1669 if (expr.value == error_mark_node)
1670 return expr;
1671 set_c_expr_source_range (&expr, tok_range);
1672 /* For default definition SSA names. */
1673 if (c_parser_next_token_is (parser, CPP_OPEN_PAREN)
1674 && c_parser_peek_2nd_token (parser)->type == CPP_NAME
1675 && strcmp ("D",
1676 IDENTIFIER_POINTER
1677 (c_parser_peek_2nd_token (parser)->value)) == 0
1678 && c_parser_peek_nth_token (parser, 3)->type == CPP_CLOSE_PAREN)
1679 {
1680 c_parser_consume_token (parser);
1681 c_parser_consume_token (parser);
1682 c_parser_consume_token (parser);
1683 if (! SSA_NAME_IS_DEFAULT_DEF (expr.value))
1684 {
1685 if (!SSA_NAME_VAR (expr.value))
1686 {
1687 error_at (loc, "anonymous SSA name cannot have"
1688 " default definition");
1689 expr.value = error_mark_node;
1690 return expr;
1691 }
1692 set_ssa_default_def (cfun, SSA_NAME_VAR (expr.value),
1693 expr.value);
1694 SSA_NAME_DEF_STMT (expr.value) = gimple_build_nop ();
1695 }
1696 }
1697 }
1698 else
1699 {
1700 c_parser_consume_token (parser);
1701 expr.value
1702 = build_external_ref (loc, id,
1703 (c_parser_peek_token (parser)->type
1704 == CPP_OPEN_PAREN), &expr.original_type);
1705 set_c_expr_source_range (&expr, tok_range);
1706 }
1707 break;
1708 }
1709 /* Fallthru. */
1710 default:
1711 c_parser_error (parser, "expected expression");
1712 expr.set_error ();
1713 break;
1714 }
1715 if (expr.value == error_mark_node)
1716 return expr;
1717 return c_parser_gimple_postfix_expression_after_primary
1718 (parser, EXPR_LOC_OR_LOC (expr.value, loc), expr);
1719 }
1720
1721 /* Parse a gimple postfix expression after the initial primary or compound
1722 literal. */
1723
1724 static struct c_expr
c_parser_gimple_postfix_expression_after_primary(gimple_parser & parser,location_t expr_loc,struct c_expr expr)1725 c_parser_gimple_postfix_expression_after_primary (gimple_parser &parser,
1726 location_t expr_loc,
1727 struct c_expr expr)
1728 {
1729 location_t start;
1730 location_t finish;
1731 tree ident;
1732 location_t comp_loc;
1733
1734 while (true)
1735 {
1736 location_t op_loc = c_parser_peek_token (parser)->location;
1737 switch (c_parser_peek_token (parser)->type)
1738 {
1739 case CPP_OPEN_SQUARE:
1740 {
1741 c_parser_consume_token (parser);
1742 tree idx = c_parser_gimple_unary_expression (parser).value;
1743
1744 if (! c_parser_require (parser, CPP_CLOSE_SQUARE, "expected %<]%>"))
1745 {
1746 c_parser_skip_until_found (parser, CPP_CLOSE_SQUARE, NULL);
1747 break;
1748 }
1749
1750 start = expr.get_start ();
1751 finish = c_parser_tokens_buf (parser, 0)->location;
1752 expr.value = build_array_ref (op_loc, expr.value, idx);
1753 set_c_expr_source_range (&expr, start, finish);
1754
1755 expr.original_code = ERROR_MARK;
1756 expr.original_type = NULL;
1757 break;
1758 }
1759 case CPP_OPEN_PAREN:
1760 {
1761 /* Function call. */
1762 c_parser_consume_token (parser);
1763 auto_vec<tree> exprlist;
1764 if (! c_parser_next_token_is (parser, CPP_CLOSE_PAREN))
1765 c_parser_gimple_expr_list (parser, &exprlist);
1766 c_parser_skip_until_found (parser, CPP_CLOSE_PAREN,
1767 "expected %<)%>");
1768 if (!FUNC_OR_METHOD_TYPE_P (TREE_TYPE (expr.value)))
1769 {
1770 c_parser_error (parser, "invalid call to non-function");
1771 expr.set_error ();
1772 break;
1773 }
1774 expr.value = build_call_array_loc
1775 (expr_loc, TREE_TYPE (TREE_TYPE (expr.value)),
1776 expr.value, exprlist.length (), exprlist.address ());
1777 expr.original_code = ERROR_MARK;
1778 expr.original_type = NULL;
1779 break;
1780 }
1781 case CPP_DOT:
1782 {
1783 /* Structure element reference. */
1784 c_parser_consume_token (parser);
1785 if (c_parser_next_token_is (parser, CPP_NAME))
1786 {
1787 c_token *comp_tok = c_parser_peek_token (parser);
1788 ident = comp_tok->value;
1789 comp_loc = comp_tok->location;
1790 }
1791 else
1792 {
1793 c_parser_error (parser, "expected identifier");
1794 expr.set_error ();
1795 expr.original_code = ERROR_MARK;
1796 expr.original_type = NULL;
1797 return expr;
1798 }
1799 start = expr.get_start ();
1800 finish = c_parser_peek_token (parser)->get_finish ();
1801 c_parser_consume_token (parser);
1802 expr.value = build_component_ref (op_loc, expr.value, ident,
1803 comp_loc);
1804 set_c_expr_source_range (&expr, start, finish);
1805 expr.original_code = ERROR_MARK;
1806 if (TREE_CODE (expr.value) != COMPONENT_REF)
1807 expr.original_type = NULL;
1808 else
1809 {
1810 /* Remember the original type of a bitfield. */
1811 tree field = TREE_OPERAND (expr.value, 1);
1812 if (TREE_CODE (field) != FIELD_DECL)
1813 expr.original_type = NULL;
1814 else
1815 expr.original_type = DECL_BIT_FIELD_TYPE (field);
1816 }
1817 break;
1818 }
1819 case CPP_DEREF:
1820 {
1821 /* Structure element reference. */
1822 if (!POINTER_TYPE_P (TREE_TYPE (expr.value)))
1823 {
1824 c_parser_error (parser, "dereference of non-pointer");
1825 expr.set_error ();
1826 expr.original_code = ERROR_MARK;
1827 expr.original_type = NULL;
1828 return expr;
1829 }
1830 c_parser_consume_token (parser);
1831 if (c_parser_next_token_is (parser, CPP_NAME))
1832 {
1833 c_token *comp_tok = c_parser_peek_token (parser);
1834 ident = comp_tok->value;
1835 comp_loc = comp_tok->location;
1836 }
1837 else
1838 {
1839 c_parser_error (parser, "expected identifier");
1840 expr.set_error ();
1841 expr.original_code = ERROR_MARK;
1842 expr.original_type = NULL;
1843 return expr;
1844 }
1845 start = expr.get_start ();
1846 finish = c_parser_peek_token (parser)->get_finish ();
1847 c_parser_consume_token (parser);
1848 expr.value = build_component_ref (op_loc,
1849 build_simple_mem_ref_loc
1850 (op_loc, expr.value),
1851 ident, comp_loc);
1852 set_c_expr_source_range (&expr, start, finish);
1853 expr.original_code = ERROR_MARK;
1854 if (TREE_CODE (expr.value) != COMPONENT_REF)
1855 expr.original_type = NULL;
1856 else
1857 {
1858 /* Remember the original type of a bitfield. */
1859 tree field = TREE_OPERAND (expr.value, 1);
1860 if (TREE_CODE (field) != FIELD_DECL)
1861 expr.original_type = NULL;
1862 else
1863 expr.original_type = DECL_BIT_FIELD_TYPE (field);
1864 }
1865 break;
1866 }
1867 default:
1868 return expr;
1869 }
1870 }
1871 }
1872
1873 /* Parse expression list.
1874
1875 gimple-expr-list:
1876 gimple-unary-expression
1877 gimple-expr-list , gimple-unary-expression
1878
1879 */
1880
1881 static void
c_parser_gimple_expr_list(gimple_parser & parser,vec<tree> * ret)1882 c_parser_gimple_expr_list (gimple_parser &parser, vec<tree> *ret)
1883 {
1884 struct c_expr expr;
1885
1886 expr = c_parser_gimple_unary_expression (parser);
1887 ret->safe_push (expr.value);
1888 while (c_parser_next_token_is (parser, CPP_COMMA))
1889 {
1890 c_parser_consume_token (parser);
1891 expr = c_parser_gimple_unary_expression (parser);
1892 ret->safe_push (expr.value);
1893 }
1894 }
1895
1896 /* Parse gimple label.
1897
1898 gimple-label:
1899 identifier :
1900 case constant-expression :
1901 default :
1902
1903 */
1904
1905 static void
c_parser_gimple_label(gimple_parser & parser,gimple_seq * seq)1906 c_parser_gimple_label (gimple_parser &parser, gimple_seq *seq)
1907 {
1908 tree name = c_parser_peek_token (parser)->value;
1909 location_t loc1 = c_parser_peek_token (parser)->location;
1910 gcc_assert (c_parser_next_token_is (parser, CPP_NAME));
1911 c_parser_consume_token (parser);
1912 gcc_assert (c_parser_next_token_is (parser, CPP_COLON));
1913 c_parser_consume_token (parser);
1914 tree label = define_label (loc1, name);
1915 if (label)
1916 gimple_seq_add_stmt_without_update (seq, gimple_build_label (label));
1917 return;
1918 }
1919
1920 /* Parse gimple/RTL pass list.
1921
1922 gimple-or-rtl-pass-list:
1923 startwith("pass-name")[,{cfg,ssa}]
1924 */
1925
1926 void
c_parser_gimple_or_rtl_pass_list(c_parser * parser,c_declspecs * specs)1927 c_parser_gimple_or_rtl_pass_list (c_parser *parser, c_declspecs *specs)
1928 {
1929 char *pass = NULL;
1930
1931 /* Accept __GIMPLE/__RTL. */
1932 if (c_parser_next_token_is_not (parser, CPP_OPEN_PAREN))
1933 return;
1934 c_parser_consume_token (parser);
1935
1936 specs->entry_bb_count = profile_count::uninitialized ();
1937 while (c_parser_next_token_is (parser, CPP_NAME))
1938 {
1939 profile_quality quality;
1940 const char *op = IDENTIFIER_POINTER (c_parser_peek_token (parser)->value);
1941 c_parser_consume_token (parser);
1942 if (! strcmp (op, "startwith"))
1943 {
1944 if (! c_parser_require (parser, CPP_OPEN_PAREN, "expected %<(%>"))
1945 return;
1946 if (c_parser_next_token_is_not (parser, CPP_STRING))
1947 {
1948 error_at (c_parser_peek_token (parser)->location,
1949 "expected pass name");
1950 return;
1951 }
1952 pass = xstrdup (TREE_STRING_POINTER
1953 (c_parser_string_literal (parser, false,
1954 false).value));
1955 if (! c_parser_require (parser, CPP_CLOSE_PAREN, "expected %<(%>"))
1956 return;
1957 }
1958 else if (parse_profile_quality (op, &quality))
1959 {
1960 tree q;
1961 if (!c_parser_require (parser, CPP_OPEN_PAREN, "expected %<(%>"))
1962 return;
1963
1964 if (!c_parser_next_token_is (parser, CPP_NUMBER)
1965 || (TREE_CODE (q = c_parser_peek_token (parser)->value)
1966 != INTEGER_CST))
1967 {
1968 c_parser_error (parser, "expected count value");
1969 return;
1970 }
1971
1972 specs->entry_bb_count
1973 = profile_count::from_gcov_type (TREE_INT_CST_LOW (q), quality);
1974 c_parser_consume_token (parser);
1975 if (!c_parser_require (parser, CPP_CLOSE_PAREN, "expected %<)%>"))
1976 return;
1977 }
1978 else if (specs->declspec_il != cdil_gimple)
1979 /* Allow only one IL specifier and none on RTL. */
1980 ;
1981 else if (! strcmp (op, "cfg"))
1982 specs->declspec_il = cdil_gimple_cfg;
1983 else if (! strcmp (op, "ssa"))
1984 specs->declspec_il = cdil_gimple_ssa;
1985 else
1986 {
1987 error_at (c_parser_peek_token (parser)->location,
1988 "invalid operation");
1989 return;
1990 }
1991 if (c_parser_next_token_is (parser, CPP_COMMA))
1992 c_parser_consume_token (parser);
1993 }
1994
1995 if (! c_parser_require (parser, CPP_CLOSE_PAREN, "expected %<)%>"))
1996 return;
1997
1998 specs->gimple_or_rtl_pass = pass;
1999 }
2000
2001 /* Parse gimple local declaration.
2002
2003 declaration-specifiers:
2004 storage-class-specifier declaration-specifiers[opt]
2005 type-specifier declaration-specifiers[opt]
2006 type-qualifier declaration-specifiers[opt]
2007 function-specifier declaration-specifiers[opt]
2008 alignment-specifier declaration-specifiers[opt]
2009
2010 storage-class-specifier:
2011 typedef
2012 extern
2013 static
2014 auto
2015 register
2016
2017 type-specifier:
2018 void
2019 char
2020 short
2021 int
2022 long
2023 float
2024 double
2025 signed
2026 unsigned
2027 _Bool
2028 _Complex
2029
2030 type-qualifier:
2031 const
2032 restrict
2033 volatile
2034 address-space-qualifier
2035 _Atomic
2036
2037 */
2038
2039 static void
c_parser_gimple_declaration(gimple_parser & parser)2040 c_parser_gimple_declaration (gimple_parser &parser)
2041 {
2042 struct c_declarator *declarator;
2043 struct c_declspecs *specs = build_null_declspecs ();
2044 c_parser_declspecs (parser, specs, true, true, true,
2045 true, true, true, true, cla_nonabstract_decl);
2046 finish_declspecs (specs);
2047
2048 /* Provide better error recovery. Note that a type name here is usually
2049 better diagnosed as a redeclaration. */
2050 if (c_parser_next_token_starts_declspecs (parser)
2051 && ! c_parser_next_token_is (parser, CPP_NAME))
2052 {
2053 c_parser_error (parser, "expected %<;%>");
2054 c_parser_set_error (parser, false);
2055 return;
2056 }
2057
2058 bool dummy = false;
2059 declarator = c_parser_declarator (parser,
2060 specs->typespec_kind != ctsk_none,
2061 C_DTR_NORMAL, &dummy);
2062
2063 if (c_parser_next_token_is (parser, CPP_SEMICOLON))
2064 {
2065 /* Handle SSA name decls specially, they do not go into the identifier
2066 table but we simply build the SSA name for later lookup. */
2067 unsigned version, ver_offset;
2068 /* Handle SSA pointer declarations in a very simplistic ways, we
2069 probably would like to call grokdeclarator in a special mode to
2070 just build the type of the decl - start_decl already pushes
2071 the identifier to the bindings for lookup, something we do not
2072 want. */
2073 struct c_declarator *id_declarator = declarator;
2074 while (id_declarator->kind == cdk_pointer)
2075 id_declarator = id_declarator->declarator;
2076 if (id_declarator->kind == cdk_id
2077 && (declarator->kind == cdk_pointer
2078 || is_gimple_reg_type (specs->type))
2079 && c_parser_parse_ssa_name_id (id_declarator->u.id.id,
2080 &version, &ver_offset)
2081 /* The following restricts it to unnamed anonymous SSA names
2082 which fails parsing of named ones in dumps (we could
2083 decide to not dump their name for -gimple). */
2084 && ver_offset == 0)
2085 {
2086 struct c_declarator *p = declarator;
2087 tree type = specs->type;
2088 while (p->kind == cdk_pointer)
2089 {
2090 type = build_pointer_type (type);
2091 p = p->declarator;
2092 }
2093 c_parser_parse_ssa_name (parser, id_declarator->u.id.id, type,
2094 version, ver_offset);
2095 }
2096 else
2097 {
2098 tree postfix_attrs = NULL_TREE;
2099 tree all_prefix_attrs = specs->attrs;
2100 specs->attrs = NULL;
2101 tree decl = start_decl (declarator, specs, false,
2102 chainon (postfix_attrs, all_prefix_attrs));
2103 if (decl)
2104 finish_decl (decl, UNKNOWN_LOCATION, NULL_TREE, NULL_TREE,
2105 NULL_TREE);
2106 }
2107 }
2108 else
2109 {
2110 c_parser_error (parser, "expected %<;%>");
2111 return;
2112 }
2113 }
2114
2115 /* Parse gimple goto statement. */
2116
2117 static void
c_parser_gimple_goto_stmt(gimple_parser & parser,location_t loc,tree label,gimple_seq * seq)2118 c_parser_gimple_goto_stmt (gimple_parser &parser,
2119 location_t loc, tree label, gimple_seq *seq)
2120 {
2121 if (cfun->curr_properties & PROP_cfg)
2122 {
2123 int dest_index;
2124 profile_probability prob;
2125 if (c_parser_gimple_parse_bb_spec_edge_probability (label, parser,
2126 &dest_index, &prob))
2127 {
2128 parser.push_edge (parser.current_bb->index, dest_index,
2129 EDGE_FALLTHRU, prob);
2130 return;
2131 }
2132 }
2133 tree decl = lookup_label_for_goto (loc, label);
2134 gimple_seq_add_stmt_without_update (seq, gimple_build_goto (decl));
2135 }
2136
2137 /* Parse a parenthesized condition.
2138 gimple-condition:
2139 ( gimple-binary-expression ) */
2140
2141 static tree
c_parser_gimple_paren_condition(gimple_parser & parser)2142 c_parser_gimple_paren_condition (gimple_parser &parser)
2143 {
2144 if (! c_parser_require (parser, CPP_OPEN_PAREN, "expected %<(%>"))
2145 return error_mark_node;
2146 tree cond = c_parser_gimple_binary_expression (parser).value;
2147 if (cond != error_mark_node
2148 && ! COMPARISON_CLASS_P (cond)
2149 && ! CONSTANT_CLASS_P (cond)
2150 && ! SSA_VAR_P (cond))
2151 {
2152 c_parser_error (parser, "comparison required");
2153 cond = error_mark_node;
2154 }
2155 if (! c_parser_require (parser, CPP_CLOSE_PAREN, "expected %<)%>"))
2156 return error_mark_node;
2157 return cond;
2158 }
2159
2160 /* Parse gimple try statement.
2161
2162 try-statement:
2163 try { ... } finally { ... }
2164 try { ... } finally { ... } else { ... }
2165
2166 This could support try/catch as well, but it's not implemented yet.
2167 */
2168
2169 static void
c_parser_gimple_try_stmt(gimple_parser & parser,gimple_seq * seq)2170 c_parser_gimple_try_stmt (gimple_parser &parser, gimple_seq *seq)
2171 {
2172 gimple_seq tryseq = NULL;
2173 c_parser_consume_token (parser);
2174 c_parser_gimple_compound_statement (parser, &tryseq);
2175
2176 if ((c_parser_next_token_is (parser, CPP_KEYWORD)
2177 && c_parser_peek_token (parser)->keyword == RID_AT_FINALLY)
2178 || (c_parser_next_token_is (parser, CPP_NAME)
2179 && c_parser_peek_token (parser)->id_kind == C_ID_ID
2180 && strcmp (IDENTIFIER_POINTER (c_parser_peek_token (parser)->value),
2181 "finally") == 0))
2182 {
2183 gimple_seq finseq = NULL;
2184 c_parser_consume_token (parser);
2185 c_parser_gimple_compound_statement (parser, &finseq);
2186
2187 if (c_parser_next_token_is (parser, CPP_KEYWORD)
2188 && c_parser_peek_token (parser)->keyword == RID_ELSE)
2189 {
2190 gimple_seq elsseq = NULL;
2191 c_parser_consume_token (parser);
2192 c_parser_gimple_compound_statement (parser, &elsseq);
2193
2194 geh_else *stmt = gimple_build_eh_else (finseq, elsseq);
2195 finseq = NULL;
2196 gimple_seq_add_stmt_without_update (&finseq, stmt);
2197 }
2198
2199 gtry *stmt = gimple_build_try (tryseq, finseq, GIMPLE_TRY_FINALLY);
2200 gimple_seq_add_stmt_without_update (seq, stmt);
2201 }
2202 else if (c_parser_next_token_is (parser, CPP_KEYWORD)
2203 && c_parser_peek_token (parser)->keyword == RID_AT_CATCH)
2204 c_parser_error (parser, "%<catch%> is not supported");
2205 else
2206 c_parser_error (parser, "expected %<finally%> or %<catch%>");
2207 }
2208
2209 /* Parse gimple if-else statement.
2210
2211 if-statement:
2212 if ( gimple-binary-expression ) gimple-goto-statement
2213 if ( gimple-binary-expression ) gimple-goto-statement \
2214 else gimple-goto-statement
2215 */
2216
2217 static void
c_parser_gimple_if_stmt(gimple_parser & parser,gimple_seq * seq)2218 c_parser_gimple_if_stmt (gimple_parser &parser, gimple_seq *seq)
2219 {
2220 tree t_label = NULL_TREE, f_label = NULL_TREE, label;
2221 location_t loc;
2222 c_parser_consume_token (parser);
2223 tree cond = c_parser_gimple_paren_condition (parser);
2224
2225 if (c_parser_next_token_is_keyword (parser, RID_GOTO))
2226 {
2227 loc = c_parser_peek_token (parser)->location;
2228 c_parser_consume_token (parser);
2229 if (! c_parser_next_token_is (parser, CPP_NAME))
2230 {
2231 c_parser_error (parser, "expected label");
2232 return;
2233 }
2234 label = c_parser_peek_token (parser)->value;
2235 c_parser_consume_token (parser);
2236 int dest_index;
2237 profile_probability prob;
2238 if ((cfun->curr_properties & PROP_cfg)
2239 && c_parser_gimple_parse_bb_spec_edge_probability (label, parser,
2240 &dest_index, &prob))
2241 parser.push_edge (parser.current_bb->index, dest_index,
2242 EDGE_TRUE_VALUE, prob);
2243 else
2244 t_label = lookup_label_for_goto (loc, label);
2245 if (! c_parser_require (parser, CPP_SEMICOLON, "expected %<;%>"))
2246 return;
2247 }
2248 else
2249 {
2250 c_parser_error (parser, "expected goto expression");
2251 return;
2252 }
2253
2254 if (c_parser_next_token_is_keyword (parser, RID_ELSE))
2255 c_parser_consume_token (parser);
2256 else
2257 {
2258 c_parser_error (parser, "expected else statement");
2259 return;
2260 }
2261
2262 if (c_parser_next_token_is_keyword (parser, RID_GOTO))
2263 {
2264 loc = c_parser_peek_token (parser)->location;
2265 c_parser_consume_token (parser);
2266 if (! c_parser_next_token_is (parser, CPP_NAME))
2267 {
2268 c_parser_error (parser, "expected label");
2269 return;
2270 }
2271 label = c_parser_peek_token (parser)->value;
2272 c_parser_consume_token (parser);
2273 int dest_index;
2274 profile_probability prob;
2275 if ((cfun->curr_properties & PROP_cfg)
2276 && c_parser_gimple_parse_bb_spec_edge_probability (label, parser,
2277 &dest_index, &prob))
2278 parser.push_edge (parser.current_bb->index, dest_index,
2279 EDGE_FALSE_VALUE, prob);
2280 else
2281 f_label = lookup_label_for_goto (loc, label);
2282 if (! c_parser_require (parser, CPP_SEMICOLON, "expected %<;%>"))
2283 return;
2284 }
2285 else
2286 {
2287 c_parser_error (parser, "expected goto expression");
2288 return;
2289 }
2290
2291 if (cond != error_mark_node)
2292 gimple_seq_add_stmt_without_update (seq, gimple_build_cond_from_tree (cond, t_label,
2293 f_label));
2294 }
2295
2296 /* Parse gimple switch-statement.
2297
2298 gimple-switch-statement:
2299 switch (gimple-postfix-expression) gimple-case-statement
2300
2301 gimple-case-statement:
2302 gimple-case-statement
2303 gimple-label-statement : gimple-goto-statment
2304 */
2305
2306 static void
c_parser_gimple_switch_stmt(gimple_parser & parser,gimple_seq * seq)2307 c_parser_gimple_switch_stmt (gimple_parser &parser, gimple_seq *seq)
2308 {
2309 c_expr cond_expr;
2310 tree case_label, label;
2311 auto_vec<tree> labels;
2312 tree default_label = NULL_TREE;
2313 c_parser_consume_token (parser);
2314
2315 if (! c_parser_require (parser, CPP_OPEN_PAREN, "expected %<(%>"))
2316 return;
2317 cond_expr = c_parser_gimple_postfix_expression (parser);
2318 if (! c_parser_require (parser, CPP_CLOSE_PAREN, "expected %<)%>"))
2319 return;
2320
2321 if (! c_parser_require (parser, CPP_OPEN_BRACE, "expected %<{%>"))
2322 return;
2323
2324 while (c_parser_next_token_is_not (parser, CPP_CLOSE_BRACE))
2325 {
2326 if (c_parser_next_token_is (parser, CPP_EOF))
2327 {
2328 c_parser_error (parser, "expected statement");
2329 return;
2330 }
2331
2332 switch (c_parser_peek_token (parser)->keyword)
2333 {
2334 case RID_CASE:
2335 {
2336 c_expr exp1;
2337 location_t loc = c_parser_peek_token (parser)->location;
2338 c_parser_consume_token (parser);
2339
2340 if (c_parser_next_token_is (parser, CPP_NAME)
2341 || c_parser_peek_token (parser)->type == CPP_NUMBER)
2342 exp1 = c_parser_gimple_postfix_expression (parser);
2343 else
2344 {
2345 c_parser_error (parser, "expected expression");
2346 return;
2347 }
2348
2349 if (c_parser_next_token_is (parser, CPP_COLON))
2350 {
2351 c_parser_consume_token (parser);
2352 if (c_parser_next_token_is (parser, CPP_NAME))
2353 {
2354 label = c_parser_peek_token (parser)->value;
2355 c_parser_consume_token (parser);
2356 tree decl = lookup_label_for_goto (loc, label);
2357 case_label = build_case_label (exp1.value, NULL_TREE,
2358 decl);
2359 labels.safe_push (case_label);
2360 if (! c_parser_require (parser, CPP_SEMICOLON,
2361 "expected %<;%>"))
2362 return;
2363 }
2364 else if (! c_parser_require (parser, CPP_NAME,
2365 "expected label"))
2366 return;
2367 }
2368 else if (! c_parser_require (parser, CPP_SEMICOLON,
2369 "expected %<:%>"))
2370 return;
2371 break;
2372 }
2373 case RID_DEFAULT:
2374 {
2375 location_t loc = c_parser_peek_token (parser)->location;
2376 c_parser_consume_token (parser);
2377 if (c_parser_next_token_is (parser, CPP_COLON))
2378 {
2379 c_parser_consume_token (parser);
2380 if (c_parser_next_token_is (parser, CPP_NAME))
2381 {
2382 label = c_parser_peek_token (parser)->value;
2383 c_parser_consume_token (parser);
2384 tree decl = lookup_label_for_goto (loc, label);
2385 default_label = build_case_label (NULL_TREE, NULL_TREE,
2386 decl);
2387 if (! c_parser_require (parser, CPP_SEMICOLON,
2388 "expected %<;%>"))
2389 return;
2390 }
2391 else if (! c_parser_require (parser, CPP_NAME,
2392 "expected label"))
2393 return;
2394 }
2395 else if (! c_parser_require (parser, CPP_SEMICOLON,
2396 "expected %<:%>"))
2397 return;
2398 break;
2399 }
2400 default:
2401 c_parser_error (parser, "expected case label");
2402 return;
2403 }
2404
2405 }
2406 if (! c_parser_require (parser, CPP_CLOSE_BRACE, "expected %<}%>"))
2407 return;
2408
2409 if (cond_expr.value != error_mark_node)
2410 {
2411 gswitch *s = gimple_build_switch (cond_expr.value, default_label, labels);
2412 gimple_seq_add_stmt_without_update (seq, s);
2413 }
2414 }
2415
2416 /* Parse gimple return statement. */
2417
2418 static void
c_parser_gimple_return_stmt(gimple_parser & parser,gimple_seq * seq)2419 c_parser_gimple_return_stmt (gimple_parser &parser, gimple_seq *seq)
2420 {
2421 location_t loc = c_parser_peek_token (parser)->location;
2422 gimple *ret = NULL;
2423 c_parser_consume_token (parser);
2424 if (c_parser_next_token_is (parser, CPP_SEMICOLON))
2425 {
2426 c_finish_gimple_return (loc, NULL_TREE);
2427 ret = gimple_build_return (NULL);
2428 gimple_seq_add_stmt_without_update (seq, ret);
2429 }
2430 else
2431 {
2432 location_t xloc = c_parser_peek_token (parser)->location;
2433 c_expr expr = c_parser_gimple_unary_expression (parser);
2434 if (expr.value != error_mark_node)
2435 {
2436 c_finish_gimple_return (xloc, expr.value);
2437 ret = gimple_build_return (expr.value);
2438 gimple_seq_add_stmt_without_update (seq, ret);
2439 }
2440 }
2441 }
2442
2443 /* Support function for c_parser_gimple_return_stmt. */
2444
2445 static void
c_finish_gimple_return(location_t loc,tree retval)2446 c_finish_gimple_return (location_t loc, tree retval)
2447 {
2448 tree valtype = TREE_TYPE (TREE_TYPE (current_function_decl));
2449
2450 /* Use the expansion point to handle cases such as returning NULL
2451 in a function returning void. */
2452 location_t xloc = expansion_point_location_if_in_system_header (loc);
2453
2454 if (TREE_THIS_VOLATILE (current_function_decl))
2455 warning_at (xloc, 0,
2456 "function declared %<noreturn%> has a %<return%> statement");
2457
2458 if (! retval)
2459 current_function_returns_null = 1;
2460 else if (valtype == 0 || TREE_CODE (valtype) == VOID_TYPE)
2461 {
2462 current_function_returns_null = 1;
2463 if (TREE_CODE (TREE_TYPE (retval)) != VOID_TYPE)
2464 {
2465 error_at
2466 (xloc, "%<return%> with a value, in function returning void");
2467 inform (DECL_SOURCE_LOCATION (current_function_decl),
2468 "declared here");
2469 }
2470 }
2471 else if (TREE_CODE (valtype) != TREE_CODE (TREE_TYPE (retval)))
2472 {
2473 error_at
2474 (xloc, "invalid conversion in return statement");
2475 inform (DECL_SOURCE_LOCATION (current_function_decl),
2476 "declared here");
2477 }
2478 return;
2479 }
2480