summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--ChangeLog8
-rw-r--r--bootstraptest/test_knownbug.rb24
-rw-r--r--bootstraptest/test_syntax.rb40
-rw-r--r--compile.c20
4 files changed, 64 insertions, 28 deletions
diff --git a/ChangeLog b/ChangeLog
index 94abdaad87..f4aadbc5af 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,11 @@
+Tue Dec 25 21:32:54 2007 Koichi Sasada <ko1@atdot.net>
+
+ * compile.c (iseq_compile_each): fix stack consistency error
+ (break is compiled to throw instead of jump insn).
+ these problems are reported by Yusuke ENDOH <mame AT tsg.ne.jp>
+
+ * bootstraptest/test_knownbug.rb, test_syntax.rb: move fixed test.
+
Tue Dec 25 21:32:44 2007 Tanaka Akira <akr@fsij.org>
* parse.y (struct parser_params): make parser_ruby_sourcefile common
diff --git a/bootstraptest/test_knownbug.rb b/bootstraptest/test_knownbug.rb
index 24e3c5483a..39dc6a9b8b 100644
--- a/bootstraptest/test_knownbug.rb
+++ b/bootstraptest/test_knownbug.rb
@@ -2,27 +2,3 @@
# This test file concludes tests which point out known bugs.
# So all tests will cause failure.
#
-
-assert_normal_exit %q{
- begin
- raise
- rescue
- counter = 2
- while true
- counter -= 1
- break if counter == 0
- next
- retry
- end
- end
-}, 'reported by Yusuke ENDOH'
-
-assert_normal_exit %q{
- counter = 2
- while true
- counter -= 1
- break if counter == 0
- next
- "#{ break }"
- end
-}, 'reported by Yusuke ENDOH'
diff --git a/bootstraptest/test_syntax.rb b/bootstraptest/test_syntax.rb
index 8d87ab990b..ed47d59876 100644
--- a/bootstraptest/test_syntax.rb
+++ b/bootstraptest/test_syntax.rb
@@ -689,7 +689,7 @@ assert_equal 'ok', %q{
"#{next}"
end
:ok
-}
+}, 'reported by Yusuke ENDOH'
assert_equal 'ok', %q{
counter = 2
@@ -700,7 +700,7 @@ assert_equal 'ok', %q{
redo
end
:ok
-}
+}, 'reported by Yusuke ENDOH'
assert_equal 'ok', %q{
counter = 2
@@ -711,4 +711,38 @@ assert_equal 'ok', %q{
"#{ redo }"
end
:ok
-}
+}, 'reported by Yusuke ENDOH'
+
+assert_normal_exit %q{
+ begin
+ raise
+ rescue
+ counter = 2
+ while true
+ counter -= 1
+ break if counter == 0
+ next
+ retry
+ end
+ end
+}, 'reported by Yusuke ENDOH'
+
+assert_normal_exit %q{
+ counter = 2
+ while true
+ counter -= 1
+ break if counter == 0
+ next
+ "#{ break }"
+ end
+}, 'reported by Yusuke ENDOH'
+
+assert_normal_exit %q{
+ counter = 2
+ while true
+ counter -= 1
+ next if counter != 0
+ "#{ break }"
+ end
+}, 'reported by Yusuke ENDOH'
+
diff --git a/compile.c b/compile.c
index 1960a3fa99..1e26d45419 100644
--- a/compile.c
+++ b/compile.c
@@ -2924,12 +2924,26 @@ iseq_compile_each(rb_iseq_t *iseq, LINK_ANCHOR *ret, NODE * node, int poped)
if (iseq->compile_data->redo_label != 0) {
/* while/until */
+#if 0
add_ensure_iseq(ret, iseq);
COMPILE_(ret, "break val (while/until)", node->nd_stts,
iseq->compile_data->loopval_popped);
ADD_INSNL(ret, nd_line(node), jump,
iseq->compile_data->end_label);
- ADD_INSN(ret, nd_line(node), pop);
+
+ if (poped) {
+ ADD_INSN(ret, nd_line(node), pop);
+ }
+#else
+ level = 0x8000 | 0x4000;
+ COMPILE(ret, "break val (while/until)", node->nd_stts);
+ ADD_INSN1(ret, nd_line(node), throw,
+ INT2FIX(level | 0x02) /* TAG_BREAK */ );
+
+ if (poped) {
+ ADD_INSN(ret, nd_line(node), pop);
+ }
+#endif
}
else if (iseq->type == ISEQ_TYPE_BLOCK) {
break_by_insn:
@@ -3089,6 +3103,10 @@ iseq_compile_each(rb_iseq_t *iseq, LINK_ANCHOR *ret, NODE * node, int poped)
ADD_INSN(ret, nd_line(node), putnil);
ADD_INSN1(ret, nd_line(node), throw,
INT2FIX(0x04) /* TAG_RETRY */ );
+
+ if (poped) {
+ ADD_INSN(ret, nd_line(node), pop);
+ }
}
else {
COMPILE_ERROR((ERROR_ARGS "Invalid retry"));