- BSF/BSR cannot do 16 bit AM in our model, because they only set the lower 16 bits...
[libfirm] / ir / be / mips / mips_transform.c
index af43e4b..2a23ff6 100644 (file)
@@ -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.
  *
@@ -23,9 +23,7 @@
  * @author  Matthias Braun, Mehdi
  * @version $Id$
  */
-#ifdef HAVE_CONFIG_H
 #include "config.h"
-#endif
 
 #include <limits.h>
 
@@ -51,7 +49,6 @@
 #include "bearch_mips_t.h"
 
 #include "mips_nodes_attr.h"
-#include "archop.h"
 #include "mips_transform.h"
 #include "mips_new_nodes.h"
 #include "mips_map_regs.h"
@@ -60,9 +57,6 @@
 
 #include "gen_mips_regalloc_if.h"
 
-/** hold the current code generator during transformation */
-static mips_code_gen_t *env_cg = NULL;
-
 /****************************************************************************************************
  *                  _        _                        __                           _   _
  *                 | |      | |                      / _|                         | | (_)
@@ -73,10 +67,10 @@ static mips_code_gen_t *env_cg = NULL;
  *
  ****************************************************************************************************/
 
-typedef ir_node *construct_binop_func(dbg_info *db, ir_graph *irg,
-       ir_node *block, ir_node *left, ir_node *right);
+typedef ir_node *construct_binop_func(dbg_info *db, ir_node *block,
+               ir_node *left, ir_node *right);
 
-static INLINE int mode_needs_gp_reg(ir_mode *mode) {
+static inline int mode_needs_gp_reg(ir_mode *mode) {
        return mode_is_int(mode) || mode_is_reference(mode);
 }
 
@@ -88,8 +82,7 @@ ir_node *mips_create_Immediate(long val)
        ir_node  *res;
 
        assert(val >=  -32768 && val <= 32767);
-       res      = new_rd_mips_Immediate(NULL, irg, block, MIPS_IMM_CONST, NULL,
-                                        val);
+       res      = new_bd_mips_Immediate(NULL, block, MIPS_IMM_CONST, NULL, val);
        slots    = get_mips_slots(res);
        slots[0] = &mips_gp_regs[REG_GP_NOREG];
 
@@ -100,7 +93,7 @@ ir_node* mips_create_zero(void)
 {
        ir_graph *irg   = current_ir_graph;
        ir_node  *block = get_irg_start_block(irg);
-       ir_node  *zero  = new_rd_mips_zero(NULL, irg, block);
+       ir_node  *zero  = new_bd_mips_zero(NULL, block);
        const arch_register_t **slots = get_mips_slots(zero);
 
        slots[0] = &mips_gp_regs[REG_ZERO];
@@ -160,7 +153,6 @@ static void create_binop_operands(ir_node **new_left, ir_node **new_right,
 static ir_node *gen_binop(ir_node *node, ir_node *left, ir_node *right,
                           construct_binop_func func, int supports_immediate)
 {
-       ir_graph *irg   = current_ir_graph;
        dbg_info *dbgi  = get_irn_dbg_info(node);
        ir_node  *block = be_transform_node(get_nodes_block(node));
        ir_node  *res;
@@ -177,7 +169,7 @@ static ir_node *gen_binop(ir_node *node, ir_node *left, ir_node *right,
                new_right = be_transform_node(right);
        }
 
-       res = func(dbgi, irg, block, new_left, new_right);
+       res = func(dbgi, block, new_left, new_right);
 
        return res;
 }
@@ -186,54 +178,53 @@ static ir_node *gen_Add(ir_node *node)
 {
        /* TODO: match add(symconst, const) */
        return gen_binop(node, get_Add_left(node), get_Add_right(node),
-                        new_rd_mips_addu, 1);
+                        new_bd_mips_addu, 1);
 }
 
 static ir_node *gen_Sub(ir_node *node)
 {
        return gen_binop(node, get_Sub_left(node), get_Sub_right(node),
-                        new_rd_mips_addu, 0);
+                        new_bd_mips_addu, 0);
 }
 
 static ir_node *gen_And(ir_node *node)
 {
        return gen_binop(node, get_Add_left(node), get_Add_right(node),
-                        new_rd_mips_and, 1);
+                        new_bd_mips_and, 1);
 }
 
 static ir_node *gen_Or(ir_node *node)
 {
        return gen_binop(node, get_Add_left(node), get_Add_right(node),
-                        new_rd_mips_or, 1);
+                        new_bd_mips_or, 1);
 }
 
 static ir_node *gen_Eor(ir_node *node)
 {
        return gen_binop(node, get_Add_left(node), get_Add_right(node),
-                        new_rd_mips_xor, 1);
+                        new_bd_mips_xor, 1);
 }
 
 static ir_node *gen_Shl(ir_node *node)
 {
        return gen_binop(node, get_Add_left(node), get_Add_right(node),
-                        new_rd_mips_sll, 1);
+                        new_bd_mips_sll, 1);
 }
 
 static ir_node *gen_Shr(ir_node *node)
 {
        return gen_binop(node, get_Add_left(node), get_Add_right(node),
-                        new_rd_mips_srl, 1);
+                        new_bd_mips_srl, 1);
 }
 
 static ir_node *gen_Shrs(ir_node *node)
 {
        return gen_binop(node, get_Add_left(node), get_Add_right(node),
-                        new_rd_mips_sra, 1);
+                        new_bd_mips_sra, 1);
 }
 
 static ir_node *gen_Not(ir_node *node)
 {
-       ir_graph *irg   = current_ir_graph;
        dbg_info *dbgi  = get_irn_dbg_info(node);
        ir_node  *block = be_transform_node(get_nodes_block(node));
        ir_node  *op    = get_Not_op(node);
@@ -244,20 +235,19 @@ static ir_node *gen_Not(ir_node *node)
        /* we can transform not->or to nor */
        if(is_Or(op)) {
                return gen_binop(op, get_Or_left(op), get_Or_right(op),
-                                new_rd_mips_nor, 1);
+                                new_bd_mips_nor, 1);
        }
 
        /* construct (op < 1) */
        one    = mips_create_Immediate(1);
        new_op = be_transform_node(op);
