diff options
| -rw-r--r-- | include/mruby.h | 1 | ||||
| -rw-r--r-- | mrbgems/mruby-time/src/time.c | 3 | ||||
| -rw-r--r-- | src/class.c | 6 | ||||
| -rw-r--r-- | src/error.c | 16 | ||||
| -rw-r--r-- | src/state.c | 6 | ||||
| -rw-r--r-- | src/vm.c | 25 | ||||
| -rw-r--r-- | test/driver.c | 36 |
7 files changed, 67 insertions, 26 deletions
diff --git a/include/mruby.h b/include/mruby.h index b112b081c..e058d409f 100644 --- a/include/mruby.h +++ b/include/mruby.h @@ -156,6 +156,7 @@ void mrb_undef_class_method(mrb_state*, struct RClass*, const char*); mrb_value mrb_instance_new(mrb_state *mrb, mrb_value cv); struct RClass * mrb_class_new(mrb_state *mrb, struct RClass *super); struct RClass * mrb_module_new(mrb_state *mrb); +int mrb_class_defined(mrb_state *mrb, const char *name); struct RClass * mrb_class_get(mrb_state *mrb, const char *name); struct RClass * mrb_class_obj_get(mrb_state *mrb, const char *name); diff --git a/mrbgems/mruby-time/src/time.c b/mrbgems/mruby-time/src/time.c index 3d806c140..74882e1e8 100644 --- a/mrbgems/mruby-time/src/time.c +++ b/mrbgems/mruby-time/src/time.c @@ -528,6 +528,8 @@ mrb_time_initialize(mrb_state *mrb, mrb_value self) if (tm) { mrb_time_free(mrb, tm); } + DATA_TYPE(self) = &mrb_time_type; + DATA_PTR(self) = NULL; n = mrb_get_args(mrb, "|iiiiiii", &ayear, &amonth, &aday, &ahour, &amin, &asec, &ausec); @@ -538,7 +540,6 @@ mrb_time_initialize(mrb_state *mrb, mrb_value self) tm = time_mktime(mrb, ayear, amonth, aday, ahour, amin, asec, ausec, MRB_TIMEZONE_LOCAL); } DATA_PTR(self) = tm; - DATA_TYPE(self) = &mrb_time_type; return self; } diff --git a/src/class.c b/src/class.c index 0ba702919..a00000375 100644 --- a/src/class.c +++ b/src/class.c @@ -203,6 +203,12 @@ mrb_vm_define_class(mrb_state *mrb, mrb_value outer, mrb_value super, mrb_sym id return c; } +int +mrb_class_defined(mrb_state *mrb, const char *name) +{ + return mrb_const_defined(mrb, mrb_obj_value(mrb->object_class), mrb_intern(mrb, name)); +} + static struct RClass * class_from_sym(mrb_state *mrb, struct RClass *klass, mrb_sym id) { diff --git a/src/error.c b/src/error.c index 421321c3d..6bd891768 100644 --- a/src/error.c +++ b/src/error.c @@ -5,6 +5,7 @@ */ #include "mruby.h" +#include <errno.h> #include <stdarg.h> #include <setjmp.h> #include <string.h> @@ -401,7 +402,20 @@ mrb_make_exception(mrb_state *mrb, int argc, mrb_value *argv) void mrb_sys_fail(mrb_state *mrb, const char *mesg) { - mrb_raise(mrb, E_RUNTIME_ERROR, mesg); + struct RClass *sce; + mrb_int no; + + no = (mrb_int)errno; + if (mrb_class_defined(mrb, "SystemCallError")) { + sce = mrb_class_get(mrb, "SystemCallError"); + if (mesg != NULL) { + mrb_funcall(mrb, mrb_obj_value(sce), "_sys_fail", 2, mrb_fixnum_value(no), mrb_str_new_cstr(mrb, mesg)); + } else { + mrb_funcall(mrb, mrb_obj_value(sce), "_sys_fail", 1, mrb_fixnum_value(no)); + } + } else { + mrb_raise(mrb, E_RUNTIME_ERROR, mesg); + } } void diff --git a/src/state.c b/src/state.c index b6805a4a4..efb6d66b1 100644 --- a/src/state.c +++ b/src/state.c @@ -53,6 +53,7 @@ mrb_alloca(mrb_state *mrb, size_t size) struct alloca_header *p; p = (struct alloca_header*) mrb_malloc(mrb, sizeof(struct alloca_header)+size); + if (p == NULL) return NULL; p->next = mrb->mems; mrb->mems = p; return (void*)p->buf; @@ -61,9 +62,12 @@ mrb_alloca(mrb_state *mrb, size_t size) static void mrb_alloca_free(mrb_state *mrb) { - struct alloca_header *p = mrb->mems; + struct alloca_header *p; struct alloca_header *tmp; + if (mrb == NULL) return NULL; + p = mrb->mems; + while (p) { tmp = p; p = p->next; @@ -55,12 +55,20 @@ The value below allows about 60000 recursive calls in the simplest case. */ #endif static inline void -stack_copy(mrb_value *dst, const mrb_value *src, size_t size) +stack_clear(mrb_value *from, size_t count) { - size_t i; + const mrb_value mrb_value_zero = { { 0 } }; + + while(count-- > 0) { + *from++ = mrb_value_zero; + } +} - for (i = 0; i < size; i++) { - dst[i] = src[i]; +static inline void +stack_copy(mrb_value *dst, const mrb_value *src, size_t size) +{ + while (size-- > 0) { + *dst++ = *src++; } } @@ -130,15 +138,14 @@ stack_extend(mrb_state *mrb, int room, int keep) } if (room > keep) { - int i; - for (i=keep; i<room; i++) { #ifndef MRB_NAN_BOXING - static const mrb_value mrb_value_zero = { { 0 } }; - mrb->stack[i] = mrb_value_zero; + stack_clear(&(mrb->stack[keep]), room - keep); #else + int i; + for (i=keep; i<room; i++) { SET_NIL_VALUE(mrb->stack[i]); -#endif } +#endif } } diff --git a/test/driver.c b/test/driver.c index eda82a7f2..4a7a7b25e 100644 --- a/test/driver.c +++ b/test/driver.c @@ -36,13 +36,31 @@ check_error(mrb_state *mrb) return mrb_fixnum_p(ko_test) && mrb_fixnum(ko_test) == 0 && mrb_fixnum_p(kill_test) && mrb_fixnum(kill_test) == 0; } +static int +eval_test(mrb_state *mrb) +{ + mrb_value return_value; + const char *prog = "report()"; + + /* evaluate the test */ + return_value = mrb_load_string(mrb, prog); + /* did an exception occur? */ + if (mrb->exc) { + mrb_p(mrb, return_value); + mrb->exc = 0; + return EXIT_FAILURE; + } + else if (!check_error(mrb)) { + return EXIT_FAILURE; + } + return EXIT_SUCCESS; +} + int main(int argc, char **argv) { mrb_state *mrb; - mrb_value return_value; - const char *prog = "report()"; - int ret = EXIT_SUCCESS; + int ret; print_hint(); @@ -59,17 +77,7 @@ main(int argc, char **argv) } mrb_init_mrbtest(mrb); - /* evaluate the test */ - return_value = mrb_load_string(mrb, prog); - /* did an exception occur? */ - if (mrb->exc) { - mrb_p(mrb, return_value); - mrb->exc = 0; - ret = EXIT_FAILURE; - } - else if (!check_error(mrb)) { - ret = EXIT_FAILURE; - } + ret = eval_test(mrb); mrb_close(mrb); return ret; |
