From: Matthias Braun Date: Tue, 5 Jun 2007 14:43:59 +0000 (+0000) Subject: make it possible to have different compare functions for different backend node attri... X-Git-Url: http://nsz.repo.hu/git/?a=commitdiff_plain;h=d11d8b4831db166f01b115a218e26e17091f898f;p=libfirm make it possible to have different compare functions for different backend node attributes [r14334] --- diff --git a/ir/be/TEMPLATE/TEMPLATE_new_nodes.c b/ir/be/TEMPLATE/TEMPLATE_new_nodes.c index de2200a7a..fe14beaaf 100644 --- a/ir/be/TEMPLATE/TEMPLATE_new_nodes.c +++ b/ir/be/TEMPLATE/TEMPLATE_new_nodes.c @@ -389,5 +389,18 @@ void init_TEMPLATE_attributes(ir_node *node, arch_irn_flags_t flags, * ***************************************************************************************/ +static +int TEMPLATE_compare_attr(ir_node *a, ir_node *b) +{ + const TEMPLATE_attr_t *attr_a = get_TEMPLATE_attr_const(a); + const TEMPLATE_attr_t *attr_b = get_TEMPLATE_attr_const(b); + + if(attr_a->flags != attr_b->flags) + return 1; + + return 0; +} + + /* Include the generated constructor functions */ #include "gen_TEMPLATE_new_nodes.c.inl" diff --git a/ir/be/arm/arm_spec.pl b/ir/be/arm/arm_spec.pl index 3c1bae5a3..68d3b6f7a 100644 --- a/ir/be/arm/arm_spec.pl +++ b/ir/be/arm/arm_spec.pl @@ -154,6 +154,8 @@ $new_emit_syntax = 1; # |_| # #--------------------------------------------------# +$default_cmp_attr = "NULL"; + %nodes = ( #-----------------------------------------------------------------# diff --git a/ir/be/ia32/ia32_new_nodes.c b/ir/be/ia32/ia32_new_nodes.c index 508745534..89a38dd5a 100644 --- a/ir/be/ia32/ia32_new_nodes.c +++ b/ir/be/ia32/ia32_new_nodes.c @@ -423,6 +423,13 @@ const ia32_x87_attr_t *get_ia32_x87_attr_const(const ir_node *node) { return x87_attr; } +const ia32_asm_attr_t *get_ia32_asm_attr_const(const ir_node *node) { + const ia32_attr_t *attr = get_ia32_attr_const(node); + const ia32_asm_attr_t *asm_attr = CONST_CAST_IA32_ATTR(ia32_asm_attr_t, attr); + + return asm_attr; +} + /** * Gets the type of an ia32 node. */ @@ -1251,6 +1258,39 @@ int ia32_compare_attr(const ia32_attr_t *a, const ia32_attr_t *b) { return 0; } +static +int ia32_compare_nodes_attr(ir_node *a, ir_node *b) +{ + const ia32_attr_t* attr_a = get_ia32_attr_const(a); + const ia32_attr_t* attr_b = get_ia32_attr_const(b); + + return ia32_compare_attr(attr_a, attr_b); +} + +static +int ia32_compare_x87_attr(ir_node *a, ir_node *b) +{ + return ia32_compare_nodes_attr(a, b); +} + +static +int ia32_compare_asm_attr(ir_node *a, ir_node *b) +{ + const ia32_asm_attr_t *attr_a; + const ia32_asm_attr_t *attr_b; + + if(ia32_compare_nodes_attr(a, b)) + return 1; + + attr_a = get_ia32_asm_attr_const(a); + attr_b = get_ia32_asm_attr_const(b); + + if(attr_a->asm_text != attr_b->asm_text) + return 1; + + return 0; +} + /* copies the ia32 attributes */ static void ia32_copy_attr(const ir_node *old_node, ir_node *new_node) { diff --git a/ir/be/ia32/ia32_spec.pl b/ir/be/ia32/ia32_spec.pl index c019c54fd..8331e3a35 100644 --- a/ir/be/ia32/ia32_spec.pl +++ b/ir/be/ia32/ia32_spec.pl @@ -286,7 +286,6 @@ $arch = "ia32"; # |_| # #--------------------------------------------------# -$default_cmp_attr = "return ia32_compare_attr(attr_a, attr_b);"; $default_attr_type = "ia32_attr_t"; %init_attr = ( @@ -301,9 +300,9 @@ $default_attr_type = "ia32_attr_t"; ); %compare_attr = ( - ia32_attr_t => "return ia32_compare_attr(attr_a, attr_b);", - ia32_x87_attr_t => "return ia32_compare_x87_attr(attr_a, attr_b);", - ia32_asm_attr_t => "return ia32_compare_asm_attr(attr_a, attr_b);" + ia32_attr_t => "ia32_compare_nodes_attr", + ia32_x87_attr_t => "ia32_compare_x87_attr", + ia32_asm_attr_t => "ia32_compare_asm_attr", ); %operands = ( diff --git a/ir/be/mips/bearch_mips.c b/ir/be/mips/bearch_mips.c index d09c1294a..d4326832d 100644 --- a/ir/be/mips/bearch_mips.c +++ b/ir/be/mips/bearch_mips.c @@ -209,12 +209,12 @@ static arch_irn_flags_t mips_get_flags(const void *self, const ir_node *irn) { static ir_entity *mips_get_frame_entity(const void *self, const ir_node *node) { - mips_attr_t *attr; + const mips_attr_t *attr; if(!is_mips_irn(node)) return NULL; - attr = get_mips_attr(node); + attr = get_mips_attr_const(node); return attr->stack_entity; } diff --git a/ir/be/mips/mips_emitter.c b/ir/be/mips/mips_emitter.c index dd0e56ac5..04c74e08b 100644 --- a/ir/be/mips/mips_emitter.c +++ b/ir/be/mips/mips_emitter.c @@ -231,7 +231,7 @@ static const char *node_const_to_str(ir_node *n) void mips_emit_immediate(mips_emit_env_t *env, const ir_node *node) { - const mips_attr_t *attr = get_mips_attr(node); + const mips_attr_t *attr = get_mips_attr_const(node); if(attr->tv != NULL) { be_emit_tarval(env->emit, attr->tv); @@ -492,11 +492,11 @@ const char* mips_get_jumptbl_label(const ir_node* switchjmp) * possible otherwise a cmp-jmp cascade). Stolen from ia32 */ void emit_mips_jump_table(mips_emit_env_t *env, const ir_node *irn) { - int lastval, i, i2, pn; - jmp_tbl_t tbl; - ir_node *proj; - const ir_edge_t *edge; - mips_attr_t *attr = get_mips_attr(irn); + int lastval, i, i2, pn; + jmp_tbl_t tbl; + ir_node *proj; + const ir_edge_t *edge; + const mips_attr_t *attr = get_mips_attr_const(irn); /* fill the table structure */ tbl.label = xmalloc(SNPRINTF_BUF_LEN); diff --git a/ir/be/mips/mips_new_nodes.c b/ir/be/mips/mips_new_nodes.c index 9d0a42c78..267dc8cb5 100644 --- a/ir/be/mips/mips_new_nodes.c +++ b/ir/be/mips/mips_new_nodes.c @@ -231,20 +231,21 @@ static int mips_dump_node(ir_node *n, FILE *F, dump_reason_t reason) { * |___/ ***************************************************************************************************/ -/** - * Wraps get_irn_generic_attr() as it takes no const ir_node, so we need to do a cast. - * Firm was made by people hating const :-( - */ -mips_attr_t *get_mips_attr(const ir_node *node) { +mips_attr_t *get_mips_attr(ir_node *node) { + assert(is_mips_irn(node) && "need mips node to get attributes"); + return (mips_attr_t *) get_irn_generic_attr(node); +} + +const mips_attr_t *get_mips_attr_const(const ir_node *node) { assert(is_mips_irn(node) && "need mips node to get attributes"); - return (mips_attr_t *)get_irn_generic_attr((ir_node *)node); + return get_irn_generic_attr_const(node); } /** * Returns the argument register requirements of a mips node. */ const arch_register_req_t **get_mips_in_req_all(const ir_node *node) { - mips_attr_t *attr = get_mips_attr(node); + const mips_attr_t *attr = get_mips_attr_const(node); return attr->in_req; } @@ -252,7 +253,7 @@ const arch_register_req_t **get_mips_in_req_all(const ir_node *node) { * Returns the result register requirements of an mips node. */ const arch_register_req_t **get_mips_out_req_all(const ir_node *node) { - mips_attr_t *attr = get_mips_attr(node); + const mips_attr_t *attr = get_mips_attr_const(node); return attr->out_req; } @@ -260,7 +261,7 @@ const arch_register_req_t **get_mips_out_req_all(const ir_node *node) { * Returns the argument register requirement at position pos of an mips node. */ const arch_register_req_t *get_mips_in_req(const ir_node *node, int pos) { - mips_attr_t *attr = get_mips_attr(node); + const mips_attr_t *attr = get_mips_attr_const(node); return attr->in_req[pos]; } @@ -268,7 +269,7 @@ const arch_register_req_t *get_mips_in_req(const ir_node *node, int pos) { * Returns the result register requirement at position pos of an mips node. */ const arch_register_req_t *get_mips_out_req(const ir_node *node, int pos) { - mips_attr_t *attr = get_mips_attr(node); + const mips_attr_t *attr = get_mips_attr_const(node); return attr->out_req[pos]; } @@ -292,14 +293,14 @@ void set_mips_req_in(ir_node *node, const arch_register_req_t *req, int pos) { * Returns the register flag of an mips node. */ arch_irn_flags_t get_mips_flags(const ir_node *node) { - mips_attr_t *attr = get_mips_attr(node); + const mips_attr_t *attr = get_mips_attr_const(node); return attr->flags; } /** * Sets the register flag of an mips node. */ -void set_mips_flags(const ir_node *node, arch_irn_flags_t flags) { +void set_mips_flags(ir_node *node, arch_irn_flags_t flags) { mips_attr_t *attr = get_mips_attr(node); attr->flags = flags; } @@ -308,7 +309,7 @@ void set_mips_flags(const ir_node *node, arch_irn_flags_t flags) { * Returns the result register slots of an mips node. */ const arch_register_t **get_mips_slots(const ir_node *node) { - mips_attr_t *attr = get_mips_attr(node); + const mips_attr_t *attr = get_mips_attr_const(node); return attr->slots; } @@ -316,7 +317,7 @@ const arch_register_t **get_mips_slots(const ir_node *node) { * Returns the name of the OUT register at position pos. */ const char *get_mips_out_reg_name(const ir_node *node, int pos) { - mips_attr_t *attr = get_mips_attr(node); + const mips_attr_t *attr = get_mips_attr_const(node); assert(is_mips_irn(node) && "Not an mips node."); assert(pos < ARR_LEN(attr->slots) && "Invalid OUT position."); @@ -329,7 +330,7 @@ const char *get_mips_out_reg_name(const ir_node *node, int pos) { * Returns the index of the OUT register at position pos within its register class. */ int get_mips_out_regnr(const ir_node *node, int pos) { - mips_attr_t *attr = get_mips_attr(node); + const mips_attr_t *attr = get_mips_attr_const(node); assert(is_mips_irn(node) && "Not an mips node."); assert(pos < ARR_LEN(attr->slots) && "Invalid OUT position."); @@ -342,7 +343,7 @@ int get_mips_out_regnr(const ir_node *node, int pos) { * Returns the OUT register at position pos. */ const arch_register_t *get_mips_out_reg(const ir_node *node, int pos) { - mips_attr_t *attr = get_mips_attr(node); + const mips_attr_t *attr = get_mips_attr_const(node); assert(is_mips_irn(node) && "Not an mips node."); assert(pos < ARR_LEN(attr->slots) && "Invalid OUT position."); @@ -355,7 +356,7 @@ const arch_register_t *get_mips_out_reg(const ir_node *node, int pos) { * Returns the number of results. */ int get_mips_n_res(const ir_node *node) { - mips_attr_t *attr = get_mips_attr(node); + const mips_attr_t *attr = get_mips_attr_const(node); return ARR_LEN(attr->slots); } @@ -380,8 +381,11 @@ void init_mips_attributes(ir_node *node, arch_irn_flags_t flags, const arch_regi } static -int mips_compare_attr(const mips_attr_t *a, const mips_attr_t *b) +int mips_compare_attr(ir_node *node_a, ir_node *node_b) { + const mips_attr_t *a = get_mips_attr_const(node_a); + const mips_attr_t *b = get_mips_attr_const(node_b); + if(a->tv != b->tv) return 1; if(a->symconst != b->symconst) diff --git a/ir/be/mips/mips_new_nodes.h b/ir/be/mips/mips_new_nodes.h index b74fcf379..91497f658 100644 --- a/ir/be/mips/mips_new_nodes.h +++ b/ir/be/mips/mips_new_nodes.h @@ -42,8 +42,8 @@ /** * Returns the attributes of an mips node. */ -mips_attr_t *get_mips_attr(const ir_node *node); - +mips_attr_t *get_mips_attr(ir_node *node); +const mips_attr_t *get_mips_attr_const(const ir_node *node); /** * Returns the argument register requirements of an mips node. */ @@ -82,7 +82,7 @@ arch_irn_flags_t get_mips_flags(const ir_node *node); /** * Sets the register flag of an mips node. */ -void set_mips_flags(const ir_node *node, arch_irn_flags_t flags); +void set_mips_flags(ir_node *node, arch_irn_flags_t flags); /** * Returns the result register slots of an mips node. diff --git a/ir/be/mips/mips_spec.pl b/ir/be/mips/mips_spec.pl index 872687cb1..61664c460 100644 --- a/ir/be/mips/mips_spec.pl +++ b/ir/be/mips/mips_spec.pl @@ -150,8 +150,6 @@ $new_emit_syntax = 1; # |_| # #--------------------------------------------------# -$default_cmp_attr = "return mips_compare_attr(attr_a, attr_b);"; - %nodes = ( #-----------------------------------------------------------------# diff --git a/ir/be/ppc32/ppc32_spec.pl b/ir/be/ppc32/ppc32_spec.pl index 75c580594..424d9f919 100644 --- a/ir/be/ppc32/ppc32_spec.pl +++ b/ir/be/ppc32/ppc32_spec.pl @@ -194,6 +194,8 @@ $new_emit_syntax = 1; RLWIMI => "${arch}_emit_rlwimi_helper(env, node);", ); +$default_cmp_attr = "NULL"; + #--------------------------------------------------# # _ # # (_) # diff --git a/ir/be/scripts/generate_new_opcodes.pl b/ir/be/scripts/generate_new_opcodes.pl index 52c903973..83bc3f441 100755 --- a/ir/be/scripts/generate_new_opcodes.pl +++ b/ir/be/scripts/generate_new_opcodes.pl @@ -38,8 +38,8 @@ our $arch; our $additional_opcodes; our %nodes; our %cpu; -our $default_cmp_attr; our $default_attr_type; +our $default_cmp_attr; our %init_attr; our %compare_attr; @@ -66,6 +66,14 @@ if(!defined(%init_attr)) { "$default_attr_type" => "\tinit_${arch}_attributes(res, flags, in_reqs, out_reqs, exec_units, n_res, latency);", ); } +if(!defined($default_cmp_attr)) { + $default_cmp_attr = "${arch}_compare_attr"; +} +if(!defined(%compare_attr)) { + %compare_attr = ( + "${default_attr_type}" => "${default_cmp_attr}", + ); +} #print Dumper(%nodes); #print Dumper(%operands); @@ -94,21 +102,6 @@ $n_opcodes += $additional_opcodes if (defined($additional_opcodes)); push(@obst_header, "void ".$arch."_create_opcodes(void);\n"); -# create default compare function -if(defined($default_cmp_attr)) { - my $cmpcode = $default_cmp_attr; - push(@obst_cmp_attr, "static int default_cmp_attr(ir_node *a, ir_node *b) {\n"); - if($cmpcode =~ m/attr_a/) { - push(@obst_cmp_attr, "\tconst ${default_attr_type} *attr_a = get_irn_generic_attr_const(a);\n"); - } - if($cmpcode =~ m/attr_b/) { - push(@obst_cmp_attr, "\tconst ${default_attr_type} *attr_b = get_irn_generic_attr_const(b);\n"); - } - push(@obst_cmp_attr, "\t${cmpcode}\n"); - push(@obst_cmp_attr, "}\n\n"); -} -# TODO: create compare functions - push(@obst_enum_op, "typedef enum _$arch\_opcodes {\n"); foreach my $op (keys(%nodes)) { my %n = %{ $nodes{"$op"} }; @@ -216,9 +209,6 @@ foreach my $op (keys(%nodes)) { # determine compare function my $cmp_attr_func; - if(defined($default_cmp_attr)) { - $cmp_attr_func = "default_cmp_attr"; - } if (exists($n{"cmp_attr"})) { my $cmpcode = $n{"cmp_attr"}; @@ -233,6 +223,12 @@ foreach my $op (keys(%nodes)) { push(@obst_cmp_attr, "}\n\n"); $cmp_attr_func = "cmp_attr_${op}"; + } else { + if(defined($compare_attr{${attr_type}})) { + $cmp_attr_func = $compare_attr{${attr_type}}; + } else { + die "No compare function defined for ${attr_type} attributes."; + } } if (exists($n{"rd_constructor"}) && $n{"rd_constructor"} =~ /^NONE$/i) {