-       res    = new_rd_mips_sltu(dbgi, irg, block, new_op, one);
+       res    = new_bd_mips_sltu(dbgi, block, new_op, one);
 
        return res;
 }
 
 static ir_node *gen_Minus(ir_node *node)
 {
-       ir_graph *irg    = current_ir_graph;
        dbg_info *dbgi   = get_irn_dbg_info(node);
        ir_node  *block  = be_transform_node(get_nodes_block(node));
        ir_node  *op     = get_Minus_op(node);
@@ -267,14 +257,13 @@ static ir_node *gen_Minus(ir_node *node)
 
        /* construct (0 - op) */
        zero = mips_create_zero();
-       res  = new_rd_mips_subu(dbgi, irg, block, zero, new_op);
+       res  = new_bd_mips_subu(dbgi, block, zero, new_op);
 
        return res;
 }
 
 static ir_node *gen_Abs(ir_node *node)
 {
-       ir_graph *irg    = current_ir_graph;
        dbg_info *dbgi   = get_irn_dbg_info(node);
        ir_node  *block  = be_transform_node(get_nodes_block(node));
        ir_node  *op     = get_Abs_op(node);
@@ -284,16 +273,15 @@ static ir_node *gen_Abs(ir_node *node)
        /* TODO: support other bit sizes... */
        assert(get_mode_size_bits(get_irn_mode(node)) == 32);
        sra_const = mips_create_Immediate(31);
-       sra       = new_rd_mips_sra(dbgi, irg, block, new_op, sra_const);
-       add       = new_rd_mips_addu(dbgi, irg, block, new_op, sra);
-       xor       = new_rd_mips_xor(dbgi, irg, block, sra, add);
+       sra       = new_bd_mips_sra( dbgi, block, new_op, sra_const);
+       add       = new_bd_mips_addu(dbgi, block, new_op, sra);
+       xor       = new_bd_mips_xor( dbgi, block, sra, add);
 
        return xor;
 }
 
 static ir_node* gen_Const(ir_node *node)
 {
-       ir_graph *irg   = current_ir_graph;
        dbg_info *dbgi  = get_irn_dbg_info(node);
        ir_node  *block = be_transform_node(get_nodes_block(node));
        tarval   *tv    = get_Const_tarval(node);
@@ -305,7 +293,7 @@ static ir_node* gen_Const(ir_node *node)
        if(tarval_is_long(tv)) {
                val = get_tarval_long(tv);
        } else {
-               panic("Can't get value of tarval %+F\n", node);
+               panic("Can't get value of tarval %+F", node);
        }
 
        val = get_tarval_long(tv);
@@ -315,25 +303,24 @@ static ir_node* gen_Const(ir_node *node)
        if(upper == 0) {
                upper_node = mips_create_zero();
        } else {
-               upper_node = new_rd_mips_lui(dbgi, irg, block, MIPS_IMM_CONST, NULL,
-                                            upper);
+               upper_node = new_bd_mips_lui(dbgi, block, MIPS_IMM_CONST, NULL, upper);
        }
 
        if(lower == 0)
                return upper_node;
 
        or_const   = mips_create_Immediate(lower);
-       lower_node = new_rd_mips_or(dbgi, irg, block, upper_node, or_const);
+       lower_node = new_bd_mips_or(dbgi, block, upper_node, or_const);
 
        return lower_node;
 }
 
 static ir_node* gen_SymConst(ir_node *node)
 {
-       ir_graph *irg   = current_ir_graph;
        dbg_info *dbgi  = get_irn_dbg_info(node);
        ir_node  *block = be_transform_node(get_nodes_block(node));
        ir_entity *entity;
+       const arch_register_t **slots;
        ir_node *lui, *or_const, *or;
 
        if(get_SymConst_kind(node) != symconst_addr_ent) {
@@ -342,25 +329,24 @@ static ir_node* gen_SymConst(ir_node *node)
 
        entity = get_SymConst_entity(node);
 
-       lui            = new_rd_mips_lui(dbgi, irg, block, MIPS_IMM_SYMCONST_HI,
-                                        entity, 0);
-       or_const       = new_rd_mips_Immediate(dbgi, irg, block,
-                                              MIPS_IMM_SYMCONST_LO, entity, 0);
-       or             = new_rd_mips_or(dbgi, irg, block, lui, or_const);
+       lui      = new_bd_mips_lui(dbgi, block, MIPS_IMM_SYMCONST_HI, entity, 0);
+       or_const = new_bd_mips_Immediate(dbgi, block, MIPS_IMM_SYMCONST_LO, entity, 0);
+       or       = new_bd_mips_or(dbgi, block, lui, or_const);
+
+       slots    = get_mips_slots(or_const);
+       slots[0] = &mips_gp_regs[REG_GP_NOREG];
 
        return or;
 }
 
-typedef ir_node* (*gen_load_func) (dbg_info *dbg, ir_graph *irg,
-                                   ir_node *block, ir_node *ptr, ir_node *mem,
-                                   ir_entity *entity, long offset);
+typedef ir_node* (*gen_load_func)(dbg_info *dbg, ir_node *block, ir_node *ptr,
+               ir_node *mem, ir_entity *entity, long offset);
 
 /**
  * Generates a mips node for a firm Load node
  */
 static ir_node *gen_Load(ir_node *node)
 {
-       ir_graph *irg     = current_ir_graph;
        dbg_info *dbgi    = get_irn_dbg_info(node);
        ir_node  *block   = be_transform_node(get_nodes_block(node));
        ir_node  *mem     = get_Load_mem(node);
@@ -379,34 +365,32 @@ static ir_node *gen_Load(ir_node *node)
 
        switch(get_mode_size_bits(mode)) {
        case 32:
-               func = new_rd_mips_lw;
+               func = new_bd_mips_lw;
                break;
        case 16:
-               func = sign ? new_rd_mips_lh : new_rd_mips_lhu;
+               func = sign ? new_bd_mips_lh : new_bd_mips_lhu;
                break;
        case 8:
-               func = sign ? new_rd_mips_lb : new_rd_mips_lbu;
+               func = sign ? new_bd_mips_lb : new_bd_mips_lbu;
                break;
        default:
                panic("mips backend only support 32, 16, 8 bit loads");
        }
 
-       res = func(dbgi, irg, block, new_ptr, new_mem, NULL, 0);
+       res = func(dbgi, block, new_ptr, new_mem, NULL, 0);
        set_irn_pinned(res, get_irn_pinned(node));
 
        return res;
 }
 
-typedef ir_node* (*gen_store_func) (dbg_info *dbg, ir_graph *irg,
-                                    ir_node *block, ir_node *ptr, ir_node *val,
-                                    ir_node *mem, ir_entity *ent, long offset);
+typedef ir_node* (*gen_store_func)(dbg_info *dbg, ir_node *block, ir_node *ptr,
+               ir_node *val, ir_node *mem, ir_entity *ent, long offset);
 
 /**
  * Generates a mips node for a firm Store node
  */
 static ir_node *gen_Store(ir_node *node)
 {
-       ir_graph    *irg     = current_ir_graph;
        dbg_info    *dbgi    = get_irn_dbg_info(node);
        ir_node     *block   = be_transform_node(get_nodes_block(node));
        ir_node     *mem     = get_Store_mem(node);
@@ -423,19 +407,19 @@ static ir_node *gen_Store(ir_node *node)
 
        switch(get_mode_size_bits(mode)) {
        case 32:
-               func = new_rd_mips_sw;
+               func = new_bd_mips_sw;
                break;
        case 16:
-               func = new_rd_mips_sh;
+               func = new_bd_mips_sh;
                break;
        case 8:
-               func = new_rd_mips_sb;
+               func = new_bd_mips_sb;
                break;
        default:
                panic("store only supported for 32, 16, 8 bit values in mips backend");
        }
 
-       res = func(dbgi, irg, block, new_ptr, new_val, new_mem, NULL, 0);
+       res = func(dbgi, block, new_ptr, new_val, new_mem, NULL, 0);
        set_irn_pinned(res, get_irn_pinned(node));
 
        return res;
@@ -462,7 +446,7 @@ static ir_node *gen_Proj_DivMod(ir_node *node)
                case pn_Div_res:
                        proj = new_rd_Proj(dbgi, irg, block, new_div, mode_M,
                                           pn_mips_div_lohi);
-                       return new_rd_mips_mflo(dbgi, irg, block, proj);
+                       return new_bd_mips_mflo(dbgi, block, proj);
                default:
                        break;
                }
@@ -474,7 +458,7 @@ static ir_node *gen_Proj_DivMod(ir_node *node)
                case pn_Mod_res:
                        proj = new_rd_Proj(dbgi, irg, block, new_div, mode_M,
                                           pn_mips_div_lohi);
-                       return new_rd_mips_mfhi(dbgi, irg, block, proj);
+                       return new_bd_mips_mfhi(dbgi, block, proj);
                default:
                        break;
                }
