removed unimplemented extension
[libfirm] / ir / ir / ircons.c
index 9e28bd1..04b8f0b 100644 (file)
@@ -56,13 +56,20 @@ ir_node *new_rd_Const_long(dbg_info *db, ir_graph *irg, ir_mode *mode,
        return new_rd_Const(db, irg, new_tarval_from_long(value, mode));
 }
 
-ir_node *new_rd_ASM(dbg_info *db, ir_node *block, int arity, ir_node *in[],
-                    ir_asm_constraint *inputs, size_t n_outs,
-                       ir_asm_constraint *outputs, size_t n_clobber,
+ir_node *new_rd_ASM(dbg_info *db, ir_node *block, ir_node *mem,
+                    int arity, ir_node *in[], ir_asm_constraint *inputs,
+                    size_t n_outs, ir_asm_constraint *outputs, size_t n_clobber,
                        ident *clobber[], ident *text)
 {
        ir_graph *irg = get_irn_irg(block);
-       ir_node  *res = new_ir_node(db, irg, block, op_ASM, mode_T, arity, in);
+
+       int r_arity = arity+1;
+       ir_node **r_in;
+       NEW_ARR_A(ir_node*, r_in, r_arity);
+       r_in[0] = mem;
+       memcpy(&r_in[1], in, arity*sizeof(ir_node*));
+
+       ir_node *res = new_ir_node(db, irg, block, op_ASM, mode_T, r_arity, r_in);
 
        res->attr.assem.pin_state = op_pin_state_pinned;
        res->attr.assem.input_constraints
@@ -142,12 +149,12 @@ ir_node *new_r_simpleSel(ir_node *block, ir_node *store, ir_node *objptr,
 {
        return new_rd_Sel(NULL, block, store, objptr, 0, NULL, ent);
 }
-ir_node *new_r_ASM(ir_node *block,
+ir_node *new_r_ASM(ir_node *block, ir_node *mem,
                    int arity, ir_node *in[], ir_asm_constraint *inputs,
                    size_t n_outs, ir_asm_constraint *outputs,
                    size_t n_clobber, ident *clobber[], ident *text)
 {
-       return new_rd_ASM(NULL, block, arity, in, inputs, n_outs, outputs, n_clobber, clobber, text);
+       return new_rd_ASM(NULL, block, mem, arity, in, inputs, n_outs, outputs, n_clobber, clobber, text);
 }
 
 /** Creates a Phi node with 0 predecessors. */
@@ -223,8 +230,6 @@ static ir_node *set_phi_arguments(ir_node *phi, int pos)
                if (is_Bad(cfgpred)) {
                        value = new_r_Bad(irg, mode);
                } else {
-                       inc_irg_visited(irg);
-
                        value = get_r_value_internal(cfgpred, pos, mode);
                }
                in[i] = value;
@@ -232,13 +237,12 @@ static ir_node *set_phi_arguments(ir_node *phi, int pos)
 
        phi->attr.phi.u.backedge = new_backedge_arr(irg->obst, arity);
        set_irn_in(phi, arity, in);
-       set_irn_op(phi, op_Phi);
 
        irn_verify_irg(phi, irg);
 
        /* Memory Phis in endless loops must be kept alive.
           As we can't distinguish these easily we keep all of them alive. */
-       if (is_Phi(phi) && mode == mode_M)
+       if (mode == mode_M)
                add_End_keepalive(get_irg_end(irg), phi);
 
        try_remove_unnecessary_phi(phi);
@@ -262,24 +266,23 @@ static ir_node *get_r_value_internal(ir_node *block, int pos, ir_mode *mode)
        if (res != NULL)
                return res;
 
-       /* We ran into a cycle. This may happen in unreachable loops. */
-       if (irn_visited_else_mark(block)) {
-               /* Since the loop is unreachable, return a Bad. */
-               return new_r_Bad(irg, mode);
-       }
-
        /* in a matured block we can immediately determine the phi arguments */
        if (get_Block_matured(block)) {
                int arity = get_irn_arity(block);
                /* no predecessors: use unknown value */
-               if (arity == 0 && block == get_irg_start_block(get_irn_irg(block))) {
-                       if (default_initialize_local_variable != NULL) {
-                               ir_node *rem = get_r_cur_block(irg);
-                               set_r_cur_block(irg, block);
-                               res = default_initialize_local_variable(irg, mode, pos - 1);
-                               set_r_cur_block(irg, rem);
+               if (arity == 0) {
+                       if (block == get_irg_start_block(irg)) {
+                               if (default_initialize_local_variable != NULL) {
+                                       ir_node *rem = get_r_cur_block(irg);
+                                       set_r_cur_block(irg, block);
+                                       res = default_initialize_local_variable(irg, mode, pos - 1);
+                                       set_r_cur_block(irg, rem);
+                               } else {
+                                       res = new_r_Unknown(irg, mode);
+                               }
                        } else {
-                               res = new_r_Unknown(irg, mode);
+                               /* unreachable block, use Bad */
+                               res = new_r_Bad(irg, mode);
                        }
                /* one predecessor just use its value */
                } else if (arity == 1) {
@@ -314,6 +317,7 @@ void mature_immBlock(ir_node *block)
        size_t   n_preds;
        ir_node  *next;
        ir_node  *phi;
+       ir_node **new_in;
        ir_graph *irg;
 
        assert(is_Block(block));
@@ -340,6 +344,15 @@ void mature_immBlock(ir_node *block)
 
        set_Block_matured(block, 1);
 
+       /* create final in-array for the block */
+       if (block->attr.block.dynamic_ins) {
+               new_in = NEW_ARR_D(ir_node*, irg->obst, n_preds+1);
+               memcpy(new_in, block->in, (n_preds+1) * sizeof(new_in[0]));
+               DEL_ARR_F(block->in);
+               block->in = new_in;
+               block->attr.block.dynamic_ins = false;
+       }
+
        /* Now, as the block is a finished Firm node, we can optimize it.
           Since other nodes have been allocated since the block was created
           we can not free the node on the obstack.  Therefore we have to call
@@ -349,19 +362,19 @@ void mature_immBlock(ir_node *block)
           We can call optimize_in_place_2(), as global cse has no effect on blocks.
         */
        irn_verify_irg(block, irg);
-       block = optimize_in_place_2(block);
+       optimize_in_place_2(block);
 }
 
 ir_node *new_d_Const_long(dbg_info *db, ir_mode *mode, long value)
 {
-       assert(get_irg_phase_state(current_ir_graph) == phase_building);
+       assert(irg_is_constrained(current_ir_graph, IR_GRAPH_CONSTRAINT_CONSTRUCTION));
        return new_rd_Const_long(db, current_ir_graph, mode, value);
 }
 
 ir_node *new_d_simpleSel(dbg_info *db, ir_node *store, ir_node *objptr,
                          ir_entity *ent)
 {
-       assert(get_irg_phase_state(current_ir_graph) == phase_building);
+       assert(irg_is_constrained(current_ir_graph, IR_GRAPH_CONSTRAINT_CONSTRUCTION));
        return new_rd_Sel(db, current_ir_graph->current_block,
                          store, objptr, 0, NULL, ent);
 }
@@ -369,51 +382,18 @@ ir_node *new_d_simpleSel(dbg_info *db, ir_node *store, ir_node *objptr,
 ir_node *new_d_SymConst(dbg_info *db, ir_mode *mode, symconst_symbol value,
                         symconst_kind kind)
 {
-       assert(get_irg_phase_state(current_ir_graph) == phase_building);
+       assert(irg_is_constrained(current_ir_graph, IR_GRAPH_CONSTRAINT_CONSTRUCTION));
        return new_rd_SymConst(db, current_ir_graph, mode, value, kind);
 }
 
-ir_node *new_d_ASM(dbg_info *db, int arity, ir_node *in[],
+ir_node *new_d_ASM(dbg_info *db, ir_node *mem, int arity, ir_node *in[],
                    ir_asm_constraint *inputs,
                    size_t n_outs, ir_asm_constraint *outputs,
                    size_t n_clobber, ident *clobber[], ident *text)
 {
-       assert(get_irg_phase_state(current_ir_graph) == phase_building);
-       return new_rd_ASM(db, current_ir_graph->current_block, arity, in, inputs,
-                         n_outs, outputs, n_clobber, clobber, text);
-}
-
-ir_node *new_rd_strictConv(dbg_info *dbgi, ir_node *block, ir_node * irn_op, ir_mode * mode)
-{
-       ir_node *res;
-       ir_graph *irg = get_Block_irg(block);
-
-       ir_node *in[1];
-       in[0] = irn_op;
-
-       res = new_ir_node(dbgi, irg, block, op_Conv, mode, 1, in);
-       res->attr.conv.strict = 1;
-       irn_verify_irg(res, irg);
-       res = optimize_node(res);
-       return res;
-}
-
-ir_node *new_r_strictConv(ir_node *block, ir_node * irn_op, ir_mode * mode)
-{
-       return new_rd_strictConv(NULL, block, irn_op, mode);
-}
-
-ir_node *new_d_strictConv(dbg_info *dbgi, ir_node * irn_op, ir_mode * mode)
-{
-       ir_node *res;
-       assert(get_irg_phase_state(current_ir_graph) == phase_building);
-       res = new_rd_strictConv(dbgi, current_ir_graph->current_block, irn_op, mode);
-       return res;
-}
-
-ir_node *new_strictConv(ir_node * irn_op, ir_mode * mode)
-{
-       return new_d_strictConv(NULL, irn_op, mode);
+       assert(irg_is_constrained(current_ir_graph, IR_GRAPH_CONSTRAINT_CONSTRUCTION));
+       return new_rd_ASM(db, current_ir_graph->current_block, mem, arity, in,
+                         inputs, n_outs, outputs, n_clobber, clobber, text);
 }
 
 ir_node *new_rd_DivRL(dbg_info *dbgi, ir_node *block, ir_node * irn_mem, ir_node * irn_left, ir_node * irn_right, ir_mode* resmode, op_pin_state pin_state)
@@ -443,7 +423,7 @@ ir_node *new_r_DivRL(ir_node *block, ir_node * irn_mem, ir_node * irn_left, ir_n
 ir_node *new_d_DivRL(dbg_info *dbgi, ir_node * irn_mem, ir_node * irn_left, ir_node * irn_right, ir_mode* resmode, op_pin_state pin_state)
 {
        ir_node *res;
-       assert(get_irg_phase_state(current_ir_graph) == phase_building);
+       assert(irg_is_constrained(current_ir_graph, IR_GRAPH_CONSTRAINT_CONSTRUCTION));
        res = new_rd_DivRL(dbgi, current_ir_graph->current_block, irn_mem, irn_left, irn_right, resmode, pin_state);
        return res;
 }
@@ -457,16 +437,14 @@ ir_node *new_rd_immBlock(dbg_info *dbgi, ir_graph *irg)
 {
        ir_node *res;
 
-       assert(get_irg_phase_state(irg) == phase_building);
+       assert(irg_is_constrained(irg, IR_GRAPH_CONSTRAINT_CONSTRUCTION));
        /* creates a new dynamic in-array as length of in is -1 */
        res = new_ir_node(dbgi, irg, NULL, op_Block, mode_BB, -1, NULL);
 
        set_Block_matured(res, 0);
+       res->attr.block.dynamic_ins = true;
        res->attr.block.irg.irg     = irg;
        res->attr.block.backedge    = NULL;
-       res->attr.block.in_cg       = NULL;
-       res->attr.block.cg_backedge = NULL;
-       res->attr.block.extblk      = NULL;
        res->attr.block.entity      = NULL;
 
        set_Block_block_visited(res, 0);
@@ -516,13 +494,15 @@ void set_cur_block(ir_node *target)
 
 void set_r_cur_block(ir_graph *irg, ir_node *target)
 {
-       assert(target == NULL || get_irn_mode(target) == mode_BB);
-       assert(target == NULL || get_irn_irg(target)  == irg);
+       assert(irg_is_constrained(irg, IR_GRAPH_CONSTRAINT_CONSTRUCTION));
+       assert(target == NULL || is_Block(target));
+       assert(target == NULL || get_irn_irg(target) == irg);
        irg->current_block = target;
 }
 
 ir_node *get_r_cur_block(ir_graph *irg)
 {
+       assert(irg_is_constrained(irg, IR_GRAPH_CONSTRAINT_CONSTRUCTION));
        return irg->current_block;
 }
 
@@ -533,9 +513,8 @@ ir_node *get_cur_block(void)
 
 ir_node *get_r_value(ir_graph *irg, int pos, ir_mode *mode)
 {
-       assert(get_irg_phase_state(irg) == phase_building);
+       assert(irg_is_constrained(irg, IR_GRAPH_CONSTRAINT_CONSTRUCTION));
        assert(pos >= 0);
-       inc_irg_visited(irg);
 
        return get_r_value_internal(irg->current_block, pos + 1, mode);
 }
@@ -601,7 +580,7 @@ ir_mode *ir_guess_mode(int pos)
 
 void set_r_value(ir_graph *irg, int pos, ir_node *value)
 {
-       assert(get_irg_phase_state(irg) == phase_building);
+       assert(irg_is_constrained(irg, IR_GRAPH_CONSTRAINT_CONSTRUCTION));
        assert(pos >= 0);
        assert(pos+1 < irg->n_loc);
        assert(is_ir_node(value));
@@ -613,27 +592,9 @@ void set_value(int pos, ir_node *value)
        set_r_value(current_ir_graph, pos, value);
 }
 
-int r_find_value(ir_graph *irg, ir_node *value)
-{
-       size_t i;
-       ir_node *bl = irg->current_block;
-
-       for (i = ARR_LEN(bl->attr.block.graph_arr); i > 1;) {
-               if (bl->attr.block.graph_arr[--i] == value)
-                       return i - 1;
-       }
-       return -1;
-}
-
-int find_value(ir_node *value)
-{
-       return r_find_value(current_ir_graph, value);
-}
-
 ir_node *get_r_store(ir_graph *irg)
 {
-       assert(get_irg_phase_state(irg) == phase_building);
-       inc_irg_visited(irg);
+       assert(irg_is_constrained(irg, IR_GRAPH_CONSTRAINT_CONSTRUCTION));
        return get_r_value_internal(irg->current_block, 0, mode_M);
 }
 
@@ -646,7 +607,7 @@ void set_r_store(ir_graph *irg, ir_node *store)
 {
        ir_node *load, *pload, *pred, *in[2];
 
-       assert(get_irg_phase_state(irg) == phase_building);
+       assert(irg_is_constrained(irg, IR_GRAPH_CONSTRAINT_CONSTRUCTION));
        /* Beware: due to dead code elimination, a store might become a Bad node even in
           the construction phase. */
        assert((get_irn_mode(store) == mode_M || is_Bad(store)) && "storing non-memory node");
@@ -699,7 +660,10 @@ void ir_set_uninitialized_local_variable_func(
 
 void irg_finalize_cons(ir_graph *irg)
 {
-       set_irg_phase_state(irg, phase_high);
+       ir_node *end_block = get_irg_end_block(irg);
+       mature_immBlock(end_block);
+
+       clear_irg_constraints(irg, IR_GRAPH_CONSTRAINT_CONSTRUCTION);
 }
 
 void irp_finalize_cons(void)
@@ -708,7 +672,6 @@ void irp_finalize_cons(void)
        for (i = 0, n = get_irp_n_irgs(); i < n; ++i) {
                irg_finalize_cons(get_irp_irg(i));
        }
-       irp->phase_state = phase_high;
 }
 
 ir_node *new_Const_long(ir_mode *mode, long value)
@@ -724,11 +687,12 @@ ir_node *new_simpleSel(ir_node *store, ir_node *objptr, ir_entity *ent)
 {
        return new_d_simpleSel(NULL, store, objptr, ent);
 }
-ir_node *new_ASM(int arity, ir_node *in[], ir_asm_constraint *inputs,
-                 size_t n_outs, ir_asm_constraint *outputs,
-                 size_t n_clobber, ident *clobber[], ident *text)
+ir_node *new_ASM(ir_node *mem, int arity, ir_node *in[],
+                 ir_asm_constraint *inputs, size_t n_outs,
+                 ir_asm_constraint *outputs, size_t n_clobber,
+                 ident *clobber[], ident *text)
 {
-       return new_d_ASM(NULL, arity, in, inputs, n_outs, outputs, n_clobber, clobber, text);
+       return new_d_ASM(NULL, mem, arity, in, inputs, n_outs, outputs, n_clobber, clobber, text);
 }
 
 ir_node *new_r_Anchor(ir_graph *irg)
@@ -759,7 +723,7 @@ ir_node *new_r_Block_noopt(ir_graph *irg, int arity, ir_node *in[])
        res->attr.block.backedge = new_backedge_arr(irg->obst, arity);
        set_Block_matured(res, 1);
        /* Create and initialize array for Phi-node construction. */
-       if (get_irg_phase_state(irg) == phase_building) {
+       if (irg_is_constrained(irg, IR_GRAPH_CONSTRAINT_CONSTRUCTION)) {
                res->attr.block.graph_arr = NEW_ARR_D(ir_node *, irg->obst, irg->n_loc);
                memset(res->attr.block.graph_arr, 0, irg->n_loc * sizeof(ir_node*));
        }