Revision: 1082 http://trac.macosforge.org/projects/ruby/changeset/1082 Author: lsansonetti@apple.com Date: 2009-03-22 21:50:22 -0700 (Sun, 22 Mar 2009) Log Message: ----------- implemented redo (works only for loops at the moment, and not blocks yet) Modified Paths: -------------- MacRuby/branches/experimental/roxor.cpp Modified: MacRuby/branches/experimental/roxor.cpp =================================================================== --- MacRuby/branches/experimental/roxor.cpp 2009-03-23 04:26:24 UTC (rev 1081) +++ MacRuby/branches/experimental/roxor.cpp 2009-03-23 04:50:22 UTC (rev 1082) @@ -193,6 +193,7 @@ Function *current_block_func; GlobalVariable *current_opened_class; BasicBlock *current_loop_begin_bb; + BasicBlock *current_loop_body_bb; BasicBlock *current_loop_end_bb; Value *current_loop_exit_val; @@ -503,6 +504,7 @@ current_block_func = NULL; current_opened_class = NULL; current_loop_begin_bb = NULL; + current_loop_body_bb = NULL; current_loop_end_bb = NULL; current_loop_exit_val = NULL; @@ -3005,9 +3007,11 @@ case NODE_BREAK: case NODE_NEXT: + case NODE_REDO: case NODE_RETURN: { const bool within_loop = current_loop_begin_bb != NULL + && current_loop_body_bb != NULL && current_loop_end_bb != NULL; if (!current_block && !within_loop) { @@ -3017,6 +3021,9 @@ if (nd_type(node) == NODE_NEXT) { rb_raise(rb_eLocalJumpError, "unexpected next"); } + if (nd_type(node) == NODE_REDO) { + rb_raise(rb_eLocalJumpError, "unexpected redo"); + } } Value *val = node->nd_head != NULL @@ -3030,6 +3037,9 @@ else if (nd_type(node) == NODE_NEXT) { BranchInst::Create(current_loop_begin_bb, bb); } + else if (nd_type(node) == NODE_REDO) { + BranchInst::Create(current_loop_body_bb, bb); + } else { ReturnInst::Create(val, bb); } @@ -3045,6 +3055,10 @@ params.push_back(val); CallInst::Create(breakFunc, params.begin(), params.end(), "", bb); } + else if (nd_type(node) == NODE_REDO) { + // TODO + abort(); + } ReturnInst::Create(val, bb); } @@ -3681,10 +3695,12 @@ } BasicBlock *old_current_loop_begin_bb = current_loop_begin_bb; + BasicBlock *old_current_loop_body_bb = current_loop_body_bb; BasicBlock *old_current_loop_end_bb = current_loop_end_bb; Value *old_current_loop_exit_val = current_loop_exit_val; current_loop_begin_bb = loopBB; + current_loop_body_bb = bodyBB; current_loop_end_bb = afterBB; current_loop_exit_val = NULL; @@ -3702,6 +3718,7 @@ } current_loop_begin_bb = old_current_loop_begin_bb; + current_loop_body_bb = old_current_loop_body_bb; current_loop_end_bb = old_current_loop_end_bb; current_loop_exit_val = old_current_loop_exit_val; @@ -3716,6 +3733,7 @@ current_block = true; BasicBlock *old_current_loop_begin_bb = current_loop_begin_bb; + BasicBlock *old_current_loop_body_bb = current_loop_body_bb; BasicBlock *old_current_loop_end_bb = current_loop_end_bb; current_loop_begin_bb = current_loop_end_bb = NULL; Function *old_current_block_func = current_block_func; @@ -3728,6 +3746,7 @@ assert(Function::classof(block)); current_loop_begin_bb = old_current_loop_begin_bb; + current_loop_body_bb = old_current_loop_body_bb; current_loop_end_bb = old_current_loop_end_bb; current_block = false; current_mid = old_current_mid;