@@ -487,11 +471,11 @@ static ir_node *gen_Proj_DivMod(ir_node *node)
                case pn_DivMod_res_div:
                        proj = new_rd_Proj(dbgi, irg, block, new_div, mode_M,
                                           pn_mips_div_lohi);
-                       return new_rd_mips_mflo(dbgi, irg, block, proj);
+                       return new_bd_mips_mflo(dbgi, block, proj);
                case pn_DivMod_res_mod:
                        proj = new_rd_Proj(dbgi, irg, block, new_div, mode_M,
                                           pn_mips_div_lohi);
-                       return new_rd_mips_mfhi(dbgi, irg, block, proj);
+                       return new_bd_mips_mfhi(dbgi, block, proj);
                default:
                        break;
                }
@@ -499,7 +483,7 @@ static ir_node *gen_Proj_DivMod(ir_node *node)
                break;
        }
 
-       panic("invalid proj attached to %+F\n", divmod);
+       panic("invalid proj attached to %+F", divmod);
 }
 
 static ir_node *gen_Proj_Start(ir_node *node)
@@ -575,7 +559,6 @@ static ir_node *gen_Phi(ir_node *node)
        copy_node_attr(node, phi);
        be_duplicate_deps(node, phi);
 
-       be_set_transformed_node(node, phi);
        be_enqueue_preds(node);
 
        return phi;
