- n_com = 0;
- for (i = 0, n_res = get_method_n_ress(ctp); i < n_res; ++i) {
- if (is_compound_type(get_method_res_type(ctp, i)))
- ++n_com;
- }
- pos = 2;
- ARR_RESIZE(ir_node *, new_in, n_params + n_com + pos);
- memset(new_in, 0, sizeof(*new_in) * (n_params + n_com + pos));
- if (hidden_params == ADD_HIDDEN_ALWAYS_IN_FRONT) {
- add_hidden_param(irg, n_com, &new_in[pos], p, env);
- pos += n_com;
+static void fix_compound_params(cl_entry *entry, ir_type *ctp)
+{
+ ir_node *call = entry->call;
+ dbg_info *dbgi = get_irn_dbg_info(call);
+ ir_node *mem = get_Call_mem(call);
+ ir_graph *irg = get_irn_irg(call);
+ ir_node *nomem = new_r_NoMem(irg);
+ ir_node *frame = get_irg_frame(irg);
+ size_t n_params = get_method_n_params(ctp);
+ size_t i;
+
+ for (i = 0; i < n_params; ++i) {
+ ir_type *type = get_method_param_type(ctp, i);
+ ir_node *block;
+ ir_node *arg;
+ ir_node *sel;
+ ir_node *copyb;
+ ir_entity *arg_entity;
+ if (!is_compound_type(type))
+ continue;
+
+ arg = get_Call_param(call, i);
+ arg_entity = create_compound_arg_entity(irg, type);
+ block = get_nodes_block(call);
+ sel = new_rd_simpleSel(dbgi, block, nomem, frame, arg_entity);
+ copyb = new_rd_CopyB(dbgi, block, mem, sel, arg, type);
+ mem = new_r_Proj(copyb, mode_M, pn_CopyB_M);
+ set_Call_param(call, i, sel);
+ }
+ set_Call_mem(call, mem);
+}
+
+static void fix_calls(wlk_env *env)
+{
+ cl_entry *entry;
+ for (entry = env->cl_list; entry; entry = entry->next) {
+ ir_node *call = entry->call;
+ ir_type *ctp = get_Call_type(call);
+ ir_type *lowered_mtp = lower_mtp(env->flags, ctp);
+ set_Call_type(call, lowered_mtp);
+
+ if (entry->has_compound_param) {
+ fix_compound_params(entry, ctp);