summaryrefslogtreecommitdiffhomepage
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/backtrace.c1
-rw-r--r--src/codedump.c3
-rw-r--r--src/gc.c5
-rw-r--r--src/kernel.c11
-rw-r--r--src/string.c2
-rw-r--r--src/vm.c28
6 files changed, 35 insertions, 15 deletions
diff --git a/src/backtrace.c b/src/backtrace.c
index b499cee5a..051d5d4e0 100644
--- a/src/backtrace.c
+++ b/src/backtrace.c
@@ -118,6 +118,7 @@ each_backtrace(mrb_state *mrb, mrb_int ciidx, mrb_code *pc0, each_backtrace_func
if (MRB_PROC_CFUNC_P(ci->proc)) continue;
irep = ci->proc->body.irep;
+ if (!irep) continue;
if (mrb->c->cibase[i].err) {
pc = mrb->c->cibase[i].err;
diff --git a/src/codedump.c b/src/codedump.c
index 4b13d4361..59ba4fdae 100644
--- a/src/codedump.c
+++ b/src/codedump.c
@@ -416,8 +416,7 @@ codedump(mrb_state *mrb, mrb_irep *irep)
print_lv(mrb, irep, c, RA);
break;
case OP_POPERR:
- printf("OP_POPERR\t%d\t\t", GETARG_A(c));
- print_lv(mrb, irep, c, RA);
+ printf("OP_POPERR\t%d\t\t\n", GETARG_A(c));
break;
case OP_EPOP:
printf("OP_EPOP\t%d\n", GETARG_A(c));
diff --git a/src/gc.c b/src/gc.c
index 88d157d9c..1608dbcb2 100644
--- a/src/gc.c
+++ b/src/gc.c
@@ -857,7 +857,12 @@ root_scan_phase(mrb_state *mrb, mrb_gc *gc)
mrb_gc_mark(mrb, (struct RBasic*)mrb->top_self);
/* mark exception */
mrb_gc_mark(mrb, (struct RBasic*)mrb->exc);
+ /* mark backtrace */
mrb_gc_mark(mrb, (struct RBasic*)mrb->backtrace.exc);
+ e = (size_t)mrb->backtrace.n;
+ for (i=0; i<e; i++) {
+ mrb_gc_mark(mrb, (struct RBasic*)mrb->backtrace.entries[i].klass);
+ }
/* mark pre-allocated exception */
mrb_gc_mark(mrb, (struct RBasic*)mrb->nomem_err);
#ifdef MRB_GC_FIXED_ARENA
diff --git a/src/kernel.c b/src/kernel.c
index 5ca1736c3..8b00d701b 100644
--- a/src/kernel.c
+++ b/src/kernel.c
@@ -6,6 +6,7 @@
#include <mruby.h>
#include <mruby/array.h>
+#include <mruby/hash.h>
#include <mruby/class.h>
#include <mruby/proc.h>
#include <mruby/string.h>
@@ -1106,8 +1107,8 @@ mrb_obj_ceqq(mrb_state *mrb, mrb_value self)
static mrb_value
mrb_local_variables(mrb_state *mrb, mrb_value self)
{
- mrb_value ret;
struct RProc *proc;
+ mrb_value vars;
struct mrb_irep *irep;
size_t i;
@@ -1121,10 +1122,10 @@ mrb_local_variables(mrb_state *mrb, mrb_value self)
if (!irep->lv) {
return mrb_ary_new(mrb);
}
- ret = mrb_ary_new_capa(mrb, irep->nlocals - 1);
+ vars = mrb_hash_new(mrb);
for (i = 0; i + 1 < irep->nlocals; ++i) {
if (irep->lv[i].name) {
- mrb_ary_push(mrb, ret, mrb_symbol_value(irep->lv[i].name));
+ mrb_hash_set(mrb, vars, mrb_symbol_value(irep->lv[i].name), mrb_true_value());
}
}
if (proc->env) {
@@ -1137,7 +1138,7 @@ mrb_local_variables(mrb_state *mrb, mrb_value self)
if (irep->lv) {
for (i = 0; i + 1 < irep->nlocals; ++i) {
if (irep->lv[i].name) {
- mrb_ary_push(mrb, ret, mrb_symbol_value(irep->lv[i].name));
+ mrb_hash_set(mrb, vars, mrb_symbol_value(irep->lv[i].name), mrb_true_value());
}
}
}
@@ -1146,7 +1147,7 @@ mrb_local_variables(mrb_state *mrb, mrb_value self)
}
}
- return ret;
+ return mrb_hash_keys(mrb, vars);
}
void
diff --git a/src/string.c b/src/string.c
index 7a75bb63e..c370e0723 100644
--- a/src/string.c
+++ b/src/string.c
@@ -2644,7 +2644,7 @@ mrb_str_inspect(mrb_state *mrb, mrb_value str)
}
#endif
c = *p;
- if (c == '"'|| c == '\\' || (c == '#' && IS_EVSTR(p, pend))) {
+ if (c == '"'|| c == '\\' || (c == '#' && IS_EVSTR(p+1, pend))) {
buf[0] = '\\'; buf[1] = c;
mrb_str_cat(mrb, result, buf, 2);
continue;
diff --git a/src/vm.c b/src/vm.c
index 0c0f5a4bb..e734775e2 100644
--- a/src/vm.c
+++ b/src/vm.c
@@ -1309,7 +1309,9 @@ RETRY_TRY_BLOCK:
else {
stack_extend(mrb, irep->nregs, ci->argc+2);
}
- regs[0] = m->env->stack[0];
+ if(m->env) {
+ regs[0] = m->env->stack[0];
+ }
pc = irep->iseq;
JUMP;
}
@@ -1364,11 +1366,22 @@ RETRY_TRY_BLOCK:
ci->mid = mid;
ci->proc = m;
ci->stackent = mrb->c->stack;
- if (n == CALL_MAXARGS) {
- ci->argc = -1;
- }
- else {
- ci->argc = n;
+ {
+ int bidx;
+ mrb_value blk;
+
+ if (n == CALL_MAXARGS) {
+ ci->argc = -1;
+ bidx = a+2;
+ }
+ else {
+ ci->argc = n;
+ bidx = a+n+1;
+ }
+ blk = regs[bidx];
+ if (!mrb_nil_p(blk) && mrb_type(blk) != MRB_TT_PROC) {
+ regs[bidx] = mrb_convert_type(mrb, blk, MRB_TT_PROC, "Proc", "to_proc");
+ }
}
ci->target_class = c;
ci->pc = pc + 1;
@@ -1705,9 +1718,10 @@ RETRY_TRY_BLOCK:
mrb->jmp = prev_jmp;
return v;
}
- cipop(mrb);
+ ci = mrb->c->ci;
acc = ci->acc;
mrb->c->stack = ci->stackent;
+ cipop(mrb);
if (acc == CI_ACC_SKIP) {
mrb->jmp = prev_jmp;
return v;