fix negated set pnc with float compare problem
authorMatthias Braun <matze@braunis.de>
Thu, 4 Oct 2007 19:24:57 +0000 (19:24 +0000)
committerMatthias Braun <matze@braunis.de>
Thu, 4 Oct 2007 19:24:57 +0000 (19:24 +0000)
[r16091]

ir/be/ia32/ia32_emitter.c
ir/be/ia32/ia32_spec.pl
ir/be/ia32/ia32_transform.c

index 00ccab4..4e05b73 100644 (file)
@@ -721,9 +721,19 @@ static void ia32_emit_cmp_suffix(int pnc)
 void ia32_emit_cmp_suffix_node(const ir_node *node,
                                int flags_pos)
 {
+       const ia32_attr_t *attr = get_ia32_attr_const(node);
+
        pn_Cmp pnc = get_ia32_pncode(node);
 
        pnc = determine_final_pnc(node, flags_pos, pnc);
+       if(attr->data.ins_permuted) {
+               if(pnc & ia32_pn_Cmp_float) {
+                       pnc = get_negated_pnc(pnc, mode_F);
+               } else {
+                       pnc = get_negated_pnc(pnc, mode_Iu);
+               }
+       }
+
        ia32_emit_cmp_suffix(pnc);
 }
 
index 8f44804..601720b 100644 (file)
@@ -961,8 +961,10 @@ Set => {
        #irn_flags => "R",
        reg_req   => { in => [ "eflags" ], out => [ "eax ebx ecx edx" ] },
        ins       => [ "eflags" ],
-       attr      => "pn_Cmp pnc",
-       init_attr => "attr->pn_code = pnc;\nset_ia32_ls_mode(res, mode_Bu);\n",
+       attr      => "pn_Cmp pnc, int ins_permuted",
+       init_attr => "attr->pn_code = pnc;\n".
+                    "attr->data.ins_permuted = ins_permuted;\n".
+                     "\tset_ia32_ls_mode(res, mode_Bu);\n",
        emit      => '. set%CMP0 %DB0',
        latency   => 1,
        units     => [ "GP" ],
index f0781e9..be42ea1 100644 (file)
@@ -2389,14 +2389,15 @@ static ir_node *create_CMov(ir_node *node, ir_node *new_flags, pn_Cmp pnc)
 
 
 static ir_node *create_set_32bit(dbg_info *dbgi, ir_node *new_block,
-                                 ir_node *flags, pn_Cmp pnc, ir_node *orig_node)
+                                 ir_node *flags, pn_Cmp pnc, ir_node *orig_node,
+                                 int ins_permuted)
 {
        ir_graph *irg   = current_ir_graph;
        ir_node  *noreg = ia32_new_NoReg_gp(env_cg);
        ir_node  *nomem = new_NoMem();
        ir_node  *res;
 
-       res = new_rd_ia32_Set(dbgi, irg, new_block, flags, pnc);
+       res = new_rd_ia32_Set(dbgi, irg, new_block, flags, pnc, ins_permuted);
        SET_IA32_ORIG_NODE(res, ia32_get_old_node_name(env_cg, orig_node));
        res = new_rd_ia32_Conv_I2I8Bit(dbgi, irg, new_block, noreg, noreg,
                                       nomem, res, mode_Bu);
@@ -2420,7 +2421,6 @@ static ir_node *gen_Psi(ir_node *node)
        ir_node  *cond        = get_Psi_cond(node, 0);
        ir_node  *flags       = NULL;
        ir_node  *res;
-       ir_mode  *cmp_mode;
        pn_Cmp    pnc;
 
        assert(get_Psi_n_conds(node) == 1);
@@ -2430,10 +2430,9 @@ static ir_node *gen_Psi(ir_node *node)
        flags = get_flags_node(cond, &pnc);
 
        if(is_Const_1(psi_true) && is_Const_0(psi_default)) {
-               res = create_set_32bit(dbgi, new_block, flags, pnc, node);
+               res = create_set_32bit(dbgi, new_block, flags, pnc, node, 0);
        } else if(is_Const_0(psi_true) && is_Const_1(psi_default)) {
-               pnc = get_negated_pnc(pnc, cmp_mode);
-               res = create_set_32bit(dbgi, new_block, flags, pnc, node);
+               res = create_set_32bit(dbgi, new_block, flags, pnc, node, 1);
        } else {
                res = create_CMov(node, flags, pnc);
        }
@@ -4434,7 +4433,7 @@ static ir_node *gen_Proj_Cmp(ir_node *node)
        long      pnc       = get_Proj_proj(node);
        ir_node  *res;
 
-       res = create_set_32bit(dbgi, new_block, new_cmp, pnc, node);
+       res = create_set_32bit(dbgi, new_block, new_cmp, pnc, node, 0);
 
        return res;
 }