@@ -634,7 +617,7 @@ ir_node *gen_node_for_SwitchCond(mips_transform_env_t *env)
        if(minval != 0) {
                minval_const = new_rd_Const(dbg, irg, block, selector_mode, new_tarval_from_long(minval, selector_mode));
                minval_const = gen_node_for_Const(env, dbg, irg, block, minval_const);
-               sub = new_rd_mips_sub(dbg, irg, block, selector, minval_const);
+               sub = new_bd_mips_sub(dbg, block, selector, minval_const);
        } else {
                sub = selector;
        }
@@ -647,10 +630,10 @@ ir_node *gen_node_for_SwitchCond(mips_transform_env_t *env)
 
        max_const = new_rd_Const(dbg, irg, block, unsigned_mode, new_tarval_from_long(maxval - minval + 1, unsigned_mode));
        max_const = gen_node_for_Const(env, dbg, irg, block, max_const);
-       sltu = new_rd_mips_slt(dbg, irg, block, sub, max_const);
+       sltu = new_bd_mips_slt(dbg, block, sub, max_const);
 
        zero = gen_zero_node(env, dbg, irg, block);
-       beq = new_rd_mips_beq(dbg, irg, block, sltu, zero, mode_T);
+       beq = new_bd_mips_beq(dbg, block, sltu, zero, mode_T);
 
        // attach defaultproj to beq now
        set_irn_n(defaultproj, 0, beq);
@@ -658,18 +641,18 @@ ir_node *gen_node_for_SwitchCond(mips_transform_env_t *env)
 
        two_const = new_rd_Const(dbg, irg, block, unsigned_mode, new_tarval_from_long(2, unsigned_mode));
        two_const = gen_node_for_Const(env, dbg, irg, block, two_const);
-       sl = new_rd_mips_sl(dbg, irg, block, sub, two_const);
+       sl = new_bd_mips_sl(dbg, block, sub, two_const);
 
