1/* Data flow functions for trees.
2   Copyright (C) 2001, 2002, 2003, 2004, 2005 Free Software Foundation, Inc.
3   Contributed by Diego Novillo <dnovillo@redhat.com>
4
5This file is part of GCC.
6
7GCC is free software; you can redistribute it and/or modify
8it under the terms of the GNU General Public License as published by
9the Free Software Foundation; either version 2, or (at your option)
10any later version.
11
12GCC is distributed in the hope that it will be useful,
13but WITHOUT ANY WARRANTY; without even the implied warranty of
14MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15GNU General Public License for more details.
16
17You should have received a copy of the GNU General Public License
18along with GCC; see the file COPYING.  If not, write to
19the Free Software Foundation, 51 Franklin Street, Fifth Floor,
20Boston, MA 02110-1301, USA.  */
21
22#include "config.h"
23#include "system.h"
24#include "coretypes.h"
25#include "tm.h"
26#include "hashtab.h"
27#include "pointer-set.h"
28#include "tree.h"
29#include "rtl.h"
30#include "tm_p.h"
31#include "hard-reg-set.h"
32#include "basic-block.h"
33#include "output.h"
34#include "timevar.h"
35#include "expr.h"
36#include "ggc.h"
37#include "langhooks.h"
38#include "flags.h"
39#include "function.h"
40#include "diagnostic.h"
41#include "tree-dump.h"
42#include "tree-gimple.h"
43#include "tree-flow.h"
44#include "tree-inline.h"
45#include "tree-pass.h"
46#include "convert.h"
47#include "params.h"
48#include "cgraph.h"
49
50/* Build and maintain data flow information for trees.  */
51
52/* Counters used to display DFA and SSA statistics.  */
53struct dfa_stats_d
54{
55  long num_stmt_anns;
56  long num_var_anns;
57  long num_defs;
58  long num_uses;
59  long num_phis;
60  long num_phi_args;
61  int max_num_phi_args;
62  long num_v_may_defs;
63  long num_vuses;
64  long num_v_must_defs;
65};
66
67
68/* Local functions.  */
69static void collect_dfa_stats (struct dfa_stats_d *);
70static tree collect_dfa_stats_r (tree *, int *, void *);
71static tree find_vars_r (tree *, int *, void *);
72static void add_referenced_var (tree, bool);
73
74
75/* Global declarations.  */
76
77/* Array of all variables referenced in the function.  */
78htab_t referenced_vars;
79
80
81/*---------------------------------------------------------------------------
82			Dataflow analysis (DFA) routines
83---------------------------------------------------------------------------*/
84/* Find all the variables referenced in the function.  This function
85   builds the global arrays REFERENCED_VARS and CALL_CLOBBERED_VARS.
86
87   Note that this function does not look for statement operands, it simply
88   determines what variables are referenced in the program and detects
89   various attributes for each variable used by alias analysis and the
90   optimizer.  */
91
92static void
93find_referenced_vars (void)
94{
95  basic_block bb;
96  block_stmt_iterator si;
97
98  FOR_EACH_BB (bb)
99    for (si = bsi_start (bb); !bsi_end_p (si); bsi_next (&si))
100      {
101	tree *stmt_p = bsi_stmt_ptr (si);
102	walk_tree (stmt_p, find_vars_r, NULL, NULL);
103      }
104
105}
106
107struct tree_opt_pass pass_referenced_vars =
108{
109  NULL,					/* name */
110  NULL,					/* gate */
111  find_referenced_vars,			/* execute */
112  NULL,					/* sub */
113  NULL,					/* next */
114  0,					/* static_pass_number */
115  TV_FIND_REFERENCED_VARS,		/* tv_id */
116  PROP_gimple_leh | PROP_cfg,		/* properties_required */
117  PROP_referenced_vars,			/* properties_provided */
118  0,					/* properties_destroyed */
119  0,					/* todo_flags_start */
120  0,                                    /* todo_flags_finish */
121  0				        /* letter */
122};
123
124
125/*---------------------------------------------------------------------------
126			    Manage annotations
127---------------------------------------------------------------------------*/
128/* Create a new annotation for a _DECL node T.  */
129
130var_ann_t
131create_var_ann (tree t)
132{
133  var_ann_t ann;
134
135  gcc_assert (t);
136  gcc_assert (DECL_P (t));
137  gcc_assert (!t->common.ann || t->common.ann->common.type == VAR_ANN);
138
139  ann = ggc_alloc (sizeof (*ann));
140  memset ((void *) ann, 0, sizeof (*ann));
141
142  ann->common.type = VAR_ANN;
143
144  t->common.ann = (tree_ann_t) ann;
145
146  return ann;
147}
148
149
150/* Create a new annotation for a statement node T.  */
151
152stmt_ann_t
153create_stmt_ann (tree t)
154{
155  stmt_ann_t ann;
156
157  gcc_assert (is_gimple_stmt (t));
158  gcc_assert (!t->common.ann || t->common.ann->common.type == STMT_ANN);
159
160  ann = ggc_alloc (sizeof (*ann));
161  memset ((void *) ann, 0, sizeof (*ann));
162
163  ann->common.type = STMT_ANN;
164
165  /* Since we just created the annotation, mark the statement modified.  */
166  ann->modified = true;
167
168  t->common.ann = (tree_ann_t) ann;
169
170  return ann;
171}
172
173/* Create a new annotation for a tree T.  */
174
175tree_ann_t
176create_tree_ann (tree t)
177{
178  tree_ann_t ann;
179
180  gcc_assert (t);
181  gcc_assert (!t->common.ann || t->common.ann->common.type == TREE_ANN_COMMON);
182
183  ann = ggc_alloc (sizeof (*ann));
184  memset ((void *) ann, 0, sizeof (*ann));
185
186  ann->common.type = TREE_ANN_COMMON;
187  t->common.ann = ann;
188
189  return ann;
190}
191
192/* Build a temporary.  Make sure and register it to be renamed.  */
193
194tree
195make_rename_temp (tree type, const char *prefix)
196{
197  tree t = create_tmp_var (type, prefix);
198
199  if (TREE_CODE (type) == COMPLEX_TYPE)
200    DECL_COMPLEX_GIMPLE_REG_P (t) = 1;
201
202  if (referenced_vars)
203    {
204      add_referenced_tmp_var (t);
205      mark_sym_for_renaming (t);
206    }
207
208  return t;
209}
210
211
212
213/*---------------------------------------------------------------------------
214			      Debugging functions
215---------------------------------------------------------------------------*/
216/* Dump the list of all the referenced variables in the current function to
217   FILE.  */
218
219void
220dump_referenced_vars (FILE *file)
221{
222  tree var;
223  referenced_var_iterator rvi;
224
225  fprintf (file, "\nReferenced variables in %s: %u\n\n",
226	   get_name (current_function_decl), (unsigned) num_referenced_vars);
227
228  FOR_EACH_REFERENCED_VAR (var, rvi)
229    {
230      fprintf (file, "Variable: ");
231      dump_variable (file, var);
232      fprintf (file, "\n");
233    }
234}
235
236
237/* Dump the list of all the referenced variables to stderr.  */
238
239void
240debug_referenced_vars (void)
241{
242  dump_referenced_vars (stderr);
243}
244
245
246/* Dump sub-variables for VAR to FILE.  */
247
248void
249dump_subvars_for (FILE *file, tree var)
250{
251  subvar_t sv = get_subvars_for_var (var);
252
253  if (!sv)
254    return;
255
256  fprintf (file, "{ ");
257
258  for (; sv; sv = sv->next)
259    {
260      print_generic_expr (file, sv->var, dump_flags);
261      fprintf (file, " ");
262    }
263
264  fprintf (file, "}");
265}
266
267
268/* Dumb sub-variables for VAR to stderr.  */
269
270void
271debug_subvars_for (tree var)
272{
273  dump_subvars_for (stderr, var);
274}
275
276
277/* Dump variable VAR and its may-aliases to FILE.  */
278
279void
280dump_variable (FILE *file, tree var)
281{
282  var_ann_t ann;
283
284  if (TREE_CODE (var) == SSA_NAME)
285    {
286      if (POINTER_TYPE_P (TREE_TYPE (var)))
287	dump_points_to_info_for (file, var);
288      var = SSA_NAME_VAR (var);
289    }
290
291  if (var == NULL_TREE)
292    {
293      fprintf (file, "<nil>");
294      return;
295    }
296
297  print_generic_expr (file, var, dump_flags);
298
299  ann = var_ann (var);
300
301  fprintf (file, ", UID %u", (unsigned) DECL_UID (var));
302
303  fprintf (file, ", ");
304  print_generic_expr (file, TREE_TYPE (var), dump_flags);
305
306  if (ann && ann->type_mem_tag)
307    {
308      fprintf (file, ", type memory tag: ");
309      print_generic_expr (file, ann->type_mem_tag, dump_flags);
310    }
311
312  if (ann && ann->is_alias_tag)
313    fprintf (file, ", is an alias tag");
314
315  if (TREE_ADDRESSABLE (var))
316    fprintf (file, ", is addressable");
317
318  if (is_global_var (var))
319    fprintf (file, ", is global");
320
321  if (TREE_THIS_VOLATILE (var))
322    fprintf (file, ", is volatile");
323
324  if (is_call_clobbered (var))
325    fprintf (file, ", call clobbered");
326
327  if (default_def (var))
328    {
329      fprintf (file, ", default def: ");
330      print_generic_expr (file, default_def (var), dump_flags);
331    }
332
333  if (may_aliases (var))
334    {
335      fprintf (file, ", may aliases: ");
336      dump_may_aliases_for (file, var);
337    }
338
339  if (get_subvars_for_var (var))
340    {
341      fprintf (file, ", sub-vars: ");
342      dump_subvars_for (file, var);
343    }
344
345  fprintf (file, "\n");
346}
347
348
349/* Dump variable VAR and its may-aliases to stderr.  */
350
351void
352debug_variable (tree var)
353{
354  dump_variable (stderr, var);
355}
356
357
358/* Dump various DFA statistics to FILE.  */
359
360void
361dump_dfa_stats (FILE *file)
362{
363  struct dfa_stats_d dfa_stats;
364
365  unsigned long size, total = 0;
366  const char * const fmt_str   = "%-30s%-13s%12s\n";
367  const char * const fmt_str_1 = "%-30s%13lu%11lu%c\n";
368  const char * const fmt_str_3 = "%-43s%11lu%c\n";
369  const char *funcname
370    = lang_hooks.decl_printable_name (current_function_decl, 2);
371
372  collect_dfa_stats (&dfa_stats);
373
374  fprintf (file, "\nDFA Statistics for %s\n\n", funcname);
375
376  fprintf (file, "---------------------------------------------------------\n");
377  fprintf (file, fmt_str, "", "  Number of  ", "Memory");
378  fprintf (file, fmt_str, "", "  instances  ", "used ");
379  fprintf (file, "---------------------------------------------------------\n");
380
381  size = num_referenced_vars * sizeof (tree);
382  total += size;
383  fprintf (file, fmt_str_1, "Referenced variables", (unsigned long)num_referenced_vars,
384	   SCALE (size), LABEL (size));
385
386  size = dfa_stats.num_stmt_anns * sizeof (struct stmt_ann_d);
387  total += size;
388  fprintf (file, fmt_str_1, "Statements annotated", dfa_stats.num_stmt_anns,
389	   SCALE (size), LABEL (size));
390
391  size = dfa_stats.num_var_anns * sizeof (struct var_ann_d);
392  total += size;
393  fprintf (file, fmt_str_1, "Variables annotated", dfa_stats.num_var_anns,
394	   SCALE (size), LABEL (size));
395
396  size = dfa_stats.num_uses * sizeof (tree *);
397  total += size;
398  fprintf (file, fmt_str_1, "USE operands", dfa_stats.num_uses,
399	   SCALE (size), LABEL (size));
400
401  size = dfa_stats.num_defs * sizeof (tree *);
402  total += size;
403  fprintf (file, fmt_str_1, "DEF operands", dfa_stats.num_defs,
404	   SCALE (size), LABEL (size));
405
406  size = dfa_stats.num_vuses * sizeof (tree *);
407  total += size;
408  fprintf (file, fmt_str_1, "VUSE operands", dfa_stats.num_vuses,
409	   SCALE (size), LABEL (size));
410
411  size = dfa_stats.num_v_may_defs * sizeof (tree *);
412  total += size;
413  fprintf (file, fmt_str_1, "V_MAY_DEF operands", dfa_stats.num_v_may_defs,
414	   SCALE (size), LABEL (size));
415
416  size = dfa_stats.num_v_must_defs * sizeof (tree *);
417  total += size;
418  fprintf (file, fmt_str_1, "V_MUST_DEF operands", dfa_stats.num_v_must_defs,
419	   SCALE (size), LABEL (size));
420
421  size = dfa_stats.num_phis * sizeof (struct tree_phi_node);
422  total += size;
423  fprintf (file, fmt_str_1, "PHI nodes", dfa_stats.num_phis,
424	   SCALE (size), LABEL (size));
425
426  size = dfa_stats.num_phi_args * sizeof (struct phi_arg_d);
427  total += size;
428  fprintf (file, fmt_str_1, "PHI arguments", dfa_stats.num_phi_args,
429 	   SCALE (size), LABEL (size));
430
431  fprintf (file, "---------------------------------------------------------\n");
432  fprintf (file, fmt_str_3, "Total memory used by DFA/SSA data", SCALE (total),
433	   LABEL (total));
434  fprintf (file, "---------------------------------------------------------\n");
435  fprintf (file, "\n");
436
437  if (dfa_stats.num_phis)
438    fprintf (file, "Average number of arguments per PHI node: %.1f (max: %d)\n",
439	     (float) dfa_stats.num_phi_args / (float) dfa_stats.num_phis,
440	     dfa_stats.max_num_phi_args);
441
442  fprintf (file, "\n");
443}
444
445
446/* Dump DFA statistics on stderr.  */
447
448void
449debug_dfa_stats (void)
450{
451  dump_dfa_stats (stderr);
452}
453
454
455/* Collect DFA statistics and store them in the structure pointed to by
456   DFA_STATS_P.  */
457
458static void
459collect_dfa_stats (struct dfa_stats_d *dfa_stats_p)
460{
461  struct pointer_set_t *pset;
462  basic_block bb;
463  block_stmt_iterator i;
464
465  gcc_assert (dfa_stats_p);
466
467  memset ((void *)dfa_stats_p, 0, sizeof (struct dfa_stats_d));
468
469  /* Walk all the trees in the function counting references.  Start at
470     basic block 0, but don't stop at block boundaries.  */
471  pset = pointer_set_create ();
472
473  for (i = bsi_start (BASIC_BLOCK (0)); !bsi_end_p (i); bsi_next (&i))
474    walk_tree (bsi_stmt_ptr (i), collect_dfa_stats_r, (void *) dfa_stats_p,
475	       pset);
476
477  pointer_set_destroy (pset);
478
479  FOR_EACH_BB (bb)
480    {
481      tree phi;
482      for (phi = phi_nodes (bb); phi; phi = PHI_CHAIN (phi))
483	{
484	  dfa_stats_p->num_phis++;
485	  dfa_stats_p->num_phi_args += PHI_NUM_ARGS (phi);
486	  if (PHI_NUM_ARGS (phi) > dfa_stats_p->max_num_phi_args)
487	    dfa_stats_p->max_num_phi_args = PHI_NUM_ARGS (phi);
488	}
489    }
490}
491
492
493/* Callback for walk_tree to collect DFA statistics for a tree and its
494   children.  */
495
496static tree
497collect_dfa_stats_r (tree *tp, int *walk_subtrees ATTRIBUTE_UNUSED,
498		     void *data)
499{
500  tree t = *tp;
501  struct dfa_stats_d *dfa_stats_p = (struct dfa_stats_d *)data;
502
503  if (t->common.ann)
504    {
505      switch (ann_type (t->common.ann))
506	{
507	case STMT_ANN:
508	  {
509	    dfa_stats_p->num_stmt_anns++;
510	    dfa_stats_p->num_defs += NUM_SSA_OPERANDS (t, SSA_OP_DEF);
511	    dfa_stats_p->num_uses += NUM_SSA_OPERANDS (t, SSA_OP_USE);
512	    dfa_stats_p->num_v_may_defs += NUM_SSA_OPERANDS (t, SSA_OP_VMAYDEF);
513	    dfa_stats_p->num_vuses += NUM_SSA_OPERANDS (t, SSA_OP_VUSE);
514	    dfa_stats_p->num_v_must_defs +=
515				  NUM_SSA_OPERANDS (t, SSA_OP_VMUSTDEF);
516	    break;
517	  }
518
519	case VAR_ANN:
520	  dfa_stats_p->num_var_anns++;
521	  break;
522
523	default:
524	  break;
525	}
526    }
527
528  return NULL;
529}
530
531
532/*---------------------------------------------------------------------------
533			     Miscellaneous helpers
534---------------------------------------------------------------------------*/
535/* Callback for walk_tree.  Used to collect variables referenced in
536   the function.  */
537
538static tree
539find_vars_r (tree *tp, int *walk_subtrees, void *data ATTRIBUTE_UNUSED)
540{
541  /* If T is a regular variable that the optimizers are interested
542     in, add it to the list of variables.  */
543  if (SSA_VAR_P (*tp))
544    add_referenced_var (*tp, false);
545
546  /* Type, _DECL and constant nodes have no interesting children.
547     Ignore them.  */
548  else if (IS_TYPE_OR_DECL_P (*tp) || CONSTANT_CLASS_P (*tp))
549    *walk_subtrees = 0;
550
551  return NULL_TREE;
552}
553
554
555/* Lookup UID in the referenced_vars hashtable and return the associated
556   variable or NULL if it is not there.  */
557
558tree
559referenced_var_lookup_if_exists (unsigned int uid)
560{
561  struct int_tree_map *h, in;
562  in.uid = uid;
563  h = htab_find_with_hash (referenced_vars, &in, uid);
564  if (h)
565    return h->to;
566  return NULL_TREE;
567}
568
569/* Lookup UID in the referenced_vars hashtable and return the associated
570   variable.  */
571
572tree
573referenced_var_lookup (unsigned int uid)
574{
575  struct int_tree_map *h, in;
576  in.uid = uid;
577  h = htab_find_with_hash (referenced_vars, &in, uid);
578  gcc_assert (h || uid == 0);
579  if (h)
580    return h->to;
581  return NULL_TREE;
582}
583
584/* Insert the pair UID, TO into the referenced_vars hashtable.  */
585
586static void
587referenced_var_insert (unsigned int uid, tree to)
588{
589  struct int_tree_map *h;
590  void **loc;
591
592  h = ggc_alloc (sizeof (struct int_tree_map));
593  h->uid = uid;
594  h->to = to;
595  loc = htab_find_slot_with_hash (referenced_vars, h, uid, INSERT);
596  /* This assert can only trigger if a variable with the same UID has been
597     inserted already.  */
598  gcc_assert ((*(struct int_tree_map **)loc) == NULL);
599  *(struct int_tree_map **)  loc = h;
600}
601
602/* Add VAR to the list of dereferenced variables.
603
604   WALK_STATE contains a hash table used to avoid adding the same
605      variable more than once. Note that this function assumes that
606      VAR is a valid SSA variable.  If WALK_STATE is NULL, no
607      duplicate checking is done.  */
608
609static void
610add_referenced_var (tree var, bool always)
611{
612  var_ann_t v_ann;
613  tree ref;
614
615  v_ann = get_var_ann (var);
616  gcc_assert (DECL_P (var));
617
618  ref = referenced_var_lookup_if_exists (DECL_UID (var));
619
620  /* Catch PRs 26757 and 27793.  If this assert triggers, REF and VAR are
621     two different variables in this function with the same DECL_UID.  */
622  gcc_assert (!ref || ref == var);
623
624  if (always || ref == NULL_TREE)
625    {
626      /* This is the first time we find this variable, add it to the
627         REFERENCED_VARS array and annotate it with attributes that are
628	 intrinsic to the variable.  */
629
630      referenced_var_insert (DECL_UID (var), var);
631
632      /* Global variables are always call-clobbered.  */
633      if (is_global_var (var))
634	mark_call_clobbered (var);
635
636      /* Scan DECL_INITIAL for pointer variables as they may contain
637	 address arithmetic referencing the address of other
638	 variables.  */
639      if (DECL_INITIAL (var)
640	  /* Initializers of external variables are not useful to the
641	     optimizers.  */
642          && !DECL_EXTERNAL (var)
643	  /* It's not necessary to walk the initial value of non-constant
644	     variables because it cannot be propagated by the
645	     optimizers.  */
646	  && (TREE_CONSTANT (var) || TREE_READONLY (var)))
647      	walk_tree (&DECL_INITIAL (var), find_vars_r, NULL, 0);
648    }
649}
650
651
652/* Return the virtual variable associated to the non-scalar variable VAR.  */
653
654tree
655get_virtual_var (tree var)
656{
657  STRIP_NOPS (var);
658
659  if (TREE_CODE (var) == SSA_NAME)
660    var = SSA_NAME_VAR (var);
661
662  while (TREE_CODE (var) == REALPART_EXPR || TREE_CODE (var) == IMAGPART_EXPR
663	 || handled_component_p (var))
664    var = TREE_OPERAND (var, 0);
665
666  /* Treating GIMPLE registers as virtual variables makes no sense.
667     Also complain if we couldn't extract a _DECL out of the original
668     expression.  */
669  gcc_assert (SSA_VAR_P (var));
670  gcc_assert (!is_gimple_reg (var));
671
672  return var;
673}
674
675/* Add a temporary variable to REFERENCED_VARS.  This is similar to
676   add_referenced_var, but is used by passes that need to add new temps to
677   the REFERENCED_VARS array after the program has been scanned for
678   variables.  The variable will just receive a new UID and be added
679   to the REFERENCED_VARS array without checking for duplicates.  */
680
681void
682add_referenced_tmp_var (tree var)
683{
684  add_referenced_var (var, true);
685}
686
687
688/* Mark all the non-SSA variables found in STMT's operands to be
689   processed by update_ssa.  */
690
691void
692mark_new_vars_to_rename (tree stmt)
693{
694  ssa_op_iter iter;
695  tree val;
696  bitmap vars_in_vops_to_rename;
697  bool found_exposed_symbol = false;
698  int v_may_defs_before, v_may_defs_after;
699  int v_must_defs_before, v_must_defs_after;
700
701  if (TREE_CODE (stmt) == PHI_NODE)
702    return;
703
704  vars_in_vops_to_rename = BITMAP_ALLOC (NULL);
705
706  /* Before re-scanning the statement for operands, mark the existing
707     virtual operands to be renamed again.  We do this because when new
708     symbols are exposed, the virtual operands that were here before due to
709     aliasing will probably be removed by the call to get_stmt_operand.
710     Therefore, we need to flag them to be renamed beforehand.
711
712     We flag them in a separate bitmap because we don't really want to
713     rename them if there are not any newly exposed symbols in the
714     statement operands.  */
715  v_may_defs_before = NUM_SSA_OPERANDS (stmt, SSA_OP_VMAYDEF);
716  v_must_defs_before = NUM_SSA_OPERANDS (stmt, SSA_OP_VMUSTDEF);
717
718  FOR_EACH_SSA_TREE_OPERAND (val, stmt, iter,
719			     SSA_OP_VMAYDEF | SSA_OP_VUSE | SSA_OP_VMUSTDEF)
720    {
721      if (!DECL_P (val))
722	val = SSA_NAME_VAR (val);
723      bitmap_set_bit (vars_in_vops_to_rename, DECL_UID (val));
724    }
725
726  /* Now force an operand re-scan on the statement and mark any newly
727     exposed variables.  */
728  update_stmt (stmt);
729
730  v_may_defs_after = NUM_SSA_OPERANDS (stmt, SSA_OP_VMAYDEF);
731  v_must_defs_after = NUM_SSA_OPERANDS (stmt, SSA_OP_VMUSTDEF);
732
733  FOR_EACH_SSA_TREE_OPERAND (val, stmt, iter, SSA_OP_ALL_OPERANDS)
734    if (DECL_P (val))
735      {
736	found_exposed_symbol = true;
737	mark_sym_for_renaming (val);
738      }
739
740  /* If we found any newly exposed symbols, or if there are fewer VDEF
741     operands in the statement, add the variables we had set in
742     VARS_IN_VOPS_TO_RENAME to VARS_TO_RENAME.  We need to check for
743     vanishing VDEFs because in those cases, the names that were formerly
744     generated by this statement are not going to be available anymore.  */
745  if (found_exposed_symbol
746      || v_may_defs_before > v_may_defs_after
747      || v_must_defs_before > v_must_defs_after)
748    mark_set_for_renaming (vars_in_vops_to_rename);
749
750  BITMAP_FREE (vars_in_vops_to_rename);
751}
752
753/* Find all variables within the gimplified statement that were not previously
754   visible to the function and add them to the referenced variables list.  */
755
756static tree
757find_new_referenced_vars_1 (tree *tp, int *walk_subtrees,
758			    void *data ATTRIBUTE_UNUSED)
759{
760  tree t = *tp;
761
762  if (TREE_CODE (t) == VAR_DECL && !var_ann (t))
763    {
764      add_referenced_tmp_var (t);
765      mark_sym_for_renaming (t);
766    }
767
768  if (IS_TYPE_OR_DECL_P (t))
769    *walk_subtrees = 0;
770
771  return NULL;
772}
773
774void
775find_new_referenced_vars (tree *stmt_p)
776{
777  walk_tree (stmt_p, find_new_referenced_vars_1, NULL, NULL);
778}
779
780
781/* If REF is a COMPONENT_REF for a structure that can have sub-variables, and
782   we know where REF is accessing, return the variable in REF that has the
783   sub-variables.  If the return value is not NULL, POFFSET will be the
784   offset, in bits, of REF inside the return value, and PSIZE will be the
785   size, in bits, of REF inside the return value.  */
786
787tree
788okay_component_ref_for_subvars (tree ref, unsigned HOST_WIDE_INT *poffset,
789				unsigned HOST_WIDE_INT *psize)
790{
791  tree result = NULL;
792  HOST_WIDE_INT bitsize;
793  HOST_WIDE_INT bitpos;
794  tree offset;
795  enum machine_mode mode;
796  int unsignedp;
797  int volatilep;
798
799  gcc_assert (!SSA_VAR_P (ref));
800  *poffset = 0;
801  *psize = (unsigned int) -1;
802
803  if (ref_contains_array_ref (ref))
804    return result;
805  ref = get_inner_reference (ref, &bitsize, &bitpos, &offset, &mode,
806			     &unsignedp, &volatilep, false);
807  if (TREE_CODE (ref) == INDIRECT_REF)
808    return result;
809  else if (offset == NULL && bitsize != -1 && SSA_VAR_P (ref))
810    {
811      *poffset = bitpos;
812      *psize = bitsize;
813      if (get_subvars_for_var (ref) != NULL)
814	return ref;
815    }
816  else if (SSA_VAR_P (ref))
817    {
818      if (get_subvars_for_var (ref) != NULL)
819	return ref;
820    }
821  return NULL_TREE;
822}
823