+ be_set_constr_single_reg(irn, be_pos_SubSP_old_sp, sp);
+ be_node_set_reg_class(irn, be_pos_SubSP_size, arch_register_get_class(sp));
+ be_set_constr_single_reg(irn, OUT_POS(pn_be_SubSP_sp), sp);
+ a->reg_data[pn_be_SubSP_sp].reg = sp;
+
+ return irn;
+}
+
+ir_node *be_new_RegParams(ir_graph *irg, ir_node *bl, int n_outs)
+{
+ ir_node *res;
+ int i;
+
+ res = new_ir_node(NULL, irg, bl, op_be_RegParams, mode_T, 0, NULL);
+ init_node_attr(res, -1);
+ for(i = 0; i < n_outs; ++i)
+ add_register_req(res);
+
+ return res;
+}
+
+ir_node *be_RegParams_append_out_reg(ir_node *regparams,
+ const arch_env_t *arch_env,
+ const arch_register_t *reg)
+{
+ ir_graph *irg = get_irn_irg(regparams);
+ ir_node *block = get_nodes_block(regparams);
+ be_node_attr_t *attr = get_irn_attr(regparams);
+ const arch_register_class_t *cls = arch_register_get_class(reg);
+ ir_mode *mode = arch_register_class_mode(cls);
+ int n = ARR_LEN(attr->reg_data);
+ ir_node *proj;
+
+ assert(be_is_RegParams(regparams));
+ proj = new_r_Proj(irg, block, regparams, mode, n);
+ add_register_req(regparams);
+ be_set_constr_single_reg(regparams, BE_OUT_POS(n), reg);
+ arch_set_irn_register(arch_env, proj, reg);
+
+ /* TODO decide, whether we need to set ignore/modify sp flags here? */
+
+ return proj;
+}
+
+ir_node *be_new_FrameAddr(const arch_register_class_t *cls_frame, ir_graph *irg, ir_node *bl, ir_node *frame, ir_entity *ent)
+{
+ be_frame_attr_t *a;
+ ir_node *irn;
+ ir_node *in[1];
+
+ in[0] = frame;
+ irn = new_ir_node(NULL, irg, bl, op_be_FrameAddr, get_irn_mode(frame), 1, in);
+ a = init_node_attr(irn, 1);
+ a->ent = ent;
+ a->offset = 0;
+ be_node_set_reg_class(irn, 0, cls_frame);
+ be_node_set_reg_class(irn, OUT_POS(0), cls_frame);
+
+ return optimize_node(irn);
+}
+
+ir_node *be_get_FrameAddr_frame(const ir_node *node) {
+ assert(be_is_FrameAddr(node));
+ return get_irn_n(node, be_pos_FrameAddr_ptr);
+}
+
+ir_entity *be_get_FrameAddr_entity(const ir_node *node)
+{
+ const be_frame_attr_t *attr = get_irn_generic_attr_const(node);
+ return attr->ent;
+}
+
+ir_node *be_new_CopyKeep(const arch_register_class_t *cls, ir_graph *irg, ir_node *bl, ir_node *src, int n, ir_node *in_keep[], ir_mode *mode)
+{
+ ir_node *irn;
+ ir_node **in = (ir_node **) alloca((n + 1) * sizeof(in[0]));
+
+ in[0] = src;
+ memcpy(&in[1], in_keep, n * sizeof(in[0]));
+ irn = new_ir_node(NULL, irg, bl, op_be_CopyKeep, mode, n + 1, in);
+ init_node_attr(irn, n + 1);
+ be_node_set_reg_class(irn, OUT_POS(0), cls);
+ be_node_set_reg_class(irn, 0, cls);
+
+ return irn;
+}
+
+ir_node *be_new_CopyKeep_single(const arch_register_class_t *cls, ir_graph *irg, ir_node *bl, ir_node *src, ir_node *keep, ir_mode *mode)
+{
+ return be_new_CopyKeep(cls, irg, bl, src, 1, &keep, mode);
+}
+
+ir_node *be_get_CopyKeep_op(const ir_node *cpy) {
+ return get_irn_n(cpy, be_pos_CopyKeep_op);
+}
+
+void be_set_CopyKeep_op(ir_node *cpy, ir_node *op) {
+ set_irn_n(cpy, be_pos_CopyKeep_op, op);
+}
+
+ir_node *be_new_Barrier(ir_graph *irg, ir_node *bl, int n, ir_node *in[])
+{
+ ir_node *res;
+ int i;
+
+ res = new_ir_node(NULL, irg, bl, op_be_Barrier, mode_T, -1, NULL);
+ init_node_attr(res, -1);
+ for(i = 0; i < n; ++i) {
+ add_irn_n(res, in[i]);
+ add_register_req(res);
+ }
+
+ return res;
+}
+
+ir_node *be_Barrier_append_node(ir_node *barrier, ir_node *node)
+{
+ ir_graph *irg = get_irn_irg(barrier);
+ ir_node *block = get_nodes_block(barrier);
+ ir_mode *mode = get_irn_mode(node);
+ int n = add_irn_n(barrier, node);
+
+ ir_node *proj = new_r_Proj(irg, block, barrier, mode, n);
+ add_register_req(barrier);
+
+ return proj;
+}
+
+/* Construct a new be_Unwind. */
+ir_node *be_new_Unwind(dbg_info *dbg, ir_graph *irg, ir_node *block,
+ ir_node *mem, ir_node *sp)
+{
+ ir_node *res;
+ ir_node *in[2];
+
+ in[be_pos_Unwind_mem] = mem;
+ in[be_pos_Unwind_sp] = sp;
+ res = new_ir_node(dbg, irg, block, op_be_Unwind, mode_X, 2, in);
+ init_node_attr(res, -1);
+
+ return res;
+}
+
+int be_has_frame_entity(const ir_node *irn)
+{
+ switch (get_irn_opcode(irn)) {
+ case beo_Spill:
+ case beo_Reload:
+ case beo_FrameAddr:
+ return 1;
+ default:
+ return 0;
+ }
+}
+
+ir_entity *be_get_frame_entity(const ir_node *irn)
+{
+ if (be_has_frame_entity(irn)) {
+ const be_frame_attr_t *a = get_irn_attr_const(irn);
+ return a->ent;
+ }
+ return NULL;
+}
+
+int be_get_frame_offset(const ir_node *irn)
+{
+ assert(is_be_node(irn));
+ if (be_has_frame_entity(irn)) {
+ const be_frame_attr_t *a = get_irn_attr_const(irn);
+ return a->offset;
+ }
+ return 0;
+}
+
+void be_set_MemPerm_in_entity(const ir_node *irn, int n, ir_entity *ent)
+{
+ const be_memperm_attr_t *attr = get_irn_attr_const(irn);
+
+ assert(be_is_MemPerm(irn));
+ assert(n < be_get_MemPerm_entity_arity(irn));