-       la = new_rd_mips_la(dbg, irg, block);
-       add = new_rd_mips_addu(dbg, irg, block, sl, la);
-       load = new_rd_mips_load_r(dbg, irg, block, new_rd_NoMem(irg), add, mode_T);
+       la   = new_bd_mips_la(    dbg, block);
+       add  = new_bd_mips_addu(  dbg, block, sl, la);
+       load = new_bd_mips_load_r(dbg, block, new_NoMem(), add, mode_T);
        attr = get_mips_attr(load);
        attr->modes.load_store_mode = mode_Iu;
        attr->tv = new_tarval_from_long(0, mode_Iu);
 
        proj = new_rd_Proj(dbg, irg, block, load, mode_Iu, pn_Load_res);
 
-       switchjmp = new_rd_mips_SwitchJump(dbg, irg, block, proj, mode_T);
+       switchjmp = new_bd_mips_SwitchJump(dbg, block, proj, mode_T);
        attr = get_mips_attr(switchjmp);
        attr->switch_default_pn = defaultprojn;
 
@@ -686,7 +669,6 @@ ir_node *gen_node_for_SwitchCond(mips_transform_env_t *env)
 
 static ir_node *gen_Cond(ir_node *node)
 {
-       ir_graph *irg       = current_ir_graph;
        dbg_info *dbgi      = get_irn_dbg_info(node);
        ir_node  *block     = get_nodes_block(node);
        ir_node  *sel_proj  = get_Cond_selector(node);
@@ -709,35 +691,35 @@ static ir_node *gen_Cond(ir_node *node)
                panic("mips backend can't handle unoptimized constant Cond");
 
        case pn_Cmp_Eq:
-               res = new_rd_mips_beq(dbgi, irg, block, new_left, new_right);
+               res = new_bd_mips_beq(dbgi, block, new_left, new_right);
                break;
 
        case pn_Cmp_Lt:
                zero = mips_create_zero();
-               slt  = new_rd_mips_slt(dbgi, irg, block, new_left, new_right);
-               res  = new_rd_mips_bne(dbgi, irg, block, slt, zero);
+               slt  = new_bd_mips_slt(dbgi, block, new_left, new_right);
+               res  = new_bd_mips_bne(dbgi, block, slt, zero);
                break;
 
        case pn_Cmp_Le:
                zero = mips_create_zero();
-               slt  = new_rd_mips_slt(dbgi, irg, block, new_right, new_left);
-               res  = new_rd_mips_beq(dbgi, irg, block, slt, zero);
+               slt  = new_bd_mips_slt(dbgi, block, new_right, new_left);
+               res  = new_bd_mips_beq(dbgi, block, slt, zero);
                break;
 
        case pn_Cmp_Gt:
                zero = mips_create_zero();
-               slt  = new_rd_mips_slt(dbgi, irg, block, new_right, new_left);
-               res  = new_rd_mips_bne(dbgi, irg, block, slt, zero);
+               slt  = new_bd_mips_slt(dbgi, block, new_right, new_left);
+               res  = new_bd_mips_bne(dbgi, block, slt, zero);
                break;
 
        case pn_Cmp_Ge:
                zero = mips_create_zero();
-               slt  = new_rd_mips_slt(dbgi, irg, block, new_right, new_left);
-               res  = new_rd_mips_bne(dbgi, irg, block, slt, zero);
+               slt  = new_bd_mips_slt(dbgi, block, new_right, new_left);
+               res  = new_bd_mips_bne(dbgi, block, slt, zero);
                break;
 
        case pn_Cmp_Lg:
-               res = new_rd_mips_bne(dbgi, irg, block, new_left, new_right);
+               res = new_bd_mips_bne(dbgi, block, new_left, new_right);
                break;
 
        default:
@@ -749,7 +731,6 @@ static ir_node *gen_Cond(ir_node *node)
 
 static ir_node *gen_Conv(ir_node *node)
 {
-       ir_graph *irg      = current_ir_graph;
        dbg_info *dbgi     = get_irn_dbg_info(node);
        ir_node  *block    = be_transform_node(get_nodes_block(node));
        ir_node  *op       = get_Conv_op(node);
@@ -771,11 +752,11 @@ static ir_node *gen_Conv(ir_node *node)
 
        if(mode_is_signed(src_mode)) {
                if(src_size == 8) {
-                       res = new_rd_mips_seb(dbgi, irg, block, new_op);
+                       res = new_bd_mips_seb(dbgi, block, new_op);
                } else if(src_size == 16) {
-                       res = new_rd_mips_seh(dbgi, irg, block, new_op);
+                       res = new_bd_mips_seh(dbgi, block, new_op);
                } else {
-                       panic("invalid conv %+F\n", node);
+                       panic("invalid conv %+F", node);
                }
        } else {
                ir_node *and_const;
@@ -785,9 +766,9 @@ static ir_node *gen_Conv(ir_node *node)
                } else if(src_size == 16) {
                        and_const = mips_create_Immediate(0xffff);
                } else {
-                       panic("invalid conv %+F\n", node);
+                       panic("invalid conv %+F", node);
                }
-               res = new_rd_mips_and(dbgi, irg, block, new_op, and_const);
+               res = new_bd_mips_and(dbgi, block, new_op, and_const);
        }
 
        return res;
@@ -796,7 +777,6 @@ static ir_node *gen_Conv(ir_node *node)
 static ir_node *create_div(ir_node *node, ir_node *left, ir_node *right,
                            ir_mode *mode)
 {
-       ir_graph *irg       = current_ir_graph;
        dbg_info *dbgi      = get_irn_dbg_info(node);
        ir_node  *block     = be_transform_node(get_nodes_block(node));
        ir_node  *new_left  = be_transform_node(left);
@@ -804,9 +784,9 @@ static ir_node *create_div(ir_node *node, ir_node *left, ir_node *right,
        ir_node  *res;
 
        if(mode_is_signed(mode)) {
-               res = new_rd_mips_div(dbgi, irg, block, new_left, new_right);
+               res = new_bd_mips_div(dbgi, block, new_left, new_right);
        } else {
-               res = new_rd_mips_divu(dbgi, irg, block, new_left, new_right);
+               res = new_bd_mips_divu(dbgi, block, new_left, new_right);
        }
 
        set_irn_pinned(res, get_irn_pinned(node));
@@ -848,24 +828,23 @@ static ir_node *gen_node_for_Mul(mips_transform_env_t *env) {
        assert(get_mode_size_bits(get_irn_mode(op2)) == get_mode_size_bits(env->mode));
 
        if(mode_is_signed(mode)) {
-               mul = new_rd_mips_mult(env->dbg, env->irg, env->block, get_Mul_left(node), get_Mul_right(node));
+               mul = new_bd_mips_mult(env->dbg, env->block, get_Mul_left(node), get_Mul_right(node));
        } else {
-               mul = new_rd_mips_multu(env->dbg, env->irg, env->block, get_Mul_left(node), get_Mul_right(node));
+               mul = new_bd_mips_multu(env->dbg, env->block, get_Mul_left(node), get_Mul_right(node));
        }
-       mflo = new_rd_mips_mflo(env->dbg, env->irg, env->block, mul);
+       mflo = new_bd_mips_mflo(env->dbg, env->block, mul);
 
        return mflo;
 }
 
 static
 ir_node *gen_node_for_IJmp(mips_transform_env_t *env) {
-       ir_graph *irg    = env->irg;
        ir_node  *node   = env->irn;
        dbg_info *dbg    = get_irn_dbg_info(node);
        ir_node  *block  = get_nodes_block(node);
        ir_node  *target = get_IJmp_target(node);
 
-       return new_rd_mips_jr(dbg, irg, block, target);
+       return new_bd_mips_jr(dbg, block, target);
 }
 
 static
@@ -873,10 +852,10 @@ ir_node *gen_node_for_Rot(mips_transform_env_t *env) {
        ir_node *node = env->irn;
        ir_node *subu, *srlv, *sllv, *or;
 
-       subu = new_rd_mips_subuzero(env->dbg, env->irg, env->block, get_Rot_right(node));
-       srlv = new_rd_mips_srlv(env->dbg, env->irg, env->block, get_Rot_left(node), subu);
-       sllv = new_rd_mips_sllv(env->dbg, env->irg, env->block, get_Rot_left(node), get_Rot_right(node));
-       or = new_rd_mips_or(env->dbg, env->irg, env->block, sllv, srlv);
+       subu = new_bd_mips_subuzero(env->dbg, env->block, get_Rot_right(node));
+       srlv = new_bd_mips_srlv(env->dbg, env->block, get_Rot_left(node), subu);
+       sllv = new_bd_mips_sllv(env->dbg, env->block, get_Rot_left(node), get_Rot_right(node));
+       or   = new_bd_mips_or(env->dbg, env->block, sllv, srlv);
 
        return or;
 }
@@ -964,7 +943,7 @@ ir_node *gen_code_for_CopyB(ir_node *block, ir_node *node) {
                for (i = 0; i < 4; ++i) {
                        ir_node *load;
 
-                       load = new_rd_mips_load_r(dbg, irg, new_bl, mem_phi, src, mode_T);
+                       load = new_bd_mips_load_r(dbg, new_bl, mem_phi, src, mode_T);
                        attr = get_mips_attr(load);
                        attr->modes.load_store_mode = mode_Iu;
                        attr->tv = new_tarval_from_long(i * 4, mode_Iu);
@@ -976,7 +955,7 @@ ir_node *gen_code_for_CopyB(ir_node *block, ir_node *node) {
                for (i = 0; i < 4; ++i) {
                        ir_node *store;
 
-                       store = new_rd_mips_store_r(dbg, irg, new_bl, mem_phi, dst, ld[i], mode_T);
+                       store = new_bd_mips_store_r(dbg, new_bl, mem_phi, dst, ld[i], mode_T);
                        attr = get_mips_attr(store);
                        attr->modes.load_store_mode = mode_Iu;
                        attr->tv = new_tarval_from_long(i * 4, mode_Iu);
@@ -1005,14 +984,14 @@ ir_node *gen_code_for_CopyB(ir_node *block, ir_node *node) {
                        i -= 1;
                }
 
-               load = new_rd_mips_load_r(dbg, irg, block, mem, src, mode_T);
+               load = new_bd_mips_load_r(dbg, block, mem, src, mode_T);
                attr = get_mips_attr(load);
                attr->modes.load_store_mode = mode;
                attr->tv = new_tarval_from_long(offset, mode_Iu);
 
                projv = new_rd_Proj(dbg, irg, block, load, mode, pn_Load_res);
 
-               store = new_rd_mips_store_r(dbg, irg, block, mem, dst, projv, mode_T);
+               store = new_bd_mips_store_r(dbg, block, mem, dst, projv, mode_T);
                attr = get_mips_attr(store);
                attr->modes.load_store_mode = mode;
                attr->tv = new_tarval_from_long(offset, mode_Iu);
@@ -1035,7 +1014,7 @@ static void mips_fix_CopyB_Proj(mips_transform_env_t* env) {
        long n = get_Proj_proj(node);
 
        if(n == pn_CopyB_M_except) {
-               assert(0);
+               panic("Unsupported Proj from CopyB");
        } else if(n == pn_CopyB_M_regular) {
                set_Proj_proj(node, pn_Store_M);
        } else if(n == pn_CopyB_M_except) {
@@ -1048,7 +1027,7 @@ static void mips_transform_Spill(mips_transform_env_t* env) {
        ir_node   *node = env->irn;
        ir_node   *sched_point = NULL;
        ir_node   *store;
-       ir_node   *nomem = new_rd_NoMem(env->irg);
+       ir_node   *nomem = new_NoMem();
        ir_node   *ptr   = get_irn_n(node, 0);
        ir_node   *val   = get_irn_n(node, 1);
        ir_entity *ent   = be_get_frame_entity(node);
@@ -1057,8 +1036,7 @@ static void mips_transform_Spill(mips_transform_env_t* env) {
                sched_point = sched_prev(node);
        }
 
-       store = new_rd_mips_sw(env->dbg, env->irg, env->block, ptr, val, nomem,
-                              ent, 0);
+       store = new_bd_mips_sw(env->dbg, env->block, ptr, val, nomem, ent, 0);
 
        if (sched_point) {
                sched_add_after(sched_point, store);
@@ -1081,7 +1059,7 @@ static void mips_transform_Reload(mips_transform_env_t* env) {
                sched_point = sched_prev(node);
        }
 
-       load = new_rd_mips_lw(env->dbg, env->irg, env->block, ptr, mem, ent, 0);
+       load = new_bd_mips_lw(env->dbg, env->block, ptr, mem, ent, 0);
 
        proj = new_rd_Proj(env->dbg, env->irg, env->block, load, mode_Iu, pn_mips_lw_res);
 
@@ -1092,8 +1070,8 @@ static void mips_transform_Reload(mips_transform_env_t* env) {
        }
 
        /* copy the register from the old node to the new Load */
-       reg = arch_get_irn_register(env->cg->arch_env, node);
-       arch_set_irn_register(env->cg->arch_env, proj, reg);
+       reg = arch_get_irn_register(node);
+       arch_set_irn_register(proj, reg);
 
        exchange(node, proj);
 }
@@ -1109,11 +1087,11 @@ static ir_node *gen_AddSP(ir_node *node)
        op1 = get_irn_n(node, 0);
        op2 = get_irn_n(node, 1);
 
-       add = new_rd_mips_addu(env->dbg, env->irg, env->block, op1, op2);
+       add = new_bd_mips_addu(env->dbg, env->block, op1, op2);
 
        /* copy the register requirements from the old node to the new node */
-       reg = arch_get_irn_register(env->cg->arch_env, node);
-       arch_set_irn_register(env->cg->arch_env, add, reg);
+       reg = arch_get_irn_register(node);
+       arch_set_irn_register(add, reg);
 
        return add;
 }
@@ -1129,59 +1107,47 @@ static ir_node *gen_AddSP(ir_node *node)
  *
  *********************************************************/
 
-static ir_node *gen_Bad(ir_node *node)
+typedef ir_node *(*mips_transform_func) (ir_node *node);
+
+static void register_transformer(ir_op *op, mips_transform_func func)
 {
-       panic("Unexpected node %+F found in mips transform phase.\n", node);
-       return NULL;
+       assert(op->ops.generic == NULL);
+       op->ops.generic = (op_func) func;
 }
 
 static void register_transformers(void)
 {
        clear_irp_opcodes_generic_func();
 
-       op_Add->ops.generic      = (op_func) gen_Add;
-       op_Sub->ops.generic      = (op_func) gen_Sub;
-       op_And->ops.generic      = (op_func) gen_And;
-       op_Or->ops.generic       = (op_func) gen_Or;
-       op_Eor->ops.generic      = (op_func) gen_Eor;
-       op_Shl->ops.generic      = (op_func) gen_Shl;
-       op_Shr->ops.generic      = (op_func) gen_Shr;
-       op_Shrs->ops.generic     = (op_func) gen_Shrs;
-       op_Not->ops.generic      = (op_func) gen_Not;
-       op_Minus->ops.generic    = (op_func) gen_Minus;
-       op_Div->ops.generic      = (op_func) gen_Div;
-       op_Mod->ops.generic      = (op_func) gen_Mod;
-       op_DivMod->ops.generic   = (op_func) gen_DivMod;
-       op_Abs->ops.generic      = (op_func) gen_Abs;
-       op_Load->ops.generic     = (op_func) gen_Load;
-       op_Store->ops.generic    = (op_func) gen_Store;
-       op_Cond->ops.generic     = (op_func) gen_Cond;
-       op_Conv->ops.generic     = (op_func) gen_Conv;
-       op_Const->ops.generic    = (op_func) gen_Const;
-       op_SymConst->ops.generic = (op_func) gen_SymConst;
-       op_Unknown->ops.generic  = (op_func) gen_Unknown;
-       op_Proj->ops.generic     = (op_func) gen_Proj;
-       op_Phi->ops.generic      = (op_func) gen_Phi;
-
-       op_Raise->ops.generic     = (op_func) gen_Bad;
-       op_Sel->ops.generic       = (op_func) gen_Bad;
-       op_InstOf->ops.generic    = (op_func) gen_Bad;
-       op_Cast->ops.generic      = (op_func) gen_Bad;
-       op_Free->ops.generic      = (op_func) gen_Bad;
-       op_Tuple->ops.generic     = (op_func) gen_Bad;
-       op_Id->ops.generic        = (op_func) gen_Bad;
-       op_Confirm->ops.generic   = (op_func) gen_Bad;
-       op_Filter->ops.generic    = (op_func) gen_Bad;
-       op_CallBegin->ops.generic = (op_func) gen_Bad;
-       op_EndReg->ops.generic    = (op_func) gen_Bad;
-       op_EndExcept->ops.generic = (op_func) gen_Bad;
+       register_transformer(op_Add, gen_Add);
+       register_transformer(op_Sub, gen_Sub);
+       register_transformer(op_And, gen_And);
+       register_transformer(op_Or,  gen_Or);
+       register_transformer(op_Eor, gen_Eor);
+       register_transformer(op_Shl, gen_Shl);
+       register_transformer(op_Shr, gen_Shr);
+       register_transformer(op_Shrs, gen_Shrs);
+       register_transformer(op_Not, gen_Not);
+       register_transformer(op_Minus, gen_Minus);
+       register_transformer(op_Div, gen_Div);
+       register_transformer(op_Mod, gen_Mod);
+       register_transformer(op_DivMod, gen_DivMod);
+       register_transformer(op_Abs, gen_Abs);
+       register_transformer(op_Load, gen_Load);
+       register_transformer(op_Store, gen_Store);
+       register_transformer(op_Cond, gen_Cond);
+       register_transformer(op_Conv, gen_Conv);
+       register_transformer(op_Const, gen_Const);
+       register_transformer(op_SymConst, gen_SymConst);
+       register_transformer(op_Unknown, gen_Unknown);
+       register_transformer(op_Proj, gen_Proj);
+       register_transformer(op_Phi, gen_Phi);
 }
 
 void mips_transform_graph(mips_code_gen_t *cg)
 {
-       env_cg = cg;
        register_transformers();
-       be_transform_graph(cg->birg, NULL, cg);
+       be_transform_graph(cg->birg, NULL);
 }
 
 /**