* inclhack.def (aix_complex): New fix.
[official-gcc.git] / gcc / ipa-prop.c
blob2842088d8f1b9d075c6f9456170edab6a06b50c7
1 /* Interprocedural analyses.
2 Copyright (C) 2005, 2007, 2008, 2009 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
9 version.
11 GCC is distributed in the hope that it will be useful, but WITHOUT ANY
12 WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
14 for more details.
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/>. */
20 #include "config.h"
21 #include "system.h"
22 #include "coretypes.h"
23 #include "tree.h"
24 #include "langhooks.h"
25 #include "ggc.h"
26 #include "target.h"
27 #include "cgraph.h"
28 #include "ipa-prop.h"
29 #include "tree-flow.h"
30 #include "tree-pass.h"
31 #include "tree-inline.h"
32 #include "flags.h"
33 #include "timevar.h"
34 #include "flags.h"
35 #include "diagnostic.h"
37 /* Vector where the parameter infos are actually stored. */
38 VEC (ipa_node_params_t, heap) *ipa_node_params_vector;
39 /* Vector where the parameter infos are actually stored. */
40 VEC (ipa_edge_args_t, heap) *ipa_edge_args_vector;
42 /* Holders of ipa cgraph hooks: */
43 static struct cgraph_edge_hook_list *edge_removal_hook_holder;
44 static struct cgraph_node_hook_list *node_removal_hook_holder;
45 static struct cgraph_2edge_hook_list *edge_duplication_hook_holder;
46 static struct cgraph_2node_hook_list *node_duplication_hook_holder;
48 /* Add cgraph NODE described by INFO to the worklist WL regardless of whether
49 it is in one or not. It should almost never be used directly, as opposed to
50 ipa_push_func_to_list. */
52 void
53 ipa_push_func_to_list_1 (struct ipa_func_list **wl,
54 struct cgraph_node *node,
55 struct ipa_node_params *info)
57 struct ipa_func_list *temp;
59 info->node_enqueued = 1;
60 temp = XCNEW (struct ipa_func_list);
61 temp->node = node;
62 temp->next = *wl;
63 *wl = temp;
66 /* Initialize worklist to contain all functions. */
68 struct ipa_func_list *
69 ipa_init_func_list (void)
71 struct cgraph_node *node;
72 struct ipa_func_list * wl;
74 wl = NULL;
75 for (node = cgraph_nodes; node; node = node->next)
76 if (node->analyzed)
78 struct ipa_node_params *info = IPA_NODE_REF (node);
79 /* Unreachable nodes should have been eliminated before ipcp and
80 inlining. */
81 gcc_assert (node->needed || node->reachable);
82 ipa_push_func_to_list_1 (&wl, node, info);
85 return wl;
88 /* Remove a function from the worklist WL and return it. */
90 struct cgraph_node *
91 ipa_pop_func_from_list (struct ipa_func_list **wl)
93 struct ipa_node_params *info;
94 struct ipa_func_list *first;
95 struct cgraph_node *node;
97 first = *wl;
98 *wl = (*wl)->next;
99 node = first->node;
100 free (first);
102 info = IPA_NODE_REF (node);
103 info->node_enqueued = 0;
104 return node;
107 /* Return index of the formal whose tree is PTREE in function which corresponds
108 to INFO. */
110 static int
111 ipa_get_param_decl_index (struct ipa_node_params *info, tree ptree)
113 int i, count;
115 count = ipa_get_param_count (info);
116 for (i = 0; i < count; i++)
117 if (ipa_get_param(info, i) == ptree)
118 return i;
120 return -1;
123 /* Populate the param_decl field in parameter descriptors of INFO that
124 corresponds to NODE. */
126 static void
127 ipa_populate_param_decls (struct cgraph_node *node,
128 struct ipa_node_params *info)
130 tree fndecl;
131 tree fnargs;
132 tree parm;
133 int param_num;
135 fndecl = node->decl;
136 fnargs = DECL_ARGUMENTS (fndecl);
137 param_num = 0;
138 for (parm = fnargs; parm; parm = TREE_CHAIN (parm))
140 info->params[param_num].decl = parm;
141 param_num++;
145 /* Return how many formal parameters FNDECL has. */
147 static inline int
148 count_formal_params_1 (tree fndecl)
150 tree parm;
151 int count = 0;
153 for (parm = DECL_ARGUMENTS (fndecl); parm; parm = TREE_CHAIN (parm))
154 count++;
156 return count;
159 /* Count number of formal parameters in NOTE. Store the result to the
160 appropriate field of INFO. */
162 static void
163 ipa_count_formal_params (struct cgraph_node *node,
164 struct ipa_node_params *info)
166 int param_num;
168 param_num = count_formal_params_1 (node->decl);
169 ipa_set_param_count (info, param_num);
172 /* Initialize the ipa_node_params structure associated with NODE by counting
173 the function parameters, creating the descriptors and populating their
174 param_decls. */
176 void
177 ipa_initialize_node_params (struct cgraph_node *node)
179 struct ipa_node_params *info = IPA_NODE_REF (node);
181 if (!info->params)
183 ipa_count_formal_params (node, info);
184 info->params = XCNEWVEC (struct ipa_param_descriptor,
185 ipa_get_param_count (info));
186 ipa_populate_param_decls (node, info);
190 /* Callback of walk_stmt_load_store_addr_ops for the visit_store and visit_addr
191 parameters. If OP is a parameter declaration, mark it as modified in the
192 info structure passed in DATA. */
194 static bool
195 visit_store_addr_for_mod_analysis (gimple stmt ATTRIBUTE_UNUSED,
196 tree op, void *data)
198 struct ipa_node_params *info = (struct ipa_node_params *) data;
200 if (TREE_CODE (op) == PARM_DECL)
202 int index = ipa_get_param_decl_index (info, op);
203 gcc_assert (index >= 0);
204 info->params[index].modified = true;
207 return false;
210 /* Compute which formal parameters of function associated with NODE are locally
211 modified or their address is taken. Note that this does not apply on
212 parameters with SSA names but those can and should be analyzed
213 differently. */
215 void
216 ipa_detect_param_modifications (struct cgraph_node *node)
218 tree decl = node->decl;
219 basic_block bb;
220 struct function *func;
221 gimple_stmt_iterator gsi;
222 struct ipa_node_params *info = IPA_NODE_REF (node);
224 if (ipa_get_param_count (info) == 0 || info->modification_analysis_done)
225 return;
227 func = DECL_STRUCT_FUNCTION (decl);
228 FOR_EACH_BB_FN (bb, func)
229 for (gsi = gsi_start_bb (bb); !gsi_end_p (gsi); gsi_next (&gsi))
230 walk_stmt_load_store_addr_ops (gsi_stmt (gsi), info, NULL,
231 visit_store_addr_for_mod_analysis,
232 visit_store_addr_for_mod_analysis);
234 info->modification_analysis_done = 1;
237 /* Count number of arguments callsite CS has and store it in
238 ipa_edge_args structure corresponding to this callsite. */
240 void
241 ipa_count_arguments (struct cgraph_edge *cs)
243 gimple stmt;
244 int arg_num;
246 stmt = cs->call_stmt;
247 gcc_assert (is_gimple_call (stmt));
248 arg_num = gimple_call_num_args (stmt);
249 if (VEC_length (ipa_edge_args_t, ipa_edge_args_vector)
250 <= (unsigned) cgraph_edge_max_uid)
251 VEC_safe_grow_cleared (ipa_edge_args_t, heap,
252 ipa_edge_args_vector, cgraph_edge_max_uid + 1);
253 ipa_set_cs_argument_count (IPA_EDGE_REF (cs), arg_num);
256 /* Print the jump functions of all arguments on all call graph edges going from
257 NODE to file F. */
259 void
260 ipa_print_node_jump_functions (FILE *f, struct cgraph_node *node)
262 int i, count;
263 struct cgraph_edge *cs;
264 struct ipa_jump_func *jump_func;
265 enum jump_func_type type;
267 fprintf (f, " Jump functions of caller %s:\n", cgraph_node_name (node));
268 for (cs = node->callees; cs; cs = cs->next_callee)
270 if (!ipa_edge_args_info_available_for_edge_p (cs))
271 continue;
273 fprintf (f, " callsite %s ", cgraph_node_name (node));
274 fprintf (f, "-> %s :: \n", cgraph_node_name (cs->callee));
276 count = ipa_get_cs_argument_count (IPA_EDGE_REF (cs));
277 for (i = 0; i < count; i++)
279 jump_func = ipa_get_ith_jump_func (IPA_EDGE_REF (cs), i);
280 type = jump_func->type;
282 fprintf (f, " param %d: ", i);
283 if (type == IPA_JF_UNKNOWN)
284 fprintf (f, "UNKNOWN\n");
285 else if (type == IPA_JF_CONST)
287 tree val = jump_func->value.constant;
288 fprintf (f, "CONST: ");
289 print_generic_expr (f, val, 0);
290 fprintf (f, "\n");
292 else if (type == IPA_JF_CONST_MEMBER_PTR)
294 fprintf (f, "CONST MEMBER PTR: ");
295 print_generic_expr (f, jump_func->value.member_cst.pfn, 0);
296 fprintf (f, ", ");
297 print_generic_expr (f, jump_func->value.member_cst.delta, 0);
298 fprintf (f, "\n");
300 else if (type == IPA_JF_PASS_THROUGH)
302 fprintf (f, "PASS THROUGH: ");
303 fprintf (f, "%d, op %s ",
304 jump_func->value.pass_through.formal_id,
305 tree_code_name[(int)
306 jump_func->value.pass_through.operation]);
307 if (jump_func->value.pass_through.operation != NOP_EXPR)
308 print_generic_expr (dump_file,
309 jump_func->value.pass_through.operand, 0);
310 fprintf (dump_file, "\n");
312 else if (type == IPA_JF_ANCESTOR)
314 fprintf (f, "ANCESTOR: ");
315 fprintf (f, "%d, offset "HOST_WIDE_INT_PRINT_DEC"\n",
316 jump_func->value.ancestor.formal_id,
317 jump_func->value.ancestor.offset);
323 /* Print ipa_jump_func data structures of all nodes in the call graph to F. */
325 void
326 ipa_print_all_jump_functions (FILE *f)
328 struct cgraph_node *node;
330 fprintf (f, "\nJump functions:\n");
331 for (node = cgraph_nodes; node; node = node->next)
333 ipa_print_node_jump_functions (f, node);
337 /* Determine whether passing ssa name NAME constitutes a polynomial
338 pass-through function or getting an address of an acestor and if so, write
339 such a jump function to JFUNC. INFO describes the caller. */
341 static void
342 compute_complex_pass_through (struct ipa_node_params *info,
343 struct ipa_jump_func *jfunc,
344 tree name)
346 HOST_WIDE_INT offset, size, max_size;
347 tree op1, op2, type;
348 int index;
349 gimple stmt = SSA_NAME_DEF_STMT (name);
351 if (!is_gimple_assign (stmt))
352 return;
353 op1 = gimple_assign_rhs1 (stmt);
354 op2 = gimple_assign_rhs2 (stmt);
356 if (op2)
358 if (TREE_CODE (op1) != SSA_NAME
359 || !SSA_NAME_IS_DEFAULT_DEF (op1)
360 || !is_gimple_ip_invariant (op2))
361 return;
363 index = ipa_get_param_decl_index (info, SSA_NAME_VAR (op1));
364 if (index >= 0)
366 jfunc->type = IPA_JF_PASS_THROUGH;
367 jfunc->value.pass_through.formal_id = index;
368 jfunc->value.pass_through.operation = gimple_assign_rhs_code (stmt);
369 jfunc->value.pass_through.operand = op2;
371 return;
374 if (TREE_CODE (op1) != ADDR_EXPR)
375 return;
376 op1 = TREE_OPERAND (op1, 0);
377 type = TREE_TYPE (op1);
379 op1 = get_ref_base_and_extent (op1, &offset, &size, &max_size);
380 if (TREE_CODE (op1) != INDIRECT_REF)
381 return;
382 op1 = TREE_OPERAND (op1, 0);
383 if (TREE_CODE (op1) != SSA_NAME
384 || !SSA_NAME_IS_DEFAULT_DEF (op1))
385 return;
387 index = ipa_get_param_decl_index (info, SSA_NAME_VAR (op1));
388 if (index >= 0)
390 jfunc->type = IPA_JF_ANCESTOR;
391 jfunc->value.ancestor.formal_id = index;
392 jfunc->value.ancestor.offset = offset;
393 jfunc->value.ancestor.type = type;
398 /* Determine the jump functions of scalar arguments. Scalar means SSA names
399 and constants of a number of selected types. INFO is the ipa_node_params
400 structure associated with the caller, FUNCTIONS is a pointer to an array of
401 jump function structures associated with CALL which is the call statement
402 being examined.*/
404 static void
405 compute_scalar_jump_functions (struct ipa_node_params *info,
406 struct ipa_jump_func *functions,
407 gimple call)
409 tree arg;
410 unsigned num = 0;
412 for (num = 0; num < gimple_call_num_args (call); num++)
414 arg = gimple_call_arg (call, num);
416 if (is_gimple_ip_invariant (arg))
418 functions[num].type = IPA_JF_CONST;
419 functions[num].value.constant = arg;
421 else if (TREE_CODE (arg) == SSA_NAME)
423 if (SSA_NAME_IS_DEFAULT_DEF (arg))
425 int index = ipa_get_param_decl_index (info, SSA_NAME_VAR (arg));
427 if (index >= 0)
429 functions[num].type = IPA_JF_PASS_THROUGH;
430 functions[num].value.pass_through.formal_id = index;
431 functions[num].value.pass_through.operation = NOP_EXPR;
434 else
435 compute_complex_pass_through (info, &functions[num], arg);
440 /* Inspect the given TYPE and return true iff it has the same structure (the
441 same number of fields of the same types) as a C++ member pointer. If
442 METHOD_PTR and DELTA are non-NULL, store the trees representing the
443 corresponding fields there. */
445 static bool
446 type_like_member_ptr_p (tree type, tree *method_ptr, tree *delta)
448 tree fld;
450 if (TREE_CODE (type) != RECORD_TYPE)
451 return false;
453 fld = TYPE_FIELDS (type);
454 if (!fld || !POINTER_TYPE_P (TREE_TYPE (fld))
455 || TREE_CODE (TREE_TYPE (TREE_TYPE (fld))) != METHOD_TYPE)
456 return false;
458 if (method_ptr)
459 *method_ptr = fld;
461 fld = TREE_CHAIN (fld);
462 if (!fld || INTEGRAL_TYPE_P (fld))
463 return false;
464 if (delta)
465 *delta = fld;
467 if (TREE_CHAIN (fld))
468 return false;
470 return true;
473 /* Go through arguments of the CALL and for every one that looks like a member
474 pointer, check whether it can be safely declared pass-through and if so,
475 mark that to the corresponding item of jump FUNCTIONS. Return true iff
476 there are non-pass-through member pointers within the arguments. INFO
477 describes formal parameters of the caller. */
479 static bool
480 compute_pass_through_member_ptrs (struct ipa_node_params *info,
481 struct ipa_jump_func *functions,
482 gimple call)
484 bool undecided_members = false;
485 unsigned num;
486 tree arg;
488 for (num = 0; num < gimple_call_num_args (call); num++)
490 arg = gimple_call_arg (call, num);
492 if (type_like_member_ptr_p (TREE_TYPE (arg), NULL, NULL))
494 if (TREE_CODE (arg) == PARM_DECL)
496 int index = ipa_get_param_decl_index (info, arg);
498 gcc_assert (index >=0);
499 if (!ipa_is_param_modified (info, index))
501 functions[num].type = IPA_JF_PASS_THROUGH;
502 functions[num].value.pass_through.formal_id = index;
503 functions[num].value.pass_through.operation = NOP_EXPR;
505 else
506 undecided_members = true;
508 else
509 undecided_members = true;
513 return undecided_members;
516 /* Simple function filling in a member pointer constant jump function (with PFN
517 and DELTA as the constant value) into JFUNC. */
519 static void
520 fill_member_ptr_cst_jump_function (struct ipa_jump_func *jfunc,
521 tree pfn, tree delta)
523 jfunc->type = IPA_JF_CONST_MEMBER_PTR;
524 jfunc->value.member_cst.pfn = pfn;
525 jfunc->value.member_cst.delta = delta;
528 /* If RHS is an SSA_NAMe and it is defined by a simple copy assign statement,
529 return the rhs of its defining statement. */
531 static inline tree
532 get_ssa_def_if_simple_copy (tree rhs)
534 while (TREE_CODE (rhs) == SSA_NAME && !SSA_NAME_IS_DEFAULT_DEF (rhs))
536 gimple def_stmt = SSA_NAME_DEF_STMT (rhs);
538 if (gimple_assign_single_p (def_stmt))
539 rhs = gimple_assign_rhs1 (def_stmt);
540 else
541 break;
543 return rhs;
546 /* Traverse statements from CALL backwards, scanning whether the argument ARG
547 which is a member pointer is filled in with constant values. If it is, fill
548 the jump function JFUNC in appropriately. METHOD_FIELD and DELTA_FIELD are
549 fields of the record type of the member pointer. To give an example, we
550 look for a pattern looking like the following:
552 D.2515.__pfn ={v} printStuff;
553 D.2515.__delta ={v} 0;
554 i_1 = doprinting (D.2515); */
556 static void
557 determine_cst_member_ptr (gimple call, tree arg, tree method_field,
558 tree delta_field, struct ipa_jump_func *jfunc)
560 gimple_stmt_iterator gsi;
561 tree method = NULL_TREE;
562 tree delta = NULL_TREE;
564 gsi = gsi_for_stmt (call);
566 gsi_prev (&gsi);
567 for (; !gsi_end_p (gsi); gsi_prev (&gsi))
569 gimple stmt = gsi_stmt (gsi);
570 tree lhs, rhs, fld;
572 if (!gimple_assign_single_p (stmt))
573 return;
575 lhs = gimple_assign_lhs (stmt);
576 rhs = gimple_assign_rhs1 (stmt);
578 if (TREE_CODE (lhs) != COMPONENT_REF
579 || TREE_OPERAND (lhs, 0) != arg)
580 continue;
582 fld = TREE_OPERAND (lhs, 1);
583 if (!method && fld == method_field)
585 rhs = get_ssa_def_if_simple_copy (rhs);
586 if (TREE_CODE (rhs) == ADDR_EXPR
587 && TREE_CODE (TREE_OPERAND (rhs, 0)) == FUNCTION_DECL
588 && TREE_CODE (TREE_TYPE (TREE_OPERAND (rhs, 0))) == METHOD_TYPE)
590 method = TREE_OPERAND (rhs, 0);
591 if (delta)
593 fill_member_ptr_cst_jump_function (jfunc, rhs, delta);
594 return;
597 else
598 return;
601 if (!delta && fld == delta_field)
603 rhs = get_ssa_def_if_simple_copy (rhs);
604 if (TREE_CODE (rhs) == INTEGER_CST)
606 delta = rhs;
607 if (method)
609 fill_member_ptr_cst_jump_function (jfunc, rhs, delta);
610 return;
613 else
614 return;
618 return;
621 /* Go through the arguments of the CALL and for every member pointer within
622 tries determine whether it is a constant. If it is, create a corresponding
623 constant jump function in FUNCTIONS which is an array of jump functions
624 associated with the call. */
626 static void
627 compute_cst_member_ptr_arguments (struct ipa_jump_func *functions,
628 gimple call)
630 unsigned num;
631 tree arg, method_field, delta_field;
633 for (num = 0; num < gimple_call_num_args (call); num++)
635 arg = gimple_call_arg (call, num);
637 if (functions[num].type == IPA_JF_UNKNOWN
638 && type_like_member_ptr_p (TREE_TYPE (arg), &method_field,
639 &delta_field))
640 determine_cst_member_ptr (call, arg, method_field, delta_field,
641 &functions[num]);
645 /* Compute jump function for all arguments of callsite CS and insert the
646 information in the jump_functions array in the ipa_edge_args corresponding
647 to this callsite. */
649 void
650 ipa_compute_jump_functions (struct cgraph_edge *cs)
652 struct ipa_node_params *info = IPA_NODE_REF (cs->caller);
653 struct ipa_edge_args *arguments = IPA_EDGE_REF (cs);
654 gimple call;
656 if (ipa_get_cs_argument_count (arguments) == 0 || arguments->jump_functions)
657 return;
658 arguments->jump_functions = XCNEWVEC (struct ipa_jump_func,
659 ipa_get_cs_argument_count (arguments));
661 call = cs->call_stmt;
662 gcc_assert (is_gimple_call (call));
664 /* We will deal with constants and SSA scalars first: */
665 compute_scalar_jump_functions (info, arguments->jump_functions, call);
667 /* Let's check whether there are any potential member pointers and if so,
668 whether we can determine their functions as pass_through. */
669 if (!compute_pass_through_member_ptrs (info, arguments->jump_functions, call))
670 return;
672 /* Finally, let's check whether we actually pass a new constant member
673 pointer here... */
674 compute_cst_member_ptr_arguments (arguments->jump_functions, call);
677 /* If RHS looks like a rhs of a statement loading pfn from a member
678 pointer formal parameter, return the parameter, otherwise return
679 NULL. If USE_DELTA, then we look for a use of the delta field
680 rather than the pfn. */
682 static tree
683 ipa_get_member_ptr_load_param (tree rhs, bool use_delta)
685 tree rec, fld;
686 tree ptr_field;
687 tree delta_field;
689 if (TREE_CODE (rhs) != COMPONENT_REF)
690 return NULL_TREE;
692 rec = TREE_OPERAND (rhs, 0);
693 if (TREE_CODE (rec) != PARM_DECL
694 || !type_like_member_ptr_p (TREE_TYPE (rec), &ptr_field, &delta_field))
695 return NULL_TREE;
697 fld = TREE_OPERAND (rhs, 1);
698 if (use_delta ? (fld == delta_field) : (fld == ptr_field))
699 return rec;
700 else
701 return NULL_TREE;
704 /* If STMT looks like a statement loading a value from a member pointer formal
705 parameter, this function returns that parameter. */
707 static tree
708 ipa_get_stmt_member_ptr_load_param (gimple stmt, bool use_delta)
710 tree rhs;
712 if (!gimple_assign_single_p (stmt))
713 return NULL_TREE;
715 rhs = gimple_assign_rhs1 (stmt);
716 return ipa_get_member_ptr_load_param (rhs, use_delta);
719 /* Returns true iff T is an SSA_NAME defined by a statement. */
721 static bool
722 ipa_is_ssa_with_stmt_def (tree t)
724 if (TREE_CODE (t) == SSA_NAME
725 && !SSA_NAME_IS_DEFAULT_DEF (t))
726 return true;
727 else
728 return false;
731 /* Creates a new note describing a call to a parameter number FORMAL_ID and
732 attaches it to the linked list of INFO. It also sets the called flag of the
733 parameter. STMT is the corresponding call statement. */
735 static void
736 ipa_note_param_call (struct ipa_node_params *info, int formal_id,
737 gimple stmt)
739 struct ipa_param_call_note *note;
740 basic_block bb = gimple_bb (stmt);
742 info->params[formal_id].called = 1;
744 note = XCNEW (struct ipa_param_call_note);
745 note->formal_id = formal_id;
746 note->stmt = stmt;
747 note->count = bb->count;
748 note->frequency = compute_call_stmt_bb_frequency (current_function_decl, bb);
750 note->next = info->param_calls;
751 info->param_calls = note;
753 return;
756 /* Analyze the CALL and examine uses of formal parameters of the caller
757 (described by INFO). Currently it checks whether the call calls a pointer
758 that is a formal parameter and if so, the parameter is marked with the
759 called flag and a note describing the call is created. This is very simple
760 for ordinary pointers represented in SSA but not-so-nice when it comes to
761 member pointers. The ugly part of this function does nothing more than
762 tries to match the pattern of such a call. An example of such a pattern is
763 the gimple dump below, the call is on the last line:
765 <bb 2>:
766 f$__delta_5 = f.__delta;
767 f$__pfn_24 = f.__pfn;
768 D.2496_3 = (int) f$__pfn_24;
769 D.2497_4 = D.2496_3 & 1;
770 if (D.2497_4 != 0)
771 goto <bb 3>;
772 else
773 goto <bb 4>;
775 <bb 3>:
776 D.2500_7 = (unsigned int) f$__delta_5;
777 D.2501_8 = &S + D.2500_7;
778 D.2502_9 = (int (*__vtbl_ptr_type) (void) * *) D.2501_8;
779 D.2503_10 = *D.2502_9;
780 D.2504_12 = f$__pfn_24 + -1;
781 D.2505_13 = (unsigned int) D.2504_12;
782 D.2506_14 = D.2503_10 + D.2505_13;
783 D.2507_15 = *D.2506_14;
784 iftmp.11_16 = (String:: *) D.2507_15;
786 <bb 4>:
787 # iftmp.11_1 = PHI <iftmp.11_16(3), f$__pfn_24(2)>
788 D.2500_19 = (unsigned int) f$__delta_5;
789 D.2508_20 = &S + D.2500_19;
790 D.2493_21 = iftmp.11_1 (D.2508_20, 4);
792 Such patterns are results of simple calls to a member pointer:
794 int doprinting (int (MyString::* f)(int) const)
796 MyString S ("somestring");
798 return (S.*f)(4);
802 static void
803 ipa_analyze_call_uses (struct ipa_node_params *info, gimple call)
805 tree target = gimple_call_fn (call);
806 gimple def;
807 tree var;
808 tree n1, n2;
809 gimple d1, d2;
810 tree rec, rec2, cond;
811 gimple branch;
812 int index;
813 basic_block bb, virt_bb, join;
815 if (TREE_CODE (target) != SSA_NAME)
816 return;
818 var = SSA_NAME_VAR (target);
819 if (SSA_NAME_IS_DEFAULT_DEF (target))
821 /* assuming TREE_CODE (var) == PARM_DECL */
822 index = ipa_get_param_decl_index (info, var);
823 if (index >= 0)
824 ipa_note_param_call (info, index, call);
825 return;
828 /* Now we need to try to match the complex pattern of calling a member
829 pointer. */
831 if (!POINTER_TYPE_P (TREE_TYPE (target))
832 || TREE_CODE (TREE_TYPE (TREE_TYPE (target))) != METHOD_TYPE)
833 return;
835 def = SSA_NAME_DEF_STMT (target);
836 if (gimple_code (def) != GIMPLE_PHI)
837 return;
839 if (gimple_phi_num_args (def) != 2)
840 return;
842 /* First, we need to check whether one of these is a load from a member
843 pointer that is a parameter to this function. */
844 n1 = PHI_ARG_DEF (def, 0);
845 n2 = PHI_ARG_DEF (def, 1);
846 if (!ipa_is_ssa_with_stmt_def (n1) || !ipa_is_ssa_with_stmt_def (n2))
847 return;
848 d1 = SSA_NAME_DEF_STMT (n1);
849 d2 = SSA_NAME_DEF_STMT (n2);
851 if ((rec = ipa_get_stmt_member_ptr_load_param (d1, false)))
853 if (ipa_get_stmt_member_ptr_load_param (d2, false))
854 return;
856 bb = gimple_bb (d1);
857 virt_bb = gimple_bb (d2);
859 else if ((rec = ipa_get_stmt_member_ptr_load_param (d2, false)))
861 bb = gimple_bb (d2);
862 virt_bb = gimple_bb (d1);
864 else
865 return;
867 /* Second, we need to check that the basic blocks are laid out in the way
868 corresponding to the pattern. */
870 join = gimple_bb (def);
871 if (!single_pred_p (virt_bb) || !single_succ_p (virt_bb)
872 || single_pred (virt_bb) != bb
873 || single_succ (virt_bb) != join)
874 return;
876 /* Third, let's see that the branching is done depending on the least
877 significant bit of the pfn. */
879 branch = last_stmt (bb);
880 if (gimple_code (branch) != GIMPLE_COND)
881 return;
883 if (gimple_cond_code (branch) != NE_EXPR
884 || !integer_zerop (gimple_cond_rhs (branch)))
885 return;
887 cond = gimple_cond_lhs (branch);
888 if (!ipa_is_ssa_with_stmt_def (cond))
889 return;
891 def = SSA_NAME_DEF_STMT (cond);
892 if (!is_gimple_assign (def)
893 || gimple_assign_rhs_code (def) != BIT_AND_EXPR
894 || !integer_onep (gimple_assign_rhs2 (def)))
895 return;
897 cond = gimple_assign_rhs1 (def);
898 if (!ipa_is_ssa_with_stmt_def (cond))
899 return;
901 def = SSA_NAME_DEF_STMT (cond);
903 if (is_gimple_assign (def)
904 && CONVERT_EXPR_CODE_P (gimple_assign_rhs_code (def)))
906 cond = gimple_assign_rhs1 (def);
907 if (!ipa_is_ssa_with_stmt_def (cond))
908 return;
909 def = SSA_NAME_DEF_STMT (cond);
912 rec2 = ipa_get_stmt_member_ptr_load_param (def,
913 (TARGET_PTRMEMFUNC_VBIT_LOCATION
914 == ptrmemfunc_vbit_in_delta));
916 if (rec != rec2)
917 return;
919 index = ipa_get_param_decl_index (info, rec);
920 if (index >= 0 && !ipa_is_param_modified (info, index))
921 ipa_note_param_call (info, index, call);
923 return;
926 /* Analyze the statement STMT with respect to formal parameters (described in
927 INFO) and their uses. Currently it only checks whether formal parameters
928 are called. */
930 static void
931 ipa_analyze_stmt_uses (struct ipa_node_params *info, gimple stmt)
933 if (is_gimple_call (stmt))
934 ipa_analyze_call_uses (info, stmt);
937 /* Scan the function body of NODE and inspect the uses of formal parameters.
938 Store the findings in various structures of the associated ipa_node_params
939 structure, such as parameter flags, notes etc. */
941 void
942 ipa_analyze_params_uses (struct cgraph_node *node)
944 tree decl = node->decl;
945 basic_block bb;
946 struct function *func;
947 gimple_stmt_iterator gsi;
948 struct ipa_node_params *info = IPA_NODE_REF (node);
950 if (ipa_get_param_count (info) == 0 || info->uses_analysis_done)
951 return;
953 func = DECL_STRUCT_FUNCTION (decl);
954 FOR_EACH_BB_FN (bb, func)
956 for (gsi = gsi_start_bb (bb); !gsi_end_p (gsi); gsi_next (&gsi))
958 gimple stmt = gsi_stmt (gsi);
959 ipa_analyze_stmt_uses (info, stmt);
963 info->uses_analysis_done = 1;
966 /* Update the jump functions associated with call graph edge E when the call
967 graph edge CS is being inlined, assuming that E->caller is already (possibly
968 indirectly) inlined into CS->callee and that E has not been inlined.
970 We keep pass through functions only if they do not contain any operation.
971 This is sufficient for inlining and greately simplifies things. */
973 static void
974 update_jump_functions_after_inlining (struct cgraph_edge *cs,
975 struct cgraph_edge *e)
977 struct ipa_edge_args *top = IPA_EDGE_REF (cs);
978 struct ipa_edge_args *args = IPA_EDGE_REF (e);
979 int count = ipa_get_cs_argument_count (args);
980 int i;
982 for (i = 0; i < count; i++)
984 struct ipa_jump_func *src, *dst = ipa_get_ith_jump_func (args, i);
986 if (dst->type == IPA_JF_ANCESTOR)
988 dst->type = IPA_JF_UNKNOWN;
989 continue;
992 if (dst->type != IPA_JF_PASS_THROUGH)
993 continue;
995 /* We must check range due to calls with variable number of arguments and
996 we cannot combine jump functions with operations. */
997 if (dst->value.pass_through.operation != NOP_EXPR
998 || (dst->value.pass_through.formal_id
999 >= ipa_get_cs_argument_count (top)))
1001 dst->type = IPA_JF_UNKNOWN;
1002 continue;
1005 src = ipa_get_ith_jump_func (top, dst->value.pass_through.formal_id);
1006 *dst = *src;
1010 /* Print out a debug message to file F that we have discovered that an indirect
1011 call described by NT is in fact a call of a known constant function described
1012 by JFUNC. NODE is the node where the call is. */
1014 static void
1015 print_edge_addition_message (FILE *f, struct ipa_param_call_note *nt,
1016 struct ipa_jump_func *jfunc,
1017 struct cgraph_node *node)
1019 fprintf (f, "ipa-prop: Discovered an indirect call to a known target (");
1020 if (jfunc->type == IPA_JF_CONST_MEMBER_PTR)
1022 print_node_brief (f, "", jfunc->value.member_cst.pfn, 0);
1023 print_node_brief (f, ", ", jfunc->value.member_cst.delta, 0);
1025 else
1026 print_node_brief(f, "", jfunc->value.constant, 0);
1028 fprintf (f, ") in %s: ", cgraph_node_name (node));
1029 print_gimple_stmt (f, nt->stmt, 2, TDF_SLIM);
1032 /* Update the param called notes associated with NODE when CS is being inlined,
1033 assuming NODE is (potentially indirectly) inlined into CS->callee.
1034 Moreover, if the callee is discovered to be constant, create a new cgraph
1035 edge for it. Newly discovered indirect edges will be added to *NEW_EDGES,
1036 unless NEW_EDGES is NULL. Return true iff a new edge(s) were created. */
1038 static bool
1039 update_call_notes_after_inlining (struct cgraph_edge *cs,
1040 struct cgraph_node *node,
1041 VEC (cgraph_edge_p, heap) **new_edges)
1043 struct ipa_node_params *info = IPA_NODE_REF (node);
1044 struct ipa_edge_args *top = IPA_EDGE_REF (cs);
1045 struct ipa_param_call_note *nt;
1046 bool res = false;
1048 for (nt = info->param_calls; nt; nt = nt->next)
1050 struct ipa_jump_func *jfunc;
1052 if (nt->processed)
1053 continue;
1055 /* We must check range due to calls with variable number of arguments: */
1056 if (nt->formal_id >= ipa_get_cs_argument_count (top))
1058 nt->processed = true;
1059 continue;
1062 jfunc = ipa_get_ith_jump_func (top, nt->formal_id);
1063 if (jfunc->type == IPA_JF_PASS_THROUGH
1064 && jfunc->value.pass_through.operation == NOP_EXPR)
1065 nt->formal_id = jfunc->value.pass_through.formal_id;
1066 else if (jfunc->type == IPA_JF_CONST
1067 || jfunc->type == IPA_JF_CONST_MEMBER_PTR)
1069 struct cgraph_node *callee;
1070 struct cgraph_edge *new_indirect_edge;
1071 tree decl;
1073 nt->processed = true;
1074 if (jfunc->type == IPA_JF_CONST_MEMBER_PTR)
1075 decl = jfunc->value.member_cst.pfn;
1076 else
1077 decl = jfunc->value.constant;
1079 if (TREE_CODE (decl) != ADDR_EXPR)
1080 continue;
1081 decl = TREE_OPERAND (decl, 0);
1083 if (TREE_CODE (decl) != FUNCTION_DECL)
1084 continue;
1085 callee = cgraph_node (decl);
1086 if (!callee || !callee->local.inlinable)
1087 continue;
1089 res = true;
1090 if (dump_file)
1091 print_edge_addition_message (dump_file, nt, jfunc, node);
1093 new_indirect_edge = cgraph_create_edge (node, callee, nt->stmt,
1094 nt->count, nt->frequency,
1095 nt->loop_nest);
1096 new_indirect_edge->indirect_call = 1;
1097 ipa_check_create_edge_args ();
1098 if (new_edges)
1099 VEC_safe_push (cgraph_edge_p, heap, *new_edges, new_indirect_edge);
1100 top = IPA_EDGE_REF (cs);
1102 else
1104 /* Ancestor jum functions and pass theoughs with operations should
1105 not be used on parameters that then get called. */
1106 gcc_assert (jfunc->type == IPA_JF_UNKNOWN);
1107 nt->processed = true;
1110 return res;
1113 /* Recursively traverse subtree of NODE (including node) made of inlined
1114 cgraph_edges when CS has been inlined and invoke
1115 update_call_notes_after_inlining on all nodes and
1116 update_jump_functions_after_inlining on all non-inlined edges that lead out
1117 of this subtree. Newly discovered indirect edges will be added to
1118 *NEW_EDGES, unless NEW_EDGES is NULL. Return true iff a new edge(s) were
1119 created. */
1121 static bool
1122 propagate_info_to_inlined_callees (struct cgraph_edge *cs,
1123 struct cgraph_node *node,
1124 VEC (cgraph_edge_p, heap) **new_edges)
1126 struct cgraph_edge *e;
1127 bool res;
1129 res = update_call_notes_after_inlining (cs, node, new_edges);
1131 for (e = node->callees; e; e = e->next_callee)
1132 if (!e->inline_failed)
1133 res |= propagate_info_to_inlined_callees (cs, e->callee, new_edges);
1134 else
1135 update_jump_functions_after_inlining (cs, e);
1137 return res;
1140 /* Update jump functions and call note functions on inlining the call site CS.
1141 CS is expected to lead to a node already cloned by
1142 cgraph_clone_inline_nodes. Newly discovered indirect edges will be added to
1143 *NEW_EDGES, unless NEW_EDGES is NULL. Return true iff a new edge(s) were +
1144 created. */
1146 bool
1147 ipa_propagate_indirect_call_infos (struct cgraph_edge *cs,
1148 VEC (cgraph_edge_p, heap) **new_edges)
1150 /* Do nothing if the preparation phase has not been carried out yet
1151 (i.e. during early inlining). */
1152 if (!ipa_node_params_vector)
1153 return false;
1154 gcc_assert (ipa_edge_args_vector);
1156 return propagate_info_to_inlined_callees (cs, cs->callee, new_edges);
1159 /* Frees all dynamically allocated structures that the argument info points
1160 to. */
1162 void
1163 ipa_free_edge_args_substructures (struct ipa_edge_args *args)
1165 if (args->jump_functions)
1166 free (args->jump_functions);
1168 memset (args, 0, sizeof (*args));
1171 /* Free all ipa_edge structures. */
1173 void
1174 ipa_free_all_edge_args (void)
1176 int i;
1177 struct ipa_edge_args *args;
1179 for (i = 0;
1180 VEC_iterate (ipa_edge_args_t, ipa_edge_args_vector, i, args);
1181 i++)
1182 ipa_free_edge_args_substructures (args);
1184 VEC_free (ipa_edge_args_t, heap, ipa_edge_args_vector);
1185 ipa_edge_args_vector = NULL;
1188 /* Frees all dynamically allocated structures that the param info points
1189 to. */
1191 void
1192 ipa_free_node_params_substructures (struct ipa_node_params *info)
1194 if (info->params)
1195 free (info->params);
1197 while (info->param_calls)
1199 struct ipa_param_call_note *note = info->param_calls;
1200 info->param_calls = note->next;
1201 free (note);
1204 memset (info, 0, sizeof (*info));
1207 /* Free all ipa_node_params structures. */
1209 void
1210 ipa_free_all_node_params (void)
1212 int i;
1213 struct ipa_node_params *info;
1215 for (i = 0;
1216 VEC_iterate (ipa_node_params_t, ipa_node_params_vector, i, info);
1217 i++)
1218 ipa_free_node_params_substructures (info);
1220 VEC_free (ipa_node_params_t, heap, ipa_node_params_vector);
1221 ipa_node_params_vector = NULL;
1224 /* Hook that is called by cgraph.c when an edge is removed. */
1226 static void
1227 ipa_edge_removal_hook (struct cgraph_edge *cs, void *data ATTRIBUTE_UNUSED)
1229 /* During IPA-CP updating we can be called on not-yet analyze clones. */
1230 if (VEC_length (ipa_edge_args_t, ipa_edge_args_vector)
1231 <= (unsigned)cs->uid)
1232 return;
1233 ipa_free_edge_args_substructures (IPA_EDGE_REF (cs));
1236 /* Hook that is called by cgraph.c when a node is removed. */
1238 static void
1239 ipa_node_removal_hook (struct cgraph_node *node, void *data ATTRIBUTE_UNUSED)
1241 ipa_free_node_params_substructures (IPA_NODE_REF (node));
1244 /* Helper function to duplicate an array of size N that is at SRC and store a
1245 pointer to it to DST. Nothing is done if SRC is NULL. */
1247 static void *
1248 duplicate_array (void *src, size_t n)
1250 void *p;
1252 if (!src)
1253 return NULL;
1255 p = xcalloc (1, n);
1256 memcpy (p, src, n);
1257 return p;
1260 /* Hook that is called by cgraph.c when a node is duplicated. */
1262 static void
1263 ipa_edge_duplication_hook (struct cgraph_edge *src, struct cgraph_edge *dst,
1264 __attribute__((unused)) void *data)
1266 struct ipa_edge_args *old_args, *new_args;
1267 int arg_count;
1269 ipa_check_create_edge_args ();
1271 old_args = IPA_EDGE_REF (src);
1272 new_args = IPA_EDGE_REF (dst);
1274 arg_count = ipa_get_cs_argument_count (old_args);
1275 ipa_set_cs_argument_count (new_args, arg_count);
1276 new_args->jump_functions = (struct ipa_jump_func *)
1277 duplicate_array (old_args->jump_functions,
1278 sizeof (struct ipa_jump_func) * arg_count);
1281 /* Hook that is called by cgraph.c when a node is duplicated. */
1283 static void
1284 ipa_node_duplication_hook (struct cgraph_node *src, struct cgraph_node *dst,
1285 __attribute__((unused)) void *data)
1287 struct ipa_node_params *old_info, *new_info;
1288 struct ipa_param_call_note *note;
1289 int param_count;
1291 ipa_check_create_node_params ();
1292 old_info = IPA_NODE_REF (src);
1293 new_info = IPA_NODE_REF (dst);
1294 param_count = ipa_get_param_count (old_info);
1296 ipa_set_param_count (new_info, param_count);
1297 new_info->params = (struct ipa_param_descriptor *)
1298 duplicate_array (old_info->params,
1299 sizeof (struct ipa_param_descriptor) * param_count);
1300 new_info->ipcp_orig_node = old_info->ipcp_orig_node;
1301 new_info->count_scale = old_info->count_scale;
1303 for (note = old_info->param_calls; note; note = note->next)
1305 struct ipa_param_call_note *nn;
1307 nn = (struct ipa_param_call_note *)
1308 xcalloc (1, sizeof (struct ipa_param_call_note));
1309 memcpy (nn, note, sizeof (struct ipa_param_call_note));
1310 nn->next = new_info->param_calls;
1311 new_info->param_calls = nn;
1315 /* Register our cgraph hooks if they are not already there. */
1317 void
1318 ipa_register_cgraph_hooks (void)
1320 if (!edge_removal_hook_holder)
1321 edge_removal_hook_holder =
1322 cgraph_add_edge_removal_hook (&ipa_edge_removal_hook, NULL);
1323 if (!node_removal_hook_holder)
1324 node_removal_hook_holder =
1325 cgraph_add_node_removal_hook (&ipa_node_removal_hook, NULL);
1326 if (!edge_duplication_hook_holder)
1327 edge_duplication_hook_holder =
1328 cgraph_add_edge_duplication_hook (&ipa_edge_duplication_hook, NULL);
1329 if (!node_duplication_hook_holder)
1330 node_duplication_hook_holder =
1331 cgraph_add_node_duplication_hook (&ipa_node_duplication_hook, NULL);
1334 /* Unregister our cgraph hooks if they are not already there. */
1336 static void
1337 ipa_unregister_cgraph_hooks (void)
1339 cgraph_remove_edge_removal_hook (edge_removal_hook_holder);
1340 edge_removal_hook_holder = NULL;
1341 cgraph_remove_node_removal_hook (node_removal_hook_holder);
1342 node_removal_hook_holder = NULL;
1343 cgraph_remove_edge_duplication_hook (edge_duplication_hook_holder);
1344 edge_duplication_hook_holder = NULL;
1345 cgraph_remove_node_duplication_hook (node_duplication_hook_holder);
1346 node_duplication_hook_holder = NULL;
1349 /* Free all ipa_node_params and all ipa_edge_args structures if they are no
1350 longer needed after ipa-cp. */
1352 void
1353 free_all_ipa_structures_after_ipa_cp (void)
1355 if (!flag_indirect_inlining)
1357 ipa_free_all_edge_args ();
1358 ipa_free_all_node_params ();
1359 ipa_unregister_cgraph_hooks ();
1363 /* Free all ipa_node_params and all ipa_edge_args structures if they are no
1364 longer needed after indirect inlining. */
1366 void
1367 free_all_ipa_structures_after_iinln (void)
1369 ipa_free_all_edge_args ();
1370 ipa_free_all_node_params ();
1371 ipa_unregister_cgraph_hooks ();
1374 /* Print ipa_tree_map data structures of all functions in the
1375 callgraph to F. */
1377 void
1378 ipa_print_node_params (FILE * f, struct cgraph_node *node)
1380 int i, count;
1381 tree temp;
1382 struct ipa_node_params *info;
1384 if (!node->analyzed)
1385 return;
1386 info = IPA_NODE_REF (node);
1387 fprintf (f, " function %s Trees :: \n", cgraph_node_name (node));
1388 count = ipa_get_param_count (info);
1389 for (i = 0; i < count; i++)
1391 temp = ipa_get_param (info, i);
1392 if (TREE_CODE (temp) == PARM_DECL)
1393 fprintf (f, " param %d : %s", i,
1394 (*lang_hooks.decl_printable_name) (temp, 2));
1395 if (ipa_is_param_modified (info, i))
1396 fprintf (f, " modified");
1397 if (ipa_is_param_called (info, i))
1398 fprintf (f, " called");
1399 fprintf (f, "\n");
1403 /* Print ipa_tree_map data structures of all functions in the
1404 callgraph to F. */
1406 void
1407 ipa_print_all_params (FILE * f)
1409 struct cgraph_node *node;
1411 fprintf (f, "\nFunction parameters:\n");
1412 for (node = cgraph_nodes; node; node = node->next)
1413 ipa_print_node_params (f, node);
1416 /* Return a heap allocated vector containing formal parameters of FNDECL. */
1418 VEC(tree, heap) *
1419 ipa_get_vector_of_formal_parms (tree fndecl)
1421 VEC(tree, heap) *args;
1422 int count;
1423 tree parm;
1425 count = count_formal_params_1 (fndecl);
1426 args = VEC_alloc (tree, heap, count);
1427 for (parm = DECL_ARGUMENTS (fndecl); parm; parm = TREE_CHAIN (parm))
1428 VEC_quick_push (tree, args, parm);
1430 return args;
1433 /* Return a heap allocated vector containing types of formal parameters of
1434 function type FNTYPE. */
1436 static inline VEC(tree, heap) *
1437 get_vector_of_formal_parm_types (tree fntype)
1439 VEC(tree, heap) *types;
1440 int count = 0;
1441 tree t;
1443 for (t = TYPE_ARG_TYPES (fntype); t; t = TREE_CHAIN (t))
1444 count++;
1446 types = VEC_alloc (tree, heap, count);
1447 for (t = TYPE_ARG_TYPES (fntype); t; t = TREE_CHAIN (t))
1448 VEC_quick_push (tree, types, TREE_VALUE (t));
1450 return types;
1453 /* Modify the function declaration FNDECL and its type according to the plan in
1454 ADJUSTMENTS. It also sets base fields of individual adjustments structures
1455 to reflect the actual parameters being modified which are determined by the
1456 base_index field. */
1458 void
1459 ipa_modify_formal_parameters (tree fndecl, ipa_parm_adjustment_vec adjustments,
1460 const char *synth_parm_prefix)
1462 VEC(tree, heap) *oparms, *otypes;
1463 tree orig_type, new_type = NULL;
1464 tree old_arg_types, t, new_arg_types = NULL;
1465 tree parm, *link = &DECL_ARGUMENTS (fndecl);
1466 int i, len = VEC_length (ipa_parm_adjustment_t, adjustments);
1467 tree new_reversed = NULL;
1468 bool care_for_types, last_parm_void;
1470 if (!synth_parm_prefix)
1471 synth_parm_prefix = "SYNTH";
1473 oparms = ipa_get_vector_of_formal_parms (fndecl);
1474 orig_type = TREE_TYPE (fndecl);
1475 old_arg_types = TYPE_ARG_TYPES (orig_type);
1477 /* The following test is an ugly hack, some functions simply don't have any
1478 arguments in their type. This is probably a bug but well... */
1479 care_for_types = (old_arg_types != NULL_TREE);
1480 if (care_for_types)
1482 last_parm_void = (TREE_VALUE (tree_last (old_arg_types))
1483 == void_type_node);
1484 otypes = get_vector_of_formal_parm_types (orig_type);
1485 if (last_parm_void)
1486 gcc_assert (VEC_length (tree, oparms) + 1 == VEC_length (tree, otypes));
1487 else
1488 gcc_assert (VEC_length (tree, oparms) == VEC_length (tree, otypes));
1490 else
1492 last_parm_void = false;
1493 otypes = NULL;
1496 for (i = 0; i < len; i++)
1498 struct ipa_parm_adjustment *adj;
1499 gcc_assert (link);
1501 adj = VEC_index (ipa_parm_adjustment_t, adjustments, i);
1502 parm = VEC_index (tree, oparms, adj->base_index);
1503 adj->base = parm;
1505 if (adj->copy_param)
1507 if (care_for_types)
1508 new_arg_types = tree_cons (NULL_TREE, VEC_index (tree, otypes,
1509 adj->base_index),
1510 new_arg_types);
1511 *link = parm;
1512 link = &TREE_CHAIN (parm);
1514 else if (!adj->remove_param)
1516 tree new_parm;
1517 tree ptype;
1519 if (adj->by_ref)
1520 ptype = build_pointer_type (adj->type);
1521 else
1522 ptype = adj->type;
1524 if (care_for_types)
1525 new_arg_types = tree_cons (NULL_TREE, ptype, new_arg_types);
1527 new_parm = build_decl (UNKNOWN_LOCATION, PARM_DECL, NULL_TREE,
1528 ptype);
1529 DECL_NAME (new_parm) = create_tmp_var_name (synth_parm_prefix);
1531 DECL_ARTIFICIAL (new_parm) = 1;
1532 DECL_ARG_TYPE (new_parm) = ptype;
1533 DECL_CONTEXT (new_parm) = fndecl;
1534 TREE_USED (new_parm) = 1;
1535 DECL_IGNORED_P (new_parm) = 1;
1536 layout_decl (new_parm, 0);
1538 add_referenced_var (new_parm);
1539 mark_sym_for_renaming (new_parm);
1540 adj->base = parm;
1541 adj->reduction = new_parm;
1543 *link = new_parm;
1545 link = &TREE_CHAIN (new_parm);
1549 *link = NULL_TREE;
1551 if (care_for_types)
1553 new_reversed = nreverse (new_arg_types);
1554 if (last_parm_void)
1556 if (new_reversed)
1557 TREE_CHAIN (new_arg_types) = void_list_node;
1558 else
1559 new_reversed = void_list_node;
1563 /* Use copy_node to preserve as much as possible from original type
1564 (debug info, attribute lists etc.)
1565 Exception is METHOD_TYPEs must have THIS argument.
1566 When we are asked to remove it, we need to build new FUNCTION_TYPE
1567 instead. */
1568 if (TREE_CODE (orig_type) != METHOD_TYPE
1569 || (VEC_index (ipa_parm_adjustment_t, adjustments, 0)->copy_param
1570 && VEC_index (ipa_parm_adjustment_t, adjustments, 0)->base_index == 0))
1572 new_type = copy_node (orig_type);
1573 TYPE_ARG_TYPES (new_type) = new_reversed;
1575 else
1577 new_type
1578 = build_distinct_type_copy (build_function_type (TREE_TYPE (orig_type),
1579 new_reversed));
1580 TYPE_CONTEXT (new_type) = TYPE_CONTEXT (orig_type);
1581 DECL_VINDEX (fndecl) = NULL_TREE;
1584 /* This is a new type, not a copy of an old type. Need to reassociate
1585 variants. We can handle everything except the main variant lazily. */
1586 t = TYPE_MAIN_VARIANT (orig_type);
1587 if (orig_type != t)
1589 TYPE_MAIN_VARIANT (new_type) = t;
1590 TYPE_NEXT_VARIANT (new_type) = TYPE_NEXT_VARIANT (t);
1591 TYPE_NEXT_VARIANT (t) = new_type;
1593 else
1595 TYPE_MAIN_VARIANT (new_type) = new_type;
1596 TYPE_NEXT_VARIANT (new_type) = NULL;
1599 TREE_TYPE (fndecl) = new_type;
1600 if (otypes)
1601 VEC_free (tree, heap, otypes);
1602 VEC_free (tree, heap, oparms);
1605 /* Modify actual arguments of a function call CS as indicated in ADJUSTMENTS.
1606 If this is a directly recursive call, CS must be NULL. Otherwise it must
1607 contain the corresponding call graph edge. */
1609 void
1610 ipa_modify_call_arguments (struct cgraph_edge *cs, gimple stmt,
1611 ipa_parm_adjustment_vec adjustments)
1613 VEC(tree, heap) *vargs;
1614 gimple new_stmt;
1615 gimple_stmt_iterator gsi;
1616 tree callee_decl;
1617 int i, len;
1619 len = VEC_length (ipa_parm_adjustment_t, adjustments);
1620 vargs = VEC_alloc (tree, heap, len);
1622 gsi = gsi_for_stmt (stmt);
1623 for (i = 0; i < len; i++)
1625 struct ipa_parm_adjustment *adj;
1627 adj = VEC_index (ipa_parm_adjustment_t, adjustments, i);
1629 if (adj->copy_param)
1631 tree arg = gimple_call_arg (stmt, adj->base_index);
1633 VEC_quick_push (tree, vargs, arg);
1635 else if (!adj->remove_param)
1637 tree expr, orig_expr;
1638 bool allow_ptr, repl_found;
1640 orig_expr = expr = gimple_call_arg (stmt, adj->base_index);
1641 if (TREE_CODE (expr) == ADDR_EXPR)
1643 allow_ptr = false;
1644 expr = TREE_OPERAND (expr, 0);
1646 else
1647 allow_ptr = true;
1649 repl_found = build_ref_for_offset (&expr, TREE_TYPE (expr),
1650 adj->offset, adj->type,
1651 allow_ptr);
1652 if (repl_found)
1654 if (adj->by_ref)
1655 expr = build_fold_addr_expr (expr);
1657 else
1659 tree ptrtype = build_pointer_type (adj->type);
1660 expr = orig_expr;
1661 if (!POINTER_TYPE_P (TREE_TYPE (expr)))
1662 expr = build_fold_addr_expr (expr);
1663 if (!useless_type_conversion_p (ptrtype, TREE_TYPE (expr)))
1664 expr = fold_convert (ptrtype, expr);
1665 expr = fold_build2 (POINTER_PLUS_EXPR, ptrtype, expr,
1666 build_int_cst (size_type_node,
1667 adj->offset / BITS_PER_UNIT));
1668 if (!adj->by_ref)
1669 expr = fold_build1 (INDIRECT_REF, adj->type, expr);
1671 expr = force_gimple_operand_gsi (&gsi, expr,
1672 adj->by_ref
1673 || is_gimple_reg_type (adj->type),
1674 NULL, true, GSI_SAME_STMT);
1675 VEC_quick_push (tree, vargs, expr);
1679 if (dump_file && (dump_flags & TDF_DETAILS))
1681 fprintf (dump_file, "replacing stmt:");
1682 print_gimple_stmt (dump_file, gsi_stmt (gsi), 0, 0);
1685 callee_decl = !cs ? gimple_call_fndecl (stmt) : cs->callee->decl;
1686 new_stmt = gimple_build_call_vec (callee_decl, vargs);
1687 VEC_free (tree, heap, vargs);
1688 if (gimple_call_lhs (stmt))
1689 gimple_call_set_lhs (new_stmt, gimple_call_lhs (stmt));
1691 gimple_set_block (new_stmt, gimple_block (stmt));
1692 if (gimple_has_location (stmt))
1693 gimple_set_location (new_stmt, gimple_location (stmt));
1694 gimple_call_copy_flags (new_stmt, stmt);
1695 gimple_call_set_chain (new_stmt, gimple_call_chain (stmt));
1697 if (dump_file && (dump_flags & TDF_DETAILS))
1699 fprintf (dump_file, "with stmt:");
1700 print_gimple_stmt (dump_file, new_stmt, 0, 0);
1701 fprintf (dump_file, "\n");
1703 gsi_replace (&gsi, new_stmt, true);
1704 if (cs)
1705 cgraph_set_call_stmt (cs, new_stmt);
1706 update_ssa (TODO_update_ssa);
1707 free_dominance_info (CDI_DOMINATORS);
1710 /* Return true iff BASE_INDEX is in ADJUSTMENTS more than once. */
1712 static bool
1713 index_in_adjustments_multiple_times_p (int base_index,
1714 ipa_parm_adjustment_vec adjustments)
1716 int i, len = VEC_length (ipa_parm_adjustment_t, adjustments);
1717 bool one = false;
1719 for (i = 0; i < len; i++)
1721 struct ipa_parm_adjustment *adj;
1722 adj = VEC_index (ipa_parm_adjustment_t, adjustments, i);
1724 if (adj->base_index == base_index)
1726 if (one)
1727 return true;
1728 else
1729 one = true;
1732 return false;
1736 /* Return adjustments that should have the same effect on function parameters
1737 and call arguments as if they were first changed according to adjustments in
1738 INNER and then by adjustments in OUTER. */
1740 ipa_parm_adjustment_vec
1741 ipa_combine_adjustments (ipa_parm_adjustment_vec inner,
1742 ipa_parm_adjustment_vec outer)
1744 int i, outlen = VEC_length (ipa_parm_adjustment_t, outer);
1745 int inlen = VEC_length (ipa_parm_adjustment_t, inner);
1746 int removals = 0;
1747 ipa_parm_adjustment_vec adjustments, tmp;
1749 tmp = VEC_alloc (ipa_parm_adjustment_t, heap, inlen);
1750 for (i = 0; i < inlen; i++)
1752 struct ipa_parm_adjustment *n;
1753 n = VEC_index (ipa_parm_adjustment_t, inner, i);
1755 if (n->remove_param)
1756 removals++;
1757 else
1758 VEC_quick_push (ipa_parm_adjustment_t, tmp, n);
1761 adjustments = VEC_alloc (ipa_parm_adjustment_t, heap, outlen + removals);
1762 for (i = 0; i < outlen; i++)
1764 struct ipa_parm_adjustment *r;
1765 struct ipa_parm_adjustment *out = VEC_index (ipa_parm_adjustment_t,
1766 outer, i);
1767 struct ipa_parm_adjustment *in = VEC_index (ipa_parm_adjustment_t, tmp,
1768 out->base_index);
1770 gcc_assert (!in->remove_param);
1771 if (out->remove_param)
1773 if (!index_in_adjustments_multiple_times_p (in->base_index, tmp))
1775 r = VEC_quick_push (ipa_parm_adjustment_t, adjustments, NULL);
1776 memset (r, 0, sizeof (*r));
1777 r->remove_param = true;
1779 continue;
1782 r = VEC_quick_push (ipa_parm_adjustment_t, adjustments, NULL);
1783 memset (r, 0, sizeof (*r));
1784 r->base_index = in->base_index;
1785 r->type = out->type;
1787 /* FIXME: Create nonlocal value too. */
1789 if (in->copy_param && out->copy_param)
1790 r->copy_param = true;
1791 else if (in->copy_param)
1792 r->offset = out->offset;
1793 else if (out->copy_param)
1794 r->offset = in->offset;
1795 else
1796 r->offset = in->offset + out->offset;
1799 for (i = 0; i < inlen; i++)
1801 struct ipa_parm_adjustment *n = VEC_index (ipa_parm_adjustment_t,
1802 inner, i);
1804 if (n->remove_param)
1805 VEC_quick_push (ipa_parm_adjustment_t, adjustments, n);
1808 VEC_free (ipa_parm_adjustment_t, heap, tmp);
1809 return adjustments;
1812 /* Dump the adjustments in the vector ADJUSTMENTS to dump_file in a human
1813 friendly way, assuming they are meant to be applied to FNDECL. */
1815 void
1816 ipa_dump_param_adjustments (FILE *file, ipa_parm_adjustment_vec adjustments,
1817 tree fndecl)
1819 int i, len = VEC_length (ipa_parm_adjustment_t, adjustments);
1820 bool first = true;
1821 VEC(tree, heap) *parms = ipa_get_vector_of_formal_parms (fndecl);
1823 fprintf (file, "IPA param adjustments: ");
1824 for (i = 0; i < len; i++)
1826 struct ipa_parm_adjustment *adj;
1827 adj = VEC_index (ipa_parm_adjustment_t, adjustments, i);
1829 if (!first)
1830 fprintf (file, " ");
1831 else
1832 first = false;
1834 fprintf (file, "%i. base_index: %i - ", i, adj->base_index);
1835 print_generic_expr (file, VEC_index (tree, parms, adj->base_index), 0);
1836 if (adj->base)
1838 fprintf (file, ", base: ");
1839 print_generic_expr (file, adj->base, 0);
1841 if (adj->reduction)
1843 fprintf (file, ", reduction: ");
1844 print_generic_expr (file, adj->reduction, 0);
1846 if (adj->new_ssa_base)
1848 fprintf (file, ", new_ssa_base: ");
1849 print_generic_expr (file, adj->new_ssa_base, 0);
1852 if (adj->copy_param)
1853 fprintf (file, ", copy_param");
1854 else if (adj->remove_param)
1855 fprintf (file, ", remove_param");
1856 else
1857 fprintf (file, ", offset %li", (long) adj->offset);
1858 if (adj->by_ref)
1859 fprintf (file, ", by_ref");
1860 print_node_brief (file, ", type: ", adj->type, 0);
1861 fprintf (file, "\n");
1863 VEC_free (tree, heap, parms);