X-Git-Url: http://nsz.repo.hu/git/?a=blobdiff_plain;f=ir%2Fbe%2Fia32%2Fia32_new_nodes.c;h=e3ddcf61fc431a42fa5beecec827159085f4e8be;hb=4c875e72735d6f438c64a9e0d8de71a5ceb838c8;hp=4645fcee992d8b8b7aa4e4ca6216234b0b845914;hpb=590df14827a8ff5a5b53c506ac654876107bd8c9;p=libfirm diff --git a/ir/be/ia32/ia32_new_nodes.c b/ir/be/ia32/ia32_new_nodes.c index 4645fcee9..e3ddcf61f 100644 --- a/ir/be/ia32/ia32_new_nodes.c +++ b/ir/be/ia32/ia32_new_nodes.c @@ -1,5 +1,5 @@ /* - * Copyright (C) 1995-2007 University of Karlsruhe. All right reserved. + * Copyright (C) 1995-2008 University of Karlsruhe. All right reserved. * * This file is part of libFirm. * @@ -26,9 +26,7 @@ * This file implements the creation of the achitecture specific firm opcodes * and the corresponding node constructors for the ia32 assembler irg. */ -#ifdef HAVE_CONFIG_H #include "config.h" -#endif #include @@ -107,7 +105,7 @@ static void dump_reg_req(FILE *F, ir_node *n, const arch_register_req_t **reqs, } } - if (reqs[i]->type & arch_register_req_type_should_be_different) { + if (reqs[i]->type & arch_register_req_type_must_be_different) { unsigned other = reqs[i]->other_different; int i; @@ -190,10 +188,9 @@ static int ia32_dump_node(ir_node *n, FILE *F, dump_reason_t reason) { break; case dump_node_mode_txt: - if (is_ia32_Ld(n) || is_ia32_St(n)) { - mode = get_ia32_ls_mode(n); - fprintf(F, "[%s]", mode ? get_mode_name(mode) : "?NOMODE?"); - } + mode = get_ia32_ls_mode(n); + if (mode != NULL) + fprintf(F, "[%s]", get_mode_name(mode)); break; case dump_node_nodeattr_txt: @@ -257,23 +254,14 @@ static int ia32_dump_node(ir_node *n, FILE *F, dump_reason_t reason) { /* dump supported am */ fprintf(F, "AM support = "); switch (get_ia32_am_support(n)) { - case ia32_am_None: - fprintf(F, "none"); - break; - case ia32_am_Source: - fprintf(F, "source only (Load)"); - break; - case ia32_am_Dest: - fprintf(F, "dest only (Load+Store)"); - break; - case ia32_am_Full: - fprintf(F, "full"); - break; + case ia32_am_none: fputs("none\n", F); break; + case ia32_am_unary: fputs("source (unary)\n", F); break; + case ia32_am_binary: fputs("source (binary)\n", F); break; + default: - fprintf(F, "unknown (%d)", get_ia32_am_support(n)); + fprintf(F, "unknown (%d)\n", get_ia32_am_support(n)); break; } - fprintf(F, "\n"); /* dump AM offset */ if(get_ia32_am_offs_int(n) != 0) { @@ -294,26 +282,21 @@ static int ia32_dump_node(ir_node *n, FILE *F, dump_reason_t reason) { if (is_ia32_SwitchJmp(n)) { fprintf(F, "pn_code = %ld\n", get_ia32_condcode(n)); } else if (is_ia32_CMov(n) || is_ia32_Set(n) || is_ia32_Jcc(n)) { + ia32_attr_t *attr = get_ia32_attr(n); long pnc = get_ia32_condcode(n); - fprintf(F, "pn_code = %ld (%s)\n", pnc, get_pnc_string(pnc)); + fprintf(F, "pn_code = 0x%lX (%s)\n", pnc, get_pnc_string(pnc & pn_Cmp_True)); + fprintf(F, "ins_permuted = %u \n", attr->data.ins_permuted); + fprintf(F, "cmp_unsigned = %u \n", attr->data.cmp_unsigned); } else if (is_ia32_CopyB(n) || is_ia32_CopyB_i(n)) { fprintf(F, "size = %u\n", get_ia32_copyb_size(n)); } - /* dump n_res */ fprintf(F, "n_res = %d\n", get_ia32_n_res(n)); - - /* dump use_frame */ fprintf(F, "use_frame = %d\n", is_ia32_use_frame(n)); - - /* commutative */ fprintf(F, "commutative = %d\n", is_ia32_commutative(n)); - - /* need stackent */ fprintf(F, "need stackent = %d\n", is_ia32_need_stackent(n)); - - /* dump latency */ + fprintf(F, "is reload = %d\n", is_ia32_is_reload(n)); fprintf(F, "latency = %d\n", get_ia32_latency(n)); /* dump flags */ @@ -335,6 +318,9 @@ static int ia32_dump_node(ir_node *n, FILE *F, dump_reason_t reason) { if (flags & arch_irn_flags_modify_sp) { fprintf(F, " modify_sp"); } + if (flags & arch_irn_flags_modify_flags) { + fprintf(F, " modify_flags"); + } } fprintf(F, " (%d)\n", flags); @@ -420,6 +406,13 @@ const ia32_asm_attr_t *get_ia32_asm_attr_const(const ir_node *node) { return asm_attr; } +ia32_immediate_attr_t *get_ia32_immediate_attr(ir_node *node) { + ia32_attr_t *attr = get_ia32_attr(node); + ia32_immediate_attr_t *imm_attr = CAST_IA32_ATTR(ia32_immediate_attr_t, attr); + + return imm_attr; +} + const ia32_immediate_attr_t *get_ia32_immediate_attr_const(const ir_node *node) { const ia32_attr_t *attr = get_ia32_attr_const(node); @@ -442,6 +435,22 @@ const ia32_condcode_attr_t *get_ia32_condcode_attr_const(const ir_node *node) { return cc_attr; } +ia32_call_attr_t *get_ia32_call_attr(ir_node *node) +{ + ia32_attr_t *attr = get_ia32_attr(node); + ia32_call_attr_t *call_attr = CAST_IA32_ATTR(ia32_call_attr_t, attr); + + return call_attr; +} + +const ia32_call_attr_t *get_ia32_call_attr_const(const ir_node *node) +{ + const ia32_attr_t *attr = get_ia32_attr_const(node); + const ia32_call_attr_t *call_attr = CONST_CAST_IA32_ATTR(ia32_call_attr_t, attr); + + return call_attr; +} + ia32_copyb_attr_t *get_ia32_copyb_attr(ir_node *node) { ia32_attr_t *attr = get_ia32_attr(node); ia32_copyb_attr_t *copyb_attr = CAST_IA32_ATTR(ia32_copyb_attr_t, attr); @@ -472,15 +481,8 @@ void set_ia32_op_type(ir_node *node, ia32_op_type_t tp) { attr->data.tp = tp; } -/** - * Gets the supported address mode of an ia32 node - */ -ia32_am_type_t get_ia32_am_support(const ir_node *node) { - const ia32_attr_t *attr = get_ia32_attr_const(node); - return attr->data.am_support; -} - -ia32_am_arity_t get_ia32_am_arity(const ir_node *node) { +ia32_am_type_t get_ia32_am_support(const ir_node *node) +{ const ia32_attr_t *attr = get_ia32_attr_const(node); return attr->data.am_arity; } @@ -488,15 +490,10 @@ ia32_am_arity_t get_ia32_am_arity(const ir_node *node) { /** * Sets the supported address mode of an ia32 node */ -void set_ia32_am_support(ir_node *node, ia32_am_type_t am_tp, - ia32_am_arity_t arity) { - ia32_attr_t *attr = get_ia32_attr(node); - attr->data.am_support = am_tp; - attr->data.am_arity = arity; - - assert((am_tp == ia32_am_None && arity == ia32_am_arity_none) || - (am_tp != ia32_am_None && - ((arity == ia32_am_unary) || (arity == ia32_am_binary) || (arity == ia32_am_ternary)))); +void set_ia32_am_support(ir_node *node, ia32_am_type_t arity) +{ + ia32_attr_t *attr = get_ia32_attr(node); + attr->data.am_arity = arity; } /** @@ -572,7 +569,8 @@ int get_ia32_am_scale(const ir_node *node) { * Sets the index register scale for address mode. */ void set_ia32_am_scale(ir_node *node, int scale) { - ia32_attr_t *attr = get_ia32_attr(node); + ia32_attr_t *attr = get_ia32_attr(node); + assert(0 <= scale && scale < 4 && "AM scale out of range"); attr->data.am_scale = scale; } @@ -652,6 +650,36 @@ int is_ia32_need_stackent(const ir_node *node) { return attr->data.need_stackent; } +void set_ia32_is_reload(ir_node *node) { + ia32_attr_t *attr = get_ia32_attr(node); + attr->data.is_reload = 1; +} + +int is_ia32_is_reload(const ir_node *node) { + const ia32_attr_t *attr = get_ia32_attr_const(node); + return attr->data.is_reload; +} + +void set_ia32_is_spill(ir_node *node) { + ia32_attr_t *attr = get_ia32_attr(node); + attr->data.is_spill = 1; +} + +int is_ia32_is_spill(const ir_node *node) { + const ia32_attr_t *attr = get_ia32_attr_const(node); + return attr->data.is_spill; +} + +void set_ia32_is_remat(ir_node *node) { + ia32_attr_t *attr = get_ia32_attr(node); + attr->data.is_remat = 1; +} + +int is_ia32_is_remat(const ir_node *node) { + const ia32_attr_t *attr = get_ia32_attr_const(node); + return attr->data.is_remat; +} + /** * Gets the mode of the stored/loaded value (only set for Store/Load) */ @@ -784,6 +812,11 @@ void set_ia32_flags(ir_node *node, arch_irn_flags_t flags) { attr->data.flags = flags; } +void add_ia32_flags(ir_node *node, arch_irn_flags_t flags) { + ia32_attr_t *attr = get_ia32_attr(node); + attr->data.flags |= flags; +} + /** * Returns the result register slots of an ia32 node. */ @@ -858,7 +891,7 @@ const be_execution_unit_t ***get_ia32_exec_units(const ir_node *node) { */ unsigned get_ia32_exc_label(const ir_node *node) { const ia32_attr_t *attr = get_ia32_attr_const(node); - return attr->data.except_label; + return attr->data.has_except_label; } /** @@ -866,7 +899,27 @@ unsigned get_ia32_exc_label(const ir_node *node) { */ void set_ia32_exc_label(ir_node *node, unsigned flag) { ia32_attr_t *attr = get_ia32_attr(node); - attr->data.except_label = flag; + attr->data.has_except_label = flag; +} + +/** + * Return the exception label id. + */ +ir_label_t get_ia32_exc_label_id(const ir_node *node) { + const ia32_attr_t *attr = get_ia32_attr_const(node); + + assert(attr->data.has_except_label); + return attr->exc_label; +} + +/** + * Assign the exception label id. + */ +void set_ia32_exc_label_id(ir_node *node, ir_label_t id) { + ia32_attr_t *attr = get_ia32_attr(node); + + assert(attr->data.has_except_label); + attr->exc_label = id; } #ifndef NDEBUG @@ -916,54 +969,6 @@ int is_ia32_AddrModeD(const ir_node *node) { return (attr->data.tp == ia32_AddrModeD); } -/** - * Checks if node is a Load or xLoad/vfLoad. - */ -int is_ia32_Ld(const ir_node *node) { - int op = get_ia32_irn_opcode(node); - return op == iro_ia32_Load || - op == iro_ia32_xLoad || - op == iro_ia32_vfld || - op == iro_ia32_fld; -} - -/** - * Checks if node is a Store or xStore/vfStore. - */ -int is_ia32_St(const ir_node *node) { - int op = get_ia32_irn_opcode(node); - return op == iro_ia32_Store || - op == iro_ia32_Store8Bit || - op == iro_ia32_xStore || - op == iro_ia32_vfst || - op == iro_ia32_fst || - op == iro_ia32_fstp; -} - -/** - * Returns the name of the OUT register at position pos. - */ -const char *get_ia32_out_reg_name(const ir_node *node, int pos) { - const ia32_attr_t *attr = get_ia32_attr_const(node); - - assert(pos < ARR_LEN(attr->slots) && "Invalid OUT position."); - assert(attr->slots[pos] && "No register assigned"); - - return arch_register_get_name(attr->slots[pos]); -} - -/** - * Returns the index of the OUT register at position pos within its register class. - */ -int get_ia32_out_regnr(const ir_node *node, int pos) { - const ia32_attr_t *attr = get_ia32_attr_const(node); - - assert(pos < ARR_LEN(attr->slots) && "Invalid OUT position."); - assert(attr->slots[pos] && "No register assigned"); - - return arch_register_get_index(attr->slots[pos]); -} - void ia32_swap_left_right(ir_node *node) { ia32_attr_t *attr = get_ia32_attr(node); @@ -1055,6 +1060,17 @@ init_ia32_immediate_attributes(ir_node *res, ir_entity *symconst, attr->offset = offset; } +void init_ia32_call_attributes(ir_node *const res, unsigned const pop, ir_type *const call_tp) +{ + ia32_call_attr_t *attr = get_irn_generic_attr(res); + +#ifndef NDEBUG + attr->attr.attr_type |= IA32_ATTR_ia32_call_attr_t; +#endif + attr->pop = pop; + attr->call_tp = call_tp; +} + void init_ia32_copyb_attributes(ir_node *res, unsigned size) { ia32_copyb_attr_t *attr = get_irn_generic_attr(res); @@ -1075,19 +1091,6 @@ init_ia32_condcode_attributes(ir_node *res, long pnc) { attr->pn_code = pnc; } -ir_node *get_ia32_result_proj(const ir_node *node) -{ - const ir_edge_t *edge; - - foreach_out_edge(node, edge) { - ir_node *proj = get_edge_src_irn(edge); - if(get_Proj_proj(proj) == 0) { - return proj; - } - } - return NULL; -} - /*************************************************************************************** * _ _ _ * | | | | | | @@ -1124,7 +1127,7 @@ int ia32_compare_attr(const ia32_attr_t *a, const ia32_attr_t *b) { if (a->data.tp != b->data.tp) return 1; - if (a->data.except_label != b->data.except_label) + if (a->data.has_except_label != b->data.has_except_label) return 1; if (a->data.ins_permuted != b->data.ins_permuted @@ -1163,6 +1166,26 @@ int ia32_compare_condcode_attr(ir_node *a, ir_node *b) return 0; } +static int ia32_compare_call_attr(ir_node *a, ir_node *b) +{ + const ia32_call_attr_t *attr_a; + const ia32_call_attr_t *attr_b; + + if (ia32_compare_nodes_attr(a, b)) + return 1; + + attr_a = get_ia32_call_attr_const(a); + attr_b = get_ia32_call_attr_const(b); + + if (attr_a->pop != attr_b->pop) + return 1; + + if (attr_a->call_tp != attr_b->call_tp) + return 1; + + return 0; +} + /** Compare node attributes for CopyB nodes. */ static int ia32_compare_copyb_attr(ir_node *a, ir_node *b) @@ -1202,6 +1225,15 @@ int ia32_compare_asm_attr(ir_node *a, ir_node *b) return 0; } +/** + * Hash function for Immediates + */ +static unsigned ia32_hash_Immediate(const ir_node *irn) { + const ia32_immediate_attr_t *a = get_ia32_immediate_attr_const(irn); + + return HASH_PTR(a->symconst) + (a->sc_sign << 16) + a->offset; +} + /** Compare node attributes for Immediates. */ static int ia32_compare_immediate_attr(ir_node *a, ir_node *b)