2 * Copyright (C) 1995-2011 University of Karlsruhe. All right reserved.
4 * This file is part of libFirm.
6 * This file may be distributed and/or modified under the terms of the
7 * GNU General Public License version 2 as published by the Free Software
8 * Foundation and appearing in the file LICENSE.GPL included in the
9 * packaging of this file.
11 * Licensees holding valid libFirm Professional Edition licenses may use
12 * this file in accordance with the libFirm Commercial License.
13 * Agreement provided with the Software.
15 * This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
16 * WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR
22 * @brief This file implements the IR transformation from firm into
24 * @author Christian Wuerdig, Matthias Braun
34 #include "irgraph_t.h"
39 #include "iredges_t.h"
50 #include "../benode.h"
51 #include "../besched.h"
53 #include "../beutil.h"
55 #include "../betranshlp.h"
58 #include "bearch_ia32_t.h"
59 #include "ia32_common_transform.h"
60 #include "ia32_nodes_attr.h"
61 #include "ia32_transform.h"
62 #include "ia32_new_nodes.h"
63 #include "ia32_dbg_stat.h"
64 #include "ia32_optimize.h"
65 #include "ia32_address_mode.h"
66 #include "ia32_architecture.h"
68 #include "gen_ia32_regalloc_if.h"
70 /* define this to construct SSE constants instead of load them */
71 #undef CONSTRUCT_SSE_CONST
74 #define SFP_SIGN "0x80000000"
75 #define DFP_SIGN "0x8000000000000000"
76 #define SFP_ABS "0x7FFFFFFF"
77 #define DFP_ABS "0x7FFFFFFFFFFFFFFF"
78 #define DFP_INTMAX "9223372036854775807"
79 #define ULL_BIAS "18446744073709551616"
81 #define ENT_SFP_SIGN "C_ia32_sfp_sign"
82 #define ENT_DFP_SIGN "C_ia32_dfp_sign"
83 #define ENT_SFP_ABS "C_ia32_sfp_abs"
84 #define ENT_DFP_ABS "C_ia32_dfp_abs"
85 #define ENT_ULL_BIAS "C_ia32_ull_bias"
87 #define mode_vfp (ia32_reg_classes[CLASS_ia32_vfp].mode)
88 #define mode_xmm (ia32_reg_classes[CLASS_ia32_xmm].mode)
90 DEBUG_ONLY(static firm_dbg_module_t *dbg = NULL;)
92 static ir_node *initial_fpcw = NULL;
93 int ia32_no_pic_adjust;
95 typedef ir_node *construct_binop_func(dbg_info *db, ir_node *block,
96 ir_node *base, ir_node *index, ir_node *mem, ir_node *op1,
99 typedef ir_node *construct_binop_flags_func(dbg_info *db, ir_node *block,
100 ir_node *base, ir_node *index, ir_node *mem, ir_node *op1, ir_node *op2,
103 typedef ir_node *construct_shift_func(dbg_info *db, ir_node *block,
104 ir_node *op1, ir_node *op2);
106 typedef ir_node *construct_binop_dest_func(dbg_info *db, ir_node *block,
107 ir_node *base, ir_node *index, ir_node *mem, ir_node *op);
109 typedef ir_node *construct_unop_dest_func(dbg_info *db, ir_node *block,
110 ir_node *base, ir_node *index, ir_node *mem);
112 typedef ir_node *construct_binop_float_func(dbg_info *db, ir_node *block,
113 ir_node *base, ir_node *index, ir_node *mem, ir_node *op1, ir_node *op2,
116 typedef ir_node *construct_unop_func(dbg_info *db, ir_node *block, ir_node *op);
118 static ir_node *create_immediate_or_transform(ir_node *node,
119 char immediate_constraint_type);
121 static ir_node *create_I2I_Conv(ir_mode *src_mode, ir_mode *tgt_mode,
122 dbg_info *dbgi, ir_node *block,
123 ir_node *op, ir_node *orig_node);
125 /* its enough to have those once */
126 static ir_node *nomem, *noreg_GP;
128 /** a list to postprocess all calls */
129 static ir_node **call_list;
130 static ir_type **call_types;
132 /** Return non-zero is a node represents the 0 constant. */
133 static bool is_Const_0(ir_node *node)
135 return is_Const(node) && is_Const_null(node);
138 /** Return non-zero is a node represents the 1 constant. */
139 static bool is_Const_1(ir_node *node)
141 return is_Const(node) && is_Const_one(node);
144 /** Return non-zero is a node represents the -1 constant. */
145 static bool is_Const_Minus_1(ir_node *node)
147 return is_Const(node) && is_Const_all_one(node);
151 * returns true if constant can be created with a simple float command
153 static bool is_simple_x87_Const(ir_node *node)
155 ir_tarval *tv = get_Const_tarval(node);
156 if (tarval_is_null(tv) || tarval_is_one(tv))
159 /* TODO: match all the other float constants */
164 * returns true if constant can be created with a simple float command
166 static bool is_simple_sse_Const(ir_node *node)
168 ir_tarval *tv = get_Const_tarval(node);
169 ir_mode *mode = get_tarval_mode(tv);
174 if (tarval_is_null(tv)
175 #ifdef CONSTRUCT_SSE_CONST
180 #ifdef CONSTRUCT_SSE_CONST
181 if (mode == mode_D) {
182 unsigned val = get_tarval_sub_bits(tv, 0) |
183 (get_tarval_sub_bits(tv, 1) << 8) |
184 (get_tarval_sub_bits(tv, 2) << 16) |
185 (get_tarval_sub_bits(tv, 3) << 24);
187 /* lower 32bit are zero, really a 32bit constant */
190 #endif /* CONSTRUCT_SSE_CONST */
191 /* TODO: match all the other float constants */
196 * return NoREG or pic_base in case of PIC.
197 * This is necessary as base address for newly created symbols
199 static ir_node *get_symconst_base(void)
201 ir_graph *irg = current_ir_graph;
203 if (be_get_irg_options(irg)->pic) {
204 const arch_env_t *arch_env = be_get_irg_arch_env(irg);
205 return arch_env->impl->get_pic_base(irg);
212 * Transforms a Const.
214 static ir_node *gen_Const(ir_node *node)
216 ir_node *old_block = get_nodes_block(node);
217 ir_node *block = be_transform_node(old_block);
218 dbg_info *dbgi = get_irn_dbg_info(node);
219 ir_mode *mode = get_irn_mode(node);
221 assert(is_Const(node));
223 if (mode_is_float(mode)) {
229 if (ia32_cg_config.use_sse2) {
230 ir_tarval *tv = get_Const_tarval(node);
231 if (tarval_is_null(tv)) {
232 load = new_bd_ia32_xZero(dbgi, block);
233 set_ia32_ls_mode(load, mode);
235 #ifdef CONSTRUCT_SSE_CONST
236 } else if (tarval_is_one(tv)) {
237 int cnst = mode == mode_F ? 26 : 55;
238 ir_node *imm1 = ia32_create_Immediate(NULL, 0, cnst);
239 ir_node *imm2 = ia32_create_Immediate(NULL, 0, 2);
240 ir_node *pslld, *psrld;
242 load = new_bd_ia32_xAllOnes(dbgi, block);
243 set_ia32_ls_mode(load, mode);
244 pslld = new_bd_ia32_xPslld(dbgi, block, load, imm1);
245 set_ia32_ls_mode(pslld, mode);
246 psrld = new_bd_ia32_xPsrld(dbgi, block, pslld, imm2);
247 set_ia32_ls_mode(psrld, mode);
249 #endif /* CONSTRUCT_SSE_CONST */
250 } else if (mode == mode_F) {
251 /* we can place any 32bit constant by using a movd gp, sse */
252 unsigned val = get_tarval_sub_bits(tv, 0) |
253 (get_tarval_sub_bits(tv, 1) << 8) |
254 (get_tarval_sub_bits(tv, 2) << 16) |
255 (get_tarval_sub_bits(tv, 3) << 24);
256 ir_node *cnst = new_bd_ia32_Const(dbgi, block, NULL, 0, 0, val);
257 load = new_bd_ia32_xMovd(dbgi, block, cnst);
258 set_ia32_ls_mode(load, mode);
261 #ifdef CONSTRUCT_SSE_CONST
262 if (mode == mode_D) {
263 unsigned val = get_tarval_sub_bits(tv, 0) |
264 (get_tarval_sub_bits(tv, 1) << 8) |
265 (get_tarval_sub_bits(tv, 2) << 16) |
266 (get_tarval_sub_bits(tv, 3) << 24);
268 ir_node *imm32 = ia32_create_Immediate(NULL, 0, 32);
269 ir_node *cnst, *psllq;
271 /* fine, lower 32bit are zero, produce 32bit value */
272 val = get_tarval_sub_bits(tv, 4) |
273 (get_tarval_sub_bits(tv, 5) << 8) |
274 (get_tarval_sub_bits(tv, 6) << 16) |
275 (get_tarval_sub_bits(tv, 7) << 24);
276 cnst = new_bd_ia32_Const(dbgi, block, NULL, 0, 0, val);
277 load = new_bd_ia32_xMovd(dbgi, block, cnst);
278 set_ia32_ls_mode(load, mode);
279 psllq = new_bd_ia32_xPsllq(dbgi, block, load, imm32);
280 set_ia32_ls_mode(psllq, mode);
285 #endif /* CONSTRUCT_SSE_CONST */
286 floatent = ia32_create_float_const_entity(node);
288 base = get_symconst_base();
289 load = new_bd_ia32_xLoad(dbgi, block, base, noreg_GP, nomem,
291 set_ia32_op_type(load, ia32_AddrModeS);
292 set_ia32_am_sc(load, floatent);
293 arch_irn_add_flags(load, arch_irn_flags_rematerializable);
294 res = new_r_Proj(load, mode_xmm, pn_ia32_xLoad_res);
297 if (is_Const_null(node)) {
298 load = new_bd_ia32_vfldz(dbgi, block);
300 set_ia32_ls_mode(load, mode);
301 } else if (is_Const_one(node)) {
302 load = new_bd_ia32_vfld1(dbgi, block);
304 set_ia32_ls_mode(load, mode);
309 floatent = ia32_create_float_const_entity(node);
310 /* create_float_const_ent is smart and sometimes creates
312 ls_mode = get_type_mode(get_entity_type(floatent));
313 base = get_symconst_base();
314 load = new_bd_ia32_vfld(dbgi, block, base, noreg_GP, nomem,
316 set_ia32_op_type(load, ia32_AddrModeS);
317 set_ia32_am_sc(load, floatent);
318 arch_irn_add_flags(load, arch_irn_flags_rematerializable);
319 res = new_r_Proj(load, mode_vfp, pn_ia32_vfld_res);
322 #ifdef CONSTRUCT_SSE_CONST
324 #endif /* CONSTRUCT_SSE_CONST */
325 SET_IA32_ORIG_NODE(load, node);
327 } else { /* non-float mode */
329 ir_tarval *tv = get_Const_tarval(node);
332 tv = tarval_convert_to(tv, mode_Iu);
334 if (tv == get_tarval_bad() || tv == get_tarval_undefined() ||
336 panic("couldn't convert constant tarval (%+F)", node);
338 val = get_tarval_long(tv);
340 cnst = new_bd_ia32_Const(dbgi, block, NULL, 0, 0, val);
341 SET_IA32_ORIG_NODE(cnst, node);
348 * Transforms a SymConst.
350 static ir_node *gen_SymConst(ir_node *node)
352 ir_node *old_block = get_nodes_block(node);
353 ir_node *block = be_transform_node(old_block);
354 dbg_info *dbgi = get_irn_dbg_info(node);
355 ir_mode *mode = get_irn_mode(node);
358 if (mode_is_float(mode)) {
359 if (ia32_cg_config.use_sse2)
360 cnst = new_bd_ia32_xLoad(dbgi, block, noreg_GP, noreg_GP, nomem, mode_E);
362 cnst = new_bd_ia32_vfld(dbgi, block, noreg_GP, noreg_GP, nomem, mode_E);
363 set_ia32_am_sc(cnst, get_SymConst_entity(node));
364 set_ia32_use_frame(cnst);
368 if (get_SymConst_kind(node) != symconst_addr_ent) {
369 panic("backend only support symconst_addr_ent (at %+F)", node);
371 entity = get_SymConst_entity(node);
372 if (get_entity_owner(entity) == get_tls_type()) {
373 ir_node *tls_base = new_bd_ia32_LdTls(NULL, block);
374 ir_node *lea = new_bd_ia32_Lea(dbgi, block, tls_base, noreg_GP);
375 set_ia32_am_sc(lea, entity);
378 cnst = new_bd_ia32_Const(dbgi, block, entity, 0, 0, 0);
382 SET_IA32_ORIG_NODE(cnst, node);
388 * Create a float type for the given mode and cache it.
390 * @param mode the mode for the float type (might be integer mode for SSE2 types)
391 * @param align alignment
393 static ir_type *ia32_create_float_type(ir_mode *mode, unsigned align)
399 if (mode == mode_Iu) {
400 static ir_type *int_Iu[16] = {NULL, };
402 if (int_Iu[align] == NULL) {
403 int_Iu[align] = tp = new_type_primitive(mode);
404 /* set the specified alignment */
405 set_type_alignment_bytes(tp, align);
407 return int_Iu[align];
408 } else if (mode == mode_Lu) {
409 static ir_type *int_Lu[16] = {NULL, };
411 if (int_Lu[align] == NULL) {
412 int_Lu[align] = tp = new_type_primitive(mode);
413 /* set the specified alignment */
414 set_type_alignment_bytes(tp, align);
416 return int_Lu[align];
417 } else if (mode == mode_F) {
418 static ir_type *float_F[16] = {NULL, };
420 if (float_F[align] == NULL) {
421 float_F[align] = tp = new_type_primitive(mode);
422 /* set the specified alignment */
423 set_type_alignment_bytes(tp, align);
425 return float_F[align];
426 } else if (mode == mode_D) {
427 static ir_type *float_D[16] = {NULL, };
429 if (float_D[align] == NULL) {
430 float_D[align] = tp = new_type_primitive(mode);
431 /* set the specified alignment */
432 set_type_alignment_bytes(tp, align);
434 return float_D[align];
436 static ir_type *float_E[16] = {NULL, };
438 if (float_E[align] == NULL) {
439 float_E[align] = tp = new_type_primitive(mode);
440 /* set the specified alignment */
441 set_type_alignment_bytes(tp, align);
443 return float_E[align];
448 * Create a float[2] array type for the given atomic type.
450 * @param tp the atomic type
452 static ir_type *ia32_create_float_array(ir_type *tp)
454 ir_mode *mode = get_type_mode(tp);
455 unsigned align = get_type_alignment_bytes(tp);
460 if (mode == mode_F) {
461 static ir_type *float_F[16] = {NULL, };
463 if (float_F[align] != NULL)
464 return float_F[align];
465 arr = float_F[align] = new_type_array(1, tp);
466 } else if (mode == mode_D) {
467 static ir_type *float_D[16] = {NULL, };
469 if (float_D[align] != NULL)
470 return float_D[align];
471 arr = float_D[align] = new_type_array(1, tp);
473 static ir_type *float_E[16] = {NULL, };
475 if (float_E[align] != NULL)
476 return float_E[align];
477 arr = float_E[align] = new_type_array(1, tp);
479 set_type_alignment_bytes(arr, align);
480 set_type_size_bytes(arr, 2 * get_type_size_bytes(tp));
481 set_type_state(arr, layout_fixed);
485 /* Generates an entity for a known FP const (used for FP Neg + Abs) */
486 ir_entity *ia32_gen_fp_known_const(ia32_known_const_t kct)
488 static const struct {
489 const char *ent_name;
490 const char *cnst_str;
493 } names [ia32_known_const_max] = {
494 { ENT_SFP_SIGN, SFP_SIGN, 0, 16 }, /* ia32_SSIGN */
495 { ENT_DFP_SIGN, DFP_SIGN, 1, 16 }, /* ia32_DSIGN */
496 { ENT_SFP_ABS, SFP_ABS, 0, 16 }, /* ia32_SABS */
497 { ENT_DFP_ABS, DFP_ABS, 1, 16 }, /* ia32_DABS */
498 { ENT_ULL_BIAS, ULL_BIAS, 2, 4 } /* ia32_ULLBIAS */
500 static ir_entity *ent_cache[ia32_known_const_max];
502 const char *ent_name, *cnst_str;
508 ent_name = names[kct].ent_name;
509 if (! ent_cache[kct]) {
510 cnst_str = names[kct].cnst_str;
512 switch (names[kct].mode) {
513 case 0: mode = mode_Iu; break;
514 case 1: mode = mode_Lu; break;
515 default: mode = mode_F; break;
517 tv = new_tarval_from_str(cnst_str, strlen(cnst_str), mode);
518 tp = ia32_create_float_type(mode, names[kct].align);
520 if (kct == ia32_ULLBIAS)
521 tp = ia32_create_float_array(tp);
522 ent = new_entity(get_glob_type(), new_id_from_str(ent_name), tp);
524 set_entity_ld_ident(ent, get_entity_ident(ent));
525 add_entity_linkage(ent, IR_LINKAGE_CONSTANT);
526 set_entity_visibility(ent, ir_visibility_private);
528 if (kct == ia32_ULLBIAS) {
529 ir_initializer_t *initializer = create_initializer_compound(2);
531 set_initializer_compound_value(initializer, 0,
532 create_initializer_tarval(get_mode_null(mode)));
533 set_initializer_compound_value(initializer, 1,
534 create_initializer_tarval(tv));
536 set_entity_initializer(ent, initializer);
538 set_entity_initializer(ent, create_initializer_tarval(tv));
541 /* cache the entry */
542 ent_cache[kct] = ent;
545 return ent_cache[kct];
549 * return true if the node is a Proj(Load) and could be used in source address
550 * mode for another node. Will return only true if the @p other node is not
551 * dependent on the memory of the Load (for binary operations use the other
552 * input here, for unary operations use NULL).
554 static int ia32_use_source_address_mode(ir_node *block, ir_node *node,
555 ir_node *other, ir_node *other2, match_flags_t flags)
560 /* float constants are always available */
561 if (is_Const(node)) {
562 ir_mode *mode = get_irn_mode(node);
563 if (mode_is_float(mode)) {
564 if (ia32_cg_config.use_sse2) {
565 if (is_simple_sse_Const(node))
568 if (is_simple_x87_Const(node))
571 if (get_irn_n_edges(node) > 1)
579 load = get_Proj_pred(node);
580 pn = get_Proj_proj(node);
581 if (!is_Load(load) || pn != pn_Load_res)
583 if (get_nodes_block(load) != block)
585 /* we only use address mode if we're the only user of the load */
586 if (get_irn_n_edges(node) != (flags & match_two_users ? 2 : 1))
588 /* in some edge cases with address mode we might reach the load normally
589 * and through some AM sequence, if it is already materialized then we
590 * can't create an AM node from it */
591 if (be_is_transformed(node))
594 /* don't do AM if other node inputs depend on the load (via mem-proj) */
595 if (other != NULL && ia32_prevents_AM(block, load, other))
598 if (other2 != NULL && ia32_prevents_AM(block, load, other2))
604 typedef struct ia32_address_mode_t ia32_address_mode_t;
605 struct ia32_address_mode_t {
610 ia32_op_type_t op_type;
614 unsigned commutative : 1;
615 unsigned ins_permuted : 1;
618 static void build_address_ptr(ia32_address_t *addr, ir_node *ptr, ir_node *mem)
620 /* construct load address */
621 memset(addr, 0, sizeof(addr[0]));
622 ia32_create_address_mode(addr, ptr, ia32_create_am_normal);
624 addr->base = addr->base ? be_transform_node(addr->base) : noreg_GP;
625 addr->index = addr->index ? be_transform_node(addr->index) : noreg_GP;
626 addr->mem = be_transform_node(mem);
629 static void build_address(ia32_address_mode_t *am, ir_node *node,
630 ia32_create_am_flags_t flags)
632 ia32_address_t *addr = &am->addr;
638 /* floating point immediates */
639 if (is_Const(node)) {
640 ir_entity *entity = ia32_create_float_const_entity(node);
641 addr->base = get_symconst_base();
642 addr->index = noreg_GP;
644 addr->symconst_ent = entity;
645 addr->tls_segment = false;
647 am->ls_mode = get_type_mode(get_entity_type(entity));
648 am->pinned = op_pin_state_floats;
652 load = get_Proj_pred(node);
653 ptr = get_Load_ptr(load);
654 mem = get_Load_mem(load);
655 new_mem = be_transform_node(mem);
656 am->pinned = get_irn_pinned(load);
657 am->ls_mode = get_Load_mode(load);
658 am->mem_proj = be_get_Proj_for_pn(load, pn_Load_M);
661 /* construct load address */
662 ia32_create_address_mode(addr, ptr, flags);
664 addr->base = addr->base ? be_transform_node(addr->base) : noreg_GP;
665 addr->index = addr->index ? be_transform_node(addr->index) : noreg_GP;
669 static void set_address(ir_node *node, const ia32_address_t *addr)
671 set_ia32_am_scale(node, addr->scale);
672 set_ia32_am_sc(node, addr->symconst_ent);
673 set_ia32_am_offs_int(node, addr->offset);
674 set_ia32_am_tls_segment(node, addr->tls_segment);
675 if (addr->symconst_sign)
676 set_ia32_am_sc_sign(node);
678 set_ia32_use_frame(node);
679 set_ia32_frame_ent(node, addr->frame_entity);
683 * Apply attributes of a given address mode to a node.
685 static void set_am_attributes(ir_node *node, const ia32_address_mode_t *am)
687 set_address(node, &am->addr);
689 set_ia32_op_type(node, am->op_type);
690 set_ia32_ls_mode(node, am->ls_mode);
691 if (am->pinned == op_pin_state_pinned) {
692 /* beware: some nodes are already pinned and did not allow to change the state */
693 if (get_irn_pinned(node) != op_pin_state_pinned)
694 set_irn_pinned(node, op_pin_state_pinned);
697 set_ia32_commutative(node);
701 * Check, if a given node is a Down-Conv, ie. a integer Conv
702 * from a mode with a mode with more bits to a mode with lesser bits.
703 * Moreover, we return only true if the node has not more than 1 user.
705 * @param node the node
706 * @return non-zero if node is a Down-Conv
708 static int is_downconv(const ir_node *node)
716 /* we only want to skip the conv when we're the only user
717 * (because this test is used in the context of address-mode selection
718 * and we don't want to use address mode for multiple users) */
719 if (get_irn_n_edges(node) > 1)
722 src_mode = get_irn_mode(get_Conv_op(node));
723 dest_mode = get_irn_mode(node);
725 ia32_mode_needs_gp_reg(src_mode) &&
726 ia32_mode_needs_gp_reg(dest_mode) &&
727 get_mode_size_bits(dest_mode) <= get_mode_size_bits(src_mode);
730 /** Skip all Down-Conv's on a given node and return the resulting node. */
731 ir_node *ia32_skip_downconv(ir_node *node)
733 while (is_downconv(node))
734 node = get_Conv_op(node);
739 static bool is_sameconv(ir_node *node)
747 /* we only want to skip the conv when we're the only user
748 * (because this test is used in the context of address-mode selection
749 * and we don't want to use address mode for multiple users) */
750 if (get_irn_n_edges(node) > 1)
753 src_mode = get_irn_mode(get_Conv_op(node));
754 dest_mode = get_irn_mode(node);
756 ia32_mode_needs_gp_reg(src_mode) &&
757 ia32_mode_needs_gp_reg(dest_mode) &&
758 get_mode_size_bits(dest_mode) == get_mode_size_bits(src_mode);
761 /** Skip all signedness convs */
762 static ir_node *ia32_skip_sameconv(ir_node *node)
764 while (is_sameconv(node))
765 node = get_Conv_op(node);
770 static ir_node *create_upconv(ir_node *node, ir_node *orig_node)
772 ir_mode *mode = get_irn_mode(node);
777 if (mode_is_signed(mode)) {
782 block = get_nodes_block(node);
783 dbgi = get_irn_dbg_info(node);
785 return create_I2I_Conv(mode, tgt_mode, dbgi, block, node, orig_node);
789 * matches operands of a node into ia32 addressing/operand modes. This covers
790 * usage of source address mode, immediates, operations with non 32-bit modes,
792 * The resulting data is filled into the @p am struct. block is the block
793 * of the node whose arguments are matched. op1, op2 are the first and second
794 * input that are matched (op1 may be NULL). other_op is another unrelated
795 * input that is not matched! but which is needed sometimes to check if AM
796 * for op1/op2 is legal.
797 * @p flags describes the supported modes of the operation in detail.
799 static void match_arguments(ia32_address_mode_t *am, ir_node *block,
800 ir_node *op1, ir_node *op2, ir_node *other_op,
803 ia32_address_t *addr = &am->addr;
804 ir_mode *mode = get_irn_mode(op2);
805 int mode_bits = get_mode_size_bits(mode);
806 ir_node *new_op1, *new_op2;
808 unsigned commutative;
809 int use_am_and_immediates;
812 memset(am, 0, sizeof(am[0]));
814 commutative = (flags & match_commutative) != 0;
815 use_am_and_immediates = (flags & match_am_and_immediates) != 0;
816 use_am = (flags & match_am) != 0;
817 use_immediate = (flags & match_immediate) != 0;
818 assert(!use_am_and_immediates || use_immediate);
821 assert(!commutative || op1 != NULL);
822 assert(use_am || !(flags & match_8bit_am));
823 assert(use_am || !(flags & match_16bit_am));
825 if ((mode_bits == 8 && !(flags & match_8bit_am)) ||
826 (mode_bits == 16 && !(flags & match_16bit_am))) {
830 /* we can simply skip downconvs for mode neutral nodes: the upper bits
831 * can be random for these operations */
832 if (flags & match_mode_neutral) {
833 op2 = ia32_skip_downconv(op2);
835 op1 = ia32_skip_downconv(op1);
838 op2 = ia32_skip_sameconv(op2);
840 op1 = ia32_skip_sameconv(op1);
844 /* match immediates. firm nodes are normalized: constants are always on the
847 if (!(flags & match_try_am) && use_immediate) {
848 new_op2 = ia32_try_create_Immediate(op2, 0);
851 if (new_op2 == NULL &&
852 use_am && ia32_use_source_address_mode(block, op2, op1, other_op, flags)) {
853 build_address(am, op2, ia32_create_am_normal);
854 new_op1 = (op1 == NULL ? NULL : be_transform_node(op1));
855 if (mode_is_float(mode)) {
856 new_op2 = ia32_new_NoReg_vfp(current_ir_graph);
860 am->op_type = ia32_AddrModeS;
861 } else if (commutative && (new_op2 == NULL || use_am_and_immediates) &&
863 ia32_use_source_address_mode(block, op1, op2, other_op, flags)) {
865 build_address(am, op1, ia32_create_am_normal);
867 if (mode_is_float(mode)) {
868 noreg = ia32_new_NoReg_vfp(current_ir_graph);
873 if (new_op2 != NULL) {
876 new_op1 = be_transform_node(op2);
878 am->ins_permuted = true;
880 am->op_type = ia32_AddrModeS;
883 am->op_type = ia32_Normal;
885 if (flags & match_try_am) {
891 mode = get_irn_mode(op2);
892 if (flags & match_upconv_32 && get_mode_size_bits(mode) != 32) {
893 new_op1 = (op1 == NULL ? NULL : create_upconv(op1, NULL));
895 new_op2 = create_upconv(op2, NULL);
896 am->ls_mode = mode_Iu;
898 new_op1 = (op1 == NULL ? NULL : be_transform_node(op1));
900 new_op2 = be_transform_node(op2);
901 am->ls_mode = (flags & match_mode_neutral) ? mode_Iu : mode;
904 if (addr->base == NULL)
905 addr->base = noreg_GP;
906 if (addr->index == NULL)
907 addr->index = noreg_GP;
908 if (addr->mem == NULL)
911 am->new_op1 = new_op1;
912 am->new_op2 = new_op2;
913 am->commutative = commutative;
917 * "Fixes" a node that uses address mode by turning it into mode_T
918 * and returning a pn_ia32_res Proj.
920 * @param node the node
921 * @param am its address mode
923 * @return a Proj(pn_ia32_res) if a memory address mode is used,
926 static ir_node *fix_mem_proj(ir_node *node, ia32_address_mode_t *am)
931 if (am->mem_proj == NULL)
934 /* we have to create a mode_T so the old MemProj can attach to us */
935 mode = get_irn_mode(node);
936 load = get_Proj_pred(am->mem_proj);
938 be_set_transformed_node(load, node);
940 if (mode != mode_T) {
941 set_irn_mode(node, mode_T);
942 return new_rd_Proj(NULL, node, mode, pn_ia32_res);
949 * Construct a standard binary operation, set AM and immediate if required.
951 * @param node The original node for which the binop is created
952 * @param op1 The first operand
953 * @param op2 The second operand
954 * @param func The node constructor function
955 * @return The constructed ia32 node.
957 static ir_node *gen_binop(ir_node *node, ir_node *op1, ir_node *op2,
958 construct_binop_func *func, match_flags_t flags)
961 ir_node *block, *new_block, *new_node;
962 ia32_address_mode_t am;
963 ia32_address_t *addr = &am.addr;
965 block = get_nodes_block(node);
966 match_arguments(&am, block, op1, op2, NULL, flags);
968 dbgi = get_irn_dbg_info(node);
969 new_block = be_transform_node(block);
970 new_node = func(dbgi, new_block, addr->base, addr->index, addr->mem,
971 am.new_op1, am.new_op2);
972 set_am_attributes(new_node, &am);
973 /* we can't use source address mode anymore when using immediates */
974 if (!(flags & match_am_and_immediates) &&
975 (is_ia32_Immediate(am.new_op1) || is_ia32_Immediate(am.new_op2)))
976 set_ia32_am_support(new_node, ia32_am_none);
977 SET_IA32_ORIG_NODE(new_node, node);
979 new_node = fix_mem_proj(new_node, &am);
985 * Generic names for the inputs of an ia32 binary op.
988 n_ia32_l_binop_left, /**< ia32 left input */
989 n_ia32_l_binop_right, /**< ia32 right input */
990 n_ia32_l_binop_eflags /**< ia32 eflags input */
992 COMPILETIME_ASSERT((int)n_ia32_l_binop_left == (int)n_ia32_l_Adc_left, n_Adc_left)
993 COMPILETIME_ASSERT((int)n_ia32_l_binop_right == (int)n_ia32_l_Adc_right, n_Adc_right)
994 COMPILETIME_ASSERT((int)n_ia32_l_binop_eflags == (int)n_ia32_l_Adc_eflags, n_Adc_eflags)
995 COMPILETIME_ASSERT((int)n_ia32_l_binop_left == (int)n_ia32_l_Sbb_minuend, n_Sbb_minuend)
996 COMPILETIME_ASSERT((int)n_ia32_l_binop_right == (int)n_ia32_l_Sbb_subtrahend, n_Sbb_subtrahend)
997 COMPILETIME_ASSERT((int)n_ia32_l_binop_eflags == (int)n_ia32_l_Sbb_eflags, n_Sbb_eflags)
1000 * Construct a binary operation which also consumes the eflags.
1002 * @param node The node to transform
1003 * @param func The node constructor function
1004 * @param flags The match flags
1005 * @return The constructor ia32 node
1007 static ir_node *gen_binop_flags(ir_node *node, construct_binop_flags_func *func,
1008 match_flags_t flags)
1010 ir_node *src_block = get_nodes_block(node);
1011 ir_node *op1 = get_irn_n(node, n_ia32_l_binop_left);
1012 ir_node *op2 = get_irn_n(node, n_ia32_l_binop_right);
1013 ir_node *eflags = get_irn_n(node, n_ia32_l_binop_eflags);
1015 ir_node *block, *new_node, *new_eflags;
1016 ia32_address_mode_t am;
1017 ia32_address_t *addr = &am.addr;
1019 match_arguments(&am, src_block, op1, op2, eflags, flags);
1021 dbgi = get_irn_dbg_info(node);
1022 block = be_transform_node(src_block);
1023 new_eflags = be_transform_node(eflags);
1024 new_node = func(dbgi, block, addr->base, addr->index, addr->mem,
1025 am.new_op1, am.new_op2, new_eflags);
1026 set_am_attributes(new_node, &am);
1027 /* we can't use source address mode anymore when using immediates */
1028 if (!(flags & match_am_and_immediates) &&
1029 (is_ia32_Immediate(am.new_op1) || is_ia32_Immediate(am.new_op2)))
1030 set_ia32_am_support(new_node, ia32_am_none);
1031 SET_IA32_ORIG_NODE(new_node, node);
1033 new_node = fix_mem_proj(new_node, &am);
1038 static ir_node *get_fpcw(void)
1041 if (initial_fpcw != NULL)
1042 return initial_fpcw;
1044 fpcw = be_abi_get_ignore_irn(current_ir_graph,
1045 &ia32_registers[REG_FPCW]);
1046 initial_fpcw = be_transform_node(fpcw);
1048 return initial_fpcw;
1052 * Construct a standard binary operation, set AM and immediate if required.
1054 * @param op1 The first operand
1055 * @param op2 The second operand
1056 * @param func The node constructor function
1057 * @return The constructed ia32 node.
1059 static ir_node *gen_binop_x87_float(ir_node *node, ir_node *op1, ir_node *op2,
1060 construct_binop_float_func *func)
1062 ir_mode *mode = get_irn_mode(node);
1064 ir_node *block, *new_block, *new_node;
1065 ia32_address_mode_t am;
1066 ia32_address_t *addr = &am.addr;
1067 ia32_x87_attr_t *attr;
1068 /* All operations are considered commutative, because there are reverse
1070 match_flags_t flags = match_commutative;
1072 /* happens for div nodes... */
1073 if (mode == mode_T) {
1075 mode = get_Div_resmode(node);
1077 panic("can't determine mode");
1080 /* cannot use address mode with long double on x87 */
1081 if (get_mode_size_bits(mode) <= 64)
1084 block = get_nodes_block(node);
1085 match_arguments(&am, block, op1, op2, NULL, flags);
1087 dbgi = get_irn_dbg_info(node);
1088 new_block = be_transform_node(block);
1089 new_node = func(dbgi, new_block, addr->base, addr->index, addr->mem,
1090 am.new_op1, am.new_op2, get_fpcw());
1091 set_am_attributes(new_node, &am);
1093 attr = get_ia32_x87_attr(new_node);
1094 attr->attr.data.ins_permuted = am.ins_permuted;
1096 SET_IA32_ORIG_NODE(new_node, node);
1098 new_node = fix_mem_proj(new_node, &am);
1104 * Construct a shift/rotate binary operation, sets AM and immediate if required.
1106 * @param op1 The first operand
1107 * @param op2 The second operand
1108 * @param func The node constructor function
1109 * @return The constructed ia32 node.
1111 static ir_node *gen_shift_binop(ir_node *node, ir_node *op1, ir_node *op2,
1112 construct_shift_func *func,
1113 match_flags_t flags)
1116 ir_node *block, *new_block, *new_op1, *new_op2, *new_node;
1118 assert(! mode_is_float(get_irn_mode(node)));
1119 assert(flags & match_immediate);
1120 assert((flags & ~(match_mode_neutral | match_immediate)) == 0);
1122 if (flags & match_mode_neutral) {
1123 op1 = ia32_skip_downconv(op1);
1124 new_op1 = be_transform_node(op1);
1125 } else if (get_mode_size_bits(get_irn_mode(node)) != 32) {
1126 new_op1 = create_upconv(op1, node);
1128 new_op1 = be_transform_node(op1);
1131 /* the shift amount can be any mode that is bigger than 5 bits, since all
1132 * other bits are ignored anyway */
1133 while (is_Conv(op2) && get_irn_n_edges(op2) == 1) {
1134 ir_node *const op = get_Conv_op(op2);
1135 if (mode_is_float(get_irn_mode(op)))
1138 assert(get_mode_size_bits(get_irn_mode(op2)) >= 5);
1140 new_op2 = create_immediate_or_transform(op2, 0);
1142 dbgi = get_irn_dbg_info(node);
1143 block = get_nodes_block(node);
1144 new_block = be_transform_node(block);
1145 new_node = func(dbgi, new_block, new_op1, new_op2);
1146 SET_IA32_ORIG_NODE(new_node, node);
1148 /* lowered shift instruction may have a dependency operand, handle it here */
1149 if (get_irn_arity(node) == 3) {
1150 /* we have a dependency */
1151 ir_node* dep = get_irn_n(node, 2);
1152 if (get_irn_n_edges(dep) > 1) {
1153 /* ... which has at least one user other than 'node' */
1154 ir_node *new_dep = be_transform_node(dep);
1155 add_irn_dep(new_node, new_dep);
1164 * Construct a standard unary operation, set AM and immediate if required.
1166 * @param op The operand
1167 * @param func The node constructor function
1168 * @return The constructed ia32 node.
1170 static ir_node *gen_unop(ir_node *node, ir_node *op, construct_unop_func *func,
1171 match_flags_t flags)
1174 ir_node *block, *new_block, *new_op, *new_node;
1176 assert(flags == 0 || flags == match_mode_neutral);
1177 if (flags & match_mode_neutral) {
1178 op = ia32_skip_downconv(op);
1181 new_op = be_transform_node(op);
1182 dbgi = get_irn_dbg_info(node);
1183 block = get_nodes_block(node);
1184 new_block = be_transform_node(block);
1185 new_node = func(dbgi, new_block, new_op);
1187 SET_IA32_ORIG_NODE(new_node, node);
1192 static ir_node *create_lea_from_address(dbg_info *dbgi, ir_node *block,
1193 ia32_address_t *addr)
1195 ir_node *base, *index, *res;
1201 base = be_transform_node(base);
1204 index = addr->index;
1205 if (index == NULL) {
1208 index = be_transform_node(index);
1211 /* segment overrides are ineffective for Leas :-( so we have to patch
1213 if (addr->tls_segment) {
1214 ir_node *tls_base = new_bd_ia32_LdTls(NULL, block);
1215 assert(addr->symconst_ent != NULL);
1216 if (base == noreg_GP)
1219 base = new_bd_ia32_Lea(dbgi, block, tls_base, base);
1220 addr->tls_segment = false;
1223 res = new_bd_ia32_Lea(dbgi, block, base, index);
1224 set_address(res, addr);
1230 * Returns non-zero if a given address mode has a symbolic or
1231 * numerical offset != 0.
1233 static int am_has_immediates(const ia32_address_t *addr)
1235 return addr->offset != 0 || addr->symconst_ent != NULL
1236 || addr->frame_entity || addr->use_frame;
1240 * Creates an ia32 Add.
1242 * @return the created ia32 Add node
1244 static ir_node *gen_Add(ir_node *node)
1246 ir_mode *mode = get_irn_mode(node);
1247 ir_node *op1 = get_Add_left(node);
1248 ir_node *op2 = get_Add_right(node);
1250 ir_node *block, *new_block, *new_node, *add_immediate_op;
1251 ia32_address_t addr;
1252 ia32_address_mode_t am;
1254 if (mode_is_float(mode)) {
1255 if (ia32_cg_config.use_sse2)
1256 return gen_binop(node, op1, op2, new_bd_ia32_xAdd,
1257 match_commutative | match_am);
1259 return gen_binop_x87_float(node, op1, op2, new_bd_ia32_vfadd);
1262 ia32_mark_non_am(node);
1264 op2 = ia32_skip_downconv(op2);
1265 op1 = ia32_skip_downconv(op1);
1269 * 0. Immediate Trees (example Add(Symconst, Const) -> Const)
1270 * 1. Add with immediate -> Lea
1271 * 2. Add with possible source address mode -> Add
1272 * 3. Otherwise -> Lea
1274 memset(&addr, 0, sizeof(addr));
1275 ia32_create_address_mode(&addr, node, ia32_create_am_force);
1276 add_immediate_op = NULL;
1278 dbgi = get_irn_dbg_info(node);
1279 block = get_nodes_block(node);
1280 new_block = be_transform_node(block);
1283 if (addr.base == NULL && addr.index == NULL) {
1284 new_node = new_bd_ia32_Const(dbgi, new_block, addr.symconst_ent,
1285 addr.symconst_sign, 0, addr.offset);
1286 SET_IA32_ORIG_NODE(new_node, node);
1289 /* add with immediate? */
1290 if (addr.index == NULL) {
1291 add_immediate_op = addr.base;
1292 } else if (addr.base == NULL && addr.scale == 0) {
1293 add_immediate_op = addr.index;
1296 if (add_immediate_op != NULL) {
1297 if (!am_has_immediates(&addr)) {
1298 #ifdef DEBUG_libfirm
1299 ir_fprintf(stderr, "Optimisation warning Add x,0 (%+F) found\n",
1302 return be_transform_node(add_immediate_op);
1305 new_node = create_lea_from_address(dbgi, new_block, &addr);
1306 SET_IA32_ORIG_NODE(new_node, node);
1310 /* test if we can use source address mode */
1311 match_arguments(&am, block, op1, op2, NULL, match_commutative
1312 | match_mode_neutral | match_am | match_immediate | match_try_am);
1314 /* construct an Add with source address mode */
1315 if (am.op_type == ia32_AddrModeS) {
1316 ia32_address_t *am_addr = &am.addr;
1317 new_node = new_bd_ia32_Add(dbgi, new_block, am_addr->base,
1318 am_addr->index, am_addr->mem, am.new_op1,
1320 set_am_attributes(new_node, &am);
1321 SET_IA32_ORIG_NODE(new_node, node);
1323 new_node = fix_mem_proj(new_node, &am);
1328 /* otherwise construct a lea */
1329 new_node = create_lea_from_address(dbgi, new_block, &addr);
1330 SET_IA32_ORIG_NODE(new_node, node);
1335 * Creates an ia32 Mul.
1337 * @return the created ia32 Mul node
1339 static ir_node *gen_Mul(ir_node *node)
1341 ir_node *op1 = get_Mul_left(node);
1342 ir_node *op2 = get_Mul_right(node);
1343 ir_mode *mode = get_irn_mode(node);
1345 if (mode_is_float(mode)) {
1346 if (ia32_cg_config.use_sse2)
1347 return gen_binop(node, op1, op2, new_bd_ia32_xMul,
1348 match_commutative | match_am);
1350 return gen_binop_x87_float(node, op1, op2, new_bd_ia32_vfmul);
1352 return gen_binop(node, op1, op2, new_bd_ia32_IMul,
1353 match_commutative | match_am | match_mode_neutral |
1354 match_immediate | match_am_and_immediates);
1358 * Creates an ia32 Mulh.
1359 * Note: Mul produces a 64Bit result and Mulh returns the upper 32 bit of
1360 * this result while Mul returns the lower 32 bit.
1362 * @return the created ia32 Mulh node
1364 static ir_node *gen_Mulh(ir_node *node)
1366 dbg_info *dbgi = get_irn_dbg_info(node);
1367 ir_node *op1 = get_Mulh_left(node);
1368 ir_node *op2 = get_Mulh_right(node);
1369 ir_mode *mode = get_irn_mode(node);
1371 ir_node *proj_res_high;
1373 if (get_mode_size_bits(mode) != 32) {
1374 panic("Mulh without 32bit size not supported in ia32 backend (%+F)", node);
1377 if (mode_is_signed(mode)) {
1378 new_node = gen_binop(node, op1, op2, new_bd_ia32_IMul1OP, match_commutative | match_am);
1379 proj_res_high = new_rd_Proj(dbgi, new_node, mode_Iu, pn_ia32_IMul1OP_res_high);
1381 new_node = gen_binop(node, op1, op2, new_bd_ia32_Mul, match_commutative | match_am);
1382 proj_res_high = new_rd_Proj(dbgi, new_node, mode_Iu, pn_ia32_Mul_res_high);
1384 return proj_res_high;
1388 * Creates an ia32 And.
1390 * @return The created ia32 And node
1392 static ir_node *gen_And(ir_node *node)
1394 ir_node *op1 = get_And_left(node);
1395 ir_node *op2 = get_And_right(node);
1396 assert(! mode_is_float(get_irn_mode(node)));
1398 /* is it a zero extension? */
1399 if (is_Const(op2)) {
1400 ir_tarval *tv = get_Const_tarval(op2);
1401 long v = get_tarval_long(tv);
1403 if (v == 0xFF || v == 0xFFFF) {
1404 dbg_info *dbgi = get_irn_dbg_info(node);
1405 ir_node *block = get_nodes_block(node);
1412 assert(v == 0xFFFF);
1415 res = create_I2I_Conv(src_mode, mode_Iu, dbgi, block, op1, node);
1420 return gen_binop(node, op1, op2, new_bd_ia32_And,
1421 match_commutative | match_mode_neutral | match_am | match_immediate);
1427 * Creates an ia32 Or.
1429 * @return The created ia32 Or node
1431 static ir_node *gen_Or(ir_node *node)
1433 ir_node *op1 = get_Or_left(node);
1434 ir_node *op2 = get_Or_right(node);
1436 assert (! mode_is_float(get_irn_mode(node)));
1437 return gen_binop(node, op1, op2, new_bd_ia32_Or, match_commutative
1438 | match_mode_neutral | match_am | match_immediate);
1444 * Creates an ia32 Eor.
1446 * @return The created ia32 Eor node
1448 static ir_node *gen_Eor(ir_node *node)
1450 ir_node *op1 = get_Eor_left(node);
1451 ir_node *op2 = get_Eor_right(node);
1453 assert(! mode_is_float(get_irn_mode(node)));
1454 return gen_binop(node, op1, op2, new_bd_ia32_Xor, match_commutative
1455 | match_mode_neutral | match_am | match_immediate);
1460 * Creates an ia32 Sub.
1462 * @return The created ia32 Sub node
1464 static ir_node *gen_Sub(ir_node *node)
1466 ir_node *op1 = get_Sub_left(node);
1467 ir_node *op2 = get_Sub_right(node);
1468 ir_mode *mode = get_irn_mode(node);
1470 if (mode_is_float(mode)) {
1471 if (ia32_cg_config.use_sse2)
1472 return gen_binop(node, op1, op2, new_bd_ia32_xSub, match_am);
1474 return gen_binop_x87_float(node, op1, op2, new_bd_ia32_vfsub);
1477 if (is_Const(op2)) {
1478 ir_fprintf(stderr, "Optimisation warning: found sub with const (%+F)\n",
1482 return gen_binop(node, op1, op2, new_bd_ia32_Sub, match_mode_neutral
1483 | match_am | match_immediate);
1486 static ir_node *transform_AM_mem(ir_node *const block,
1487 ir_node *const src_val,
1488 ir_node *const src_mem,
1489 ir_node *const am_mem)
1491 if (is_NoMem(am_mem)) {
1492 return be_transform_node(src_mem);
1493 } else if (is_Proj(src_val) &&
1495 get_Proj_pred(src_val) == get_Proj_pred(src_mem)) {
1496 /* avoid memory loop */
1498 } else if (is_Proj(src_val) && is_Sync(src_mem)) {
1499 ir_node *const ptr_pred = get_Proj_pred(src_val);
1500 int const arity = get_Sync_n_preds(src_mem);
1505 NEW_ARR_A(ir_node*, ins, arity + 1);
1507 /* NOTE: This sometimes produces dead-code because the old sync in
1508 * src_mem might not be used anymore, we should detect this case
1509 * and kill the sync... */
1510 for (i = arity - 1; i >= 0; --i) {
1511 ir_node *const pred = get_Sync_pred(src_mem, i);
1513 /* avoid memory loop */
1514 if (is_Proj(pred) && get_Proj_pred(pred) == ptr_pred)
1517 ins[n++] = be_transform_node(pred);
1520 if (n==1 && ins[0] == am_mem) {
1522 /* creating a new Sync and relying on CSE may fail,
1523 * if am_mem is a ProjM, which does not yet verify. */
1527 return new_r_Sync(block, n, ins);
1531 ins[0] = be_transform_node(src_mem);
1533 return new_r_Sync(block, 2, ins);
1538 * Create a 32bit to 64bit signed extension.
1540 * @param dbgi debug info
1541 * @param block the block where node nodes should be placed
1542 * @param val the value to extend
1543 * @param orig the original node
1545 static ir_node *create_sex_32_64(dbg_info *dbgi, ir_node *block,
1546 ir_node *val, const ir_node *orig)
1551 if (ia32_cg_config.use_short_sex_eax) {
1552 ir_node *pval = new_bd_ia32_ProduceVal(dbgi, block);
1553 res = new_bd_ia32_Cltd(dbgi, block, val, pval);
1555 ir_node *imm31 = ia32_create_Immediate(NULL, 0, 31);
1556 res = new_bd_ia32_Sar(dbgi, block, val, imm31);
1558 SET_IA32_ORIG_NODE(res, orig);
1563 * Generates an ia32 Div with additional infrastructure for the
1564 * register allocator if needed.
1566 static ir_node *create_Div(ir_node *node)
1568 dbg_info *dbgi = get_irn_dbg_info(node);
1569 ir_node *block = get_nodes_block(node);
1570 ir_node *new_block = be_transform_node(block);
1577 ir_node *sign_extension;
1578 ia32_address_mode_t am;
1579 ia32_address_t *addr = &am.addr;
1581 /* the upper bits have random contents for smaller modes */
1582 switch (get_irn_opcode(node)) {
1584 op1 = get_Div_left(node);
1585 op2 = get_Div_right(node);
1586 mem = get_Div_mem(node);
1587 mode = get_Div_resmode(node);
1590 op1 = get_Mod_left(node);
1591 op2 = get_Mod_right(node);
1592 mem = get_Mod_mem(node);
1593 mode = get_Mod_resmode(node);
1596 panic("invalid divmod node %+F", node);
1599 match_arguments(&am, block, op1, op2, NULL, match_am | match_upconv_32);
1601 /* Beware: We don't need a Sync, if the memory predecessor of the Div node
1602 is the memory of the consumed address. We can have only the second op as address
1603 in Div nodes, so check only op2. */
1604 new_mem = transform_AM_mem(block, op2, mem, addr->mem);
1606 if (mode_is_signed(mode)) {
1607 sign_extension = create_sex_32_64(dbgi, new_block, am.new_op1, node);
1608 new_node = new_bd_ia32_IDiv(dbgi, new_block, addr->base,
1609 addr->index, new_mem, am.new_op2, am.new_op1, sign_extension);
1611 sign_extension = new_bd_ia32_Const(dbgi, new_block, NULL, 0, 0, 0);
1613 new_node = new_bd_ia32_Div(dbgi, new_block, addr->base,
1614 addr->index, new_mem, am.new_op2,
1615 am.new_op1, sign_extension);
1618 set_irn_pinned(new_node, get_irn_pinned(node));
1620 set_am_attributes(new_node, &am);
1621 SET_IA32_ORIG_NODE(new_node, node);
1623 new_node = fix_mem_proj(new_node, &am);
1629 * Generates an ia32 Mod.
1631 static ir_node *gen_Mod(ir_node *node)
1633 return create_Div(node);
1637 * Generates an ia32 Div.
1639 static ir_node *gen_Div(ir_node *node)
1641 ir_mode *mode = get_Div_resmode(node);
1642 if (mode_is_float(mode)) {
1643 ir_node *op1 = get_Div_left(node);
1644 ir_node *op2 = get_Div_right(node);
1646 if (ia32_cg_config.use_sse2) {
1647 return gen_binop(node, op1, op2, new_bd_ia32_xDiv, match_am);
1649 return gen_binop_x87_float(node, op1, op2, new_bd_ia32_vfdiv);
1653 return create_Div(node);
1657 * Creates an ia32 Shl.
1659 * @return The created ia32 Shl node
1661 static ir_node *gen_Shl(ir_node *node)
1663 ir_node *left = get_Shl_left(node);
1664 ir_node *right = get_Shl_right(node);
1666 return gen_shift_binop(node, left, right, new_bd_ia32_Shl,
1667 match_mode_neutral | match_immediate);
1671 * Creates an ia32 Shr.
1673 * @return The created ia32 Shr node
1675 static ir_node *gen_Shr(ir_node *node)
1677 ir_node *left = get_Shr_left(node);
1678 ir_node *right = get_Shr_right(node);
1680 return gen_shift_binop(node, left, right, new_bd_ia32_Shr, match_immediate);
1686 * Creates an ia32 Sar.
1688 * @return The created ia32 Shrs node
1690 static ir_node *gen_Shrs(ir_node *node)
1692 ir_node *left = get_Shrs_left(node);
1693 ir_node *right = get_Shrs_right(node);
1695 if (is_Const(right)) {
1696 ir_tarval *tv = get_Const_tarval(right);
1697 long val = get_tarval_long(tv);
1699 /* this is a sign extension */
1700 dbg_info *dbgi = get_irn_dbg_info(node);
1701 ir_node *block = be_transform_node(get_nodes_block(node));
1702 ir_node *new_op = be_transform_node(left);
1704 return create_sex_32_64(dbgi, block, new_op, node);
1708 /* 8 or 16 bit sign extension? */
1709 if (is_Const(right) && is_Shl(left)) {
1710 ir_node *shl_left = get_Shl_left(left);
1711 ir_node *shl_right = get_Shl_right(left);
1712 if (is_Const(shl_right)) {
1713 ir_tarval *tv1 = get_Const_tarval(right);
1714 ir_tarval *tv2 = get_Const_tarval(shl_right);
1715 if (tv1 == tv2 && tarval_is_long(tv1)) {
1716 long val = get_tarval_long(tv1);
1717 if (val == 16 || val == 24) {
1718 dbg_info *dbgi = get_irn_dbg_info(node);
1719 ir_node *block = get_nodes_block(node);
1729 res = create_I2I_Conv(src_mode, mode_Is, dbgi, block,
1738 return gen_shift_binop(node, left, right, new_bd_ia32_Sar, match_immediate);
1744 * Creates an ia32 Rol.
1746 * @param op1 The first operator
1747 * @param op2 The second operator
1748 * @return The created ia32 RotL node
1750 static ir_node *gen_Rol(ir_node *node, ir_node *op1, ir_node *op2)
1752 return gen_shift_binop(node, op1, op2, new_bd_ia32_Rol, match_immediate);
1758 * Creates an ia32 Ror.
1759 * NOTE: There is no RotR with immediate because this would always be a RotL
1760 * "imm-mode_size_bits" which can be pre-calculated.
1762 * @param op1 The first operator
1763 * @param op2 The second operator
1764 * @return The created ia32 RotR node
1766 static ir_node *gen_Ror(ir_node *node, ir_node *op1, ir_node *op2)
1768 return gen_shift_binop(node, op1, op2, new_bd_ia32_Ror, match_immediate);
1774 * Creates an ia32 RotR or RotL (depending on the found pattern).
1776 * @return The created ia32 RotL or RotR node
1778 static ir_node *gen_Rotl(ir_node *node)
1780 ir_node *op1 = get_Rotl_left(node);
1781 ir_node *op2 = get_Rotl_right(node);
1783 if (is_Minus(op2)) {
1784 return gen_Ror(node, op1, get_Minus_op(op2));
1787 return gen_Rol(node, op1, op2);
1793 * Transforms a Minus node.
1795 * @return The created ia32 Minus node
1797 static ir_node *gen_Minus(ir_node *node)
1799 ir_node *op = get_Minus_op(node);
1800 ir_node *block = be_transform_node(get_nodes_block(node));
1801 dbg_info *dbgi = get_irn_dbg_info(node);
1802 ir_mode *mode = get_irn_mode(node);
1807 if (mode_is_float(mode)) {
1808 ir_node *new_op = be_transform_node(op);
1809 if (ia32_cg_config.use_sse2) {
1810 /* TODO: non-optimal... if we have many xXors, then we should
1811 * rather create a load for the const and use that instead of
1812 * several AM nodes... */
1813 ir_node *noreg_xmm = ia32_new_NoReg_xmm(current_ir_graph);
1815 new_node = new_bd_ia32_xXor(dbgi, block, get_symconst_base(),
1816 noreg_GP, nomem, new_op, noreg_xmm);
1818 size = get_mode_size_bits(mode);
1819 ent = ia32_gen_fp_known_const(size == 32 ? ia32_SSIGN : ia32_DSIGN);
1821 set_ia32_am_sc(new_node, ent);
1822 set_ia32_op_type(new_node, ia32_AddrModeS);
1823 set_ia32_ls_mode(new_node, mode);
1825 new_node = new_bd_ia32_vfchs(dbgi, block, new_op);
1828 new_node = gen_unop(node, op, new_bd_ia32_Neg, match_mode_neutral);
1831 SET_IA32_ORIG_NODE(new_node, node);
1837 * Transforms a Not node.
1839 * @return The created ia32 Not node
1841 static ir_node *gen_Not(ir_node *node)
1843 ir_node *op = get_Not_op(node);
1845 assert(get_irn_mode(node) != mode_b); /* should be lowered already */
1846 assert (! mode_is_float(get_irn_mode(node)));
1848 return gen_unop(node, op, new_bd_ia32_Not, match_mode_neutral);
1851 static ir_node *create_abs(dbg_info *dbgi, ir_node *block, ir_node *op,
1852 bool negate, ir_node *node)
1854 ir_node *new_block = be_transform_node(block);
1855 ir_mode *mode = get_irn_mode(op);
1861 if (mode_is_float(mode)) {
1862 new_op = be_transform_node(op);
1864 if (ia32_cg_config.use_sse2) {
1865 ir_node *noreg_fp = ia32_new_NoReg_xmm(current_ir_graph);
1866 new_node = new_bd_ia32_xAnd(dbgi, new_block, get_symconst_base(),
1867 noreg_GP, nomem, new_op, noreg_fp);
1869 size = get_mode_size_bits(mode);
1870 ent = ia32_gen_fp_known_const(size == 32 ? ia32_SABS : ia32_DABS);
1872 set_ia32_am_sc(new_node, ent);
1874 SET_IA32_ORIG_NODE(new_node, node);
1876 set_ia32_op_type(new_node, ia32_AddrModeS);
1877 set_ia32_ls_mode(new_node, mode);
1879 /* TODO, implement -Abs case */
1882 new_node = new_bd_ia32_vfabs(dbgi, new_block, new_op);
1883 SET_IA32_ORIG_NODE(new_node, node);
1885 new_node = new_bd_ia32_vfchs(dbgi, new_block, new_node);
1886 SET_IA32_ORIG_NODE(new_node, node);
1891 ir_node *sign_extension;
1893 if (get_mode_size_bits(mode) == 32) {
1894 new_op = be_transform_node(op);
1896 new_op = create_I2I_Conv(mode, mode_Is, dbgi, block, op, node);
1899 sign_extension = create_sex_32_64(dbgi, new_block, new_op, node);
1901 xorn = new_bd_ia32_Xor(dbgi, new_block, noreg_GP, noreg_GP,
1902 nomem, new_op, sign_extension);
1903 SET_IA32_ORIG_NODE(xorn, node);
1906 new_node = new_bd_ia32_Sub(dbgi, new_block, noreg_GP, noreg_GP,
1907 nomem, sign_extension, xorn);
1909 new_node = new_bd_ia32_Sub(dbgi, new_block, noreg_GP, noreg_GP,
1910 nomem, xorn, sign_extension);
1912 SET_IA32_ORIG_NODE(new_node, node);
1919 * Create a bt instruction for x & (1 << n) and place it into the block of cmp.
1921 static ir_node *gen_bt(ir_node *cmp, ir_node *x, ir_node *n)
1923 dbg_info *dbgi = get_irn_dbg_info(cmp);
1924 ir_node *block = get_nodes_block(cmp);
1925 ir_node *new_block = be_transform_node(block);
1926 ir_node *op1 = be_transform_node(x);
1927 ir_node *op2 = be_transform_node(n);
1929 return new_bd_ia32_Bt(dbgi, new_block, op1, op2);
1932 static ia32_condition_code_t relation_to_condition_code(ir_relation relation,
1935 if (mode_is_float(mode)) {
1937 case ir_relation_equal: return ia32_cc_float_equal;
1938 case ir_relation_less: return ia32_cc_float_below;
1939 case ir_relation_less_equal: return ia32_cc_float_below_equal;
1940 case ir_relation_greater: return ia32_cc_float_above;
1941 case ir_relation_greater_equal: return ia32_cc_float_above_equal;
1942 case ir_relation_less_greater: return ia32_cc_not_equal;
1943 case ir_relation_less_equal_greater: return ia32_cc_not_parity;
1944 case ir_relation_unordered: return ia32_cc_parity;
1945 case ir_relation_unordered_equal: return ia32_cc_equal;
1946 case ir_relation_unordered_less: return ia32_cc_float_unordered_below;
1947 case ir_relation_unordered_less_equal:
1948 return ia32_cc_float_unordered_below_equal;
1949 case ir_relation_unordered_greater:
1950 return ia32_cc_float_unordered_above;
1951 case ir_relation_unordered_greater_equal:
1952 return ia32_cc_float_unordered_above_equal;
1953 case ir_relation_unordered_less_greater:
1954 return ia32_cc_float_not_equal;
1955 case ir_relation_false:
1956 case ir_relation_true:
1957 /* should we introduce a jump always/jump never? */
1960 panic("Unexpected float pnc");
1961 } else if (mode_is_signed(mode)) {
1963 case ir_relation_unordered_equal:
1964 case ir_relation_equal: return ia32_cc_equal;
1965 case ir_relation_unordered_less:
1966 case ir_relation_less: return ia32_cc_less;
1967 case ir_relation_unordered_less_equal:
1968 case ir_relation_less_equal: return ia32_cc_less_equal;
1969 case ir_relation_unordered_greater:
1970 case ir_relation_greater: return ia32_cc_greater;
1971 case ir_relation_unordered_greater_equal:
1972 case ir_relation_greater_equal: return ia32_cc_greater_equal;
1973 case ir_relation_unordered_less_greater:
1974 case ir_relation_less_greater: return ia32_cc_not_equal;
1975 case ir_relation_less_equal_greater:
1976 case ir_relation_unordered:
1977 case ir_relation_false:
1978 case ir_relation_true:
1979 /* introduce jump always/jump never? */
1982 panic("Unexpected pnc");
1985 case ir_relation_unordered_equal:
1986 case ir_relation_equal: return ia32_cc_equal;
1987 case ir_relation_unordered_less:
1988 case ir_relation_less: return ia32_cc_below;
1989 case ir_relation_unordered_less_equal:
1990 case ir_relation_less_equal: return ia32_cc_below_equal;
1991 case ir_relation_unordered_greater:
1992 case ir_relation_greater: return ia32_cc_above;
1993 case ir_relation_unordered_greater_equal:
1994 case ir_relation_greater_equal: return ia32_cc_above_equal;
1995 case ir_relation_unordered_less_greater:
1996 case ir_relation_less_greater: return ia32_cc_not_equal;
1997 case ir_relation_less_equal_greater:
1998 case ir_relation_unordered:
1999 case ir_relation_false:
2000 case ir_relation_true:
2001 /* introduce jump always/jump never? */
2004 panic("Unexpected pnc");
2008 static ir_node *get_flags_mode_b(ir_node *node, ia32_condition_code_t *cc_out)
2010 /* a mode_b value, we have to compare it against 0 */
2011 dbg_info *dbgi = get_irn_dbg_info(node);
2012 ir_node *new_block = be_transform_node(get_nodes_block(node));
2013 ir_node *new_op = be_transform_node(node);
2014 ir_node *flags = new_bd_ia32_Test(dbgi, new_block, noreg_GP, noreg_GP, nomem, new_op, new_op, false);
2015 *cc_out = ia32_cc_not_equal;
2019 static ir_node *get_flags_node_cmp(ir_node *cmp, ia32_condition_code_t *cc_out)
2021 /* must have a Cmp as input */
2022 ir_relation relation = get_Cmp_relation(cmp);
2023 ir_relation possible;
2024 ir_node *l = get_Cmp_left(cmp);
2025 ir_node *r = get_Cmp_right(cmp);
2026 ir_mode *mode = get_irn_mode(l);
2029 /* check for bit-test */
2030 if (ia32_cg_config.use_bt && (relation == ir_relation_equal
2031 || (mode_is_signed(mode) && relation == ir_relation_less_greater)
2032 || (!mode_is_signed(mode) && ((relation & ir_relation_greater_equal) == ir_relation_greater)))
2034 ir_node *la = get_And_left(l);
2035 ir_node *ra = get_And_right(l);
2042 ir_node *c = get_Shl_left(la);
2043 if (is_Const_1(c) && is_Const_0(r)) {
2044 /* (1 << n) & ra) */
2045 ir_node *n = get_Shl_right(la);
2046 flags = gen_bt(cmp, ra, n);
2047 /* the bit is copied into the CF flag */
2048 if (relation & ir_relation_equal)
2049 *cc_out = ia32_cc_above_equal; /* test for CF=0 */
2051 *cc_out = ia32_cc_below; /* test for CF=1 */
2057 /* the middle-end tries to eliminate impossible relations, so a ptr != 0
2058 * test becomes ptr > 0. But for x86 an equal comparison is preferable to
2059 * a >0 (we can sometimes eliminate the cmp in favor of flags produced by
2060 * a predecessor node). So add the < bit */
2061 possible = ir_get_possible_cmp_relations(l, r);
2062 if (((relation & ir_relation_less) && !(possible & ir_relation_greater))
2063 || ((relation & ir_relation_greater) && !(possible & ir_relation_less)))
2064 relation |= ir_relation_less_greater;
2066 /* just do a normal transformation of the Cmp */
2067 *cc_out = relation_to_condition_code(relation, mode);
2068 flags = be_transform_node(cmp);
2073 * Transform a node returning a "flag" result.
2075 * @param node the node to transform
2076 * @param cc_out the compare mode to use
2078 static ir_node *get_flags_node(ir_node *node, ia32_condition_code_t *cc_out)
2081 return get_flags_node_cmp(node, cc_out);
2082 assert(get_irn_mode(node) == mode_b);
2083 return get_flags_mode_b(node, cc_out);
2087 * Transforms a Load.
2089 * @return the created ia32 Load node
2091 static ir_node *gen_Load(ir_node *node)
2093 ir_node *old_block = get_nodes_block(node);
2094 ir_node *block = be_transform_node(old_block);
2095 ir_node *ptr = get_Load_ptr(node);
2096 ir_node *mem = get_Load_mem(node);
2097 ir_node *new_mem = be_transform_node(mem);
2098 dbg_info *dbgi = get_irn_dbg_info(node);
2099 ir_mode *mode = get_Load_mode(node);
2103 ia32_address_t addr;
2105 /* construct load address */
2106 memset(&addr, 0, sizeof(addr));
2107 ia32_create_address_mode(&addr, ptr, ia32_create_am_normal);
2114 base = be_transform_node(base);
2117 if (index == NULL) {
2120 index = be_transform_node(index);
2123 if (mode_is_float(mode)) {
2124 if (ia32_cg_config.use_sse2) {
2125 new_node = new_bd_ia32_xLoad(dbgi, block, base, index, new_mem,
2128 new_node = new_bd_ia32_vfld(dbgi, block, base, index, new_mem,
2132 assert(mode != mode_b);
2134 /* create a conv node with address mode for smaller modes */
2135 if (get_mode_size_bits(mode) < 32) {
2136 new_node = new_bd_ia32_Conv_I2I(dbgi, block, base, index,
2137 new_mem, noreg_GP, mode);
2139 new_node = new_bd_ia32_Load(dbgi, block, base, index, new_mem);
2143 set_irn_pinned(new_node, get_irn_pinned(node));
2144 set_ia32_op_type(new_node, ia32_AddrModeS);
2145 set_ia32_ls_mode(new_node, mode);
2146 set_address(new_node, &addr);
2148 if (get_irn_pinned(node) == op_pin_state_floats) {
2149 assert((int)pn_ia32_xLoad_res == (int)pn_ia32_vfld_res
2150 && (int)pn_ia32_vfld_res == (int)pn_ia32_Load_res
2151 && (int)pn_ia32_Load_res == (int)pn_ia32_res);
2152 arch_irn_add_flags(new_node, arch_irn_flags_rematerializable);
2155 SET_IA32_ORIG_NODE(new_node, node);
2160 static int use_dest_am(ir_node *block, ir_node *node, ir_node *mem,
2161 ir_node *ptr, ir_node *other)
2168 /* we only use address mode if we're the only user of the load */
2169 if (get_irn_n_edges(node) > 1)
2172 load = get_Proj_pred(node);
2175 if (get_nodes_block(load) != block)
2178 /* store should have the same pointer as the load */
2179 if (get_Load_ptr(load) != ptr)
2182 /* don't do AM if other node inputs depend on the load (via mem-proj) */
2183 if (other != NULL &&
2184 get_nodes_block(other) == block &&
2185 heights_reachable_in_block(ia32_heights, other, load)) {
2189 if (ia32_prevents_AM(block, load, mem))
2191 /* Store should be attached to the load via mem */
2192 assert(heights_reachable_in_block(ia32_heights, mem, load));
2197 static ir_node *dest_am_binop(ir_node *node, ir_node *op1, ir_node *op2,
2198 ir_node *mem, ir_node *ptr, ir_mode *mode,
2199 construct_binop_dest_func *func,
2200 construct_binop_dest_func *func8bit,
2201 match_flags_t flags)
2203 ir_node *src_block = get_nodes_block(node);
2211 ia32_address_mode_t am;
2212 ia32_address_t *addr = &am.addr;
2213 memset(&am, 0, sizeof(am));
2215 assert(flags & match_immediate); /* there is no destam node without... */
2216 commutative = (flags & match_commutative) != 0;
2218 if (use_dest_am(src_block, op1, mem, ptr, op2)) {
2219 build_address(&am, op1, ia32_create_am_double_use);
2220 new_op = create_immediate_or_transform(op2, 0);
2221 } else if (commutative && use_dest_am(src_block, op2, mem, ptr, op1)) {
2222 build_address(&am, op2, ia32_create_am_double_use);
2223 new_op = create_immediate_or_transform(op1, 0);
2228 if (addr->base == NULL)
2229 addr->base = noreg_GP;
2230 if (addr->index == NULL)
2231 addr->index = noreg_GP;
2232 if (addr->mem == NULL)
2235 dbgi = get_irn_dbg_info(node);
2236 block = be_transform_node(src_block);
2237 new_mem = transform_AM_mem(block, am.am_node, mem, addr->mem);
2239 if (get_mode_size_bits(mode) == 8) {
2240 new_node = func8bit(dbgi, block, addr->base, addr->index, new_mem, new_op);
2242 new_node = func(dbgi, block, addr->base, addr->index, new_mem, new_op);
2244 set_address(new_node, addr);
2245 set_ia32_op_type(new_node, ia32_AddrModeD);
2246 set_ia32_ls_mode(new_node, mode);
2247 SET_IA32_ORIG_NODE(new_node, node);
2249 be_set_transformed_node(get_Proj_pred(am.mem_proj), new_node);
2250 mem_proj = be_transform_node(am.mem_proj);
2251 be_set_transformed_node(am.mem_proj, new_node);
2252 be_set_transformed_node(mem_proj, new_node);
2257 static ir_node *dest_am_unop(ir_node *node, ir_node *op, ir_node *mem,
2258 ir_node *ptr, ir_mode *mode,
2259 construct_unop_dest_func *func)
2261 ir_node *src_block = get_nodes_block(node);
2267 ia32_address_mode_t am;
2268 ia32_address_t *addr = &am.addr;
2270 if (!use_dest_am(src_block, op, mem, ptr, NULL))
2273 memset(&am, 0, sizeof(am));
2274 build_address(&am, op, ia32_create_am_double_use);
2276 dbgi = get_irn_dbg_info(node);
2277 block = be_transform_node(src_block);
2278 new_mem = transform_AM_mem(block, am.am_node, mem, addr->mem);
2279 new_node = func(dbgi, block, addr->base, addr->index, new_mem);
2280 set_address(new_node, addr);
2281 set_ia32_op_type(new_node, ia32_AddrModeD);
2282 set_ia32_ls_mode(new_node, mode);
2283 SET_IA32_ORIG_NODE(new_node, node);
2285 be_set_transformed_node(get_Proj_pred(am.mem_proj), new_node);
2286 mem_proj = be_transform_node(am.mem_proj);
2287 be_set_transformed_node(am.mem_proj, new_node);
2288 be_set_transformed_node(mem_proj, new_node);
2293 static ir_node *try_create_SetMem(ir_node *node, ir_node *ptr, ir_node *mem)
2295 ir_mode *mode = get_irn_mode(node);
2296 ir_node *mux_true = get_Mux_true(node);
2297 ir_node *mux_false = get_Mux_false(node);
2305 ia32_condition_code_t cc;
2306 ia32_address_t addr;
2308 if (get_mode_size_bits(mode) != 8)
2311 if (is_Const_1(mux_true) && is_Const_0(mux_false)) {
2313 } else if (is_Const_0(mux_true) && is_Const_1(mux_false)) {
2319 cond = get_Mux_sel(node);
2320 flags = get_flags_node(cond, &cc);
2321 /* we can't handle the float special cases with SetM */
2322 if (cc & ia32_cc_additional_float_cases)
2325 cc = ia32_negate_condition_code(cc);
2327 build_address_ptr(&addr, ptr, mem);
2329 dbgi = get_irn_dbg_info(node);
2330 block = get_nodes_block(node);
2331 new_block = be_transform_node(block);
2332 new_node = new_bd_ia32_SetccMem(dbgi, new_block, addr.base,
2333 addr.index, addr.mem, flags, cc);
2334 set_address(new_node, &addr);
2335 set_ia32_op_type(new_node, ia32_AddrModeD);
2336 set_ia32_ls_mode(new_node, mode);
2337 SET_IA32_ORIG_NODE(new_node, node);
2342 static ir_node *try_create_dest_am(ir_node *node)
2344 ir_node *val = get_Store_value(node);
2345 ir_node *mem = get_Store_mem(node);
2346 ir_node *ptr = get_Store_ptr(node);
2347 ir_mode *mode = get_irn_mode(val);
2348 unsigned bits = get_mode_size_bits(mode);
2353 /* handle only GP modes for now... */
2354 if (!ia32_mode_needs_gp_reg(mode))
2358 /* store must be the only user of the val node */
2359 if (get_irn_n_edges(val) > 1)
2361 /* skip pointless convs */
2363 ir_node *conv_op = get_Conv_op(val);
2364 ir_mode *pred_mode = get_irn_mode(conv_op);
2365 if (!ia32_mode_needs_gp_reg(pred_mode))
2367 if (pred_mode == mode_b || bits <= get_mode_size_bits(pred_mode)) {
2375 /* value must be in the same block */
2376 if (get_nodes_block(node) != get_nodes_block(val))
2379 switch (get_irn_opcode(val)) {
2381 op1 = get_Add_left(val);
2382 op2 = get_Add_right(val);
2383 if (ia32_cg_config.use_incdec) {
2384 if (is_Const_1(op2)) {
2385 new_node = dest_am_unop(val, op1, mem, ptr, mode, new_bd_ia32_IncMem);
2387 } else if (is_Const_Minus_1(op2)) {
2388 new_node = dest_am_unop(val, op1, mem, ptr, mode, new_bd_ia32_DecMem);
2392 new_node = dest_am_binop(val, op1, op2, mem, ptr, mode,
2393 new_bd_ia32_AddMem, new_bd_ia32_AddMem8Bit,
2394 match_commutative | match_immediate);
2397 op1 = get_Sub_left(val);
2398 op2 = get_Sub_right(val);
2399 if (is_Const(op2)) {
2400 ir_fprintf(stderr, "Optimisation warning: not-normalized sub ,C found\n");
2402 new_node = dest_am_binop(val, op1, op2, mem, ptr, mode,
2403 new_bd_ia32_SubMem, new_bd_ia32_SubMem8Bit,
2407 op1 = get_And_left(val);
2408 op2 = get_And_right(val);
2409 new_node = dest_am_binop(val, op1, op2, mem, ptr, mode,
2410 new_bd_ia32_AndMem, new_bd_ia32_AndMem8Bit,
2411 match_commutative | match_immediate);
2414 op1 = get_Or_left(val);
2415 op2 = get_Or_right(val);
2416 new_node = dest_am_binop(val, op1, op2, mem, ptr, mode,
2417 new_bd_ia32_OrMem, new_bd_ia32_OrMem8Bit,
2418 match_commutative | match_immediate);
2421 op1 = get_Eor_left(val);
2422 op2 = get_Eor_right(val);
2423 new_node = dest_am_binop(val, op1, op2, mem, ptr, mode,
2424 new_bd_ia32_XorMem, new_bd_ia32_XorMem8Bit,
2425 match_commutative | match_immediate);
2428 op1 = get_Shl_left(val);
2429 op2 = get_Shl_right(val);
2430 new_node = dest_am_binop(val, op1, op2, mem, ptr, mode,
2431 new_bd_ia32_ShlMem, new_bd_ia32_ShlMem,
2435 op1 = get_Shr_left(val);
2436 op2 = get_Shr_right(val);
2437 new_node = dest_am_binop(val, op1, op2, mem, ptr, mode,
2438 new_bd_ia32_ShrMem, new_bd_ia32_ShrMem,
2442 op1 = get_Shrs_left(val);
2443 op2 = get_Shrs_right(val);
2444 new_node = dest_am_binop(val, op1, op2, mem, ptr, mode,
2445 new_bd_ia32_SarMem, new_bd_ia32_SarMem,
2449 op1 = get_Rotl_left(val);
2450 op2 = get_Rotl_right(val);
2451 new_node = dest_am_binop(val, op1, op2, mem, ptr, mode,
2452 new_bd_ia32_RolMem, new_bd_ia32_RolMem,
2455 /* TODO: match ROR patterns... */
2457 new_node = try_create_SetMem(val, ptr, mem);
2461 op1 = get_Minus_op(val);
2462 new_node = dest_am_unop(val, op1, mem, ptr, mode, new_bd_ia32_NegMem);
2465 /* should be lowered already */
2466 assert(mode != mode_b);
2467 op1 = get_Not_op(val);
2468 new_node = dest_am_unop(val, op1, mem, ptr, mode, new_bd_ia32_NotMem);
2474 if (new_node != NULL) {
2475 if (get_irn_pinned(new_node) != op_pin_state_pinned &&
2476 get_irn_pinned(node) == op_pin_state_pinned) {
2477 set_irn_pinned(new_node, op_pin_state_pinned);
2484 static bool possible_int_mode_for_fp(ir_mode *mode)
2488 if (!mode_is_signed(mode))
2490 size = get_mode_size_bits(mode);
2491 if (size != 16 && size != 32)
2496 static int is_float_to_int_conv(const ir_node *node)
2498 ir_mode *mode = get_irn_mode(node);
2502 if (!possible_int_mode_for_fp(mode))
2507 conv_op = get_Conv_op(node);
2508 conv_mode = get_irn_mode(conv_op);
2510 if (!mode_is_float(conv_mode))
2517 * Transform a Store(floatConst) into a sequence of
2520 * @return the created ia32 Store node
2522 static ir_node *gen_float_const_Store(ir_node *node, ir_node *cns)
2524 ir_mode *mode = get_irn_mode(cns);
2525 unsigned size = get_mode_size_bytes(mode);
2526 ir_tarval *tv = get_Const_tarval(cns);
2527 ir_node *block = get_nodes_block(node);
2528 ir_node *new_block = be_transform_node(block);
2529 ir_node *ptr = get_Store_ptr(node);
2530 ir_node *mem = get_Store_mem(node);
2531 dbg_info *dbgi = get_irn_dbg_info(node);
2535 ia32_address_t addr;
2537 assert(size % 4 == 0);
2540 build_address_ptr(&addr, ptr, mem);
2544 get_tarval_sub_bits(tv, ofs) |
2545 (get_tarval_sub_bits(tv, ofs + 1) << 8) |
2546 (get_tarval_sub_bits(tv, ofs + 2) << 16) |
2547 (get_tarval_sub_bits(tv, ofs + 3) << 24);
2548 ir_node *imm = ia32_create_Immediate(NULL, 0, val);
2550 ir_node *new_node = new_bd_ia32_Store(dbgi, new_block, addr.base,
2551 addr.index, addr.mem, imm);
2553 set_irn_pinned(new_node, get_irn_pinned(node));
2554 set_ia32_op_type(new_node, ia32_AddrModeD);
2555 set_ia32_ls_mode(new_node, mode_Iu);
2556 set_address(new_node, &addr);
2557 SET_IA32_ORIG_NODE(new_node, node);
2560 ins[i++] = new_node;
2565 } while (size != 0);
2568 return new_rd_Sync(dbgi, new_block, i, ins);
2575 * Generate a vfist or vfisttp instruction.
2577 static ir_node *gen_vfist(dbg_info *dbgi, ir_node *block, ir_node *base, ir_node *index,
2578 ir_node *mem, ir_node *val, ir_node **fist)
2582 if (ia32_cg_config.use_fisttp) {
2583 /* Note: fisttp ALWAYS pop the tos. We have to ensure here that the value is copied
2584 if other users exists */
2585 ir_node *vfisttp = new_bd_ia32_vfisttp(dbgi, block, base, index, mem, val);
2586 ir_node *value = new_r_Proj(vfisttp, mode_E, pn_ia32_vfisttp_res);
2587 be_new_Keep(block, 1, &value);
2589 new_node = new_r_Proj(vfisttp, mode_M, pn_ia32_vfisttp_M);
2592 ir_node *trunc_mode = ia32_new_Fpu_truncate(current_ir_graph);
2595 new_node = new_bd_ia32_vfist(dbgi, block, base, index, mem, val, trunc_mode);
2601 * Transforms a general (no special case) Store.
2603 * @return the created ia32 Store node
2605 static ir_node *gen_general_Store(ir_node *node)
2607 ir_node *val = get_Store_value(node);
2608 ir_mode *mode = get_irn_mode(val);
2609 ir_node *block = get_nodes_block(node);
2610 ir_node *new_block = be_transform_node(block);
2611 ir_node *ptr = get_Store_ptr(node);
2612 ir_node *mem = get_Store_mem(node);
2613 dbg_info *dbgi = get_irn_dbg_info(node);
2614 ir_node *new_val, *new_node, *store;
2615 ia32_address_t addr;
2617 /* check for destination address mode */
2618 new_node = try_create_dest_am(node);
2619 if (new_node != NULL)
2622 /* construct store address */
2623 memset(&addr, 0, sizeof(addr));
2624 ia32_create_address_mode(&addr, ptr, ia32_create_am_normal);
2626 if (addr.base == NULL) {
2627 addr.base = noreg_GP;
2629 addr.base = be_transform_node(addr.base);
2632 if (addr.index == NULL) {
2633 addr.index = noreg_GP;
2635 addr.index = be_transform_node(addr.index);
2637 addr.mem = be_transform_node(mem);
2639 if (mode_is_float(mode)) {
2640 /* Convs (and strict-Convs) before stores are unnecessary if the mode
2642 while (is_Conv(val) && mode == get_irn_mode(val)) {
2643 ir_node *op = get_Conv_op(val);
2644 if (!mode_is_float(get_irn_mode(op)))
2648 new_val = be_transform_node(val);
2649 if (ia32_cg_config.use_sse2) {
2650 new_node = new_bd_ia32_xStore(dbgi, new_block, addr.base,
2651 addr.index, addr.mem, new_val);
2653 new_node = new_bd_ia32_vfst(dbgi, new_block, addr.base,
2654 addr.index, addr.mem, new_val, mode);
2657 } else if (!ia32_cg_config.use_sse2 && is_float_to_int_conv(val)) {
2658 val = get_Conv_op(val);
2660 /* TODO: is this optimisation still necessary at all (middleend)? */
2661 /* We can skip ALL float->float up-Convs (and strict-up-Convs) before stores. */
2662 while (is_Conv(val)) {
2663 ir_node *op = get_Conv_op(val);
2664 if (!mode_is_float(get_irn_mode(op)))
2666 if (get_mode_size_bits(get_irn_mode(op)) > get_mode_size_bits(get_irn_mode(val)))
2670 new_val = be_transform_node(val);
2671 new_node = gen_vfist(dbgi, new_block, addr.base, addr.index, addr.mem, new_val, &store);
2673 new_val = create_immediate_or_transform(val, 0);
2674 assert(mode != mode_b);
2676 if (get_mode_size_bits(mode) == 8) {
2677 new_node = new_bd_ia32_Store8Bit(dbgi, new_block, addr.base,
2678 addr.index, addr.mem, new_val);
2680 new_node = new_bd_ia32_Store(dbgi, new_block, addr.base,
2681 addr.index, addr.mem, new_val);
2686 set_irn_pinned(store, get_irn_pinned(node));
2687 set_ia32_op_type(store, ia32_AddrModeD);
2688 set_ia32_ls_mode(store, mode);
2690 set_address(store, &addr);
2691 SET_IA32_ORIG_NODE(store, node);
2697 * Transforms a Store.
2699 * @return the created ia32 Store node
2701 static ir_node *gen_Store(ir_node *node)
2703 ir_node *val = get_Store_value(node);
2704 ir_mode *mode = get_irn_mode(val);
2706 if (mode_is_float(mode) && is_Const(val)) {
2707 /* We can transform every floating const store
2708 into a sequence of integer stores.
2709 If the constant is already in a register,
2710 it would be better to use it, but we don't
2711 have this information here. */
2712 return gen_float_const_Store(node, val);
2714 return gen_general_Store(node);
2718 * Transforms a Switch.
2720 * @return the created ia32 SwitchJmp node
2722 static ir_node *create_Switch(ir_node *node)
2724 dbg_info *dbgi = get_irn_dbg_info(node);
2725 ir_node *block = be_transform_node(get_nodes_block(node));
2726 ir_node *sel = get_Cond_selector(node);
2727 ir_node *new_sel = be_transform_node(sel);
2728 long switch_min = LONG_MAX;
2729 long switch_max = LONG_MIN;
2730 long default_pn = get_Cond_default_proj(node);
2732 const ir_edge_t *edge;
2734 assert(get_mode_size_bits(get_irn_mode(sel)) == 32);
2736 /* determine the smallest switch case value */
2737 foreach_out_edge(node, edge) {
2738 ir_node *proj = get_edge_src_irn(edge);
2739 long pn = get_Proj_proj(proj);
2740 if (pn == default_pn)
2743 if (pn < switch_min)
2745 if (pn > switch_max)
2749 if ((unsigned long) (switch_max - switch_min) > 128000) {
2750 panic("Size of switch %+F bigger than 128000", node);
2753 if (switch_min != 0) {
2754 /* if smallest switch case is not 0 we need an additional sub */
2755 new_sel = new_bd_ia32_Lea(dbgi, block, new_sel, noreg_GP);
2756 add_ia32_am_offs_int(new_sel, -switch_min);
2757 set_ia32_op_type(new_sel, ia32_AddrModeS);
2759 SET_IA32_ORIG_NODE(new_sel, node);
2762 new_node = new_bd_ia32_SwitchJmp(dbgi, block, new_sel, default_pn);
2763 SET_IA32_ORIG_NODE(new_node, node);
2769 * Transform a Cond node.
2771 static ir_node *gen_Cond(ir_node *node)
2773 ir_node *block = get_nodes_block(node);
2774 ir_node *new_block = be_transform_node(block);
2775 dbg_info *dbgi = get_irn_dbg_info(node);
2776 ir_node *sel = get_Cond_selector(node);
2777 ir_mode *sel_mode = get_irn_mode(sel);
2778 ir_node *flags = NULL;
2780 ia32_condition_code_t cc;
2782 if (sel_mode != mode_b) {
2783 return create_Switch(node);
2786 /* we get flags from a Cmp */
2787 flags = get_flags_node(sel, &cc);
2789 new_node = new_bd_ia32_Jcc(dbgi, new_block, flags, cc);
2790 SET_IA32_ORIG_NODE(new_node, node);
2796 * Transform a be_Copy.
2798 static ir_node *gen_be_Copy(ir_node *node)
2800 ir_node *new_node = be_duplicate_node(node);
2801 ir_mode *mode = get_irn_mode(new_node);
2803 if (ia32_mode_needs_gp_reg(mode)) {
2804 set_irn_mode(new_node, mode_Iu);
2810 static ir_node *create_Fucom(ir_node *node)
2812 dbg_info *dbgi = get_irn_dbg_info(node);
2813 ir_node *block = get_nodes_block(node);
2814 ir_node *new_block = be_transform_node(block);
2815 ir_node *left = get_Cmp_left(node);
2816 ir_node *new_left = be_transform_node(left);
2817 ir_node *right = get_Cmp_right(node);
2821 if (ia32_cg_config.use_fucomi) {
2822 new_right = be_transform_node(right);
2823 new_node = new_bd_ia32_vFucomi(dbgi, new_block, new_left,
2825 set_ia32_commutative(new_node);
2826 SET_IA32_ORIG_NODE(new_node, node);
2828 if (ia32_cg_config.use_ftst && is_Const_0(right)) {
2829 new_node = new_bd_ia32_vFtstFnstsw(dbgi, new_block, new_left, 0);
2831 new_right = be_transform_node(right);
2832 new_node = new_bd_ia32_vFucomFnstsw(dbgi, new_block, new_left, new_right, 0);
2835 set_ia32_commutative(new_node);
2837 SET_IA32_ORIG_NODE(new_node, node);
2839 new_node = new_bd_ia32_Sahf(dbgi, new_block, new_node);
2840 SET_IA32_ORIG_NODE(new_node, node);
2846 static ir_node *create_Ucomi(ir_node *node)
2848 dbg_info *dbgi = get_irn_dbg_info(node);
2849 ir_node *src_block = get_nodes_block(node);
2850 ir_node *new_block = be_transform_node(src_block);
2851 ir_node *left = get_Cmp_left(node);
2852 ir_node *right = get_Cmp_right(node);
2854 ia32_address_mode_t am;
2855 ia32_address_t *addr = &am.addr;
2857 match_arguments(&am, src_block, left, right, NULL,
2858 match_commutative | match_am);
2860 new_node = new_bd_ia32_Ucomi(dbgi, new_block, addr->base, addr->index,
2861 addr->mem, am.new_op1, am.new_op2,
2863 set_am_attributes(new_node, &am);
2865 SET_IA32_ORIG_NODE(new_node, node);
2867 new_node = fix_mem_proj(new_node, &am);
2873 * returns true if it is assured, that the upper bits of a node are "clean"
2874 * which means for a 16 or 8 bit value, that the upper bits in the register
2875 * are 0 for unsigned and a copy of the last significant bit for signed
2878 static bool upper_bits_clean(ir_node *transformed_node, ir_mode *mode)
2880 assert(ia32_mode_needs_gp_reg(mode));
2881 if (get_mode_size_bits(mode) >= 32)
2884 if (is_Proj(transformed_node))
2885 return upper_bits_clean(get_Proj_pred(transformed_node), mode);
2887 switch (get_ia32_irn_opcode(transformed_node)) {
2888 case iro_ia32_Conv_I2I:
2889 case iro_ia32_Conv_I2I8Bit: {
2890 ir_mode *smaller_mode = get_ia32_ls_mode(transformed_node);
2891 if (mode_is_signed(smaller_mode) != mode_is_signed(mode))
2893 if (get_mode_size_bits(smaller_mode) > get_mode_size_bits(mode))
2900 if (mode_is_signed(mode)) {
2901 return false; /* TODO handle signed modes */
2903 ir_node *right = get_irn_n(transformed_node, n_ia32_Shr_count);
2904 if (is_ia32_Immediate(right) || is_ia32_Const(right)) {
2905 const ia32_immediate_attr_t *attr
2906 = get_ia32_immediate_attr_const(right);
2907 if (attr->symconst == 0 &&
2908 (unsigned)attr->offset >= 32 - get_mode_size_bits(mode)) {
2912 return upper_bits_clean(get_irn_n(transformed_node, n_ia32_Shr_val), mode);
2916 /* TODO too conservative if shift amount is constant */
2917 return upper_bits_clean(get_irn_n(transformed_node, n_ia32_Sar_val), mode);
2920 if (!mode_is_signed(mode)) {
2922 upper_bits_clean(get_irn_n(transformed_node, n_ia32_And_right), mode) ||
2923 upper_bits_clean(get_irn_n(transformed_node, n_ia32_And_left), mode);
2925 /* TODO if one is known to be zero extended, then || is sufficient */
2930 upper_bits_clean(get_irn_n(transformed_node, n_ia32_binary_right), mode) &&
2931 upper_bits_clean(get_irn_n(transformed_node, n_ia32_binary_left), mode);
2933 case iro_ia32_Const:
2934 case iro_ia32_Immediate: {
2935 const ia32_immediate_attr_t *attr =
2936 get_ia32_immediate_attr_const(transformed_node);
2937 if (mode_is_signed(mode)) {
2938 long shifted = attr->offset >> (get_mode_size_bits(mode) - 1);
2939 return shifted == 0 || shifted == -1;
2941 unsigned long shifted = (unsigned long)attr->offset;
2942 shifted >>= get_mode_size_bits(mode);
2943 return shifted == 0;
2953 * Generate code for a Cmp.
2955 static ir_node *gen_Cmp(ir_node *node)
2957 dbg_info *dbgi = get_irn_dbg_info(node);
2958 ir_node *block = get_nodes_block(node);
2959 ir_node *new_block = be_transform_node(block);
2960 ir_node *left = get_Cmp_left(node);
2961 ir_node *right = get_Cmp_right(node);
2962 ir_mode *cmp_mode = get_irn_mode(left);
2964 ia32_address_mode_t am;
2965 ia32_address_t *addr = &am.addr;
2967 if (mode_is_float(cmp_mode)) {
2968 if (ia32_cg_config.use_sse2) {
2969 return create_Ucomi(node);
2971 return create_Fucom(node);
2975 assert(ia32_mode_needs_gp_reg(cmp_mode));
2977 /* Prefer the Test instruction, when encountering (x & y) ==/!= 0 */
2978 if (is_Const_0(right) &&
2980 get_irn_n_edges(left) == 1) {
2981 /* Test(and_left, and_right) */
2982 ir_node *and_left = get_And_left(left);
2983 ir_node *and_right = get_And_right(left);
2985 /* matze: code here used mode instead of cmd_mode, I think it is always
2986 * the same as cmp_mode, but I leave this here to see if this is really
2989 assert(get_irn_mode(and_left) == cmp_mode);
2991 match_arguments(&am, block, and_left, and_right, NULL,
2993 match_am | match_8bit_am | match_16bit_am |
2994 match_am_and_immediates | match_immediate);
2996 /* use 32bit compare mode if possible since the opcode is smaller */
2997 if (upper_bits_clean(am.new_op1, cmp_mode) &&
2998 upper_bits_clean(am.new_op2, cmp_mode)) {
2999 cmp_mode = mode_is_signed(cmp_mode) ? mode_Is : mode_Iu;
3002 if (get_mode_size_bits(cmp_mode) == 8) {
3003 new_node = new_bd_ia32_Test8Bit(dbgi, new_block, addr->base,
3004 addr->index, addr->mem, am.new_op1, am.new_op2, am.ins_permuted);
3006 new_node = new_bd_ia32_Test(dbgi, new_block, addr->base, addr->index,
3007 addr->mem, am.new_op1, am.new_op2, am.ins_permuted);
3010 /* Cmp(left, right) */
3011 match_arguments(&am, block, left, right, NULL,
3012 match_commutative | match_am | match_8bit_am |
3013 match_16bit_am | match_am_and_immediates |
3015 /* use 32bit compare mode if possible since the opcode is smaller */
3016 if (upper_bits_clean(am.new_op1, cmp_mode) &&
3017 upper_bits_clean(am.new_op2, cmp_mode)) {
3018 cmp_mode = mode_is_signed(cmp_mode) ? mode_Is : mode_Iu;
3021 if (get_mode_size_bits(cmp_mode) == 8) {
3022 new_node = new_bd_ia32_Cmp8Bit(dbgi, new_block, addr->base,
3023 addr->index, addr->mem, am.new_op1,
3024 am.new_op2, am.ins_permuted);
3026 new_node = new_bd_ia32_Cmp(dbgi, new_block, addr->base, addr->index,
3027 addr->mem, am.new_op1, am.new_op2, am.ins_permuted);
3030 set_am_attributes(new_node, &am);
3031 set_ia32_ls_mode(new_node, cmp_mode);
3033 SET_IA32_ORIG_NODE(new_node, node);
3035 new_node = fix_mem_proj(new_node, &am);
3040 static ir_node *create_CMov(ir_node *node, ir_node *flags, ir_node *new_flags,
3041 ia32_condition_code_t cc)
3043 dbg_info *dbgi = get_irn_dbg_info(node);
3044 ir_node *block = get_nodes_block(node);
3045 ir_node *new_block = be_transform_node(block);
3046 ir_node *val_true = get_Mux_true(node);
3047 ir_node *val_false = get_Mux_false(node);
3049 ia32_address_mode_t am;
3050 ia32_address_t *addr;
3052 assert(ia32_cg_config.use_cmov);
3053 assert(ia32_mode_needs_gp_reg(get_irn_mode(val_true)));
3057 match_arguments(&am, block, val_false, val_true, flags,
3058 match_commutative | match_am | match_16bit_am | match_mode_neutral);
3060 if (am.ins_permuted)
3061 cc = ia32_negate_condition_code(cc);
3063 new_node = new_bd_ia32_CMovcc(dbgi, new_block, addr->base, addr->index,
3064 addr->mem, am.new_op1, am.new_op2, new_flags,
3066 set_am_attributes(new_node, &am);
3068 SET_IA32_ORIG_NODE(new_node, node);
3070 new_node = fix_mem_proj(new_node, &am);
3076 * Creates a ia32 Setcc instruction.
3078 static ir_node *create_set_32bit(dbg_info *dbgi, ir_node *new_block,
3079 ir_node *flags, ia32_condition_code_t cc,
3082 ir_mode *mode = get_irn_mode(orig_node);
3085 new_node = new_bd_ia32_Setcc(dbgi, new_block, flags, cc);
3086 SET_IA32_ORIG_NODE(new_node, orig_node);
3088 /* we might need to conv the result up */
3089 if (get_mode_size_bits(mode) > 8) {
3090 new_node = new_bd_ia32_Conv_I2I8Bit(dbgi, new_block, noreg_GP, noreg_GP,
3091 nomem, new_node, mode_Bu);
3092 SET_IA32_ORIG_NODE(new_node, orig_node);
3099 * Create instruction for an unsigned Difference or Zero.
3101 static ir_node *create_doz(ir_node *psi, ir_node *a, ir_node *b)
3103 ir_mode *mode = get_irn_mode(psi);
3113 new_node = gen_binop(psi, a, b, new_bd_ia32_Sub,
3114 match_mode_neutral | match_am | match_immediate | match_two_users);
3116 block = get_nodes_block(new_node);
3118 if (is_Proj(new_node)) {
3119 sub = get_Proj_pred(new_node);
3122 set_irn_mode(sub, mode_T);
3123 new_node = new_rd_Proj(NULL, sub, mode, pn_ia32_res);
3125 assert(is_ia32_Sub(sub));
3126 eflags = new_rd_Proj(NULL, sub, mode_Iu, pn_ia32_Sub_flags);
3128 dbgi = get_irn_dbg_info(psi);
3129 sbb = new_bd_ia32_Sbb0(dbgi, block, eflags);
3130 notn = new_bd_ia32_Not(dbgi, block, sbb);
3132 new_node = new_bd_ia32_And(dbgi, block, noreg_GP, noreg_GP, nomem, new_node, notn);
3133 set_ia32_commutative(new_node);
3138 * Create an const array of two float consts.
3140 * @param c0 the first constant
3141 * @param c1 the second constant
3142 * @param new_mode IN/OUT for the mode of the constants, if NULL
3143 * smallest possible mode will be used
3145 static ir_entity *ia32_create_const_array(ir_node *c0, ir_node *c1, ir_mode **new_mode)
3148 ir_mode *mode = *new_mode;
3150 ir_initializer_t *initializer;
3151 ir_tarval *tv0 = get_Const_tarval(c0);
3152 ir_tarval *tv1 = get_Const_tarval(c1);
3155 /* detect the best mode for the constants */
3156 mode = get_tarval_mode(tv0);
3158 if (mode != mode_F) {
3159 if (tarval_ieee754_can_conv_lossless(tv0, mode_F) &&
3160 tarval_ieee754_can_conv_lossless(tv1, mode_F)) {
3162 tv0 = tarval_convert_to(tv0, mode);
3163 tv1 = tarval_convert_to(tv1, mode);
3164 } else if (mode != mode_D) {
3165 if (tarval_ieee754_can_conv_lossless(tv0, mode_D) &&
3166 tarval_ieee754_can_conv_lossless(tv1, mode_D)) {
3168 tv0 = tarval_convert_to(tv0, mode);
3169 tv1 = tarval_convert_to(tv1, mode);
3176 tp = ia32_create_float_type(mode, 4);
3177 tp = ia32_create_float_array(tp);
3179 ent = new_entity(get_glob_type(), id_unique("C%u"), tp);
3181 set_entity_ld_ident(ent, get_entity_ident(ent));
3182 set_entity_visibility(ent, ir_visibility_private);
3183 add_entity_linkage(ent, IR_LINKAGE_CONSTANT);
3185 initializer = create_initializer_compound(2);
3187 set_initializer_compound_value(initializer, 0, create_initializer_tarval(tv0));
3188 set_initializer_compound_value(initializer, 1, create_initializer_tarval(tv1));
3190 set_entity_initializer(ent, initializer);
3197 * Possible transformations for creating a Setcc.
3199 enum setcc_transform_insn {
3212 typedef struct setcc_transform {
3214 ia32_condition_code_t cc;
3216 enum setcc_transform_insn transform;
3220 } setcc_transform_t;
3223 * Setcc can only handle 0 and 1 result.
3224 * Find a transformation that creates 0 and 1 from
3227 static void find_const_transform(ia32_condition_code_t cc,
3228 ir_tarval *t, ir_tarval *f,
3229 setcc_transform_t *res)
3235 if (tarval_is_null(t)) {
3239 cc = ia32_negate_condition_code(cc);
3240 } else if (tarval_cmp(t, f) == ir_relation_less) {
3241 // now, t is the bigger one
3245 cc = ia32_negate_condition_code(cc);
3249 if (! tarval_is_null(f)) {
3250 ir_tarval *t_sub = tarval_sub(t, f, NULL);
3253 res->steps[step].transform = SETCC_TR_ADD;
3255 if (t == tarval_bad)
3256 panic("constant subtract failed");
3257 if (! tarval_is_long(f))
3258 panic("tarval is not long");
3260 res->steps[step].val = get_tarval_long(f);
3262 f = tarval_sub(f, f, NULL);
3263 assert(tarval_is_null(f));
3266 if (tarval_is_one(t)) {
3267 res->steps[step].transform = SETCC_TR_SET;
3268 res->num_steps = ++step;
3272 if (tarval_is_minus_one(t)) {
3273 res->steps[step].transform = SETCC_TR_NEG;
3275 res->steps[step].transform = SETCC_TR_SET;
3276 res->num_steps = ++step;
3279 if (tarval_is_long(t)) {
3280 long v = get_tarval_long(t);
3282 res->steps[step].val = 0;
3285 if (step > 0 && res->steps[step - 1].transform == SETCC_TR_ADD)
3287 res->steps[step].transform = SETCC_TR_LEAxx;
3288 res->steps[step].scale = 3; /* (a << 3) + a */
3291 if (step > 0 && res->steps[step - 1].transform == SETCC_TR_ADD)
3293 res->steps[step].transform = res->steps[step].val == 0 ? SETCC_TR_SHL : SETCC_TR_LEA;
3294 res->steps[step].scale = 3; /* (a << 3) */
3297 if (step > 0 && res->steps[step - 1].transform == SETCC_TR_ADD)
3299 res->steps[step].transform = SETCC_TR_LEAxx;
3300 res->steps[step].scale = 2; /* (a << 2) + a */
3303 if (step > 0 && res->steps[step - 1].transform == SETCC_TR_ADD)
3305 res->steps[step].transform = res->steps[step].val == 0 ? SETCC_TR_SHL : SETCC_TR_LEA;
3306 res->steps[step].scale = 2; /* (a << 2) */
3309 if (step > 0 && res->steps[step - 1].transform == SETCC_TR_ADD)
3311 res->steps[step].transform = SETCC_TR_LEAxx;
3312 res->steps[step].scale = 1; /* (a << 1) + a */
3315 if (step > 0 && res->steps[step - 1].transform == SETCC_TR_ADD)
3317 res->steps[step].transform = res->steps[step].val == 0 ? SETCC_TR_SHL : SETCC_TR_LEA;
3318 res->steps[step].scale = 1; /* (a << 1) */
3321 res->num_steps = step;
3324 if (! tarval_is_single_bit(t)) {
3325 res->steps[step].transform = SETCC_TR_AND;
3326 res->steps[step].val = v;
3328 res->steps[step].transform = SETCC_TR_NEG;
3330 int v = get_tarval_lowest_bit(t);
3333 res->steps[step].transform = SETCC_TR_SHL;
3334 res->steps[step].scale = v;
3338 res->steps[step].transform = SETCC_TR_SET;
3339 res->num_steps = ++step;
3342 panic("tarval is not long");
3346 * Transforms a Mux node into some code sequence.
3348 * @return The transformed node.
3350 static ir_node *gen_Mux(ir_node *node)
3352 dbg_info *dbgi = get_irn_dbg_info(node);
3353 ir_node *block = get_nodes_block(node);
3354 ir_node *new_block = be_transform_node(block);
3355 ir_node *mux_true = get_Mux_true(node);
3356 ir_node *mux_false = get_Mux_false(node);
3357 ir_node *sel = get_Mux_sel(node);
3358 ir_mode *mode = get_irn_mode(node);
3362 ia32_condition_code_t cc;
3364 assert(get_irn_mode(sel) == mode_b);
3366 is_abs = be_mux_is_abs(sel, mux_true, mux_false);
3368 return create_abs(dbgi, block, be_get_abs_op(sel), is_abs < 0, node);
3371 /* Note: a Mux node uses a Load two times IFF it's used in the compare AND in the result */
3372 if (mode_is_float(mode)) {
3373 ir_node *cmp_left = get_Cmp_left(sel);
3374 ir_node *cmp_right = get_Cmp_right(sel);
3375 ir_relation relation = get_Cmp_relation(sel);
3377 if (ia32_cg_config.use_sse2) {
3378 if (relation == ir_relation_less || relation == ir_relation_less_equal) {
3379 if (cmp_left == mux_true && cmp_right == mux_false) {
3380 /* Mux(a <= b, a, b) => MIN */
3381 return gen_binop(node, cmp_left, cmp_right, new_bd_ia32_xMin,
3382 match_commutative | match_am | match_two_users);
3383 } else if (cmp_left == mux_false && cmp_right == mux_true) {
3384 /* Mux(a <= b, b, a) => MAX */
3385 return gen_binop(node, cmp_left, cmp_right, new_bd_ia32_xMax,
3386 match_commutative | match_am | match_two_users);
3388 } else if (relation == ir_relation_greater || relation == ir_relation_greater_equal) {
3389 if (cmp_left == mux_true && cmp_right == mux_false) {
3390 /* Mux(a >= b, a, b) => MAX */
3391 return gen_binop(node, cmp_left, cmp_right, new_bd_ia32_xMax,
3392 match_commutative | match_am | match_two_users);
3393 } else if (cmp_left == mux_false && cmp_right == mux_true) {
3394 /* Mux(a >= b, b, a) => MIN */
3395 return gen_binop(node, cmp_left, cmp_right, new_bd_ia32_xMin,
3396 match_commutative | match_am | match_two_users);
3401 if (is_Const(mux_true) && is_Const(mux_false)) {
3402 ia32_address_mode_t am;
3407 flags = get_flags_node(sel, &cc);
3408 new_node = create_set_32bit(dbgi, new_block, flags, cc, node);
3410 if (ia32_cg_config.use_sse2) {
3411 /* cannot load from different mode on SSE */
3414 /* x87 can load any mode */
3418 am.addr.symconst_ent = ia32_create_const_array(mux_false, mux_true, &new_mode);
3420 switch (get_mode_size_bytes(new_mode)) {
3430 new_node = new_bd_ia32_Lea(dbgi, new_block, new_node, new_node);
3431 set_ia32_am_scale(new_node, 2);
3436 new_node = new_bd_ia32_Lea(dbgi, new_block, new_node, new_node);
3437 set_ia32_am_scale(new_node, 1);
3440 /* arg, shift 16 NOT supported */
3442 new_node = new_bd_ia32_Lea(dbgi, new_block, new_node, new_node);
3445 panic("Unsupported constant size");
3448 am.ls_mode = new_mode;
3449 am.addr.base = get_symconst_base();
3450 am.addr.index = new_node;
3451 am.addr.mem = nomem;
3453 am.addr.scale = scale;
3454 am.addr.use_frame = 0;
3455 am.addr.tls_segment = false;
3456 am.addr.frame_entity = NULL;
3457 am.addr.symconst_sign = 0;
3458 am.mem_proj = am.addr.mem;
3459 am.op_type = ia32_AddrModeS;
3462 am.pinned = op_pin_state_floats;
3464 am.ins_permuted = false;
3466 if (ia32_cg_config.use_sse2)
3467 load = new_bd_ia32_xLoad(dbgi, block, am.addr.base, am.addr.index, am.addr.mem, new_mode);
3469 load = new_bd_ia32_vfld(dbgi, block, am.addr.base, am.addr.index, am.addr.mem, new_mode);
3470 set_am_attributes(load, &am);
3472 return new_rd_Proj(NULL, load, mode_vfp, pn_ia32_res);
3474 panic("cannot transform floating point Mux");
3477 assert(ia32_mode_needs_gp_reg(mode));
3480 ir_node *cmp_left = get_Cmp_left(sel);
3481 ir_node *cmp_right = get_Cmp_right(sel);
3482 ir_relation relation = get_Cmp_relation(sel);
3483 ir_node *val_true = mux_true;
3484 ir_node *val_false = mux_false;
3486 if (is_Const(val_true) && is_Const_null(val_true)) {
3487 ir_node *tmp = val_false;
3488 val_false = val_true;
3490 relation = get_negated_relation(relation);
3492 if (is_Const_0(val_false) && is_Sub(val_true)) {
3493 if ((relation & ir_relation_greater)
3494 && get_Sub_left(val_true) == cmp_left
3495 && get_Sub_right(val_true) == cmp_right) {
3496 return create_doz(node, cmp_left, cmp_right);
3498 if ((relation & ir_relation_less)
3499 && get_Sub_left(val_true) == cmp_right
3500 && get_Sub_right(val_true) == cmp_left) {
3501 return create_doz(node, cmp_right, cmp_left);
3506 flags = get_flags_node(sel, &cc);
3508 if (is_Const(mux_true) && is_Const(mux_false)) {
3509 /* both are const, good */
3510 ir_tarval *tv_true = get_Const_tarval(mux_true);
3511 ir_tarval *tv_false = get_Const_tarval(mux_false);
3512 setcc_transform_t res;
3515 find_const_transform(cc, tv_true, tv_false, &res);
3517 for (step = (int)res.num_steps - 1; step >= 0; --step) {
3520 switch (res.steps[step].transform) {
3522 new_node = new_bd_ia32_Lea(dbgi, new_block, new_node, noreg_GP);
3523 add_ia32_am_offs_int(new_node, res.steps[step].val);
3525 case SETCC_TR_ADDxx:
3526 new_node = new_bd_ia32_Lea(dbgi, new_block, new_node, new_node);
3529 new_node = new_bd_ia32_Lea(dbgi, new_block, noreg_GP, new_node);
3530 set_ia32_am_scale(new_node, res.steps[step].scale);
3531 set_ia32_am_offs_int(new_node, res.steps[step].val);
3533 case SETCC_TR_LEAxx:
3534 new_node = new_bd_ia32_Lea(dbgi, new_block, new_node, new_node);
3535 set_ia32_am_scale(new_node, res.steps[step].scale);
3536 set_ia32_am_offs_int(new_node, res.steps[step].val);
3539 imm = ia32_immediate_from_long(res.steps[step].scale);
3540 new_node = new_bd_ia32_Shl(dbgi, new_block, new_node, imm);
3543 new_node = new_bd_ia32_Neg(dbgi, new_block, new_node);
3546 new_node = new_bd_ia32_Not(dbgi, new_block, new_node);
3549 imm = ia32_immediate_from_long(res.steps[step].val);
3550 new_node = new_bd_ia32_And(dbgi, new_block, noreg_GP, noreg_GP, nomem, new_node, imm);
3553 new_node = create_set_32bit(dbgi, new_block, flags, res.cc, node);
3556 new_node = new_bd_ia32_Sbb0(dbgi, new_block, flags);
3559 panic("unknown setcc transform");
3563 new_node = create_CMov(node, sel, flags, cc);
3571 * Create a conversion from x87 state register to general purpose.
3573 static ir_node *gen_x87_fp_to_gp(ir_node *node)
3575 ir_node *block = be_transform_node(get_nodes_block(node));
3576 ir_node *op = get_Conv_op(node);
3577 ir_node *new_op = be_transform_node(op);
3578 ir_graph *irg = current_ir_graph;
3579 dbg_info *dbgi = get_irn_dbg_info(node);
3580 ir_mode *mode = get_irn_mode(node);
3581 ir_node *fist, *load, *mem;
3583 mem = gen_vfist(dbgi, block, get_irg_frame(irg), noreg_GP, nomem, new_op, &fist);
3584 set_irn_pinned(fist, op_pin_state_floats);
3585 set_ia32_use_frame(fist);
3586 set_ia32_op_type(fist, ia32_AddrModeD);
3588 assert(get_mode_size_bits(mode) <= 32);
3589 /* exception we can only store signed 32 bit integers, so for unsigned
3590 we store a 64bit (signed) integer and load the lower bits */
3591 if (get_mode_size_bits(mode) == 32 && !mode_is_signed(mode)) {
3592 set_ia32_ls_mode(fist, mode_Ls);
3594 set_ia32_ls_mode(fist, mode_Is);
3596 SET_IA32_ORIG_NODE(fist, node);
3599 load = new_bd_ia32_Load(dbgi, block, get_irg_frame(irg), noreg_GP, mem);
3601 set_irn_pinned(load, op_pin_state_floats);
3602 set_ia32_use_frame(load);
3603 set_ia32_op_type(load, ia32_AddrModeS);
3604 set_ia32_ls_mode(load, mode_Is);
3605 if (get_ia32_ls_mode(fist) == mode_Ls) {
3606 ia32_attr_t *attr = get_ia32_attr(load);
3607 attr->data.need_64bit_stackent = 1;
3609 ia32_attr_t *attr = get_ia32_attr(load);
3610 attr->data.need_32bit_stackent = 1;
3612 SET_IA32_ORIG_NODE(load, node);
3614 return new_r_Proj(load, mode_Iu, pn_ia32_Load_res);
3618 * Creates a x87 strict Conv by placing a Store and a Load
3620 static ir_node *gen_x87_strict_conv(ir_mode *tgt_mode, ir_node *node)
3622 ir_node *block = get_nodes_block(node);
3623 ir_graph *irg = get_Block_irg(block);
3624 dbg_info *dbgi = get_irn_dbg_info(node);
3625 ir_node *frame = get_irg_frame(irg);
3626 ir_node *store, *load;
3629 store = new_bd_ia32_vfst(dbgi, block, frame, noreg_GP, nomem, node, tgt_mode);
3630 set_ia32_use_frame(store);
3631 set_ia32_op_type(store, ia32_AddrModeD);
3632 SET_IA32_ORIG_NODE(store, node);
3634 load = new_bd_ia32_vfld(dbgi, block, frame, noreg_GP, store, tgt_mode);
3635 set_ia32_use_frame(load);
3636 set_ia32_op_type(load, ia32_AddrModeS);
3637 SET_IA32_ORIG_NODE(load, node);
3639 new_node = new_r_Proj(load, mode_E, pn_ia32_vfld_res);
3643 static ir_node *create_Conv_I2I(dbg_info *dbgi, ir_node *block, ir_node *base,
3644 ir_node *index, ir_node *mem, ir_node *val, ir_mode *mode)
3646 ir_node *(*func)(dbg_info*, ir_node*, ir_node*, ir_node*, ir_node*, ir_node*, ir_mode*);
3648 func = get_mode_size_bits(mode) == 8 ?
3649 new_bd_ia32_Conv_I2I8Bit : new_bd_ia32_Conv_I2I;
3650 return func(dbgi, block, base, index, mem, val, mode);
3654 * Create a conversion from general purpose to x87 register
3656 static ir_node *gen_x87_gp_to_fp(ir_node *node, ir_mode *src_mode)
3658 ir_node *src_block = get_nodes_block(node);
3659 ir_node *block = be_transform_node(src_block);
3660 ir_graph *irg = get_Block_irg(block);
3661 dbg_info *dbgi = get_irn_dbg_info(node);
3662 ir_node *op = get_Conv_op(node);
3663 ir_node *new_op = NULL;
3665 ir_mode *store_mode;
3670 /* fild can use source AM if the operand is a signed 16bit or 32bit integer */
3671 if (possible_int_mode_for_fp(src_mode)) {
3672 ia32_address_mode_t am;
3674 match_arguments(&am, src_block, NULL, op, NULL, match_am | match_try_am | match_16bit_am);
3675 if (am.op_type == ia32_AddrModeS) {
3676 ia32_address_t *addr = &am.addr;
3678 fild = new_bd_ia32_vfild(dbgi, block, addr->base, addr->index, addr->mem);
3679 new_node = new_r_Proj(fild, mode_vfp, pn_ia32_vfild_res);
3681 set_am_attributes(fild, &am);
3682 SET_IA32_ORIG_NODE(fild, node);
3684 fix_mem_proj(fild, &am);
3689 if (new_op == NULL) {
3690 new_op = be_transform_node(op);
3693 mode = get_irn_mode(op);
3695 /* first convert to 32 bit signed if necessary */
3696 if (get_mode_size_bits(src_mode) < 32) {
3697 if (!upper_bits_clean(new_op, src_mode)) {
3698 new_op = create_Conv_I2I(dbgi, block, noreg_GP, noreg_GP, nomem, new_op, src_mode);
3699 SET_IA32_ORIG_NODE(new_op, node);
3704 assert(get_mode_size_bits(mode) == 32);
3707 store = new_bd_ia32_Store(dbgi, block, get_irg_frame(irg), noreg_GP, nomem, new_op);
3709 set_ia32_use_frame(store);
3710 set_ia32_op_type(store, ia32_AddrModeD);
3711 set_ia32_ls_mode(store, mode_Iu);
3713 /* exception for 32bit unsigned, do a 64bit spill+load */
3714 if (!mode_is_signed(mode)) {
3717 ir_node *zero_const = ia32_create_Immediate(NULL, 0, 0);
3719 ir_node *zero_store = new_bd_ia32_Store(dbgi, block, get_irg_frame(irg),
3720 noreg_GP, nomem, zero_const);
3722 set_ia32_use_frame(zero_store);
3723 set_ia32_op_type(zero_store, ia32_AddrModeD);
3724 add_ia32_am_offs_int(zero_store, 4);
3725 set_ia32_ls_mode(zero_store, mode_Iu);
3730 store = new_rd_Sync(dbgi, block, 2, in);
3731 store_mode = mode_Ls;
3733 store_mode = mode_Is;
3737 fild = new_bd_ia32_vfild(dbgi, block, get_irg_frame(irg), noreg_GP, store);
3739 set_ia32_use_frame(fild);
3740 set_ia32_op_type(fild, ia32_AddrModeS);
3741 set_ia32_ls_mode(fild, store_mode);
3743 new_node = new_r_Proj(fild, mode_vfp, pn_ia32_vfild_res);
3749 * Create a conversion from one integer mode into another one
3751 static ir_node *create_I2I_Conv(ir_mode *src_mode, ir_mode *tgt_mode,
3752 dbg_info *dbgi, ir_node *block, ir_node *op,
3755 ir_node *new_block = be_transform_node(block);
3757 ir_mode *smaller_mode;
3758 ia32_address_mode_t am;
3759 ia32_address_t *addr = &am.addr;
3762 if (get_mode_size_bits(src_mode) < get_mode_size_bits(tgt_mode)) {
3763 smaller_mode = src_mode;
3765 smaller_mode = tgt_mode;
3768 #ifdef DEBUG_libfirm
3770 ir_fprintf(stderr, "Optimisation warning: conv after constant %+F\n",
3775 match_arguments(&am, block, NULL, op, NULL,
3776 match_am | match_8bit_am | match_16bit_am);
3778 if (upper_bits_clean(am.new_op2, smaller_mode)) {
3779 /* unnecessary conv. in theory it shouldn't have been AM */
3780 assert(is_ia32_NoReg_GP(addr->base));
3781 assert(is_ia32_NoReg_GP(addr->index));
3782 assert(is_NoMem(addr->mem));
3783 assert(am.addr.offset == 0);
3784 assert(am.addr.symconst_ent == NULL);
3788 new_node = create_Conv_I2I(dbgi, new_block, addr->base, addr->index,
3789 addr->mem, am.new_op2, smaller_mode);
3790 set_am_attributes(new_node, &am);
3791 /* match_arguments assume that out-mode = in-mode, this isn't true here
3793 set_ia32_ls_mode(new_node, smaller_mode);
3794 SET_IA32_ORIG_NODE(new_node, node);
3795 new_node = fix_mem_proj(new_node, &am);
3800 * Transforms a Conv node.
3802 * @return The created ia32 Conv node
3804 static ir_node *gen_Conv(ir_node *node)
3806 ir_node *block = get_nodes_block(node);
3807 ir_node *new_block = be_transform_node(block);
3808 ir_node *op = get_Conv_op(node);
3809 ir_node *new_op = NULL;
3810 dbg_info *dbgi = get_irn_dbg_info(node);
3811 ir_mode *src_mode = get_irn_mode(op);
3812 ir_mode *tgt_mode = get_irn_mode(node);
3813 int src_bits = get_mode_size_bits(src_mode);
3814 int tgt_bits = get_mode_size_bits(tgt_mode);
3815 ir_node *res = NULL;
3817 assert(!mode_is_int(src_mode) || src_bits <= 32);
3818 assert(!mode_is_int(tgt_mode) || tgt_bits <= 32);
3820 /* modeB -> X should already be lowered by the lower_mode_b pass */
3821 if (src_mode == mode_b) {
3822 panic("ConvB not lowered %+F", node);
3825 if (src_mode == tgt_mode) {
3826 if (get_Conv_strict(node)) {
3827 if (ia32_cg_config.use_sse2) {
3828 /* when we are in SSE mode, we can kill all strict no-op conversion */
3829 return be_transform_node(op);
3832 /* this should be optimized already, but who knows... */
3833 DEBUG_ONLY(ir_fprintf(stderr, "Debug warning: conv %+F is pointless\n", node));
3834 DB((dbg, LEVEL_1, "killed Conv(mode, mode) ..."));
3835 return be_transform_node(op);
3839 if (mode_is_float(src_mode)) {
3840 new_op = be_transform_node(op);
3841 /* we convert from float ... */
3842 if (mode_is_float(tgt_mode)) {
3844 if (ia32_cg_config.use_sse2) {
3845 DB((dbg, LEVEL_1, "create Conv(float, float) ..."));
3846 res = new_bd_ia32_Conv_FP2FP(dbgi, new_block, noreg_GP, noreg_GP,
3848 set_ia32_ls_mode(res, tgt_mode);
3850 if (get_Conv_strict(node)) {
3851 /* if fp_no_float_fold is not set then we assume that we
3852 * don't have any float operations in a non
3853 * mode_float_arithmetic mode and can skip strict upconvs */
3854 if (src_bits < tgt_bits) {
3855 DB((dbg, LEVEL_1, "killed Conv(float, float) ..."));
3858 res = gen_x87_strict_conv(tgt_mode, new_op);
3859 SET_IA32_ORIG_NODE(get_Proj_pred(res), node);
3863 DB((dbg, LEVEL_1, "killed Conv(float, float) ..."));
3868 DB((dbg, LEVEL_1, "create Conv(float, int) ..."));
3869 if (ia32_cg_config.use_sse2) {
3870 res = new_bd_ia32_Conv_FP2I(dbgi, new_block, noreg_GP, noreg_GP,
3872 set_ia32_ls_mode(res, src_mode);
3874 return gen_x87_fp_to_gp(node);
3878 /* we convert from int ... */
3879 if (mode_is_float(tgt_mode)) {
3881 DB((dbg, LEVEL_1, "create Conv(int, float) ..."));
3882 if (ia32_cg_config.use_sse2) {
3883 new_op = be_transform_node(op);
3884 res = new_bd_ia32_Conv_I2FP(dbgi, new_block, noreg_GP, noreg_GP,
3886 set_ia32_ls_mode(res, tgt_mode);
3888 unsigned int_mantissa = get_mode_size_bits(src_mode) - (mode_is_signed(src_mode) ? 1 : 0);
3889 unsigned float_mantissa = tarval_ieee754_get_mantissa_size(tgt_mode);
3890 res = gen_x87_gp_to_fp(node, src_mode);
3892 /* we need a strict-Conv, if the int mode has more bits than the
3894 if (float_mantissa < int_mantissa) {
3895 res = gen_x87_strict_conv(tgt_mode, res);
3896 SET_IA32_ORIG_NODE(get_Proj_pred(res), node);
3900 } else if (tgt_mode == mode_b) {
3901 /* mode_b lowering already took care that we only have 0/1 values */
3902 DB((dbg, LEVEL_1, "omitting unnecessary Conv(%+F, %+F) ...",
3903 src_mode, tgt_mode));
3904 return be_transform_node(op);
3907 if (src_bits == tgt_bits) {
3908 DB((dbg, LEVEL_1, "omitting unnecessary Conv(%+F, %+F) ...",
3909 src_mode, tgt_mode));
3910 return be_transform_node(op);
3913 res = create_I2I_Conv(src_mode, tgt_mode, dbgi, block, op, node);
3921 static ir_node *create_immediate_or_transform(ir_node *node,
3922 char immediate_constraint_type)
3924 ir_node *new_node = ia32_try_create_Immediate(node, immediate_constraint_type);
3925 if (new_node == NULL) {
3926 new_node = be_transform_node(node);
3932 * Transforms a FrameAddr into an ia32 Add.
3934 static ir_node *gen_be_FrameAddr(ir_node *node)
3936 ir_node *block = be_transform_node(get_nodes_block(node));
3937 ir_node *op = be_get_FrameAddr_frame(node);
3938 ir_node *new_op = be_transform_node(op);
3939 dbg_info *dbgi = get_irn_dbg_info(node);
3942 new_node = new_bd_ia32_Lea(dbgi, block, new_op, noreg_GP);
3943 set_ia32_frame_ent(new_node, arch_get_frame_entity(node));
3944 set_ia32_use_frame(new_node);
3946 SET_IA32_ORIG_NODE(new_node, node);
3952 * In case SSE is used we need to copy the result from XMM0 to FPU TOS before return.
3954 static ir_node *gen_be_Return(ir_node *node)
3956 ir_graph *irg = current_ir_graph;
3957 ir_node *ret_val = get_irn_n(node, n_be_Return_val);
3958 ir_node *ret_mem = get_irn_n(node, n_be_Return_mem);
3959 ir_node *new_ret_val = be_transform_node(ret_val);
3960 ir_node *new_ret_mem = be_transform_node(ret_mem);
3961 ir_entity *ent = get_irg_entity(irg);
3962 ir_type *tp = get_entity_type(ent);
3963 dbg_info *dbgi = get_irn_dbg_info(node);
3964 ir_node *block = be_transform_node(get_nodes_block(node));
3967 ir_node *frame, *sse_store, *fld, *mproj;
3974 assert(ret_val != NULL);
3975 if (be_Return_get_n_rets(node) < 1 || ! ia32_cg_config.use_sse2) {
3976 return be_duplicate_node(node);
3979 res_type = get_method_res_type(tp, 0);
3981 if (! is_Primitive_type(res_type)) {
3982 return be_duplicate_node(node);
3985 mode = get_type_mode(res_type);
3986 if (! mode_is_float(mode)) {
3987 return be_duplicate_node(node);
3990 assert(get_method_n_ress(tp) == 1);
3992 frame = get_irg_frame(irg);
3994 /* store xmm0 onto stack */
3995 sse_store = new_bd_ia32_xStoreSimple(dbgi, block, frame, noreg_GP,
3996 new_ret_mem, new_ret_val);
3997 set_ia32_ls_mode(sse_store, mode);
3998 set_ia32_op_type(sse_store, ia32_AddrModeD);
3999 set_ia32_use_frame(sse_store);
4001 /* load into x87 register */
4002 fld = new_bd_ia32_vfld(dbgi, block, frame, noreg_GP, sse_store, mode);
4003 set_ia32_op_type(fld, ia32_AddrModeS);
4004 set_ia32_use_frame(fld);
4006 mproj = new_r_Proj(fld, mode_M, pn_ia32_vfld_M);
4007 fld = new_r_Proj(fld, mode_vfp, pn_ia32_vfld_res);
4009 /* create a new return */
4010 arity = get_irn_arity(node);
4011 in = ALLOCAN(ir_node*, arity);
4012 pop = be_Return_get_pop(node);
4013 for (i = 0; i < arity; ++i) {
4014 ir_node *op = get_irn_n(node, i);
4015 if (op == ret_val) {
4017 } else if (op == ret_mem) {
4020 in[i] = be_transform_node(op);
4023 new_node = be_new_Return(dbgi, irg, block, arity, pop, arity, in);
4024 copy_node_attr(irg, node, new_node);
4030 * Transform a be_AddSP into an ia32_SubSP.
4032 static ir_node *gen_be_AddSP(ir_node *node)
4034 ir_node *sz = get_irn_n(node, n_be_AddSP_size);
4035 ir_node *sp = get_irn_n(node, n_be_AddSP_old_sp);
4037 ir_node *new_node = gen_binop(node, sp, sz, new_bd_ia32_SubSP,
4038 match_am | match_immediate);
4039 assert(is_ia32_SubSP(new_node));
4040 arch_irn_set_register(new_node, pn_ia32_SubSP_stack,
4041 &ia32_registers[REG_ESP]);
4046 * Transform a be_SubSP into an ia32_AddSP
4048 static ir_node *gen_be_SubSP(ir_node *node)
4050 ir_node *sz = get_irn_n(node, n_be_SubSP_size);
4051 ir_node *sp = get_irn_n(node, n_be_SubSP_old_sp);
4053 ir_node *new_node = gen_binop(node, sp, sz, new_bd_ia32_AddSP,
4054 match_am | match_immediate);
4055 assert(is_ia32_AddSP(new_node));
4056 arch_irn_set_register(new_node, pn_ia32_AddSP_stack,
4057 &ia32_registers[REG_ESP]);
4062 * Change some phi modes
4064 static ir_node *gen_Phi(ir_node *node)
4066 const arch_register_req_t *req;
4067 ir_node *block = be_transform_node(get_nodes_block(node));
4068 ir_graph *irg = current_ir_graph;
4069 dbg_info *dbgi = get_irn_dbg_info(node);
4070 ir_mode *mode = get_irn_mode(node);
4073 if (ia32_mode_needs_gp_reg(mode)) {
4074 /* we shouldn't have any 64bit stuff around anymore */
4075 assert(get_mode_size_bits(mode) <= 32);
4076 /* all integer operations are on 32bit registers now */
4078 req = ia32_reg_classes[CLASS_ia32_gp].class_req;
4079 } else if (mode_is_float(mode)) {
4080 if (ia32_cg_config.use_sse2) {
4082 req = ia32_reg_classes[CLASS_ia32_xmm].class_req;
4085 req = ia32_reg_classes[CLASS_ia32_vfp].class_req;
4088 req = arch_no_register_req;
4091 /* phi nodes allow loops, so we use the old arguments for now
4092 * and fix this later */
4093 phi = new_ir_node(dbgi, irg, block, op_Phi, mode, get_irn_arity(node),
4094 get_irn_in(node) + 1);
4095 copy_node_attr(irg, node, phi);
4096 be_duplicate_deps(node, phi);
4098 arch_set_out_register_req(phi, 0, req);
4100 be_enqueue_preds(node);
4105 static ir_node *gen_Jmp(ir_node *node)
4107 ir_node *block = get_nodes_block(node);
4108 ir_node *new_block = be_transform_node(block);
4109 dbg_info *dbgi = get_irn_dbg_info(node);
4112 new_node = new_bd_ia32_Jmp(dbgi, new_block);
4113 SET_IA32_ORIG_NODE(new_node, node);
4121 static ir_node *gen_IJmp(ir_node *node)
4123 ir_node *block = get_nodes_block(node);
4124 ir_node *new_block = be_transform_node(block);
4125 dbg_info *dbgi = get_irn_dbg_info(node);
4126 ir_node *op = get_IJmp_target(node);
4128 ia32_address_mode_t am;
4129 ia32_address_t *addr = &am.addr;
4131 assert(get_irn_mode(op) == mode_P);
4133 match_arguments(&am, block, NULL, op, NULL, match_am | match_immediate);
4135 new_node = new_bd_ia32_IJmp(dbgi, new_block, addr->base, addr->index,
4136 addr->mem, am.new_op2);
4137 set_am_attributes(new_node, &am);
4138 SET_IA32_ORIG_NODE(new_node, node);
4140 new_node = fix_mem_proj(new_node, &am);
4145 static ir_node *gen_ia32_l_ShlDep(ir_node *node)
4147 ir_node *left = get_irn_n(node, n_ia32_l_ShlDep_val);
4148 ir_node *right = get_irn_n(node, n_ia32_l_ShlDep_count);
4150 return gen_shift_binop(node, left, right, new_bd_ia32_Shl,
4151 match_immediate | match_mode_neutral);
4154 static ir_node *gen_ia32_l_ShrDep(ir_node *node)
4156 ir_node *left = get_irn_n(node, n_ia32_l_ShrDep_val);
4157 ir_node *right = get_irn_n(node, n_ia32_l_ShrDep_count);
4158 return gen_shift_binop(node, left, right, new_bd_ia32_Shr,
4162 static ir_node *gen_ia32_l_SarDep(ir_node *node)
4164 ir_node *left = get_irn_n(node, n_ia32_l_SarDep_val);
4165 ir_node *right = get_irn_n(node, n_ia32_l_SarDep_count);
4166 return gen_shift_binop(node, left, right, new_bd_ia32_Sar,
4170 static ir_node *gen_ia32_l_Add(ir_node *node)
4172 ir_node *left = get_irn_n(node, n_ia32_l_Add_left);
4173 ir_node *right = get_irn_n(node, n_ia32_l_Add_right);
4174 ir_node *lowered = gen_binop(node, left, right, new_bd_ia32_Add,
4175 match_commutative | match_am | match_immediate |
4176 match_mode_neutral);
4178 if (is_Proj(lowered)) {
4179 lowered = get_Proj_pred(lowered);
4181 assert(is_ia32_Add(lowered));
4182 set_irn_mode(lowered, mode_T);
4188 static ir_node *gen_ia32_l_Adc(ir_node *node)
4190 return gen_binop_flags(node, new_bd_ia32_Adc,
4191 match_commutative | match_am | match_immediate |
4192 match_mode_neutral);
4196 * Transforms a l_MulS into a "real" MulS node.
4198 * @return the created ia32 Mul node
4200 static ir_node *gen_ia32_l_Mul(ir_node *node)
4202 ir_node *left = get_binop_left(node);
4203 ir_node *right = get_binop_right(node);
4205 return gen_binop(node, left, right, new_bd_ia32_Mul,
4206 match_commutative | match_am | match_mode_neutral);
4210 * Transforms a l_IMulS into a "real" IMul1OPS node.
4212 * @return the created ia32 IMul1OP node
4214 static ir_node *gen_ia32_l_IMul(ir_node *node)
4216 ir_node *left = get_binop_left(node);
4217 ir_node *right = get_binop_right(node);
4219 return gen_binop(node, left, right, new_bd_ia32_IMul1OP,
4220 match_commutative | match_am | match_mode_neutral);
4223 static ir_node *gen_ia32_l_Sub(ir_node *node)
4225 ir_node *left = get_irn_n(node, n_ia32_l_Sub_minuend);
4226 ir_node *right = get_irn_n(node, n_ia32_l_Sub_subtrahend);
4227 ir_node *lowered = gen_binop(node, left, right, new_bd_ia32_Sub,
4228 match_am | match_immediate | match_mode_neutral);
4230 if (is_Proj(lowered)) {
4231 lowered = get_Proj_pred(lowered);
4233 assert(is_ia32_Sub(lowered));
4234 set_irn_mode(lowered, mode_T);
4240 static ir_node *gen_ia32_l_Sbb(ir_node *node)
4242 return gen_binop_flags(node, new_bd_ia32_Sbb,
4243 match_am | match_immediate | match_mode_neutral);
4247 * Transforms a l_ShlD/l_ShrD into a ShlD/ShrD. Those nodes have 3 data inputs:
4248 * op1 - target to be shifted
4249 * op2 - contains bits to be shifted into target
4251 * Only op3 can be an immediate.
4253 static ir_node *gen_lowered_64bit_shifts(ir_node *node, ir_node *high,
4254 ir_node *low, ir_node *count)
4256 ir_node *block = get_nodes_block(node);
4257 ir_node *new_block = be_transform_node(block);
4258 dbg_info *dbgi = get_irn_dbg_info(node);
4259 ir_node *new_high = be_transform_node(high);
4260 ir_node *new_low = be_transform_node(low);
4264 /* the shift amount can be any mode that is bigger than 5 bits, since all
4265 * other bits are ignored anyway */
4266 while (is_Conv(count) &&
4267 get_irn_n_edges(count) == 1 &&
4268 mode_is_int(get_irn_mode(count))) {
4269 assert(get_mode_size_bits(get_irn_mode(count)) >= 5);
4270 count = get_Conv_op(count);
4272 new_count = create_immediate_or_transform(count, 0);
4274 if (is_ia32_l_ShlD(node)) {
4275 new_node = new_bd_ia32_ShlD(dbgi, new_block, new_high, new_low,
4278 new_node = new_bd_ia32_ShrD(dbgi, new_block, new_high, new_low,
4281 SET_IA32_ORIG_NODE(new_node, node);
4286 static ir_node *gen_ia32_l_ShlD(ir_node *node)
4288 ir_node *high = get_irn_n(node, n_ia32_l_ShlD_val_high);
4289 ir_node *low = get_irn_n(node, n_ia32_l_ShlD_val_low);
4290 ir_node *count = get_irn_n(node, n_ia32_l_ShlD_count);
4291 return gen_lowered_64bit_shifts(node, high, low, count);
4294 static ir_node *gen_ia32_l_ShrD(ir_node *node)
4296 ir_node *high = get_irn_n(node, n_ia32_l_ShrD_val_high);
4297 ir_node *low = get_irn_n(node, n_ia32_l_ShrD_val_low);
4298 ir_node *count = get_irn_n(node, n_ia32_l_ShrD_count);
4299 return gen_lowered_64bit_shifts(node, high, low, count);
4302 static ir_node *gen_ia32_l_LLtoFloat(ir_node *node)
4304 ir_node *src_block = get_nodes_block(node);
4305 ir_node *block = be_transform_node(src_block);
4306 ir_graph *irg = current_ir_graph;
4307 dbg_info *dbgi = get_irn_dbg_info(node);
4308 ir_node *frame = get_irg_frame(irg);
4309 ir_node *val_low = get_irn_n(node, n_ia32_l_LLtoFloat_val_low);
4310 ir_node *val_high = get_irn_n(node, n_ia32_l_LLtoFloat_val_high);
4311 ir_node *new_val_low = be_transform_node(val_low);
4312 ir_node *new_val_high = be_transform_node(val_high);
4314 ir_node *sync, *fild, *res;
4315 ir_node *store_low, *store_high;
4317 if (ia32_cg_config.use_sse2) {
4318 panic("ia32_l_LLtoFloat not implemented for SSE2");
4322 store_low = new_bd_ia32_Store(dbgi, block, frame, noreg_GP, nomem,
4324 store_high = new_bd_ia32_Store(dbgi, block, frame, noreg_GP, nomem,
4326 SET_IA32_ORIG_NODE(store_low, node);
4327 SET_IA32_ORIG_NODE(store_high, node);
4329 set_ia32_use_frame(store_low);
4330 set_ia32_use_frame(store_high);
4331 set_ia32_op_type(store_low, ia32_AddrModeD);
4332 set_ia32_op_type(store_high, ia32_AddrModeD);
4333 set_ia32_ls_mode(store_low, mode_Iu);
4334 set_ia32_ls_mode(store_high, mode_Is);
4335 add_ia32_am_offs_int(store_high, 4);
4339 sync = new_rd_Sync(dbgi, block, 2, in);
4342 fild = new_bd_ia32_vfild(dbgi, block, frame, noreg_GP, sync);
4344 set_ia32_use_frame(fild);
4345 set_ia32_op_type(fild, ia32_AddrModeS);
4346 set_ia32_ls_mode(fild, mode_Ls);
4348 SET_IA32_ORIG_NODE(fild, node);
4350 res = new_r_Proj(fild, mode_vfp, pn_ia32_vfild_res);
4352 if (! mode_is_signed(get_irn_mode(val_high))) {
4353 ia32_address_mode_t am;
4355 ir_node *count = ia32_create_Immediate(NULL, 0, 31);
4358 am.addr.base = get_symconst_base();
4359 am.addr.index = new_bd_ia32_Shr(dbgi, block, new_val_high, count);
4360 am.addr.mem = nomem;
4363 am.addr.symconst_ent = ia32_gen_fp_known_const(ia32_ULLBIAS);
4364 am.addr.tls_segment = false;
4365 am.addr.use_frame = 0;
4366 am.addr.frame_entity = NULL;
4367 am.addr.symconst_sign = 0;
4368 am.ls_mode = mode_F;
4369 am.mem_proj = nomem;
4370 am.op_type = ia32_AddrModeS;
4372 am.new_op2 = ia32_new_NoReg_vfp(current_ir_graph);
4373 am.pinned = op_pin_state_floats;
4375 am.ins_permuted = false;
4377 fadd = new_bd_ia32_vfadd(dbgi, block, am.addr.base, am.addr.index, am.addr.mem,
4378 am.new_op1, am.new_op2, get_fpcw());
4379 set_am_attributes(fadd, &am);
4381 set_irn_mode(fadd, mode_T);
4382 res = new_rd_Proj(NULL, fadd, mode_vfp, pn_ia32_res);
4387 static ir_node *gen_ia32_l_FloattoLL(ir_node *node)
4389 ir_node *src_block = get_nodes_block(node);
4390 ir_node *block = be_transform_node(src_block);
4391 ir_graph *irg = get_Block_irg(block);
4392 dbg_info *dbgi = get_irn_dbg_info(node);
4393 ir_node *frame = get_irg_frame(irg);
4394 ir_node *val = get_irn_n(node, n_ia32_l_FloattoLL_val);
4395 ir_node *new_val = be_transform_node(val);
4396 ir_node *fist, *mem;
4398 mem = gen_vfist(dbgi, block, frame, noreg_GP, nomem, new_val, &fist);
4399 SET_IA32_ORIG_NODE(fist, node);
4400 set_ia32_use_frame(fist);
4401 set_ia32_op_type(fist, ia32_AddrModeD);
4402 set_ia32_ls_mode(fist, mode_Ls);
4407 static ir_node *gen_Proj_l_FloattoLL(ir_node *node)
4409 ir_node *block = be_transform_node(get_nodes_block(node));
4410 ir_graph *irg = get_Block_irg(block);
4411 ir_node *pred = get_Proj_pred(node);
4412 ir_node *new_pred = be_transform_node(pred);
4413 ir_node *frame = get_irg_frame(irg);
4414 dbg_info *dbgi = get_irn_dbg_info(node);
4415 long pn = get_Proj_proj(node);
4420 load = new_bd_ia32_Load(dbgi, block, frame, noreg_GP, new_pred);
4421 SET_IA32_ORIG_NODE(load, node);
4422 set_ia32_use_frame(load);
4423 set_ia32_op_type(load, ia32_AddrModeS);
4424 set_ia32_ls_mode(load, mode_Iu);
4425 /* we need a 64bit stackslot (fist stores 64bit) even though we only load
4426 * 32 bit from it with this particular load */
4427 attr = get_ia32_attr(load);
4428 attr->data.need_64bit_stackent = 1;
4430 if (pn == pn_ia32_l_FloattoLL_res_high) {
4431 add_ia32_am_offs_int(load, 4);
4433 assert(pn == pn_ia32_l_FloattoLL_res_low);
4436 proj = new_r_Proj(load, mode_Iu, pn_ia32_Load_res);
4442 * Transform the Projs of an AddSP.
4444 static ir_node *gen_Proj_be_AddSP(ir_node *node)
4446 ir_node *pred = get_Proj_pred(node);
4447 ir_node *new_pred = be_transform_node(pred);
4448 dbg_info *dbgi = get_irn_dbg_info(node);
4449 long proj = get_Proj_proj(node);
4451 if (proj == pn_be_AddSP_sp) {
4452 ir_node *res = new_rd_Proj(dbgi, new_pred, mode_Iu,
4453 pn_ia32_SubSP_stack);
4454 arch_set_irn_register(res, &ia32_registers[REG_ESP]);
4456 } else if (proj == pn_be_AddSP_res) {
4457 return new_rd_Proj(dbgi, new_pred, mode_Iu,
4458 pn_ia32_SubSP_addr);
4459 } else if (proj == pn_be_AddSP_M) {
4460 return new_rd_Proj(dbgi, new_pred, mode_M, pn_ia32_SubSP_M);
4463 panic("No idea how to transform proj->AddSP");
4467 * Transform the Projs of a SubSP.
4469 static ir_node *gen_Proj_be_SubSP(ir_node *node)
4471 ir_node *pred = get_Proj_pred(node);
4472 ir_node *new_pred = be_transform_node(pred);
4473 dbg_info *dbgi = get_irn_dbg_info(node);
4474 long proj = get_Proj_proj(node);
4476 if (proj == pn_be_SubSP_sp) {
4477 ir_node *res = new_rd_Proj(dbgi, new_pred, mode_Iu,
4478 pn_ia32_AddSP_stack);
4479 arch_set_irn_register(res, &ia32_registers[REG_ESP]);
4481 } else if (proj == pn_be_SubSP_M) {
4482 return new_rd_Proj(dbgi, new_pred, mode_M, pn_ia32_AddSP_M);
4485 panic("No idea how to transform proj->SubSP");
4489 * Transform and renumber the Projs from a Load.
4491 static ir_node *gen_Proj_Load(ir_node *node)
4494 ir_node *block = be_transform_node(get_nodes_block(node));
4495 ir_node *pred = get_Proj_pred(node);
4496 dbg_info *dbgi = get_irn_dbg_info(node);
4497 long proj = get_Proj_proj(node);
4499 /* loads might be part of source address mode matches, so we don't
4500 * transform the ProjMs yet (with the exception of loads whose result is
4503 if (is_Load(pred) && proj == pn_Load_M && get_irn_n_edges(pred) > 1) {
4506 /* this is needed, because sometimes we have loops that are only
4507 reachable through the ProjM */
4508 be_enqueue_preds(node);
4509 /* do it in 2 steps, to silence firm verifier */
4510 res = new_rd_Proj(dbgi, pred, mode_M, pn_Load_M);
4511 set_Proj_proj(res, pn_ia32_mem);
4515 /* renumber the proj */
4516 new_pred = be_transform_node(pred);
4517 if (is_ia32_Load(new_pred)) {
4520 return new_rd_Proj(dbgi, new_pred, mode_Iu, pn_ia32_Load_res);
4522 return new_rd_Proj(dbgi, new_pred, mode_M, pn_ia32_Load_M);
4523 case pn_Load_X_regular:
4524 return new_rd_Jmp(dbgi, block);
4525 case pn_Load_X_except:
4526 /* This Load might raise an exception. Mark it. */
4527 set_ia32_exc_label(new_pred, 1);
4528 return new_rd_Proj(dbgi, new_pred, mode_X, pn_ia32_Load_X_exc);
4532 } else if (is_ia32_Conv_I2I(new_pred) ||
4533 is_ia32_Conv_I2I8Bit(new_pred)) {
4534 set_irn_mode(new_pred, mode_T);
4535 if (proj == pn_Load_res) {
4536 return new_rd_Proj(dbgi, new_pred, mode_Iu, pn_ia32_res);
4537 } else if (proj == pn_Load_M) {
4538 return new_rd_Proj(dbgi, new_pred, mode_M, pn_ia32_mem);
4540 } else if (is_ia32_xLoad(new_pred)) {
4543 return new_rd_Proj(dbgi, new_pred, mode_xmm, pn_ia32_xLoad_res);
4545 return new_rd_Proj(dbgi, new_pred, mode_M, pn_ia32_xLoad_M);
4546 case pn_Load_X_regular:
4547 return new_rd_Jmp(dbgi, block);
4548 case pn_Load_X_except:
4549 /* This Load might raise an exception. Mark it. */
4550 set_ia32_exc_label(new_pred, 1);
4551 return new_rd_Proj(dbgi, new_pred, mode_X, pn_ia32_xLoad_X_exc);
4555 } else if (is_ia32_vfld(new_pred)) {
4558 return new_rd_Proj(dbgi, new_pred, mode_vfp, pn_ia32_vfld_res);
4560 return new_rd_Proj(dbgi, new_pred, mode_M, pn_ia32_vfld_M);
4561 case pn_Load_X_regular:
4562 return new_rd_Jmp(dbgi, block);
4563 case pn_Load_X_except:
4564 /* This Load might raise an exception. Mark it. */
4565 set_ia32_exc_label(new_pred, 1);
4566 return new_rd_Proj(dbgi, new_pred, mode_X, pn_ia32_vfld_X_exc);
4571 /* can happen for ProJMs when source address mode happened for the
4574 /* however it should not be the result proj, as that would mean the
4575 load had multiple users and should not have been used for
4577 if (proj != pn_Load_M) {
4578 panic("internal error: transformed node not a Load");
4580 return new_rd_Proj(dbgi, new_pred, mode_M, 1);
4583 panic("No idea how to transform proj");
4587 * Transform and renumber the Projs from a Div or Mod instruction.
4589 static ir_node *gen_Proj_Div(ir_node *node)
4591 ir_node *block = be_transform_node(get_nodes_block(node));
4592 ir_node *pred = get_Proj_pred(node);
4593 ir_node *new_pred = be_transform_node(pred);
4594 dbg_info *dbgi = get_irn_dbg_info(node);
4595 long proj = get_Proj_proj(node);
4597 assert(pn_ia32_Div_M == pn_ia32_IDiv_M);
4598 assert(pn_ia32_Div_div_res == pn_ia32_IDiv_div_res);
4602 if (is_ia32_Div(new_pred) || is_ia32_IDiv(new_pred)) {
4603 return new_rd_Proj(dbgi, new_pred, mode_M, pn_ia32_Div_M);
4604 } else if (is_ia32_xDiv(new_pred)) {
4605 return new_rd_Proj(dbgi, new_pred, mode_M, pn_ia32_xDiv_M);
4606 } else if (is_ia32_vfdiv(new_pred)) {
4607 return new_rd_Proj(dbgi, new_pred, mode_M, pn_ia32_vfdiv_M);
4609 panic("Div transformed to unexpected thing %+F", new_pred);
4612 if (is_ia32_Div(new_pred) || is_ia32_IDiv(new_pred)) {
4613 return new_rd_Proj(dbgi, new_pred, mode_Iu, pn_ia32_Div_div_res);
4614 } else if (is_ia32_xDiv(new_pred)) {
4615 return new_rd_Proj(dbgi, new_pred, mode_xmm, pn_ia32_xDiv_res);
4616 } else if (is_ia32_vfdiv(new_pred)) {
4617 return new_rd_Proj(dbgi, new_pred, mode_vfp, pn_ia32_vfdiv_res);
4619 panic("Div transformed to unexpected thing %+F", new_pred);
4621 case pn_Div_X_regular:
4622 return new_rd_Jmp(dbgi, block);
4623 case pn_Div_X_except:
4624 set_ia32_exc_label(new_pred, 1);
4625 return new_rd_Proj(dbgi, new_pred, mode_X, pn_ia32_Div_X_exc);
4630 panic("No idea how to transform proj->Div");
4634 * Transform and renumber the Projs from a Div or Mod instruction.
4636 static ir_node *gen_Proj_Mod(ir_node *node)
4638 ir_node *pred = get_Proj_pred(node);
4639 ir_node *new_pred = be_transform_node(pred);
4640 dbg_info *dbgi = get_irn_dbg_info(node);
4641 long proj = get_Proj_proj(node);
4643 assert(is_ia32_Div(new_pred) || is_ia32_IDiv(new_pred));
4644 assert(pn_ia32_Div_M == pn_ia32_IDiv_M);
4645 assert(pn_ia32_Div_mod_res == pn_ia32_IDiv_mod_res);
4649 return new_rd_Proj(dbgi, new_pred, mode_M, pn_ia32_Div_M);
4651 return new_rd_Proj(dbgi, new_pred, mode_Iu, pn_ia32_Div_mod_res);
4652 case pn_Mod_X_except:
4653 set_ia32_exc_label(new_pred, 1);
4654 return new_rd_Proj(dbgi, new_pred, mode_X, pn_ia32_Div_X_exc);
4658 panic("No idea how to transform proj->Mod");
4662 * Transform and renumber the Projs from a CopyB.
4664 static ir_node *gen_Proj_CopyB(ir_node *node)
4666 ir_node *pred = get_Proj_pred(node);
4667 ir_node *new_pred = be_transform_node(pred);
4668 dbg_info *dbgi = get_irn_dbg_info(node);
4669 long proj = get_Proj_proj(node);
4673 if (is_ia32_CopyB_i(new_pred)) {
4674 return new_rd_Proj(dbgi, new_pred, mode_M, pn_ia32_CopyB_i_M);
4675 } else if (is_ia32_CopyB(new_pred)) {
4676 return new_rd_Proj(dbgi, new_pred, mode_M, pn_ia32_CopyB_M);
4683 panic("No idea how to transform proj->CopyB");
4686 static ir_node *gen_be_Call(ir_node *node)
4688 dbg_info *const dbgi = get_irn_dbg_info(node);
4689 ir_node *const src_block = get_nodes_block(node);
4690 ir_node *const block = be_transform_node(src_block);
4691 ir_node *const src_mem = get_irn_n(node, n_be_Call_mem);
4692 ir_node *const src_sp = get_irn_n(node, n_be_Call_sp);
4693 ir_node *const sp = be_transform_node(src_sp);
4694 ir_node *const src_ptr = get_irn_n(node, n_be_Call_ptr);
4695 ia32_address_mode_t am;
4696 ia32_address_t *const addr = &am.addr;
4701 ir_node * eax = noreg_GP;
4702 ir_node * ecx = noreg_GP;
4703 ir_node * edx = noreg_GP;
4704 unsigned const pop = be_Call_get_pop(node);
4705 ir_type *const call_tp = be_Call_get_type(node);
4706 int old_no_pic_adjust;
4708 /* Run the x87 simulator if the call returns a float value */
4709 if (get_method_n_ress(call_tp) > 0) {
4710 ir_type *const res_type = get_method_res_type(call_tp, 0);
4711 ir_mode *const res_mode = get_type_mode(res_type);
4713 if (res_mode != NULL && mode_is_float(res_mode)) {
4714 ir_graph *irg = current_ir_graph;
4715 ia32_irg_data_t *irg_data = ia32_get_irg_data(irg);
4716 irg_data->do_x87_sim = 1;
4720 /* We do not want be_Call direct calls */
4721 assert(be_Call_get_entity(node) == NULL);
4723 /* special case for PIC trampoline calls */
4724 old_no_pic_adjust = ia32_no_pic_adjust;
4725 ia32_no_pic_adjust = be_get_irg_options(current_ir_graph)->pic;
4727 match_arguments(&am, src_block, NULL, src_ptr, src_mem,
4728 match_am | match_immediate);
4730 ia32_no_pic_adjust = old_no_pic_adjust;
4732 i = get_irn_arity(node) - 1;
4733 fpcw = be_transform_node(get_irn_n(node, i--));
4734 for (; i >= n_be_Call_first_arg; --i) {
4735 arch_register_req_t const *const req = arch_get_register_req(node, i);
4736 ir_node *const reg_parm = be_transform_node(get_irn_n(node, i));
4738 assert(req->type == arch_register_req_type_limited);
4739 assert(req->cls == &ia32_reg_classes[CLASS_ia32_gp]);
4741 switch (*req->limited) {
4742 case 1 << REG_GP_EAX: assert(eax == noreg_GP); eax = reg_parm; break;
4743 case 1 << REG_GP_ECX: assert(ecx == noreg_GP); ecx = reg_parm; break;
4744 case 1 << REG_GP_EDX: assert(edx == noreg_GP); edx = reg_parm; break;
4745 default: panic("Invalid GP register for register parameter");
4749 mem = transform_AM_mem(block, src_ptr, src_mem, addr->mem);
4750 call = new_bd_ia32_Call(dbgi, block, addr->base, addr->index, mem,
4751 am.new_op2, sp, fpcw, eax, ecx, edx, pop, call_tp);
4752 set_am_attributes(call, &am);
4753 call = fix_mem_proj(call, &am);
4755 if (get_irn_pinned(node) == op_pin_state_pinned)
4756 set_irn_pinned(call, op_pin_state_pinned);
4758 SET_IA32_ORIG_NODE(call, node);
4760 if (ia32_cg_config.use_sse2) {
4761 /* remember this call for post-processing */
4762 ARR_APP1(ir_node *, call_list, call);
4763 ARR_APP1(ir_type *, call_types, be_Call_get_type(node));
4770 * Transform Builtin trap
4772 static ir_node *gen_trap(ir_node *node)
4774 dbg_info *dbgi = get_irn_dbg_info(node);
4775 ir_node *block = be_transform_node(get_nodes_block(node));
4776 ir_node *mem = be_transform_node(get_Builtin_mem(node));
4778 return new_bd_ia32_UD2(dbgi, block, mem);
4782 * Transform Builtin debugbreak
4784 static ir_node *gen_debugbreak(ir_node *node)
4786 dbg_info *dbgi = get_irn_dbg_info(node);
4787 ir_node *block = be_transform_node(get_nodes_block(node));
4788 ir_node *mem = be_transform_node(get_Builtin_mem(node));
4790 return new_bd_ia32_Breakpoint(dbgi, block, mem);
4794 * Transform Builtin return_address
4796 static ir_node *gen_return_address(ir_node *node)
4798 ir_node *param = get_Builtin_param(node, 0);
4799 ir_node *frame = get_Builtin_param(node, 1);
4800 dbg_info *dbgi = get_irn_dbg_info(node);
4801 ir_tarval *tv = get_Const_tarval(param);
4802 ir_graph *irg = get_irn_irg(node);
4803 unsigned long value = get_tarval_long(tv);
4805 ir_node *block = be_transform_node(get_nodes_block(node));
4806 ir_node *ptr = be_transform_node(frame);
4810 ir_node *cnt = new_bd_ia32_ProduceVal(dbgi, block);
4811 ir_node *res = new_bd_ia32_ProduceVal(dbgi, block);
4812 ptr = new_bd_ia32_ClimbFrame(dbgi, block, ptr, cnt, res, value);
4815 /* load the return address from this frame */
4816 load = new_bd_ia32_Load(dbgi, block, ptr, noreg_GP, nomem);
4818 set_irn_pinned(load, get_irn_pinned(node));
4819 set_ia32_op_type(load, ia32_AddrModeS);
4820 set_ia32_ls_mode(load, mode_Iu);
4822 set_ia32_am_offs_int(load, 0);
4823 set_ia32_use_frame(load);
4824 set_ia32_frame_ent(load, ia32_get_return_address_entity(irg));
4826 if (get_irn_pinned(node) == op_pin_state_floats) {
4827 assert((int)pn_ia32_xLoad_res == (int)pn_ia32_vfld_res
4828 && (int)pn_ia32_vfld_res == (int)pn_ia32_Load_res
4829 && (int)pn_ia32_Load_res == (int)pn_ia32_res);
4830 arch_irn_add_flags(load, arch_irn_flags_rematerializable);
4833 SET_IA32_ORIG_NODE(load, node);
4834 return new_r_Proj(load, mode_Iu, pn_ia32_Load_res);
4838 * Transform Builtin frame_address
4840 static ir_node *gen_frame_address(ir_node *node)
4842 ir_node *param = get_Builtin_param(node, 0);
4843 ir_node *frame = get_Builtin_param(node, 1);
4844 dbg_info *dbgi = get_irn_dbg_info(node);
4845 ir_tarval *tv = get_Const_tarval(param);
4846 ir_graph *irg = get_irn_irg(node);
4847 unsigned long value = get_tarval_long(tv);
4849 ir_node *block = be_transform_node(get_nodes_block(node));
4850 ir_node *ptr = be_transform_node(frame);
4855 ir_node *cnt = new_bd_ia32_ProduceVal(dbgi, block);
4856 ir_node *res = new_bd_ia32_ProduceVal(dbgi, block);
4857 ptr = new_bd_ia32_ClimbFrame(dbgi, block, ptr, cnt, res, value);
4860 /* load the frame address from this frame */
4861 load = new_bd_ia32_Load(dbgi, block, ptr, noreg_GP, nomem);
4863 set_irn_pinned(load, get_irn_pinned(node));
4864 set_ia32_op_type(load, ia32_AddrModeS);
4865 set_ia32_ls_mode(load, mode_Iu);
4867 ent = ia32_get_frame_address_entity(irg);
4869 set_ia32_am_offs_int(load, 0);
4870 set_ia32_use_frame(load);
4871 set_ia32_frame_ent(load, ent);
4873 /* will fail anyway, but gcc does this: */
4874 set_ia32_am_offs_int(load, 0);
4877 if (get_irn_pinned(node) == op_pin_state_floats) {
4878 assert((int)pn_ia32_xLoad_res == (int)pn_ia32_vfld_res
4879 && (int)pn_ia32_vfld_res == (int)pn_ia32_Load_res
4880 && (int)pn_ia32_Load_res == (int)pn_ia32_res);
4881 arch_irn_add_flags(load, arch_irn_flags_rematerializable);
4884 SET_IA32_ORIG_NODE(load, node);
4885 return new_r_Proj(load, mode_Iu, pn_ia32_Load_res);
4889 * Transform Builtin frame_address
4891 static ir_node *gen_prefetch(ir_node *node)
4894 ir_node *ptr, *block, *mem, *base, *index;
4895 ir_node *param, *new_node;
4898 ia32_address_t addr;
4900 if (!ia32_cg_config.use_sse_prefetch && !ia32_cg_config.use_3dnow_prefetch) {
4901 /* no prefetch at all, route memory */
4902 return be_transform_node(get_Builtin_mem(node));
4905 param = get_Builtin_param(node, 1);
4906 tv = get_Const_tarval(param);
4907 rw = get_tarval_long(tv);
4909 /* construct load address */
4910 memset(&addr, 0, sizeof(addr));
4911 ptr = get_Builtin_param(node, 0);
4912 ia32_create_address_mode(&addr, ptr, ia32_create_am_normal);
4919 base = be_transform_node(base);
4922 if (index == NULL) {
4925 index = be_transform_node(index);
4928 dbgi = get_irn_dbg_info(node);
4929 block = be_transform_node(get_nodes_block(node));
4930 mem = be_transform_node(get_Builtin_mem(node));
4932 if (rw == 1 && ia32_cg_config.use_3dnow_prefetch) {
4933 /* we have 3DNow!, this was already checked above */
4934 new_node = new_bd_ia32_PrefetchW(dbgi, block, base, index, mem);
4935 } else if (ia32_cg_config.use_sse_prefetch) {
4936 /* note: rw == 1 is IGNORED in that case */
4937 param = get_Builtin_param(node, 2);
4938 tv = get_Const_tarval(param);
4939 locality = get_tarval_long(tv);
4941 /* SSE style prefetch */
4944 new_node = new_bd_ia32_PrefetchNTA(dbgi, block, base, index, mem);
4947 new_node = new_bd_ia32_Prefetch2(dbgi, block, base, index, mem);
4950 new_node = new_bd_ia32_Prefetch1(dbgi, block, base, index, mem);
4953 new_node = new_bd_ia32_Prefetch0(dbgi, block, base, index, mem);
4957 assert(ia32_cg_config.use_3dnow_prefetch);
4958 /* 3DNow! style prefetch */
4959 new_node = new_bd_ia32_Prefetch(dbgi, block, base, index, mem);
4962 set_irn_pinned(new_node, get_irn_pinned(node));
4963 set_ia32_op_type(new_node, ia32_AddrModeS);
4964 set_ia32_ls_mode(new_node, mode_Bu);
4965 set_address(new_node, &addr);
4967 SET_IA32_ORIG_NODE(new_node, node);
4969 return new_r_Proj(new_node, mode_M, pn_ia32_Prefetch_M);
4973 * Transform bsf like node
4975 static ir_node *gen_unop_AM(ir_node *node, construct_binop_dest_func *func)
4977 ir_node *param = get_Builtin_param(node, 0);
4978 dbg_info *dbgi = get_irn_dbg_info(node);
4980 ir_node *block = get_nodes_block(node);
4981 ir_node *new_block = be_transform_node(block);
4983 ia32_address_mode_t am;
4984 ia32_address_t *addr = &am.addr;
4987 match_arguments(&am, block, NULL, param, NULL, match_am);
4989 cnt = func(dbgi, new_block, addr->base, addr->index, addr->mem, am.new_op2);
4990 set_am_attributes(cnt, &am);
4991 set_ia32_ls_mode(cnt, get_irn_mode(param));
4993 SET_IA32_ORIG_NODE(cnt, node);
4994 return fix_mem_proj(cnt, &am);
4998 * Transform builtin ffs.
5000 static ir_node *gen_ffs(ir_node *node)
5002 ir_node *bsf = gen_unop_AM(node, new_bd_ia32_Bsf);
5003 ir_node *real = skip_Proj(bsf);
5004 dbg_info *dbgi = get_irn_dbg_info(real);
5005 ir_node *block = get_nodes_block(real);
5006 ir_node *flag, *set, *conv, *neg, *orn, *add;
5009 if (get_irn_mode(real) != mode_T) {
5010 set_irn_mode(real, mode_T);
5011 bsf = new_r_Proj(real, mode_Iu, pn_ia32_res);
5014 flag = new_r_Proj(real, mode_b, pn_ia32_flags);
5017 set = new_bd_ia32_Setcc(dbgi, block, flag, ia32_cc_equal);
5018 SET_IA32_ORIG_NODE(set, node);
5021 conv = new_bd_ia32_Conv_I2I8Bit(dbgi, block, noreg_GP, noreg_GP, nomem, set, mode_Bu);
5022 SET_IA32_ORIG_NODE(conv, node);
5025 neg = new_bd_ia32_Neg(dbgi, block, conv);
5028 orn = new_bd_ia32_Or(dbgi, block, noreg_GP, noreg_GP, nomem, bsf, neg);
5029 set_ia32_commutative(orn);
5032 add = new_bd_ia32_Lea(dbgi, block, orn, noreg_GP);
5033 add_ia32_am_offs_int(add, 1);
5038 * Transform builtin clz.
5040 static ir_node *gen_clz(ir_node *node)
5042 ir_node *bsr = gen_unop_AM(node, new_bd_ia32_Bsr);
5043 ir_node *real = skip_Proj(bsr);
5044 dbg_info *dbgi = get_irn_dbg_info(real);
5045 ir_node *block = get_nodes_block(real);
5046 ir_node *imm = ia32_create_Immediate(NULL, 0, 31);
5048 return new_bd_ia32_Xor(dbgi, block, noreg_GP, noreg_GP, nomem, bsr, imm);
5052 * Transform builtin ctz.
5054 static ir_node *gen_ctz(ir_node *node)
5056 return gen_unop_AM(node, new_bd_ia32_Bsf);
5060 * Transform builtin parity.
5062 static ir_node *gen_parity(ir_node *node)
5064 dbg_info *dbgi = get_irn_dbg_info(node);
5065 ir_node *block = get_nodes_block(node);
5066 ir_node *new_block = be_transform_node(block);
5067 ir_node *param = get_Builtin_param(node, 0);
5068 ir_node *new_param = be_transform_node(param);
5071 /* the x86 parity bit is stupid: it only looks at the lowest byte,
5072 * so we have to do complicated xoring first.
5073 * (we should also better lower this before the backend so we still have a
5074 * chance for CSE, constant folding and other goodies for some of these
5077 ir_node *count = ia32_create_Immediate(NULL, 0, 16);
5078 ir_node *shr = new_bd_ia32_Shr(dbgi, new_block, new_param, count);
5079 ir_node *xor = new_bd_ia32_Xor(dbgi, new_block, noreg_GP, noreg_GP, nomem,
5081 ir_node *xor2 = new_bd_ia32_XorHighLow(dbgi, new_block, xor);
5084 set_irn_mode(xor2, mode_T);
5085 flags = new_r_Proj(xor2, mode_Iu, pn_ia32_XorHighLow_flags);
5088 new_node = new_bd_ia32_Setcc(dbgi, new_block, flags, ia32_cc_not_parity);
5089 SET_IA32_ORIG_NODE(new_node, node);
5092 new_node = new_bd_ia32_Conv_I2I8Bit(dbgi, new_block, noreg_GP, noreg_GP,
5093 nomem, new_node, mode_Bu);
5094 SET_IA32_ORIG_NODE(new_node, node);
5099 * Transform builtin popcount
5101 static ir_node *gen_popcount(ir_node *node)
5103 ir_node *param = get_Builtin_param(node, 0);
5104 dbg_info *dbgi = get_irn_dbg_info(node);
5106 ir_node *block = get_nodes_block(node);
5107 ir_node *new_block = be_transform_node(block);
5110 ir_node *imm, *simm, *m1, *s1, *s2, *s3, *s4, *s5, *m2, *m3, *m4, *m5, *m6, *m7, *m8, *m9, *m10, *m11, *m12, *m13;
5112 /* check for SSE4.2 or SSE4a and use the popcnt instruction */
5113 if (ia32_cg_config.use_popcnt) {
5114 ia32_address_mode_t am;
5115 ia32_address_t *addr = &am.addr;
5118 match_arguments(&am, block, NULL, param, NULL, match_am | match_16bit_am);
5120 cnt = new_bd_ia32_Popcnt(dbgi, new_block, addr->base, addr->index, addr->mem, am.new_op2);
5121 set_am_attributes(cnt, &am);
5122 set_ia32_ls_mode(cnt, get_irn_mode(param));
5124 SET_IA32_ORIG_NODE(cnt, node);
5125 return fix_mem_proj(cnt, &am);
5128 new_param = be_transform_node(param);
5130 /* do the standard popcount algo */
5131 /* TODO: This is stupid, we should transform this before the backend,
5132 * to get CSE, localopts, etc. for the operations
5133 * TODO: This is also not the optimal algorithm (it is just the starting
5134 * example in hackers delight, they optimize it more on the following page)
5135 * But I'm too lazy to fix this now, as the code should get lowered before
5136 * the backend anyway.
5139 /* m1 = x & 0x55555555 */
5140 imm = ia32_create_Immediate(NULL, 0, 0x55555555);
5141 m1 = new_bd_ia32_And(dbgi, new_block, noreg_GP, noreg_GP, nomem, new_param, imm);
5144 simm = ia32_create_Immediate(NULL, 0, 1);
5145 s1 = new_bd_ia32_Shr(dbgi, new_block, new_param, simm);
5147 /* m2 = s1 & 0x55555555 */
5148 m2 = new_bd_ia32_And(dbgi, new_block, noreg_GP, noreg_GP, nomem, s1, imm);
5151 m3 = new_bd_ia32_Lea(dbgi, new_block, m2, m1);
5153 /* m4 = m3 & 0x33333333 */
5154 imm = ia32_create_Immediate(NULL, 0, 0x33333333);
5155 m4 = new_bd_ia32_And(dbgi, new_block, noreg_GP, noreg_GP, nomem, m3, imm);
5158 simm = ia32_create_Immediate(NULL, 0, 2);
5159 s2 = new_bd_ia32_Shr(dbgi, new_block, m3, simm);
5161 /* m5 = s2 & 0x33333333 */
5162 m5 = new_bd_ia32_And(dbgi, new_block, noreg_GP, noreg_GP, nomem, s2, imm);
5165 m6 = new_bd_ia32_Lea(dbgi, new_block, m4, m5);
5167 /* m7 = m6 & 0x0F0F0F0F */
5168 imm = ia32_create_Immediate(NULL, 0, 0x0F0F0F0F);
5169 m7 = new_bd_ia32_And(dbgi, new_block, noreg_GP, noreg_GP, nomem, m6, imm);
5172 simm = ia32_create_Immediate(NULL, 0, 4);
5173 s3 = new_bd_ia32_Shr(dbgi, new_block, m6, simm);
5175 /* m8 = s3 & 0x0F0F0F0F */
5176 m8 = new_bd_ia32_And(dbgi, new_block, noreg_GP, noreg_GP, nomem, s3, imm);
5179 m9 = new_bd_ia32_Lea(dbgi, new_block, m7, m8);
5181 /* m10 = m9 & 0x00FF00FF */
5182 imm = ia32_create_Immediate(NULL, 0, 0x00FF00FF);
5183 m10 = new_bd_ia32_And(dbgi, new_block, noreg_GP, noreg_GP, nomem, m9, imm);
5186 simm = ia32_create_Immediate(NULL, 0, 8);
5187 s4 = new_bd_ia32_Shr(dbgi, new_block, m9, simm);
5189 /* m11 = s4 & 0x00FF00FF */
5190 m11 = new_bd_ia32_And(dbgi, new_block, noreg_GP, noreg_GP, nomem, s4, imm);
5192 /* m12 = m10 + m11 */
5193 m12 = new_bd_ia32_Lea(dbgi, new_block, m10, m11);
5195 /* m13 = m12 & 0x0000FFFF */
5196 imm = ia32_create_Immediate(NULL, 0, 0x0000FFFF);
5197 m13 = new_bd_ia32_And(dbgi, new_block, noreg_GP, noreg_GP, nomem, m12, imm);
5199 /* s5 = m12 >> 16 */
5200 simm = ia32_create_Immediate(NULL, 0, 16);
5201 s5 = new_bd_ia32_Shr(dbgi, new_block, m12, simm);
5203 /* res = m13 + s5 */
5204 return new_bd_ia32_Lea(dbgi, new_block, m13, s5);
5208 * Transform builtin byte swap.
5210 static ir_node *gen_bswap(ir_node *node)
5212 ir_node *param = be_transform_node(get_Builtin_param(node, 0));
5213 dbg_info *dbgi = get_irn_dbg_info(node);
5215 ir_node *block = get_nodes_block(node);
5216 ir_node *new_block = be_transform_node(block);
5217 ir_mode *mode = get_irn_mode(param);
5218 unsigned size = get_mode_size_bits(mode);
5219 ir_node *m1, *m2, *m3, *m4, *s1, *s2, *s3, *s4;
5223 if (ia32_cg_config.use_i486) {
5224 /* swap available */
5225 return new_bd_ia32_Bswap(dbgi, new_block, param);
5227 s1 = new_bd_ia32_Shl(dbgi, new_block, param, ia32_create_Immediate(NULL, 0, 24));
5228 s2 = new_bd_ia32_Shl(dbgi, new_block, param, ia32_create_Immediate(NULL, 0, 8));
5230 m1 = new_bd_ia32_And(dbgi, new_block, noreg_GP, noreg_GP, nomem, s2, ia32_create_Immediate(NULL, 0, 0xFF00));
5231 m2 = new_bd_ia32_Lea(dbgi, new_block, s1, m1);
5233 s3 = new_bd_ia32_Shr(dbgi, new_block, param, ia32_create_Immediate(NULL, 0, 8));
5235 m3 = new_bd_ia32_And(dbgi, new_block, noreg_GP, noreg_GP, nomem, s3, ia32_create_Immediate(NULL, 0, 0xFF0000));
5236 m4 = new_bd_ia32_Lea(dbgi, new_block, m2, m3);
5238 s4 = new_bd_ia32_Shr(dbgi, new_block, param, ia32_create_Immediate(NULL, 0, 24));
5239 return new_bd_ia32_Lea(dbgi, new_block, m4, s4);
5242 /* swap16 always available */
5243 return new_bd_ia32_Bswap16(dbgi, new_block, param);
5246 panic("Invalid bswap size (%d)", size);
5251 * Transform builtin outport.
5253 static ir_node *gen_outport(ir_node *node)
5255 ir_node *port = create_immediate_or_transform(get_Builtin_param(node, 0), 0);
5256 ir_node *oldv = get_Builtin_param(node, 1);
5257 ir_mode *mode = get_irn_mode(oldv);
5258 ir_node *value = be_transform_node(oldv);
5259 ir_node *block = be_transform_node(get_nodes_block(node));
5260 ir_node *mem = be_transform_node(get_Builtin_mem(node));
5261 dbg_info *dbgi = get_irn_dbg_info(node);
5263 ir_node *res = new_bd_ia32_Outport(dbgi, block, port, value, mem);
5264 set_ia32_ls_mode(res, mode);
5269 * Transform builtin inport.
5271 static ir_node *gen_inport(ir_node *node)
5273 ir_type *tp = get_Builtin_type(node);
5274 ir_type *rstp = get_method_res_type(tp, 0);
5275 ir_mode *mode = get_type_mode(rstp);
5276 ir_node *port = create_immediate_or_transform(get_Builtin_param(node, 0), 0);
5277 ir_node *block = be_transform_node(get_nodes_block(node));
5278 ir_node *mem = be_transform_node(get_Builtin_mem(node));
5279 dbg_info *dbgi = get_irn_dbg_info(node);
5281 ir_node *res = new_bd_ia32_Inport(dbgi, block, port, mem);
5282 set_ia32_ls_mode(res, mode);
5284 /* check for missing Result Proj */
5289 * Transform a builtin inner trampoline
5291 static ir_node *gen_inner_trampoline(ir_node *node)
5293 ir_node *ptr = get_Builtin_param(node, 0);
5294 ir_node *callee = get_Builtin_param(node, 1);
5295 ir_node *env = be_transform_node(get_Builtin_param(node, 2));
5296 ir_node *mem = get_Builtin_mem(node);
5297 ir_node *block = get_nodes_block(node);
5298 ir_node *new_block = be_transform_node(block);
5302 ir_node *trampoline;
5304 dbg_info *dbgi = get_irn_dbg_info(node);
5305 ia32_address_t addr;
5307 /* construct store address */
5308 memset(&addr, 0, sizeof(addr));
5309 ia32_create_address_mode(&addr, ptr, ia32_create_am_normal);
5311 if (addr.base == NULL) {
5312 addr.base = noreg_GP;
5314 addr.base = be_transform_node(addr.base);
5317 if (addr.index == NULL) {
5318 addr.index = noreg_GP;
5320 addr.index = be_transform_node(addr.index);
5322 addr.mem = be_transform_node(mem);
5324 /* mov ecx, <env> */
5325 val = ia32_create_Immediate(NULL, 0, 0xB9);
5326 store = new_bd_ia32_Store8Bit(dbgi, new_block, addr.base,
5327 addr.index, addr.mem, val);
5328 set_irn_pinned(store, get_irn_pinned(node));
5329 set_ia32_op_type(store, ia32_AddrModeD);
5330 set_ia32_ls_mode(store, mode_Bu);
5331 set_address(store, &addr);
5335 store = new_bd_ia32_Store(dbgi, new_block, addr.base,
5336 addr.index, addr.mem, env);
5337 set_irn_pinned(store, get_irn_pinned(node));
5338 set_ia32_op_type(store, ia32_AddrModeD);
5339 set_ia32_ls_mode(store, mode_Iu);
5340 set_address(store, &addr);
5344 /* jmp rel <callee> */
5345 val = ia32_create_Immediate(NULL, 0, 0xE9);
5346 store = new_bd_ia32_Store8Bit(dbgi, new_block, addr.base,
5347 addr.index, addr.mem, val);
5348 set_irn_pinned(store, get_irn_pinned(node));
5349 set_ia32_op_type(store, ia32_AddrModeD);
5350 set_ia32_ls_mode(store, mode_Bu);
5351 set_address(store, &addr);
5355 trampoline = be_transform_node(ptr);
5357 /* the callee is typically an immediate */
5358 if (is_SymConst(callee)) {
5359 rel = new_bd_ia32_Const(dbgi, new_block, get_SymConst_entity(callee), 0, 0, -10);
5361 rel = new_bd_ia32_Lea(dbgi, new_block, be_transform_node(callee), noreg_GP);
5362 add_ia32_am_offs_int(rel, -10);
5364 rel = new_bd_ia32_Sub(dbgi, new_block, noreg_GP, noreg_GP, nomem, rel, trampoline);
5366 store = new_bd_ia32_Store(dbgi, new_block, addr.base,
5367 addr.index, addr.mem, rel);
5368 set_irn_pinned(store, get_irn_pinned(node));
5369 set_ia32_op_type(store, ia32_AddrModeD);
5370 set_ia32_ls_mode(store, mode_Iu);
5371 set_address(store, &addr);
5376 return new_r_Tuple(new_block, 2, in);
5380 * Transform Builtin node.
5382 static ir_node *gen_Builtin(ir_node *node)
5384 ir_builtin_kind kind = get_Builtin_kind(node);
5388 return gen_trap(node);
5389 case ir_bk_debugbreak:
5390 return gen_debugbreak(node);
5391 case ir_bk_return_address:
5392 return gen_return_address(node);
5393 case ir_bk_frame_address:
5394 return gen_frame_address(node);
5395 case ir_bk_prefetch:
5396 return gen_prefetch(node);
5398 return gen_ffs(node);
5400 return gen_clz(node);
5402 return gen_ctz(node);
5404 return gen_parity(node);
5405 case ir_bk_popcount:
5406 return gen_popcount(node);
5408 return gen_bswap(node);
5410 return gen_outport(node);
5412 return gen_inport(node);
5413 case ir_bk_inner_trampoline:
5414 return gen_inner_trampoline(node);
5416 panic("Builtin %s not implemented in IA32", get_builtin_kind_name(kind));
5420 * Transform Proj(Builtin) node.
5422 static ir_node *gen_Proj_Builtin(ir_node *proj)
5424 ir_node *node = get_Proj_pred(proj);
5425 ir_node *new_node = be_transform_node(node);
5426 ir_builtin_kind kind = get_Builtin_kind(node);
5429 case ir_bk_return_address:
5430 case ir_bk_frame_address:
5435 case ir_bk_popcount:
5437 assert(get_Proj_proj(proj) == pn_Builtin_1_result);
5440 case ir_bk_debugbreak:
5441 case ir_bk_prefetch:
5443 assert(get_Proj_proj(proj) == pn_Builtin_M);
5446 if (get_Proj_proj(proj) == pn_Builtin_1_result) {
5447 return new_r_Proj(new_node, get_irn_mode(proj), pn_ia32_Inport_res);
5449 assert(get_Proj_proj(proj) == pn_Builtin_M);
5450 return new_r_Proj(new_node, mode_M, pn_ia32_Inport_M);
5452 case ir_bk_inner_trampoline:
5453 if (get_Proj_proj(proj) == pn_Builtin_1_result) {
5454 return get_Tuple_pred(new_node, 1);
5456 assert(get_Proj_proj(proj) == pn_Builtin_M);
5457 return get_Tuple_pred(new_node, 0);
5460 panic("Builtin %s not implemented in IA32", get_builtin_kind_name(kind));
5463 static ir_node *gen_be_IncSP(ir_node *node)
5465 ir_node *res = be_duplicate_node(node);
5466 arch_irn_add_flags(res, arch_irn_flags_modify_flags);
5472 * Transform the Projs from a be_Call.
5474 static ir_node *gen_Proj_be_Call(ir_node *node)
5476 ir_node *call = get_Proj_pred(node);
5477 ir_node *new_call = be_transform_node(call);
5478 dbg_info *dbgi = get_irn_dbg_info(node);
5479 long proj = get_Proj_proj(node);
5480 ir_mode *mode = get_irn_mode(node);
5483 if (proj == pn_be_Call_M_regular) {
5484 return new_rd_Proj(dbgi, new_call, mode_M, n_ia32_Call_mem);
5486 /* transform call modes */
5487 if (mode_is_data(mode)) {
5488 const arch_register_class_t *cls = arch_get_irn_reg_class_out(node);
5492 /* Map from be_Call to ia32_Call proj number */
5493 if (proj == pn_be_Call_sp) {
5494 proj = pn_ia32_Call_stack;
5495 } else if (proj == pn_be_Call_M_regular) {
5496 proj = pn_ia32_Call_M;
5498 arch_register_req_t const *const req = arch_get_register_req_out(node);
5499 int const n_outs = arch_irn_get_n_outs(new_call);
5502 assert(proj >= pn_be_Call_first_res);
5503 assert(req->type & arch_register_req_type_limited);
5505 for (i = 0; i < n_outs; ++i) {
5506 arch_register_req_t const *const new_req
5507 = arch_get_out_register_req(new_call, i);
5509 if (!(new_req->type & arch_register_req_type_limited) ||
5510 new_req->cls != req->cls ||
5511 *new_req->limited != *req->limited)
5520 res = new_rd_Proj(dbgi, new_call, mode, proj);
5522 /* TODO arch_set_irn_register() only operates on Projs, need variant with index */
5524 case pn_ia32_Call_stack:
5525 arch_set_irn_register(res, &ia32_registers[REG_ESP]);
5528 case pn_ia32_Call_fpcw:
5529 arch_set_irn_register(res, &ia32_registers[REG_FPCW]);
5537 * Transform the Projs from a Cmp.
5539 static ir_node *gen_Proj_Cmp(ir_node *node)
5541 /* this probably means not all mode_b nodes were lowered... */
5542 panic("trying to directly transform Proj_Cmp %+F (mode_b not lowered?)",
5546 static ir_node *gen_Proj_ASM(ir_node *node)
5548 ir_mode *mode = get_irn_mode(node);
5549 ir_node *pred = get_Proj_pred(node);
5550 ir_node *new_pred = be_transform_node(pred);
5551 long pos = get_Proj_proj(node);
5553 if (mode == mode_M) {
5554 pos = arch_irn_get_n_outs(new_pred)-1;
5555 } else if (mode_is_int(mode) || mode_is_reference(mode)) {
5557 } else if (mode_is_float(mode)) {
5560 panic("unexpected proj mode at ASM");
5563 return new_r_Proj(new_pred, mode, pos);
5567 * Transform and potentially renumber Proj nodes.
5569 static ir_node *gen_Proj(ir_node *node)
5571 ir_node *pred = get_Proj_pred(node);
5574 switch (get_irn_opcode(pred)) {
5576 proj = get_Proj_proj(node);
5577 if (proj == pn_Store_M) {
5578 return be_transform_node(pred);
5580 panic("No idea how to transform proj->Store");
5583 return gen_Proj_Load(node);
5585 return gen_Proj_ASM(node);
5587 return gen_Proj_Builtin(node);
5589 return gen_Proj_Div(node);
5591 return gen_Proj_Mod(node);
5593 return gen_Proj_CopyB(node);
5595 return gen_Proj_be_SubSP(node);
5597 return gen_Proj_be_AddSP(node);
5599 return gen_Proj_be_Call(node);
5601 return gen_Proj_Cmp(node);
5603 proj = get_Proj_proj(node);
5605 case pn_Start_X_initial_exec: {
5606 ir_node *block = get_nodes_block(pred);
5607 ir_node *new_block = be_transform_node(block);
5608 dbg_info *dbgi = get_irn_dbg_info(node);
5609 /* we exchange the ProjX with a jump */
5610 ir_node *jump = new_rd_Jmp(dbgi, new_block);
5618 if (is_ia32_l_FloattoLL(pred)) {
5619 return gen_Proj_l_FloattoLL(node);
5621 } else if (!is_ia32_irn(pred)) { // Quick hack for SIMD optimization
5625 ir_mode *mode = get_irn_mode(node);
5626 if (ia32_mode_needs_gp_reg(mode)) {
5627 ir_node *new_pred = be_transform_node(pred);
5628 ir_node *new_proj = new_r_Proj(new_pred, mode_Iu,
5629 get_Proj_proj(node));
5630 new_proj->node_nr = node->node_nr;
5635 return be_duplicate_node(node);
5639 * Enters all transform functions into the generic pointer
5641 static void register_transformers(void)
5643 /* first clear the generic function pointer for all ops */
5644 be_start_transform_setup();
5646 be_set_transform_function(op_Add, gen_Add);
5647 be_set_transform_function(op_And, gen_And);
5648 be_set_transform_function(op_ASM, ia32_gen_ASM);
5649 be_set_transform_function(op_be_AddSP, gen_be_AddSP);
5650 be_set_transform_function(op_be_Call, gen_be_Call);
5651 be_set_transform_function(op_be_Copy, gen_be_Copy);
5652 be_set_transform_function(op_be_FrameAddr, gen_be_FrameAddr);
5653 be_set_transform_function(op_be_IncSP, gen_be_IncSP);
5654 be_set_transform_function(op_be_Return, gen_be_Return);
5655 be_set_transform_function(op_be_SubSP, gen_be_SubSP);
5656 be_set_transform_function(op_Builtin, gen_Builtin);
5657 be_set_transform_function(op_Cmp, gen_Cmp);
5658 be_set_transform_function(op_Cond, gen_Cond);
5659 be_set_transform_function(op_Const, gen_Const);
5660 be_set_transform_function(op_Conv, gen_Conv);
5661 be_set_transform_function(op_CopyB, ia32_gen_CopyB);
5662 be_set_transform_function(op_Div, gen_Div);
5663 be_set_transform_function(op_Eor, gen_Eor);
5664 be_set_transform_function(op_ia32_l_Adc, gen_ia32_l_Adc);
5665 be_set_transform_function(op_ia32_l_Add, gen_ia32_l_Add);
5666 be_set_transform_function(op_ia32_Leave, be_duplicate_node);
5667 be_set_transform_function(op_ia32_l_FloattoLL, gen_ia32_l_FloattoLL);
5668 be_set_transform_function(op_ia32_l_IMul, gen_ia32_l_IMul);
5669 be_set_transform_function(op_ia32_l_LLtoFloat, gen_ia32_l_LLtoFloat);
5670 be_set_transform_function(op_ia32_l_Mul, gen_ia32_l_Mul);
5671 be_set_transform_function(op_ia32_l_SarDep, gen_ia32_l_SarDep);
5672 be_set_transform_function(op_ia32_l_Sbb, gen_ia32_l_Sbb);
5673 be_set_transform_function(op_ia32_l_ShlDep, gen_ia32_l_ShlDep);
5674 be_set_transform_function(op_ia32_l_ShlD, gen_ia32_l_ShlD);
5675 be_set_transform_function(op_ia32_l_ShrDep, gen_ia32_l_ShrDep);
5676 be_set_transform_function(op_ia32_l_ShrD, gen_ia32_l_ShrD);
5677 be_set_transform_function(op_ia32_l_Sub, gen_ia32_l_Sub);
5678 be_set_transform_function(op_ia32_GetEIP, be_duplicate_node);
5679 be_set_transform_function(op_ia32_Minus64Bit, be_duplicate_node);
5680 be_set_transform_function(op_ia32_NoReg_GP, be_duplicate_node);
5681 be_set_transform_function(op_ia32_NoReg_VFP, be_duplicate_node);
5682 be_set_transform_function(op_ia32_NoReg_XMM, be_duplicate_node);
5683 be_set_transform_function(op_ia32_PopEbp, be_duplicate_node);
5684 be_set_transform_function(op_ia32_Push, be_duplicate_node);
5685 be_set_transform_function(op_IJmp, gen_IJmp);
5686 be_set_transform_function(op_Jmp, gen_Jmp);
5687 be_set_transform_function(op_Load, gen_Load);
5688 be_set_transform_function(op_Minus, gen_Minus);
5689 be_set_transform_function(op_Mod, gen_Mod);
5690 be_set_transform_function(op_Mul, gen_Mul);
5691 be_set_transform_function(op_Mulh, gen_Mulh);
5692 be_set_transform_function(op_Mux, gen_Mux);
5693 be_set_transform_function(op_Not, gen_Not);
5694 be_set_transform_function(op_Or, gen_Or);
5695 be_set_transform_function(op_Phi, gen_Phi);
5696 be_set_transform_function(op_Proj, gen_Proj);
5697 be_set_transform_function(op_Rotl, gen_Rotl);
5698 be_set_transform_function(op_Shl, gen_Shl);
5699 be_set_transform_function(op_Shr, gen_Shr);
5700 be_set_transform_function(op_Shrs, gen_Shrs);
5701 be_set_transform_function(op_Store, gen_Store);
5702 be_set_transform_function(op_Sub, gen_Sub);
5703 be_set_transform_function(op_SymConst, gen_SymConst);
5704 be_set_transform_function(op_Unknown, ia32_gen_Unknown);
5708 * Pre-transform all unknown and noreg nodes.
5710 static void ia32_pretransform_node(void)
5712 ir_graph *irg = current_ir_graph;
5713 ia32_irg_data_t *irg_data = ia32_get_irg_data(current_ir_graph);
5715 irg_data->noreg_gp = be_pre_transform_node(irg_data->noreg_gp);
5716 irg_data->noreg_vfp = be_pre_transform_node(irg_data->noreg_vfp);
5717 irg_data->noreg_xmm = be_pre_transform_node(irg_data->noreg_xmm);
5718 irg_data->get_eip = be_pre_transform_node(irg_data->get_eip);
5719 irg_data->fpu_trunc_mode = be_pre_transform_node(irg_data->fpu_trunc_mode);
5721 nomem = get_irg_no_mem(irg);
5722 noreg_GP = ia32_new_NoReg_gp(irg);
5728 * Post-process all calls if we are in SSE mode.
5729 * The ABI requires that the results are in st0, copy them
5730 * to a xmm register.
5732 static void postprocess_fp_call_results(void)
5736 for (i = 0, n = ARR_LEN(call_list); i < n; ++i) {
5737 ir_node *call = call_list[i];
5738 ir_type *mtp = call_types[i];
5741 for (j = get_method_n_ress(mtp) - 1; j >= 0; --j) {
5742 ir_type *res_tp = get_method_res_type(mtp, j);
5743 ir_node *res, *new_res;
5744 const ir_edge_t *edge, *next;
5747 if (! is_atomic_type(res_tp)) {
5748 /* no floating point return */
5751 mode = get_type_mode(res_tp);
5752 if (! mode_is_float(mode)) {
5753 /* no floating point return */
5757 res = be_get_Proj_for_pn(call, pn_ia32_Call_vf0 + j);
5760 /* now patch the users */
5761 foreach_out_edge_safe(res, edge, next) {
5762 ir_node *succ = get_edge_src_irn(edge);
5765 if (be_is_Keep(succ))
5768 if (is_ia32_xStore(succ)) {
5769 /* an xStore can be patched into an vfst */
5770 dbg_info *db = get_irn_dbg_info(succ);
5771 ir_node *block = get_nodes_block(succ);
5772 ir_node *base = get_irn_n(succ, n_ia32_xStore_base);
5773 ir_node *index = get_irn_n(succ, n_ia32_xStore_index);
5774 ir_node *mem = get_irn_n(succ, n_ia32_xStore_mem);
5775 ir_node *value = get_irn_n(succ, n_ia32_xStore_val);
5776 ir_mode *mode = get_ia32_ls_mode(succ);
5778 ir_node *st = new_bd_ia32_vfst(db, block, base, index, mem, value, mode);
5779 set_ia32_am_offs_int(st, get_ia32_am_offs_int(succ));
5780 if (is_ia32_use_frame(succ))
5781 set_ia32_use_frame(st);
5782 set_ia32_frame_ent(st, get_ia32_frame_ent(succ));
5783 set_irn_pinned(st, get_irn_pinned(succ));
5784 set_ia32_op_type(st, ia32_AddrModeD);
5788 if (new_res == NULL) {
5789 dbg_info *db = get_irn_dbg_info(call);
5790 ir_node *block = get_nodes_block(call);
5791 ir_node *frame = get_irg_frame(current_ir_graph);
5792 ir_node *old_mem = be_get_Proj_for_pn(call, pn_ia32_Call_M);
5793 ir_node *call_mem = new_r_Proj(call, mode_M, pn_ia32_Call_M);
5794 ir_node *vfst, *xld, *new_mem;
5796 /* store st(0) on stack */
5797 vfst = new_bd_ia32_vfst(db, block, frame, noreg_GP, call_mem, res, mode);
5798 set_ia32_op_type(vfst, ia32_AddrModeD);
5799 set_ia32_use_frame(vfst);
5801 /* load into SSE register */
5802 xld = new_bd_ia32_xLoad(db, block, frame, noreg_GP, vfst, mode);
5803 set_ia32_op_type(xld, ia32_AddrModeS);
5804 set_ia32_use_frame(xld);
5806 new_res = new_r_Proj(xld, mode, pn_ia32_xLoad_res);
5807 new_mem = new_r_Proj(xld, mode_M, pn_ia32_xLoad_M);
5809 if (old_mem != NULL) {
5810 edges_reroute(old_mem, new_mem);
5814 set_irn_n(succ, get_edge_src_pos(edge), new_res);
5821 /* do the transformation */
5822 void ia32_transform_graph(ir_graph *irg)
5826 register_transformers();
5827 initial_fpcw = NULL;
5828 ia32_no_pic_adjust = 0;
5830 be_timer_push(T_HEIGHTS);
5831 ia32_heights = heights_new(irg);
5832 be_timer_pop(T_HEIGHTS);
5833 ia32_calculate_non_address_mode_nodes(irg);
5835 /* the transform phase is not safe for CSE (yet) because several nodes get
5836 * attributes set after their creation */
5837 cse_last = get_opt_cse();
5840 call_list = NEW_ARR_F(ir_node *, 0);
5841 call_types = NEW_ARR_F(ir_type *, 0);
5842 be_transform_graph(irg, ia32_pretransform_node);
5844 if (ia32_cg_config.use_sse2)
5845 postprocess_fp_call_results();
5846 DEL_ARR_F(call_types);
5847 DEL_ARR_F(call_list);
5849 set_opt_cse(cse_last);
5851 ia32_free_non_address_mode_nodes();
5852 heights_free(ia32_heights);
5853 ia32_heights = NULL;
5856 void ia32_init_transform(void)
5858 FIRM_DBG_REGISTER(dbg, "firm.be.ia32.transform");