tree-switch-conversion.c (info): Remove global pass info.
[gcc.git] / gcc / tree-switch-conversion.c
1 /* Switch Conversion converts variable initializations based on switch
2 statements to initializations from a static array.
3 Copyright (C) 2006, 2008, 2009, 2010, 2011 Free Software Foundation, Inc.
4 Contributed by Martin Jambor <jamborm@suse.cz>
5
6 This file is part of GCC.
7
8 GCC is free software; you can redistribute it and/or modify it
9 under the terms of the GNU General Public License as published by the
10 Free Software Foundation; either version 3, or (at your option) any
11 later version.
12
13 GCC is distributed in the hope that it will be useful, but WITHOUT
14 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
15 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
16 for more details.
17
18 You should have received a copy of the GNU General Public License
19 along with GCC; see the file COPYING3. If not, write to the Free
20 Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA
21 02110-1301, USA. */
22
23 /*
24 Switch initialization conversion
25
26 The following pass changes simple initializations of scalars in a switch
27 statement into initializations from a static array. Obviously, the values
28 must be constant and known at compile time and a default branch must be
29 provided. For example, the following code:
30
31 int a,b;
32
33 switch (argc)
34 {
35 case 1:
36 case 2:
37 a_1 = 8;
38 b_1 = 6;
39 break;
40 case 3:
41 a_2 = 9;
42 b_2 = 5;
43 break;
44 case 12:
45 a_3 = 10;
46 b_3 = 4;
47 break;
48 default:
49 a_4 = 16;
50 b_4 = 1;
51 }
52 a_5 = PHI <a_1, a_2, a_3, a_4>
53 b_5 = PHI <b_1, b_2, b_3, b_4>
54
55
56 is changed into:
57
58 static const int = CSWTCH01[] = {6, 6, 5, 1, 1, 1, 1, 1, 1, 1, 1, 4};
59 static const int = CSWTCH02[] = {8, 8, 9, 16, 16, 16, 16, 16, 16, 16,
60 16, 16, 10};
61
62 if (((unsigned) argc) - 1 < 11)
63 {
64 a_6 = CSWTCH02[argc - 1];
65 b_6 = CSWTCH01[argc - 1];
66 }
67 else
68 {
69 a_7 = 16;
70 b_7 = 1;
71 }
72 a_5 = PHI <a_6, a_7>
73 b_b = PHI <b_6, b_7>
74
75 There are further constraints. Specifically, the range of values across all
76 case labels must not be bigger than SWITCH_CONVERSION_BRANCH_RATIO (default
77 eight) times the number of the actual switch branches. */
78
79 #include "config.h"
80 #include "system.h"
81 #include "coretypes.h"
82 #include "tm.h"
83 #include "line-map.h"
84 #include "params.h"
85 #include "flags.h"
86 #include "tree.h"
87 #include "basic-block.h"
88 #include "tree-flow.h"
89 #include "tree-flow-inline.h"
90 #include "tree-ssa-operands.h"
91 #include "output.h"
92 #include "input.h"
93 #include "tree-pass.h"
94 #include "gimple-pretty-print.h"
95 #include "tree-dump.h"
96 #include "timevar.h"
97 #include "langhooks.h"
98
99 /* The main structure of the pass. */
100 struct switch_conv_info
101 {
102 /* The expression used to decide the switch branch. (It is subsequently used
103 as the index to the created array.) */
104 tree index_expr;
105
106 /* The following integer constants store the minimum value covered by the
107 cases. */
108 tree range_min;
109
110 /* The difference between the above two numbers, i.e. The size of the array
111 that would have to be created by the transformation. */
112 tree range_size;
113
114 /* Basic block that contains the actual SWITCH_EXPR. */
115 basic_block switch_bb;
116
117 /* All branches of the switch statement must have a single successor stored in
118 the following variable. */
119 basic_block final_bb;
120
121 /* Number of phi nodes in the final bb (that we'll be replacing). */
122 int phi_count;
123
124 /* Array of default values, in the same order as phi nodes. */
125 tree *default_values;
126
127 /* Constructors of new static arrays. */
128 VEC (constructor_elt, gc) **constructors;
129
130 /* Array of ssa names that are initialized with a value from a new static
131 array. */
132 tree *target_inbound_names;
133
134 /* Array of ssa names that are initialized with the default value if the
135 switch expression is out of range. */
136 tree *target_outbound_names;
137
138 /* The probability of the default edge in the replaced switch. */
139 int default_prob;
140
141 /* The count of the default edge in the replaced switch. */
142 gcov_type default_count;
143
144 /* Combined count of all other (non-default) edges in the replaced switch. */
145 gcov_type other_count;
146
147 /* The first load statement that loads a temporary from a new static array.
148 */
149 gimple arr_ref_first;
150
151 /* The last load statement that loads a temporary from a new static array. */
152 gimple arr_ref_last;
153
154 /* String reason why the case wasn't a good candidate that is written to the
155 dump file, if there is one. */
156 const char *reason;
157
158 /* Parameters for expand_switch_using_bit_tests. Should be computed
159 the same way as in expand_case. */
160 unsigned int bit_test_uniq;
161 unsigned int bit_test_count;
162 basic_block bit_test_bb[2];
163 };
164
165 /* Checks whether the range given by individual case statements of the SWTCH
166 switch statement isn't too big and whether the number of branches actually
167 satisfies the size of the new array. */
168
169 static bool
170 check_range (gimple swtch, struct switch_conv_info *info)
171 {
172 tree min_case, max_case;
173 unsigned int branch_num = gimple_switch_num_labels (swtch);
174 tree range_max;
175
176 /* The gimplifier has already sorted the cases by CASE_LOW and ensured there
177 is a default label which is the first in the vector. */
178
179 min_case = gimple_switch_label (swtch, 1);
180 info->range_min = CASE_LOW (min_case);
181
182 gcc_assert (branch_num > 1);
183 gcc_assert (CASE_LOW (gimple_switch_label (swtch, 0)) == NULL_TREE);
184 max_case = gimple_switch_label (swtch, branch_num - 1);
185 if (CASE_HIGH (max_case) != NULL_TREE)
186 range_max = CASE_HIGH (max_case);
187 else
188 range_max = CASE_LOW (max_case);
189
190 gcc_assert (info->range_min);
191 gcc_assert (range_max);
192
193 info->range_size = int_const_binop (MINUS_EXPR, range_max, info->range_min);
194
195 gcc_assert (info->range_size);
196 if (!host_integerp (info->range_size, 1))
197 {
198 info->reason = "index range way too large or otherwise unusable";
199 return false;
200 }
201
202 if ((unsigned HOST_WIDE_INT) tree_low_cst (info->range_size, 1)
203 > ((unsigned) branch_num * SWITCH_CONVERSION_BRANCH_RATIO))
204 {
205 info->reason = "the maximum range-branch ratio exceeded";
206 return false;
207 }
208
209 return true;
210 }
211
212 /* Checks the given CS switch case whether it is suitable for conversion
213 (whether all but the default basic blocks are empty and so on). If it is,
214 adds the case to the branch list along with values for the defined variables
215 and returns true. Otherwise returns false. */
216
217 static bool
218 check_process_case (tree cs, struct switch_conv_info *info)
219 {
220 tree ldecl;
221 basic_block label_bb, following_bb;
222 edge e;
223
224 ldecl = CASE_LABEL (cs);
225 label_bb = label_to_block (ldecl);
226
227 e = find_edge (info->switch_bb, label_bb);
228 gcc_assert (e);
229
230 if (CASE_LOW (cs) == NULL_TREE)
231 {
232 /* Default branch. */
233 info->default_prob = e->probability;
234 info->default_count = e->count;
235 }
236 else
237 {
238 int i;
239 info->other_count += e->count;
240 for (i = 0; i < 2; i++)
241 if (info->bit_test_bb[i] == label_bb)
242 break;
243 else if (info->bit_test_bb[i] == NULL)
244 {
245 info->bit_test_bb[i] = label_bb;
246 info->bit_test_uniq++;
247 break;
248 }
249 if (i == 2)
250 info->bit_test_uniq = 3;
251 if (CASE_HIGH (cs) != NULL_TREE
252 && ! tree_int_cst_equal (CASE_LOW (cs), CASE_HIGH (cs)))
253 info->bit_test_count += 2;
254 else
255 info->bit_test_count++;
256 }
257
258 if (!label_bb)
259 {
260 info->reason = "bad case - cs BB label is NULL";
261 return false;
262 }
263
264 if (!single_pred_p (label_bb))
265 {
266 if (info->final_bb && info->final_bb != label_bb)
267 {
268 info->reason = "bad case - a non-final BB has two predecessors";
269 return false; /* sth complex going on in this branch */
270 }
271
272 following_bb = label_bb;
273 }
274 else
275 {
276 if (!empty_block_p (label_bb))
277 {
278 info->reason = "bad case - a non-final BB not empty";
279 return false;
280 }
281
282 e = single_succ_edge (label_bb);
283 following_bb = single_succ (label_bb);
284 }
285
286 if (!info->final_bb)
287 info->final_bb = following_bb;
288 else if (info->final_bb != following_bb)
289 {
290 info->reason = "bad case - different final BB";
291 return false; /* the only successor is not common for all the branches */
292 }
293
294 return true;
295 }
296
297 /* This function checks whether all required values in phi nodes in final_bb
298 are constants. Required values are those that correspond to a basic block
299 which is a part of the examined switch statement. It returns true if the
300 phi nodes are OK, otherwise false. */
301
302 static bool
303 check_final_bb (struct switch_conv_info *info)
304 {
305 gimple_stmt_iterator gsi;
306
307 info->phi_count = 0;
308 for (gsi = gsi_start_phis (info->final_bb); !gsi_end_p (gsi); gsi_next (&gsi))
309 {
310 gimple phi = gsi_stmt (gsi);
311 unsigned int i;
312
313 info->phi_count++;
314
315 for (i = 0; i < gimple_phi_num_args (phi); i++)
316 {
317 basic_block bb = gimple_phi_arg_edge (phi, i)->src;
318
319 if (bb == info->switch_bb
320 || (single_pred_p (bb) && single_pred (bb) == info->switch_bb))
321 {
322 tree reloc, val;
323
324 val = gimple_phi_arg_def (phi, i);
325 if (!is_gimple_ip_invariant (val))
326 {
327 info->reason = "non-invariant value from a case";
328 return false; /* Non-invariant argument. */
329 }
330 reloc = initializer_constant_valid_p (val, TREE_TYPE (val));
331 if ((flag_pic && reloc != null_pointer_node)
332 || (!flag_pic && reloc == NULL_TREE))
333 {
334 if (reloc)
335 info->reason
336 = "value from a case would need runtime relocations";
337 else
338 info->reason
339 = "value from a case is not a valid initializer";
340 return false;
341 }
342 }
343 }
344 }
345
346 return true;
347 }
348
349 /* The following function allocates default_values, target_{in,out}_names and
350 constructors arrays. The last one is also populated with pointers to
351 vectors that will become constructors of new arrays. */
352
353 static void
354 create_temp_arrays (struct switch_conv_info *info)
355 {
356 int i;
357
358 info->default_values = XCNEWVEC (tree, info->phi_count * 3);
359 info->constructors = XCNEWVEC (VEC (constructor_elt, gc) *, info->phi_count);
360 info->target_inbound_names = info->default_values + info->phi_count;
361 info->target_outbound_names = info->target_inbound_names + info->phi_count;
362 for (i = 0; i < info->phi_count; i++)
363 info->constructors[i]
364 = VEC_alloc (constructor_elt, gc, tree_low_cst (info->range_size, 1) + 1);
365 }
366
367 /* Free the arrays created by create_temp_arrays(). The vectors that are
368 created by that function are not freed here, however, because they have
369 already become constructors and must be preserved. */
370
371 static void
372 free_temp_arrays (struct switch_conv_info *info)
373 {
374 XDELETEVEC (info->constructors);
375 XDELETEVEC (info->default_values);
376 }
377
378 /* Populate the array of default values in the order of phi nodes.
379 DEFAULT_CASE is the CASE_LABEL_EXPR for the default switch branch. */
380
381 static void
382 gather_default_values (tree default_case, struct switch_conv_info *info)
383 {
384 gimple_stmt_iterator gsi;
385 basic_block bb = label_to_block (CASE_LABEL (default_case));
386 edge e;
387 int i = 0;
388
389 gcc_assert (CASE_LOW (default_case) == NULL_TREE);
390
391 if (bb == info->final_bb)
392 e = find_edge (info->switch_bb, bb);
393 else
394 e = single_succ_edge (bb);
395
396 for (gsi = gsi_start_phis (info->final_bb); !gsi_end_p (gsi); gsi_next (&gsi))
397 {
398 gimple phi = gsi_stmt (gsi);
399 tree val = PHI_ARG_DEF_FROM_EDGE (phi, e);
400 gcc_assert (val);
401 info->default_values[i++] = val;
402 }
403 }
404
405 /* The following function populates the vectors in the constructors array with
406 future contents of the static arrays. The vectors are populated in the
407 order of phi nodes. SWTCH is the switch statement being converted. */
408
409 static void
410 build_constructors (gimple swtch, struct switch_conv_info *info)
411 {
412 unsigned i, branch_num = gimple_switch_num_labels (swtch);
413 tree pos = info->range_min;
414
415 for (i = 1; i < branch_num; i++)
416 {
417 tree cs = gimple_switch_label (swtch, i);
418 basic_block bb = label_to_block (CASE_LABEL (cs));
419 edge e;
420 tree high;
421 gimple_stmt_iterator gsi;
422 int j;
423
424 if (bb == info->final_bb)
425 e = find_edge (info->switch_bb, bb);
426 else
427 e = single_succ_edge (bb);
428 gcc_assert (e);
429
430 while (tree_int_cst_lt (pos, CASE_LOW (cs)))
431 {
432 int k;
433 for (k = 0; k < info->phi_count; k++)
434 {
435 constructor_elt *elt;
436
437 elt = VEC_quick_push (constructor_elt,
438 info->constructors[k], NULL);
439 elt->index = int_const_binop (MINUS_EXPR, pos,
440 info->range_min);
441 elt->value = info->default_values[k];
442 }
443
444 pos = int_const_binop (PLUS_EXPR, pos, integer_one_node);
445 }
446 gcc_assert (tree_int_cst_equal (pos, CASE_LOW (cs)));
447
448 j = 0;
449 if (CASE_HIGH (cs))
450 high = CASE_HIGH (cs);
451 else
452 high = CASE_LOW (cs);
453 for (gsi = gsi_start_phis (info->final_bb);
454 !gsi_end_p (gsi); gsi_next (&gsi))
455 {
456 gimple phi = gsi_stmt (gsi);
457 tree val = PHI_ARG_DEF_FROM_EDGE (phi, e);
458 tree low = CASE_LOW (cs);
459 pos = CASE_LOW (cs);
460
461 do
462 {
463 constructor_elt *elt;
464
465 elt = VEC_quick_push (constructor_elt,
466 info->constructors[j], NULL);
467 elt->index = int_const_binop (MINUS_EXPR, pos, info->range_min);
468 elt->value = val;
469
470 pos = int_const_binop (PLUS_EXPR, pos, integer_one_node);
471 } while (!tree_int_cst_lt (high, pos)
472 && tree_int_cst_lt (low, pos));
473 j++;
474 }
475 }
476 }
477
478 /* If all values in the constructor vector are the same, return the value.
479 Otherwise return NULL_TREE. Not supposed to be called for empty
480 vectors. */
481
482 static tree
483 constructor_contains_same_values_p (VEC (constructor_elt, gc) *vec)
484 {
485 unsigned int i;
486 tree prev = NULL_TREE;
487 constructor_elt *elt;
488
489 FOR_EACH_VEC_ELT (constructor_elt, vec, i, elt)
490 {
491 if (!prev)
492 prev = elt->value;
493 else if (!operand_equal_p (elt->value, prev, OEP_ONLY_CONST))
494 return NULL_TREE;
495 }
496 return prev;
497 }
498
499 /* Return type which should be used for array elements, either TYPE,
500 or for integral type some smaller integral type that can still hold
501 all the constants. */
502
503 static tree
504 array_value_type (gimple swtch, tree type, int num,
505 struct switch_conv_info *info)
506 {
507 unsigned int i, len = VEC_length (constructor_elt, info->constructors[num]);
508 constructor_elt *elt;
509 enum machine_mode mode;
510 int sign = 0;
511 tree smaller_type;
512
513 if (!INTEGRAL_TYPE_P (type))
514 return type;
515
516 mode = GET_CLASS_NARROWEST_MODE (GET_MODE_CLASS (TYPE_MODE (type)));
517 if (GET_MODE_SIZE (TYPE_MODE (type)) <= GET_MODE_SIZE (mode))
518 return type;
519
520 if (len < (optimize_bb_for_size_p (gimple_bb (swtch)) ? 2 : 32))
521 return type;
522
523 FOR_EACH_VEC_ELT (constructor_elt, info->constructors[num], i, elt)
524 {
525 double_int cst;
526
527 if (TREE_CODE (elt->value) != INTEGER_CST)
528 return type;
529
530 cst = TREE_INT_CST (elt->value);
531 while (1)
532 {
533 unsigned int prec = GET_MODE_BITSIZE (mode);
534 if (prec > HOST_BITS_PER_WIDE_INT)
535 return type;
536
537 if (sign >= 0
538 && double_int_equal_p (cst, double_int_zext (cst, prec)))
539 {
540 if (sign == 0
541 && double_int_equal_p (cst, double_int_sext (cst, prec)))
542 break;
543 sign = 1;
544 break;
545 }
546 if (sign <= 0
547 && double_int_equal_p (cst, double_int_sext (cst, prec)))
548 {
549 sign = -1;
550 break;
551 }
552
553 if (sign == 1)
554 sign = 0;
555
556 mode = GET_MODE_WIDER_MODE (mode);
557 if (mode == VOIDmode
558 || GET_MODE_SIZE (mode) >= GET_MODE_SIZE (TYPE_MODE (type)))
559 return type;
560 }
561 }
562
563 if (sign == 0)
564 sign = TYPE_UNSIGNED (type) ? 1 : -1;
565 smaller_type = lang_hooks.types.type_for_mode (mode, sign >= 0);
566 if (GET_MODE_SIZE (TYPE_MODE (type))
567 <= GET_MODE_SIZE (TYPE_MODE (smaller_type)))
568 return type;
569
570 return smaller_type;
571 }
572
573 /* Create an appropriate array type and declaration and assemble a static array
574 variable. Also create a load statement that initializes the variable in
575 question with a value from the static array. SWTCH is the switch statement
576 being converted, NUM is the index to arrays of constructors, default values
577 and target SSA names for this particular array. ARR_INDEX_TYPE is the type
578 of the index of the new array, PHI is the phi node of the final BB that
579 corresponds to the value that will be loaded from the created array. TIDX
580 is an ssa name of a temporary variable holding the index for loads from the
581 new array. */
582
583 static void
584 build_one_array (gimple swtch, int num, tree arr_index_type, gimple phi,
585 tree tidx, struct switch_conv_info *info)
586 {
587 tree name, cst;
588 gimple load;
589 gimple_stmt_iterator gsi = gsi_for_stmt (swtch);
590 location_t loc = gimple_location (swtch);
591
592 gcc_assert (info->default_values[num]);
593
594 name = make_ssa_name (SSA_NAME_VAR (PHI_RESULT (phi)), NULL);
595 info->target_inbound_names[num] = name;
596
597 cst = constructor_contains_same_values_p (info->constructors[num]);
598 if (cst)
599 load = gimple_build_assign (name, cst);
600 else
601 {
602 tree array_type, ctor, decl, value_type, fetch, default_type;
603
604 default_type = TREE_TYPE (info->default_values[num]);
605 value_type = array_value_type (swtch, default_type, num, info);
606 array_type = build_array_type (value_type, arr_index_type);
607 if (default_type != value_type)
608 {
609 unsigned int i;
610 constructor_elt *elt;
611
612 FOR_EACH_VEC_ELT (constructor_elt, info->constructors[num], i, elt)
613 elt->value = fold_convert (value_type, elt->value);
614 }
615 ctor = build_constructor (array_type, info->constructors[num]);
616 TREE_CONSTANT (ctor) = true;
617 TREE_STATIC (ctor) = true;
618
619 decl = build_decl (loc, VAR_DECL, NULL_TREE, array_type);
620 TREE_STATIC (decl) = 1;
621 DECL_INITIAL (decl) = ctor;
622
623 DECL_NAME (decl) = create_tmp_var_name ("CSWTCH");
624 DECL_ARTIFICIAL (decl) = 1;
625 TREE_CONSTANT (decl) = 1;
626 TREE_READONLY (decl) = 1;
627 add_referenced_var (decl);
628 varpool_mark_needed_node (varpool_node (decl));
629 varpool_finalize_decl (decl);
630
631 fetch = build4 (ARRAY_REF, value_type, decl, tidx, NULL_TREE,
632 NULL_TREE);
633 if (default_type != value_type)
634 {
635 fetch = fold_convert (default_type, fetch);
636 fetch = force_gimple_operand_gsi (&gsi, fetch, true, NULL_TREE,
637 true, GSI_SAME_STMT);
638 }
639 load = gimple_build_assign (name, fetch);
640 }
641
642 SSA_NAME_DEF_STMT (name) = load;
643 gsi_insert_before (&gsi, load, GSI_SAME_STMT);
644 update_stmt (load);
645 info->arr_ref_last = load;
646 }
647
648 /* Builds and initializes static arrays initialized with values gathered from
649 the SWTCH switch statement. Also creates statements that load values from
650 them. */
651
652 static void
653 build_arrays (gimple swtch, struct switch_conv_info *info)
654 {
655 tree arr_index_type;
656 tree tidx, sub, tmp, utype;
657 gimple stmt;
658 gimple_stmt_iterator gsi;
659 int i;
660 location_t loc = gimple_location (swtch);
661
662 gsi = gsi_for_stmt (swtch);
663
664 /* Make sure we do not generate arithmetics in a subrange. */
665 utype = TREE_TYPE (info->index_expr);
666 if (TREE_TYPE (utype))
667 utype = lang_hooks.types.type_for_mode (TYPE_MODE (TREE_TYPE (utype)), 1);
668 else
669 utype = lang_hooks.types.type_for_mode (TYPE_MODE (utype), 1);
670
671 arr_index_type = build_index_type (info->range_size);
672 tmp = create_tmp_var (utype, "csui");
673 add_referenced_var (tmp);
674 tidx = make_ssa_name (tmp, NULL);
675 sub = fold_build2_loc (loc, MINUS_EXPR, utype,
676 fold_convert_loc (loc, utype, info->index_expr),
677 fold_convert_loc (loc, utype, info->range_min));
678 sub = force_gimple_operand_gsi (&gsi, sub,
679 false, NULL, true, GSI_SAME_STMT);
680 stmt = gimple_build_assign (tidx, sub);
681 SSA_NAME_DEF_STMT (tidx) = stmt;
682
683 gsi_insert_before (&gsi, stmt, GSI_SAME_STMT);
684 update_stmt (stmt);
685 info->arr_ref_first = stmt;
686
687 for (gsi = gsi_start_phis (info->final_bb), i = 0;
688 !gsi_end_p (gsi); gsi_next (&gsi), i++)
689 build_one_array (swtch, i, arr_index_type, gsi_stmt (gsi), tidx, info);
690 }
691
692 /* Generates and appropriately inserts loads of default values at the position
693 given by BSI. Returns the last inserted statement. */
694
695 static gimple
696 gen_def_assigns (gimple_stmt_iterator *gsi, struct switch_conv_info *info)
697 {
698 int i;
699 gimple assign = NULL;
700
701 for (i = 0; i < info->phi_count; i++)
702 {
703 tree name
704 = make_ssa_name (SSA_NAME_VAR (info->target_inbound_names[i]), NULL);
705
706 info->target_outbound_names[i] = name;
707 assign = gimple_build_assign (name, info->default_values[i]);
708 SSA_NAME_DEF_STMT (name) = assign;
709 gsi_insert_before (gsi, assign, GSI_SAME_STMT);
710 update_stmt (assign);
711 }
712 return assign;
713 }
714
715 /* Deletes the unused bbs and edges that now contain the switch statement and
716 its empty branch bbs. BBD is the now dead BB containing the original switch
717 statement, FINAL is the last BB of the converted switch statement (in terms
718 of succession). */
719
720 static void
721 prune_bbs (basic_block bbd, basic_block final)
722 {
723 edge_iterator ei;
724 edge e;
725
726 for (ei = ei_start (bbd->succs); (e = ei_safe_edge (ei)); )
727 {
728 basic_block bb;
729 bb = e->dest;
730 remove_edge (e);
731 if (bb != final)
732 delete_basic_block (bb);
733 }
734 delete_basic_block (bbd);
735 }
736
737 /* Add values to phi nodes in final_bb for the two new edges. E1F is the edge
738 from the basic block loading values from an array and E2F from the basic
739 block loading default values. BBF is the last switch basic block (see the
740 bbf description in the comment below). */
741
742 static void
743 fix_phi_nodes (edge e1f, edge e2f, basic_block bbf,
744 struct switch_conv_info *info)
745 {
746 gimple_stmt_iterator gsi;
747 int i;
748
749 for (gsi = gsi_start_phis (bbf), i = 0;
750 !gsi_end_p (gsi); gsi_next (&gsi), i++)
751 {
752 gimple phi = gsi_stmt (gsi);
753 add_phi_arg (phi, info->target_inbound_names[i], e1f, UNKNOWN_LOCATION);
754 add_phi_arg (phi, info->target_outbound_names[i], e2f, UNKNOWN_LOCATION);
755 }
756 }
757
758 /* Creates a check whether the switch expression value actually falls into the
759 range given by all the cases. If it does not, the temporaries are loaded
760 with default values instead. SWTCH is the switch statement being converted.
761
762 bb0 is the bb with the switch statement, however, we'll end it with a
763 condition instead.
764
765 bb1 is the bb to be used when the range check went ok. It is derived from
766 the switch BB
767
768 bb2 is the bb taken when the expression evaluated outside of the range
769 covered by the created arrays. It is populated by loads of default
770 values.
771
772 bbF is a fall through for both bb1 and bb2 and contains exactly what
773 originally followed the switch statement.
774
775 bbD contains the switch statement (in the end). It is unreachable but we
776 still need to strip off its edges.
777 */
778
779 static void
780 gen_inbound_check (gimple swtch, struct switch_conv_info *info)
781 {
782 tree label_decl1 = create_artificial_label (UNKNOWN_LOCATION);
783 tree label_decl2 = create_artificial_label (UNKNOWN_LOCATION);
784 tree label_decl3 = create_artificial_label (UNKNOWN_LOCATION);
785 gimple label1, label2, label3;
786 tree utype, tidx;
787 tree bound;
788
789 gimple cond_stmt;
790
791 gimple last_assign;
792 gimple_stmt_iterator gsi;
793 basic_block bb0, bb1, bb2, bbf, bbd;
794 edge e01, e02, e21, e1d, e1f, e2f;
795 location_t loc = gimple_location (swtch);
796
797 gcc_assert (info->default_values);
798 bb0 = gimple_bb (swtch);
799
800 tidx = gimple_assign_lhs (info->arr_ref_first);
801 utype = TREE_TYPE (tidx);
802
803 /* (end of) block 0 */
804 gsi = gsi_for_stmt (info->arr_ref_first);
805 gsi_next (&gsi);
806
807 bound = fold_convert_loc (loc, utype, info->range_size);
808 cond_stmt = gimple_build_cond (LE_EXPR, tidx, bound, NULL_TREE, NULL_TREE);
809 gsi_insert_before (&gsi, cond_stmt, GSI_SAME_STMT);
810 update_stmt (cond_stmt);
811
812 /* block 2 */
813 label2 = gimple_build_label (label_decl2);
814 gsi_insert_before (&gsi, label2, GSI_SAME_STMT);
815 last_assign = gen_def_assigns (&gsi, info);
816
817 /* block 1 */
818 label1 = gimple_build_label (label_decl1);
819 gsi_insert_before (&gsi, label1, GSI_SAME_STMT);
820
821 /* block F */
822 gsi = gsi_start_bb (info->final_bb);
823 label3 = gimple_build_label (label_decl3);
824 gsi_insert_before (&gsi, label3, GSI_SAME_STMT);
825
826 /* cfg fix */
827 e02 = split_block (bb0, cond_stmt);
828 bb2 = e02->dest;
829
830 e21 = split_block (bb2, last_assign);
831 bb1 = e21->dest;
832 remove_edge (e21);
833
834 e1d = split_block (bb1, info->arr_ref_last);
835 bbd = e1d->dest;
836 remove_edge (e1d);
837
838 /* flags and profiles of the edge for in-range values */
839 e01 = make_edge (bb0, bb1, EDGE_TRUE_VALUE);
840 e01->probability = REG_BR_PROB_BASE - info->default_prob;
841 e01->count = info->other_count;
842
843 /* flags and profiles of the edge taking care of out-of-range values */
844 e02->flags &= ~EDGE_FALLTHRU;
845 e02->flags |= EDGE_FALSE_VALUE;
846 e02->probability = info->default_prob;
847 e02->count = info->default_count;
848
849 bbf = info->final_bb;
850
851 e1f = make_edge (bb1, bbf, EDGE_FALLTHRU);
852 e1f->probability = REG_BR_PROB_BASE;
853 e1f->count = info->other_count;
854
855 e2f = make_edge (bb2, bbf, EDGE_FALLTHRU);
856 e2f->probability = REG_BR_PROB_BASE;
857 e2f->count = info->default_count;
858
859 /* frequencies of the new BBs */
860 bb1->frequency = EDGE_FREQUENCY (e01);
861 bb2->frequency = EDGE_FREQUENCY (e02);
862 bbf->frequency = EDGE_FREQUENCY (e1f) + EDGE_FREQUENCY (e2f);
863
864 prune_bbs (bbd, info->final_bb); /* To keep calc_dfs_tree() in dominance.c
865 happy. */
866
867 fix_phi_nodes (e1f, e2f, bbf, info);
868
869 free_dominance_info (CDI_DOMINATORS);
870 free_dominance_info (CDI_POST_DOMINATORS);
871 }
872
873 /* The following function is invoked on every switch statement (the current one
874 is given in SWTCH) and runs the individual phases of switch conversion on it
875 one after another until one fails or the conversion is completed.
876 Returns NULL on success, or a pointer to a string with the reason why the
877 conversion failed. */
878
879 static const char *
880 process_switch (gimple swtch)
881 {
882 unsigned int i, branch_num = gimple_switch_num_labels (swtch);
883 tree index_type;
884 struct switch_conv_info info;
885
886 /* Operand 2 is either NULL_TREE or a vector of cases (stmt.c). */
887 if (branch_num < 2)
888 return "switch has no labels";
889
890 info.reason = NULL;
891 info.final_bb = NULL;
892 info.switch_bb = gimple_bb (swtch);
893 info.index_expr = gimple_switch_index (swtch);
894 info.arr_ref_first = NULL;
895 info.arr_ref_last = NULL;
896 info.default_prob = 0;
897 info.default_count = 0;
898 info.other_count = 0;
899 info.bit_test_uniq = 0;
900 info.bit_test_count = 0;
901 info.bit_test_bb[0] = NULL;
902 info.bit_test_bb[1] = NULL;
903
904 /* An ERROR_MARK occurs for various reasons including invalid data type.
905 (comment from stmt.c) */
906 index_type = TREE_TYPE (info.index_expr);
907 if (index_type == error_mark_node)
908 return "index error\n";
909
910 /* Check the case label values are within reasonable range: */
911 if (!check_range (swtch, &info))
912 {
913 gcc_assert (info.reason);
914 return info.reason;
915 }
916
917 /* For all the cases, see whether they are empty, the assignments they
918 represent constant and so on... */
919 for (i = 0; i < branch_num; i++)
920 if (!check_process_case (gimple_switch_label (swtch, i), &info))
921 {
922 gcc_assert (info.reason);
923 if (dump_file)
924 fprintf (dump_file, "processing of case %i failed\n\t", i);
925 return info.reason;
926 }
927
928 if (info.bit_test_uniq <= 2)
929 {
930 rtl_profile_for_bb (gimple_bb (swtch));
931 if (expand_switch_using_bit_tests_p (gimple_switch_index (swtch),
932 info.range_size, info.bit_test_uniq,
933 info.bit_test_count))
934 {
935 return "expanding as bit test is preferable";
936 }
937 }
938
939 if (!check_final_bb (&info))
940 {
941 gcc_assert (info.reason);
942 return info.reason;
943 }
944
945 /* At this point all checks have passed and we can proceed with the
946 transformation. */
947
948 create_temp_arrays (&info);
949 gather_default_values (gimple_switch_label (swtch, 0), &info);
950 build_constructors (swtch, &info);
951
952 build_arrays (swtch, &info); /* Build the static arrays and assignments. */
953 gen_inbound_check (swtch, &info); /* Build the bounds check. */
954
955 /* Cleanup: */
956 free_temp_arrays (&info);
957 return NULL;
958 }
959
960 /* The main function of the pass scans statements for switches and invokes
961 process_switch on them. */
962
963 static unsigned int
964 do_switchconv (void)
965 {
966 basic_block bb;
967
968 FOR_EACH_BB (bb)
969 {
970 const char *failure_reason;
971 gimple stmt = last_stmt (bb);
972 if (stmt && gimple_code (stmt) == GIMPLE_SWITCH)
973 {
974 if (dump_file)
975 {
976 expanded_location loc = expand_location (gimple_location (stmt));
977
978 fprintf (dump_file, "beginning to process the following "
979 "SWITCH statement (%s:%d) : ------- \n",
980 loc.file, loc.line);
981 print_gimple_stmt (dump_file, stmt, 0, TDF_SLIM);
982 putc ('\n', dump_file);
983 }
984
985 failure_reason = process_switch (stmt);
986 if (! failure_reason)
987 {
988 if (dump_file)
989 {
990 fputs ("Switch converted\n", dump_file);
991 fputs ("--------------------------------\n", dump_file);
992 }
993 }
994 else
995 {
996 if (dump_file)
997 {
998 fputs ("Bailing out - ", dump_file);
999 fputs (failure_reason, dump_file);
1000 fputs ("\n--------------------------------\n", dump_file);
1001 }
1002 }
1003 }
1004 }
1005
1006 return 0;
1007 }
1008
1009 /* The pass gate. */
1010
1011 static bool
1012 switchconv_gate (void)
1013 {
1014 return flag_tree_switch_conversion != 0;
1015 }
1016
1017 struct gimple_opt_pass pass_convert_switch =
1018 {
1019 {
1020 GIMPLE_PASS,
1021 "switchconv", /* name */
1022 switchconv_gate, /* gate */
1023 do_switchconv, /* execute */
1024 NULL, /* sub */
1025 NULL, /* next */
1026 0, /* static_pass_number */
1027 TV_TREE_SWITCH_CONVERSION, /* tv_id */
1028 PROP_cfg | PROP_ssa, /* properties_required */
1029 0, /* properties_provided */
1030 0, /* properties_destroyed */
1031 0, /* todo_flags_start */
1032 TODO_update_ssa
1033 | TODO_ggc_collect | TODO_verify_ssa /* todo_flags_finish */
1034 }
1035 };