1 /* Preamble and helpers for the autogenerated gimple-match.c file.
2 Copyright (C) 2014 Free Software Foundation, Inc.
4 This file is part of GCC.
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
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
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/>. */
22 #include "coretypes.h"
24 #include "stringpool.h"
25 #include "stor-layout.h"
28 #include "hard-reg-set.h"
36 #include "basic-block.h"
37 #include "tree-ssa-alias.h"
38 #include "internal-fn.h"
39 #include "gimple-expr.h"
42 #include "gimple-ssa.h"
43 #include "tree-ssanames.h"
44 #include "gimple-fold.h"
45 #include "gimple-iterator.h"
49 #include "tree-phinodes.h"
50 #include "ssa-iterators.h"
52 #include "gimple-match.h"
55 /* Forward declarations of the private auto-generated matchers.
56 They expect valueized operands in canonical order and do not
57 perform simplification of all-constant operands. */
58 static bool gimple_simplify (code_helper
*, tree
*,
59 gimple_seq
*, tree (*)(tree
),
60 code_helper
, tree
, tree
);
61 static bool gimple_simplify (code_helper
*, tree
*,
62 gimple_seq
*, tree (*)(tree
),
63 code_helper
, tree
, tree
, tree
);
64 static bool gimple_simplify (code_helper
*, tree
*,
65 gimple_seq
*, tree (*)(tree
),
66 code_helper
, tree
, tree
, tree
, tree
);
69 /* Return whether T is a constant that we'll dispatch to fold to
70 evaluate fully constant expressions. */
73 constant_for_folding (tree t
)
75 return (CONSTANT_CLASS_P (t
)
76 /* The following is only interesting to string builtins. */
77 || (TREE_CODE (t
) == ADDR_EXPR
78 && TREE_CODE (TREE_OPERAND (t
, 0)) == STRING_CST
));
82 /* Helper that matches and simplifies the toplevel result from
83 a gimple_simplify run (where we don't want to build
84 a stmt in case it's used in in-place folding). Replaces
85 *RES_CODE and *RES_OPS with a simplified and/or canonicalized
86 result and returns whether any change was made. */
89 gimple_resimplify1 (gimple_seq
*seq
,
90 code_helper
*res_code
, tree type
, tree
*res_ops
,
91 tree (*valueize
)(tree
))
93 if (constant_for_folding (res_ops
[0]))
96 if (res_code
->is_tree_code ())
97 tem
= fold_unary_to_constant (*res_code
, type
, res_ops
[0]);
100 tree decl
= builtin_decl_implicit (*res_code
);
103 tem
= fold_builtin_n (UNKNOWN_LOCATION
, decl
, res_ops
, 1, false);
106 /* fold_builtin_n wraps the result inside a NOP_EXPR. */
108 tem
= fold_convert (type
, tem
);
113 && CONSTANT_CLASS_P (tem
))
116 res_ops
[1] = NULL_TREE
;
117 res_ops
[2] = NULL_TREE
;
118 *res_code
= TREE_CODE (res_ops
[0]);
123 code_helper res_code2
;
124 tree res_ops2
[3] = {};
125 if (gimple_simplify (&res_code2
, res_ops2
, seq
, valueize
,
126 *res_code
, type
, res_ops
[0]))
128 *res_code
= res_code2
;
129 res_ops
[0] = res_ops2
[0];
130 res_ops
[1] = res_ops2
[1];
131 res_ops
[2] = res_ops2
[2];
138 /* Helper that matches and simplifies the toplevel result from
139 a gimple_simplify run (where we don't want to build
140 a stmt in case it's used in in-place folding). Replaces
141 *RES_CODE and *RES_OPS with a simplified and/or canonicalized
142 result and returns whether any change was made. */
145 gimple_resimplify2 (gimple_seq
*seq
,
146 code_helper
*res_code
, tree type
, tree
*res_ops
,
147 tree (*valueize
)(tree
))
149 if (constant_for_folding (res_ops
[0]) && constant_for_folding (res_ops
[1]))
151 tree tem
= NULL_TREE
;
152 if (res_code
->is_tree_code ())
153 tem
= fold_binary_to_constant (*res_code
, type
,
154 res_ops
[0], res_ops
[1]);
157 tree decl
= builtin_decl_implicit (*res_code
);
160 tem
= fold_builtin_n (UNKNOWN_LOCATION
, decl
, res_ops
, 2, false);
163 /* fold_builtin_n wraps the result inside a NOP_EXPR. */
165 tem
= fold_convert (type
, tem
);
170 && CONSTANT_CLASS_P (tem
))
173 res_ops
[1] = NULL_TREE
;
174 res_ops
[2] = NULL_TREE
;
175 *res_code
= TREE_CODE (res_ops
[0]);
180 /* Canonicalize operand order. */
181 bool canonicalized
= false;
182 if (res_code
->is_tree_code ()
183 && (TREE_CODE_CLASS ((enum tree_code
) *res_code
) == tcc_comparison
184 || commutative_tree_code (*res_code
))
185 && tree_swap_operands_p (res_ops
[0], res_ops
[1], false))
187 tree tem
= res_ops
[0];
188 res_ops
[0] = res_ops
[1];
190 if (TREE_CODE_CLASS ((enum tree_code
) *res_code
) == tcc_comparison
)
191 *res_code
= swap_tree_comparison (*res_code
);
192 canonicalized
= true;
195 code_helper res_code2
;
196 tree res_ops2
[3] = {};
197 if (gimple_simplify (&res_code2
, res_ops2
, seq
, valueize
,
198 *res_code
, type
, res_ops
[0], res_ops
[1]))
200 *res_code
= res_code2
;
201 res_ops
[0] = res_ops2
[0];
202 res_ops
[1] = res_ops2
[1];
203 res_ops
[2] = res_ops2
[2];
207 return canonicalized
;
210 /* Helper that matches and simplifies the toplevel result from
211 a gimple_simplify run (where we don't want to build
212 a stmt in case it's used in in-place folding). Replaces
213 *RES_CODE and *RES_OPS with a simplified and/or canonicalized
214 result and returns whether any change was made. */
217 gimple_resimplify3 (gimple_seq
*seq
,
218 code_helper
*res_code
, tree type
, tree
*res_ops
,
219 tree (*valueize
)(tree
))
221 if (constant_for_folding (res_ops
[0]) && constant_for_folding (res_ops
[1])
222 && constant_for_folding (res_ops
[2]))
224 tree tem
= NULL_TREE
;
225 if (res_code
->is_tree_code ())
226 tem
= fold_ternary
/*_to_constant*/ (*res_code
, type
, res_ops
[0],
227 res_ops
[1], res_ops
[2]);
230 tree decl
= builtin_decl_implicit (*res_code
);
233 tem
= fold_builtin_n (UNKNOWN_LOCATION
, decl
, res_ops
, 3, false);
236 /* fold_builtin_n wraps the result inside a NOP_EXPR. */
238 tem
= fold_convert (type
, tem
);
243 && CONSTANT_CLASS_P (tem
))
246 res_ops
[1] = NULL_TREE
;
247 res_ops
[2] = NULL_TREE
;
248 *res_code
= TREE_CODE (res_ops
[0]);
253 /* Canonicalize operand order. */
254 bool canonicalized
= false;
255 if (res_code
->is_tree_code ()
256 && commutative_ternary_tree_code (*res_code
)
257 && tree_swap_operands_p (res_ops
[0], res_ops
[1], false))
259 tree tem
= res_ops
[0];
260 res_ops
[0] = res_ops
[1];
262 canonicalized
= true;
265 code_helper res_code2
;
266 tree res_ops2
[3] = {};
267 if (gimple_simplify (&res_code2
, res_ops2
, seq
, valueize
,
269 res_ops
[0], res_ops
[1], res_ops
[2]))
271 *res_code
= res_code2
;
272 res_ops
[0] = res_ops2
[0];
273 res_ops
[1] = res_ops2
[1];
274 res_ops
[2] = res_ops2
[2];
278 return canonicalized
;
282 /* If in GIMPLE expressions with CODE go as single-rhs build
283 a GENERIC tree for that expression into *OP0. */
286 maybe_build_generic_op (enum tree_code code
, tree type
,
287 tree
*op0
, tree op1
, tree op2
)
293 case VIEW_CONVERT_EXPR
:
294 *op0
= build1 (code
, type
, *op0
);
297 *op0
= build3 (code
, type
, *op0
, op1
, op2
);
303 /* Push the exploded expression described by RCODE, TYPE and OPS
304 as a statement to SEQ if necessary and return a gimple value
305 denoting the value of the expression. If RES is not NULL
306 then the result will be always RES and even gimple values are
310 maybe_push_res_to_seq (code_helper rcode
, tree type
, tree
*ops
,
311 gimple_seq
*seq
, tree res
)
313 if (rcode
.is_tree_code ())
316 && (TREE_CODE_LENGTH ((tree_code
) rcode
) == 0
317 || ((tree_code
) rcode
) == ADDR_EXPR
)
318 && is_gimple_val (ops
[0]))
322 /* Play safe and do not allow abnormals to be mentioned in
323 newly created statements. */
324 if ((TREE_CODE (ops
[0]) == SSA_NAME
325 && SSA_NAME_OCCURS_IN_ABNORMAL_PHI (ops
[0]))
327 && TREE_CODE (ops
[1]) == SSA_NAME
328 && SSA_NAME_OCCURS_IN_ABNORMAL_PHI (ops
[1]))
330 && TREE_CODE (ops
[2]) == SSA_NAME
331 && SSA_NAME_OCCURS_IN_ABNORMAL_PHI (ops
[2])))
334 res
= make_ssa_name (type
, NULL
);
335 maybe_build_generic_op (rcode
, type
, &ops
[0], ops
[1], ops
[2]);
336 gimple new_stmt
= gimple_build_assign_with_ops (rcode
, res
,
337 ops
[0], ops
[1], ops
[2]);
338 gimple_seq_add_stmt_without_update (seq
, new_stmt
);
345 tree decl
= builtin_decl_implicit (rcode
);
348 unsigned nargs
= type_num_arguments (TREE_TYPE (decl
));
349 gcc_assert (nargs
<= 3);
350 /* Play safe and do not allow abnormals to be mentioned in
351 newly created statements. */
352 if ((TREE_CODE (ops
[0]) == SSA_NAME
353 && SSA_NAME_OCCURS_IN_ABNORMAL_PHI (ops
[0]))
355 && TREE_CODE (ops
[1]) == SSA_NAME
356 && SSA_NAME_OCCURS_IN_ABNORMAL_PHI (ops
[1]))
358 && TREE_CODE (ops
[2]) == SSA_NAME
359 && SSA_NAME_OCCURS_IN_ABNORMAL_PHI (ops
[2])))
362 res
= make_ssa_name (type
, NULL
);
363 gimple new_stmt
= gimple_build_call (decl
, nargs
, ops
[0], ops
[1], ops
[2]);
364 gimple_call_set_lhs (new_stmt
, res
);
365 gimple_seq_add_stmt_without_update (seq
, new_stmt
);
371 /* Public API overloads follow for operation being tree_code or
372 built_in_function and for one to three operands or arguments.
373 They return NULL_TREE if nothing could be simplified or
374 the resulting simplified value with parts pushed to SEQ.
375 If SEQ is NULL then if the simplification needs to create
376 new stmts it will fail. If VALUEIZE is non-NULL then all
377 SSA names will be valueized using that hook prior to
378 applying simplifications. */
383 gimple_simplify (enum tree_code code
, tree type
,
385 gimple_seq
*seq
, tree (*valueize
)(tree
))
387 if (constant_for_folding (op0
))
389 tree res
= fold_unary_to_constant (code
, type
, op0
);
391 && CONSTANT_CLASS_P (res
))
397 if (!gimple_simplify (&rcode
, ops
, seq
, valueize
,
400 return maybe_push_res_to_seq (rcode
, type
, ops
, seq
);
406 gimple_simplify (enum tree_code code
, tree type
,
408 gimple_seq
*seq
, tree (*valueize
)(tree
))
410 if (constant_for_folding (op0
) && constant_for_folding (op1
))
412 tree res
= fold_binary_to_constant (code
, type
, op0
, op1
);
414 && CONSTANT_CLASS_P (res
))
418 /* Canonicalize operand order both for matching and fallback stmt
420 if ((commutative_tree_code (code
)
421 || TREE_CODE_CLASS (code
) == tcc_comparison
)
422 && tree_swap_operands_p (op0
, op1
, false))
427 if (TREE_CODE_CLASS (code
) == tcc_comparison
)
428 code
= swap_tree_comparison (code
);
433 if (!gimple_simplify (&rcode
, ops
, seq
, valueize
,
434 code
, type
, op0
, op1
))
436 return maybe_push_res_to_seq (rcode
, type
, ops
, seq
);
442 gimple_simplify (enum tree_code code
, tree type
,
443 tree op0
, tree op1
, tree op2
,
444 gimple_seq
*seq
, tree (*valueize
)(tree
))
446 if (constant_for_folding (op0
) && constant_for_folding (op1
)
447 && constant_for_folding (op2
))
449 tree res
= fold_ternary
/*_to_constant */ (code
, type
, op0
, op1
, op2
);
451 && CONSTANT_CLASS_P (res
))
455 /* Canonicalize operand order both for matching and fallback stmt
457 if (commutative_ternary_tree_code (code
)
458 && tree_swap_operands_p (op0
, op1
, false))
467 if (!gimple_simplify (&rcode
, ops
, seq
, valueize
,
468 code
, type
, op0
, op1
, op2
))
470 return maybe_push_res_to_seq (rcode
, type
, ops
, seq
);
473 /* Builtin function with one argument. */
476 gimple_simplify (enum built_in_function fn
, tree type
,
478 gimple_seq
*seq
, tree (*valueize
)(tree
))
480 if (constant_for_folding (arg0
))
482 tree decl
= builtin_decl_implicit (fn
);
485 tree res
= fold_builtin_n (UNKNOWN_LOCATION
, decl
, &arg0
, 1, false);
488 /* fold_builtin_n wraps the result inside a NOP_EXPR. */
490 res
= fold_convert (type
, res
);
491 if (CONSTANT_CLASS_P (res
))
499 if (!gimple_simplify (&rcode
, ops
, seq
, valueize
,
502 return maybe_push_res_to_seq (rcode
, type
, ops
, seq
);
505 /* Builtin function with two arguments. */
508 gimple_simplify (enum built_in_function fn
, tree type
,
509 tree arg0
, tree arg1
,
510 gimple_seq
*seq
, tree (*valueize
)(tree
))
512 if (constant_for_folding (arg0
)
513 && constant_for_folding (arg1
))
515 tree decl
= builtin_decl_implicit (fn
);
521 tree res
= fold_builtin_n (UNKNOWN_LOCATION
, decl
, args
, 2, false);
524 /* fold_builtin_n wraps the result inside a NOP_EXPR. */
526 res
= fold_convert (type
, res
);
527 if (CONSTANT_CLASS_P (res
))
535 if (!gimple_simplify (&rcode
, ops
, seq
, valueize
,
536 fn
, type
, arg0
, arg1
))
538 return maybe_push_res_to_seq (rcode
, type
, ops
, seq
);
541 /* Builtin function with three arguments. */
544 gimple_simplify (enum built_in_function fn
, tree type
,
545 tree arg0
, tree arg1
, tree arg2
,
546 gimple_seq
*seq
, tree (*valueize
)(tree
))
548 if (constant_for_folding (arg0
)
549 && constant_for_folding (arg1
)
550 && constant_for_folding (arg2
))
552 tree decl
= builtin_decl_implicit (fn
);
559 tree res
= fold_builtin_n (UNKNOWN_LOCATION
, decl
, args
, 3, false);
562 /* fold_builtin_n wraps the result inside a NOP_EXPR. */
564 res
= fold_convert (type
, res
);
565 if (CONSTANT_CLASS_P (res
))
573 if (!gimple_simplify (&rcode
, ops
, seq
, valueize
,
574 fn
, type
, arg0
, arg1
, arg2
))
576 return maybe_push_res_to_seq (rcode
, type
, ops
, seq
);
580 /* The main STMT based simplification entry. It is used by the fold_stmt
581 and the fold_stmt_to_constant APIs. */
584 gimple_simplify (gimple stmt
,
585 code_helper
*rcode
, tree
*ops
,
586 gimple_seq
*seq
, tree (*valueize
)(tree
))
588 switch (gimple_code (stmt
))
592 enum tree_code code
= gimple_assign_rhs_code (stmt
);
593 tree type
= TREE_TYPE (gimple_assign_lhs (stmt
));
594 switch (gimple_assign_rhs_class (stmt
))
596 case GIMPLE_SINGLE_RHS
:
597 if (code
== REALPART_EXPR
598 || code
== IMAGPART_EXPR
599 || code
== VIEW_CONVERT_EXPR
)
601 tree op0
= TREE_OPERAND (gimple_assign_rhs1 (stmt
), 0);
602 if (valueize
&& TREE_CODE (op0
) == SSA_NAME
)
604 tree tem
= valueize (op0
);
610 return gimple_resimplify1 (seq
, rcode
, type
, ops
, valueize
);
612 else if (code
== BIT_FIELD_REF
)
614 tree rhs1
= gimple_assign_rhs1 (stmt
);
615 tree op0
= TREE_OPERAND (rhs1
, 0);
616 if (valueize
&& TREE_CODE (op0
) == SSA_NAME
)
618 tree tem
= valueize (op0
);
624 ops
[1] = TREE_OPERAND (rhs1
, 1);
625 ops
[2] = TREE_OPERAND (rhs1
, 2);
626 return gimple_resimplify3 (seq
, rcode
, type
, ops
, valueize
);
628 else if (code
== SSA_NAME
631 tree op0
= gimple_assign_rhs1 (stmt
);
632 tree valueized
= valueize (op0
);
633 if (!valueized
|| op0
== valueized
)
636 *rcode
= TREE_CODE (op0
);
640 case GIMPLE_UNARY_RHS
:
642 tree rhs1
= gimple_assign_rhs1 (stmt
);
643 if (valueize
&& TREE_CODE (rhs1
) == SSA_NAME
)
645 tree tem
= valueize (rhs1
);
651 return gimple_resimplify1 (seq
, rcode
, type
, ops
, valueize
);
653 case GIMPLE_BINARY_RHS
:
655 tree rhs1
= gimple_assign_rhs1 (stmt
);
656 if (valueize
&& TREE_CODE (rhs1
) == SSA_NAME
)
658 tree tem
= valueize (rhs1
);
662 tree rhs2
= gimple_assign_rhs2 (stmt
);
663 if (valueize
&& TREE_CODE (rhs2
) == SSA_NAME
)
665 tree tem
= valueize (rhs2
);
672 return gimple_resimplify2 (seq
, rcode
, type
, ops
, valueize
);
674 case GIMPLE_TERNARY_RHS
:
676 tree rhs1
= gimple_assign_rhs1 (stmt
);
677 if (valueize
&& TREE_CODE (rhs1
) == SSA_NAME
)
679 tree tem
= valueize (rhs1
);
683 tree rhs2
= gimple_assign_rhs2 (stmt
);
684 if (valueize
&& TREE_CODE (rhs2
) == SSA_NAME
)
686 tree tem
= valueize (rhs2
);
690 tree rhs3
= gimple_assign_rhs3 (stmt
);
691 if (valueize
&& TREE_CODE (rhs3
) == SSA_NAME
)
693 tree tem
= valueize (rhs3
);
701 return gimple_resimplify3 (seq
, rcode
, type
, ops
, valueize
);
710 /* ??? This way we can't simplify calls with side-effects. */
711 if (gimple_call_lhs (stmt
) != NULL_TREE
)
713 tree fn
= gimple_call_fn (stmt
);
714 /* ??? Internal function support missing. */
717 if (valueize
&& TREE_CODE (fn
) == SSA_NAME
)
719 tree tem
= valueize (fn
);
724 || TREE_CODE (fn
) != ADDR_EXPR
725 || TREE_CODE (TREE_OPERAND (fn
, 0)) != FUNCTION_DECL
726 || DECL_BUILT_IN_CLASS (TREE_OPERAND (fn
, 0)) != BUILT_IN_NORMAL
727 || !builtin_decl_implicit (DECL_FUNCTION_CODE (TREE_OPERAND (fn
, 0)))
728 || !gimple_builtin_call_types_compatible_p (stmt
,
729 TREE_OPERAND (fn
, 0)))
732 tree decl
= TREE_OPERAND (fn
, 0);
733 tree type
= TREE_TYPE (gimple_call_lhs (stmt
));
734 switch (gimple_call_num_args (stmt
))
738 tree arg1
= gimple_call_arg (stmt
, 0);
739 if (valueize
&& TREE_CODE (arg1
) == SSA_NAME
)
741 tree tem
= valueize (arg1
);
745 *rcode
= DECL_FUNCTION_CODE (decl
);
747 return gimple_resimplify1 (seq
, rcode
, type
, ops
, valueize
);
751 tree arg1
= gimple_call_arg (stmt
, 0);
752 if (valueize
&& TREE_CODE (arg1
) == SSA_NAME
)
754 tree tem
= valueize (arg1
);
758 tree arg2
= gimple_call_arg (stmt
, 1);
759 if (valueize
&& TREE_CODE (arg2
) == SSA_NAME
)
761 tree tem
= valueize (arg2
);
765 *rcode
= DECL_FUNCTION_CODE (decl
);
768 return gimple_resimplify2 (seq
, rcode
, type
, ops
, valueize
);
772 tree arg1
= gimple_call_arg (stmt
, 0);
773 if (valueize
&& TREE_CODE (arg1
) == SSA_NAME
)
775 tree tem
= valueize (arg1
);
779 tree arg2
= gimple_call_arg (stmt
, 1);
780 if (valueize
&& TREE_CODE (arg2
) == SSA_NAME
)
782 tree tem
= valueize (arg2
);
786 tree arg3
= gimple_call_arg (stmt
, 2);
787 if (valueize
&& TREE_CODE (arg3
) == SSA_NAME
)
789 tree tem
= valueize (arg3
);
793 *rcode
= DECL_FUNCTION_CODE (decl
);
797 return gimple_resimplify3 (seq
, rcode
, type
, ops
, valueize
);
807 tree lhs
= gimple_cond_lhs (stmt
);
808 if (valueize
&& TREE_CODE (lhs
) == SSA_NAME
)
810 tree tem
= valueize (lhs
);
814 tree rhs
= gimple_cond_rhs (stmt
);
815 if (valueize
&& TREE_CODE (rhs
) == SSA_NAME
)
817 tree tem
= valueize (rhs
);
821 *rcode
= gimple_cond_code (stmt
);
824 return gimple_resimplify2 (seq
, rcode
, boolean_type_node
, ops
, valueize
);
835 /* Helper for the autogenerated code, valueize OP. */
838 do_valueize (tree (*valueize
)(tree
), tree op
)
840 if (valueize
&& TREE_CODE (op
) == SSA_NAME
)
841 return valueize (op
);