]> git.ipfire.org Git - thirdparty/gcc.git/blame - gcc/tree-ssa-loop.c
fix PR68343: disable fuse-*.c tests for isl 0.14 or earlier
[thirdparty/gcc.git] / gcc / tree-ssa-loop.c
CommitLineData
6de9cd9a 1/* Loop optimizations over tree-ssa.
818ab71a 2 Copyright (C) 2003-2016 Free Software Foundation, Inc.
b8698a0f 3
6de9cd9a 4This file is part of GCC.
b8698a0f 5
6de9cd9a
DN
6GCC is free software; you can redistribute it and/or modify it
7under the terms of the GNU General Public License as published by the
9dcd6f09 8Free Software Foundation; either version 3, or (at your option) any
6de9cd9a 9later version.
b8698a0f 10
6de9cd9a
DN
11GCC is distributed in the hope that it will be useful, but WITHOUT
12ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
14for more details.
b8698a0f 15
6de9cd9a 16You should have received a copy of the GNU General Public License
9dcd6f09
NC
17along with GCC; see the file COPYING3. If not see
18<http://www.gnu.org/licenses/>. */
6de9cd9a
DN
19
20#include "config.h"
21#include "system.h"
22#include "coretypes.h"
c7131fb2 23#include "backend.h"
6de9cd9a 24#include "tree.h"
c7131fb2 25#include "gimple.h"
957060b5
AM
26#include "tree-pass.h"
27#include "tm_p.h"
40e23961 28#include "fold-const.h"
5be5c238 29#include "gimple-iterator.h"
e28030cf
AM
30#include "tree-ssa-loop-ivopts.h"
31#include "tree-ssa-loop-manip.h"
32#include "tree-ssa-loop-niter.h"
442b4905 33#include "tree-ssa-loop.h"
6de9cd9a 34#include "cfgloop.h"
6de9cd9a 35#include "tree-inline.h"
79fe1b3b 36#include "tree-scalar-evolution.h"
8ed77e22 37#include "tree-vectorizer.h"
896522ee 38#include "omp-low.h"
597a8ab9 39#include "diagnostic-core.h"
6de9cd9a 40
e5d8bd8c 41
7d39012c
RB
42/* A pass making sure loops are fixed up. */
43
44namespace {
45
46const pass_data pass_data_fix_loops =
47{
48 GIMPLE_PASS, /* type */
49 "fix_loops", /* name */
50 OPTGROUP_LOOP, /* optinfo_flags */
51 TV_TREE_LOOP, /* tv_id */
52 PROP_cfg, /* properties_required */
53 0, /* properties_provided */
54 0, /* properties_destroyed */
55 0, /* todo_flags_start */
56 0, /* todo_flags_finish */
57};
58
59class pass_fix_loops : public gimple_opt_pass
60{
61public:
62 pass_fix_loops (gcc::context *ctxt)
63 : gimple_opt_pass (pass_data_fix_loops, ctxt)
64 {}
65
66 /* opt_pass methods: */
67 virtual bool gate (function *) { return flag_tree_loop_optimize; }
68
69 virtual unsigned int execute (function *fn);
70}; // class pass_fix_loops
71
72unsigned int
73pass_fix_loops::execute (function *)
74{
75 if (loops_state_satisfies_p (LOOPS_NEED_FIXUP))
76 {
77 calculate_dominance_info (CDI_DOMINATORS);
78 fix_loop_structure (NULL);
79 }
80 return 0;
81}
82
83} // anon namespace
84
85gimple_opt_pass *
86make_pass_fix_loops (gcc::context *ctxt)
87{
88 return new pass_fix_loops (ctxt);
89}
90
91
e5d8bd8c
RB
92/* Gate for loop pass group. The group is controlled by -ftree-loop-optimize
93 but we also avoid running it when the IL doesn't contain any loop. */
94
95static bool
96gate_loop (function *fn)
97{
98 if (!flag_tree_loop_optimize)
99 return false;
100
101 /* For -fdump-passes which runs before loop discovery print the
102 state of -ftree-loop-optimize. */
103 if (!loops_for_fn (fn))
104 return true;
105
e5d8bd8c
RB
106 return number_of_loops (fn) > 1;
107}
108
c66b6c66
ZD
109/* The loop superpass. */
110
27a4cd48
DM
111namespace {
112
113const pass_data pass_data_tree_loop =
114{
115 GIMPLE_PASS, /* type */
116 "loop", /* name */
117 OPTGROUP_LOOP, /* optinfo_flags */
27a4cd48
DM
118 TV_TREE_LOOP, /* tv_id */
119 PROP_cfg, /* properties_required */
120 0, /* properties_provided */
121 0, /* properties_destroyed */
122 0, /* todo_flags_start */
3bea341f 123 0, /* todo_flags_finish */
c66b6c66
ZD
124};
125
27a4cd48
DM
126class pass_tree_loop : public gimple_opt_pass
127{
128public:
c3284718
RS
129 pass_tree_loop (gcc::context *ctxt)
130 : gimple_opt_pass (pass_data_tree_loop, ctxt)
27a4cd48
DM
131 {}
132
133 /* opt_pass methods: */
e5d8bd8c 134 virtual bool gate (function *fn) { return gate_loop (fn); }
27a4cd48
DM
135
136}; // class pass_tree_loop
137
138} // anon namespace
139
140gimple_opt_pass *
141make_pass_tree_loop (gcc::context *ctxt)
142{
143 return new pass_tree_loop (ctxt);
144}
145
896522ee
TV
146/* Gate for oacc kernels pass group. */
147
148static bool
149gate_oacc_kernels (function *fn)
150{
151 if (flag_tree_parallelize_loops <= 1)
152 return false;
153
154 tree oacc_function_attr = get_oacc_fn_attrib (fn->decl);
155 if (oacc_function_attr == NULL_TREE)
156 return false;
157
158 tree val = TREE_VALUE (oacc_function_attr);
159 while (val != NULL_TREE && TREE_VALUE (val) == NULL_TREE)
160 val = TREE_CHAIN (val);
161
162 if (val != NULL_TREE)
163 return false;
164
165 struct loop *loop;
166 FOR_EACH_LOOP (loop, 0)
167 if (loop->in_oacc_kernels_region)
168 return true;
169
170 return false;
171}
172
173/* The oacc kernels superpass. */
174
175namespace {
176
177const pass_data pass_data_oacc_kernels =
178{
179 GIMPLE_PASS, /* type */
180 "oacc_kernels", /* name */
181 OPTGROUP_LOOP, /* optinfo_flags */
182 TV_TREE_LOOP, /* tv_id */
183 PROP_cfg, /* properties_required */
184 0, /* properties_provided */
185 0, /* properties_destroyed */
186 0, /* todo_flags_start */
187 0, /* todo_flags_finish */
188};
189
190class pass_oacc_kernels : public gimple_opt_pass
191{
192public:
193 pass_oacc_kernels (gcc::context *ctxt)
194 : gimple_opt_pass (pass_data_oacc_kernels, ctxt)
195 {}
196
197 /* opt_pass methods: */
198 virtual bool gate (function *fn) { return gate_oacc_kernels (fn); }
199
200}; // class pass_oacc_kernels
201
202} // anon namespace
203
204gimple_opt_pass *
205make_pass_oacc_kernels (gcc::context *ctxt)
206{
207 return new pass_oacc_kernels (ctxt);
208}
209
597a8ab9
TV
210/* The ipa oacc superpass. */
211
896522ee
TV
212namespace {
213
597a8ab9 214const pass_data pass_data_ipa_oacc =
896522ee 215{
597a8ab9
TV
216 SIMPLE_IPA_PASS, /* type */
217 "ipa_oacc", /* name */
896522ee
TV
218 OPTGROUP_LOOP, /* optinfo_flags */
219 TV_TREE_LOOP, /* tv_id */
220 PROP_cfg, /* properties_required */
221 0, /* properties_provided */
222 0, /* properties_destroyed */
223 0, /* todo_flags_start */
224 0, /* todo_flags_finish */
225};
226
597a8ab9 227class pass_ipa_oacc : public simple_ipa_opt_pass
896522ee
TV
228{
229public:
597a8ab9
TV
230 pass_ipa_oacc (gcc::context *ctxt)
231 : simple_ipa_opt_pass (pass_data_ipa_oacc, ctxt)
896522ee
TV
232 {}
233
234 /* opt_pass methods: */
597a8ab9
TV
235 virtual bool gate (function *)
236 {
237 return (optimize
238 /* Don't bother doing anything if the program has errors. */
239 && !seen_error ()
240 && flag_openacc
241 && flag_tree_parallelize_loops > 1);
242 }
896522ee 243
597a8ab9 244}; // class pass_ipa_oacc
896522ee
TV
245
246} // anon namespace
247
597a8ab9
TV
248simple_ipa_opt_pass *
249make_pass_ipa_oacc (gcc::context *ctxt)
250{
251 return new pass_ipa_oacc (ctxt);
252}
253
254/* The ipa oacc kernels pass. */
255
256namespace {
257
258const pass_data pass_data_ipa_oacc_kernels =
259{
260 SIMPLE_IPA_PASS, /* type */
261 "ipa_oacc_kernels", /* name */
262 OPTGROUP_LOOP, /* optinfo_flags */
263 TV_TREE_LOOP, /* tv_id */
264 PROP_cfg, /* properties_required */
265 0, /* properties_provided */
266 0, /* properties_destroyed */
267 0, /* todo_flags_start */
268 0, /* todo_flags_finish */
269};
270
271class pass_ipa_oacc_kernels : public simple_ipa_opt_pass
272{
273public:
274 pass_ipa_oacc_kernels (gcc::context *ctxt)
275 : simple_ipa_opt_pass (pass_data_ipa_oacc_kernels, ctxt)
276 {}
277
278}; // class pass_ipa_oacc_kernels
279
280} // anon namespace
281
282simple_ipa_opt_pass *
283make_pass_ipa_oacc_kernels (gcc::context *ctxt)
896522ee 284{
597a8ab9 285 return new pass_ipa_oacc_kernels (ctxt);
896522ee
TV
286}
287
e5d8bd8c
RB
288/* The no-loop superpass. */
289
290namespace {
291
292const pass_data pass_data_tree_no_loop =
293{
294 GIMPLE_PASS, /* type */
295 "no_loop", /* name */
296 OPTGROUP_NONE, /* optinfo_flags */
e5d8bd8c
RB
297 TV_TREE_NOLOOP, /* tv_id */
298 PROP_cfg, /* properties_required */
299 0, /* properties_provided */
300 0, /* properties_destroyed */
301 0, /* todo_flags_start */
302 0, /* todo_flags_finish */
303};
304
305class pass_tree_no_loop : public gimple_opt_pass
306{
307public:
308 pass_tree_no_loop (gcc::context *ctxt)
309 : gimple_opt_pass (pass_data_tree_no_loop, ctxt)
310 {}
311
312 /* opt_pass methods: */
313 virtual bool gate (function *fn) { return !gate_loop (fn); }
314
315}; // class pass_tree_no_loop
316
317} // anon namespace
318
319gimple_opt_pass *
320make_pass_tree_no_loop (gcc::context *ctxt)
321{
322 return new pass_tree_no_loop (ctxt);
323}
324
325
c66b6c66
ZD
326/* Loop optimizer initialization. */
327
27a4cd48
DM
328namespace {
329
330const pass_data pass_data_tree_loop_init =
331{
332 GIMPLE_PASS, /* type */
333 "loopinit", /* name */
334 OPTGROUP_LOOP, /* optinfo_flags */
27a4cd48
DM
335 TV_NONE, /* tv_id */
336 PROP_cfg, /* properties_required */
337 0, /* properties_provided */
338 0, /* properties_destroyed */
339 0, /* todo_flags_start */
340 0, /* todo_flags_finish */
c66b6c66
ZD
341};
342
27a4cd48
DM
343class pass_tree_loop_init : public gimple_opt_pass
344{
345public:
c3284718
RS
346 pass_tree_loop_init (gcc::context *ctxt)
347 : gimple_opt_pass (pass_data_tree_loop_init, ctxt)
27a4cd48
DM
348 {}
349
350 /* opt_pass methods: */
be55bfe6 351 virtual unsigned int execute (function *);
27a4cd48
DM
352
353}; // class pass_tree_loop_init
354
be55bfe6 355unsigned int
3e455386 356pass_tree_loop_init::execute (function *fun ATTRIBUTE_UNUSED)
be55bfe6 357{
33c6daf4
TV
358 /* When processing a loop in the loop pipeline, we should be able to assert
359 that:
360 (loops_state_satisfies_p (LOOPS_NORMAL | LOOPS_HAVE_RECORDED_EXITS
361 | LOOP_CLOSED_SSA)
362 && scev_initialized_p ())
363 */
be55bfe6
TS
364 loop_optimizer_init (LOOPS_NORMAL
365 | LOOPS_HAVE_RECORDED_EXITS);
366 rewrite_into_loop_closed_ssa (NULL, TODO_update_ssa);
be55bfe6
TS
367 scev_initialize ();
368
be55bfe6
TS
369 return 0;
370}
371
27a4cd48
DM
372} // anon namespace
373
374gimple_opt_pass *
375make_pass_tree_loop_init (gcc::context *ctxt)
376{
377 return new pass_tree_loop_init (ctxt);
378}
379
79fe1b3b
DN
380/* Loop autovectorization. */
381
27a4cd48
DM
382namespace {
383
384const pass_data pass_data_vectorize =
385{
386 GIMPLE_PASS, /* type */
387 "vect", /* name */
388 OPTGROUP_LOOP | OPTGROUP_VEC, /* optinfo_flags */
27a4cd48
DM
389 TV_TREE_VECTORIZATION, /* tv_id */
390 ( PROP_cfg | PROP_ssa ), /* properties_required */
391 0, /* properties_provided */
392 0, /* properties_destroyed */
393 0, /* todo_flags_start */
394 0, /* todo_flags_finish */
79fe1b3b
DN
395};
396
27a4cd48
DM
397class pass_vectorize : public gimple_opt_pass
398{
399public:
c3284718
RS
400 pass_vectorize (gcc::context *ctxt)
401 : gimple_opt_pass (pass_data_vectorize, ctxt)
27a4cd48
DM
402 {}
403
404 /* opt_pass methods: */
1a3d085c
TS
405 virtual bool gate (function *fun)
406 {
407 return flag_tree_loop_vectorize || fun->has_force_vectorize_loops;
408 }
409
be55bfe6 410 virtual unsigned int execute (function *);
27a4cd48
DM
411
412}; // class pass_vectorize
413
be55bfe6
TS
414unsigned int
415pass_vectorize::execute (function *fun)
416{
417 if (number_of_loops (fun) <= 1)
418 return 0;
419
420 return vectorize_loops ();
421}
422
27a4cd48
DM
423} // anon namespace
424
425gimple_opt_pass *
426make_pass_vectorize (gcc::context *ctxt)
427{
428 return new pass_vectorize (ctxt);
429}
430
684aaf29
ZD
431/* Propagation of constants using scev. */
432
27a4cd48
DM
433namespace {
434
435const pass_data pass_data_scev_cprop =
436{
437 GIMPLE_PASS, /* type */
438 "sccp", /* name */
439 OPTGROUP_LOOP, /* optinfo_flags */
27a4cd48
DM
440 TV_SCEV_CONST, /* tv_id */
441 ( PROP_cfg | PROP_ssa ), /* properties_required */
442 0, /* properties_provided */
443 0, /* properties_destroyed */
444 0, /* todo_flags_start */
445 ( TODO_cleanup_cfg
446 | TODO_update_ssa_only_virtuals ), /* todo_flags_finish */
b7eae7b8
ZD
447};
448
27a4cd48
DM
449class pass_scev_cprop : public gimple_opt_pass
450{
451public:
c3284718
RS
452 pass_scev_cprop (gcc::context *ctxt)
453 : gimple_opt_pass (pass_data_scev_cprop, ctxt)
27a4cd48
DM
454 {}
455
456 /* opt_pass methods: */
1a3d085c 457 virtual bool gate (function *) { return flag_tree_scev_cprop; }
be55bfe6 458 virtual unsigned int execute (function *) { return scev_const_prop (); }
27a4cd48
DM
459
460}; // class pass_scev_cprop
461
462} // anon namespace
463
464gimple_opt_pass *
465make_pass_scev_cprop (gcc::context *ctxt)
466{
467 return new pass_scev_cprop (ctxt);
468}
469
f3cd574f
ZD
470/* Record bounds on numbers of iterations of loops. */
471
27a4cd48
DM
472namespace {
473
474const pass_data pass_data_record_bounds =
475{
476 GIMPLE_PASS, /* type */
477 "*record_bounds", /* name */
478 OPTGROUP_NONE, /* optinfo_flags */
27a4cd48
DM
479 TV_TREE_LOOP_BOUNDS, /* tv_id */
480 ( PROP_cfg | PROP_ssa ), /* properties_required */
481 0, /* properties_provided */
482 0, /* properties_destroyed */
483 0, /* todo_flags_start */
484 0, /* todo_flags_finish */
f3cd574f
ZD
485};
486
27a4cd48
DM
487class pass_record_bounds : public gimple_opt_pass
488{
489public:
c3284718
RS
490 pass_record_bounds (gcc::context *ctxt)
491 : gimple_opt_pass (pass_data_record_bounds, ctxt)
27a4cd48
DM
492 {}
493
494 /* opt_pass methods: */
be55bfe6 495 virtual unsigned int execute (function *);
27a4cd48
DM
496
497}; // class pass_record_bounds
498
be55bfe6
TS
499unsigned int
500pass_record_bounds::execute (function *fun)
501{
502 if (number_of_loops (fun) <= 1)
503 return 0;
504
505 estimate_numbers_of_iterations ();
506 scev_reset ();
507 return 0;
508}
509
27a4cd48
DM
510} // anon namespace
511
512gimple_opt_pass *
513make_pass_record_bounds (gcc::context *ctxt)
514{
515 return new pass_record_bounds (ctxt);
516}
517
8b11a64c
ZD
518/* Induction variable optimizations. */
519
27a4cd48
DM
520namespace {
521
522const pass_data pass_data_iv_optimize =
523{
524 GIMPLE_PASS, /* type */
525 "ivopts", /* name */
526 OPTGROUP_LOOP, /* optinfo_flags */
27a4cd48
DM
527 TV_TREE_LOOP_IVOPTS, /* tv_id */
528 ( PROP_cfg | PROP_ssa ), /* properties_required */
529 0, /* properties_provided */
530 0, /* properties_destroyed */
531 0, /* todo_flags_start */
532 TODO_update_ssa, /* todo_flags_finish */
82b85a85
ZD
533};
534
27a4cd48
DM
535class pass_iv_optimize : public gimple_opt_pass
536{
537public:
c3284718
RS
538 pass_iv_optimize (gcc::context *ctxt)
539 : gimple_opt_pass (pass_data_iv_optimize, ctxt)
27a4cd48
DM
540 {}
541
542 /* opt_pass methods: */
1a3d085c 543 virtual bool gate (function *) { return flag_ivopts != 0; }
be55bfe6 544 virtual unsigned int execute (function *);
27a4cd48
DM
545
546}; // class pass_iv_optimize
547
be55bfe6
TS
548unsigned int
549pass_iv_optimize::execute (function *fun)
550{
551 if (number_of_loops (fun) <= 1)
552 return 0;
553
554 tree_ssa_iv_optimize ();
555 return 0;
556}
557
27a4cd48
DM
558} // anon namespace
559
560gimple_opt_pass *
561make_pass_iv_optimize (gcc::context *ctxt)
562{
563 return new pass_iv_optimize (ctxt);
564}
565
c66b6c66
ZD
566/* Loop optimizer finalization. */
567
c2924966 568static unsigned int
c66b6c66
ZD
569tree_ssa_loop_done (void)
570{
61183076 571 free_numbers_of_iterations_estimates (cfun);
82b85a85 572 scev_finalize ();
598ec7bd 573 loop_optimizer_finalize ();
c2924966 574 return 0;
c66b6c66 575}
b8698a0f 576
27a4cd48
DM
577namespace {
578
579const pass_data pass_data_tree_loop_done =
580{
581 GIMPLE_PASS, /* type */
582 "loopdone", /* name */
583 OPTGROUP_LOOP, /* optinfo_flags */
27a4cd48
DM
584 TV_NONE, /* tv_id */
585 PROP_cfg, /* properties_required */
586 0, /* properties_provided */
587 0, /* properties_destroyed */
588 0, /* todo_flags_start */
3bea341f 589 TODO_cleanup_cfg, /* todo_flags_finish */
c66b6c66 590};
27a4cd48
DM
591
592class pass_tree_loop_done : public gimple_opt_pass
593{
594public:
c3284718
RS
595 pass_tree_loop_done (gcc::context *ctxt)
596 : gimple_opt_pass (pass_data_tree_loop_done, ctxt)
27a4cd48
DM
597 {}
598
599 /* opt_pass methods: */
be55bfe6 600 virtual unsigned int execute (function *) { return tree_ssa_loop_done (); }
27a4cd48
DM
601
602}; // class pass_tree_loop_done
603
604} // anon namespace
605
606gimple_opt_pass *
607make_pass_tree_loop_done (gcc::context *ctxt)
608{
609 return new pass_tree_loop_done (ctxt);
610}
71343877
AM
611
612/* Calls CBCK for each index in memory reference ADDR_P. There are two
613 kinds situations handled; in each of these cases, the memory reference
614 and DATA are passed to the callback:
615
616 Access to an array: ARRAY_{RANGE_}REF (base, index). In this case we also
617 pass the pointer to the index to the callback.
618
619 Pointer dereference: INDIRECT_REF (addr). In this case we also pass the
620 pointer to addr to the callback.
621
622 If the callback returns false, the whole search stops and false is returned.
623 Otherwise the function returns true after traversing through the whole
624 reference *ADDR_P. */
625
626bool
627for_each_index (tree *addr_p, bool (*cbck) (tree, tree *, void *), void *data)
628{
629 tree *nxt, *idx;
630
631 for (; ; addr_p = nxt)
632 {
633 switch (TREE_CODE (*addr_p))
634 {
635 case SSA_NAME:
636 return cbck (*addr_p, addr_p, data);
637
638 case MEM_REF:
639 nxt = &TREE_OPERAND (*addr_p, 0);
640 return cbck (*addr_p, nxt, data);
641
642 case BIT_FIELD_REF:
643 case VIEW_CONVERT_EXPR:
644 case REALPART_EXPR:
645 case IMAGPART_EXPR:
646 nxt = &TREE_OPERAND (*addr_p, 0);
647 break;
648
649 case COMPONENT_REF:
650 /* If the component has varying offset, it behaves like index
651 as well. */
652 idx = &TREE_OPERAND (*addr_p, 2);
653 if (*idx
654 && !cbck (*addr_p, idx, data))
655 return false;
656
657 nxt = &TREE_OPERAND (*addr_p, 0);
658 break;
659
660 case ARRAY_REF:
661 case ARRAY_RANGE_REF:
662 nxt = &TREE_OPERAND (*addr_p, 0);
663 if (!cbck (*addr_p, &TREE_OPERAND (*addr_p, 1), data))
664 return false;
665 break;
666
667 case VAR_DECL:
668 case PARM_DECL:
669 case CONST_DECL:
670 case STRING_CST:
671 case RESULT_DECL:
672 case VECTOR_CST:
673 case COMPLEX_CST:
674 case INTEGER_CST:
675 case REAL_CST:
676 case FIXED_CST:
677 case CONSTRUCTOR:
678 return true;
679
680 case ADDR_EXPR:
681 gcc_assert (is_gimple_min_invariant (*addr_p));
682 return true;
683
684 case TARGET_MEM_REF:
685 idx = &TMR_BASE (*addr_p);
686 if (*idx
687 && !cbck (*addr_p, idx, data))
688 return false;
689 idx = &TMR_INDEX (*addr_p);
690 if (*idx
691 && !cbck (*addr_p, idx, data))
692 return false;
693 idx = &TMR_INDEX2 (*addr_p);
694 if (*idx
695 && !cbck (*addr_p, idx, data))
696 return false;
697 return true;
698
699 default:
700 gcc_unreachable ();
701 }
702 }
703}
704
705
706/* The name and the length of the currently generated variable
707 for lsm. */
708#define MAX_LSM_NAME_LENGTH 40
709static char lsm_tmp_name[MAX_LSM_NAME_LENGTH + 1];
710static int lsm_tmp_name_length;
711
712/* Adds S to lsm_tmp_name. */
713
714static void
715lsm_tmp_name_add (const char *s)
716{
717 int l = strlen (s) + lsm_tmp_name_length;
718 if (l > MAX_LSM_NAME_LENGTH)
719 return;
720
721 strcpy (lsm_tmp_name + lsm_tmp_name_length, s);
722 lsm_tmp_name_length = l;
723}
724
725/* Stores the name for temporary variable that replaces REF to
726 lsm_tmp_name. */
727
728static void
729gen_lsm_tmp_name (tree ref)
730{
731 const char *name;
732
733 switch (TREE_CODE (ref))
734 {
735 case MEM_REF:
736 case TARGET_MEM_REF:
737 gen_lsm_tmp_name (TREE_OPERAND (ref, 0));
738 lsm_tmp_name_add ("_");
739 break;
740
741 case ADDR_EXPR:
742 gen_lsm_tmp_name (TREE_OPERAND (ref, 0));
743 break;
744
745 case BIT_FIELD_REF:
746 case VIEW_CONVERT_EXPR:
747 case ARRAY_RANGE_REF:
748 gen_lsm_tmp_name (TREE_OPERAND (ref, 0));
749 break;
750
751 case REALPART_EXPR:
752 gen_lsm_tmp_name (TREE_OPERAND (ref, 0));
753 lsm_tmp_name_add ("_RE");
754 break;
755
756 case IMAGPART_EXPR:
757 gen_lsm_tmp_name (TREE_OPERAND (ref, 0));
758 lsm_tmp_name_add ("_IM");
759 break;
760
761 case COMPONENT_REF:
762 gen_lsm_tmp_name (TREE_OPERAND (ref, 0));
763 lsm_tmp_name_add ("_");
764 name = get_name (TREE_OPERAND (ref, 1));
765 if (!name)
766 name = "F";
767 lsm_tmp_name_add (name);
768 break;
769
770 case ARRAY_REF:
771 gen_lsm_tmp_name (TREE_OPERAND (ref, 0));
772 lsm_tmp_name_add ("_I");
773 break;
774
775 case SSA_NAME:
776 case VAR_DECL:
777 case PARM_DECL:
778 name = get_name (ref);
779 if (!name)
780 name = "D";
781 lsm_tmp_name_add (name);
782 break;
783
784 case STRING_CST:
785 lsm_tmp_name_add ("S");
786 break;
787
788 case RESULT_DECL:
789 lsm_tmp_name_add ("R");
790 break;
791
792 case INTEGER_CST:
793 /* Nothing. */
794 break;
795
796 default:
797 gcc_unreachable ();
798 }
799}
800
801/* Determines name for temporary variable that replaces REF.
802 The name is accumulated into the lsm_tmp_name variable.
803 N is added to the name of the temporary. */
804
805char *
806get_lsm_tmp_name (tree ref, unsigned n, const char *suffix)
807{
808 char ns[2];
809
810 lsm_tmp_name_length = 0;
811 gen_lsm_tmp_name (ref);
812 lsm_tmp_name_add ("_lsm");
813 if (n < 10)
814 {
815 ns[0] = '0' + n;
816 ns[1] = 0;
817 lsm_tmp_name_add (ns);
818 }
819 return lsm_tmp_name;
820 if (suffix != NULL)
821 lsm_tmp_name_add (suffix);
822}
823
824/* Computes an estimated number of insns in LOOP, weighted by WEIGHTS. */
825
826unsigned
827tree_num_loop_insns (struct loop *loop, eni_weights *weights)
828{
829 basic_block *body = get_loop_body (loop);
830 gimple_stmt_iterator gsi;
831 unsigned size = 0, i;
832
833 for (i = 0; i < loop->num_nodes; i++)
834 for (gsi = gsi_start_bb (body[i]); !gsi_end_p (gsi); gsi_next (&gsi))
835 size += estimate_num_insns (gsi_stmt (gsi), weights);
836 free (body);
837
838 return size;
839}
840
841
842