ruby-changes:13914
From: nobu <ko1@a...>
Date: Wed, 11 Nov 2009 15:14:04 +0900 (JST)
Subject: [ruby-changes:13914] Ruby:r25718 (mvm): * merged from trunk r25704:25717.
nobu 2009-11-11 15:13:37 +0900 (Wed, 11 Nov 2009) New Revision: 25718 http://svn.ruby-lang.org/cgi-bin/viewvc.cgi?view=rev&revision=25718 Log: * merged from trunk r25704:25717. Modified files: branches/mvm/.merged-trunk-revision branches/mvm/ChangeLog branches/mvm/common.mk branches/mvm/dir.c branches/mvm/eval.c branches/mvm/eval_intern.h branches/mvm/file.c branches/mvm/gc.c branches/mvm/hash.c branches/mvm/include/ruby/ruby.h branches/mvm/include/ruby/vm.h branches/mvm/io.c branches/mvm/main.c branches/mvm/marshal.c branches/mvm/mvm.c branches/mvm/pack.c branches/mvm/parse.y branches/mvm/process.c branches/mvm/ruby.c branches/mvm/test/dl/test_func.rb branches/mvm/test/matrix/test_matrix.rb branches/mvm/thread.c branches/mvm/thread_pthread.c branches/mvm/util.c branches/mvm/version.h branches/mvm/vm.c branches/mvm/vm_core.h Index: mvm/eval_intern.h =================================================================== --- mvm/eval_intern.h (revision 25717) +++ mvm/eval_intern.h (revision 25718) @@ -221,6 +221,11 @@ void ruby_native_thread_lock(rb_thread_lock_t *lock); void ruby_native_thread_unlock(rb_thread_lock_t *lock); void ruby_native_thread_yield(void); +void ruby_native_cond_signal(pthread_cond_t *cond); +void ruby_native_cond_broadcast(pthread_cond_t *cond); +void ruby_native_cond_wait(pthread_cond_t *cond, pthread_mutex_t *mutex); +void ruby_native_cond_initialize(pthread_cond_t *cond); +void ruby_native_cond_destroy(pthread_cond_t *cond); VALUE ruby_vm_get_argv(rb_vm_t *vm); const char *ruby_vm_get_inplace_mode(rb_vm_t *vm); Index: mvm/include/ruby/ruby.h =================================================================== --- mvm/include/ruby/ruby.h (revision 25717) +++ mvm/include/ruby/ruby.h (revision 25718) @@ -1131,7 +1131,6 @@ VALUE rb_require(const char*); /* obsolete */ -void ruby_init(void); void *ruby_options(int, char**); int ruby_run_node(void *); int ruby_exec_node(void *); Index: mvm/include/ruby/vm.h =================================================================== --- mvm/include/ruby/vm.h (revision 25717) +++ mvm/include/ruby/vm.h (revision 25718) @@ -26,8 +26,10 @@ int ruby_vm_start(ruby_vm_t *vm); int ruby_vm_join(ruby_vm_t *vm); int ruby_vm_destruct(ruby_vm_t *vm); +void ruby_vm_die(ruby_vm_t *); /* initialize API */ +ruby_vm_t *ruby_init(void); int ruby_vm_init_add_argv(ruby_vm_t *vm, const char *arg); int ruby_vm_init_add_library(ruby_vm_t *vm, const char *lib); int ruby_vm_init_add_library_path(ruby_vm_t *vm, const char *path); @@ -60,6 +62,8 @@ struct rb_objspace; void *rb_objspace_xmalloc(struct rb_objspace *objspace, size_t size); void *rb_objspace_xrealloc(struct rb_objspace *objspace, void *ptr, size_t size); +void *rb_objspace_xmalloc2(struct rb_objspace *objspace, size_t n, size_t size); +void *rb_objspace_xrealloc2(struct rb_objspace *objspace, void *ptr, size_t n, size_t size); void rb_objspace_xfree(struct rb_objspace *objspace, void *ptr); #endif /* RUBY_VM_H */ Index: mvm/ChangeLog =================================================================== --- mvm/ChangeLog (revision 25717) +++ mvm/ChangeLog (revision 25718) @@ -1,3 +1,30 @@ +Wed Nov 11 12:54:02 2009 Nobuyoshi Nakada <nobu@r...> + + * hash.c (ruby_setenv): use ruby_strdup(). + +Wed Nov 11 12:19:27 2009 NAKAMURA Usaku <usa@r...> + + * hash.c (ruby_setenv): also set CRT workarea. ref [ruby-core:25010] + +Wed Nov 11 09:36:02 2009 Nobuyoshi Nakada <nobu@r...> + + * marshal.c (w_object, r_object0): use RHASH_IFNONE but not ifnone + directly. + +Wed Nov 11 08:32:45 2009 Tanaka Akira <akr@f...> + + * thread.c (blocking_region_begin): define before BLOCKING_REGION. + reported by Luis Lavena. [ruby-core:26670] + +Wed Nov 11 08:22:19 2009 Tanaka Akira <akr@f...> + + * util.c (ruby_strtod): use dval() consistently. + +Wed Nov 11 02:14:48 2009 Yuki Sonoda (Yugui) <yugui@y...> + + * test/matrix/test_matrix.rb (TestMatrix#test_rank): + added a test method for r24969. + Tue Nov 10 08:23:21 2009 Nobuyoshi Nakada <nobu@r...> * process.c (rb_f_exec, rb_f_system, rb_f_spawn): mentioned abou Index: mvm/thread_pthread.c =================================================================== --- mvm/thread_pthread.c (revision 25717) +++ mvm/thread_pthread.c (revision 25718) @@ -28,15 +28,6 @@ static int native_mutex_trylock(pthread_mutex_t *lock); -static void native_cond_signal(pthread_cond_t *cond); -static void native_cond_broadcast(pthread_cond_t *cond); -static void native_cond_wait(pthread_cond_t *cond, pthread_mutex_t *mutex); -static void native_cond_initialize(pthread_cond_t *cond); -static void native_cond_destroy(pthread_cond_t *cond); - -#define native_mutex_lock ruby_native_thread_lock -#define native_mutex_unlock ruby_native_thread_unlock - void ruby_native_thread_lock(pthread_mutex_t *lock) { @@ -88,8 +79,8 @@ } } -static void -native_cond_initialize(pthread_cond_t *cond) +void +ruby_native_cond_initialize(pthread_cond_t *cond) { int r = pthread_cond_init(cond, 0); if (r != 0) { @@ -97,7 +88,7 @@ } } -static void +void native_cond_destroy(pthread_cond_t *cond) { int r = pthread_cond_destroy(cond); @@ -106,25 +97,25 @@ } } -static void +void native_cond_signal(pthread_cond_t *cond) { pthread_cond_signal(cond); } -static void +void native_cond_broadcast(pthread_cond_t *cond) { pthread_cond_broadcast(cond); } -static void +void native_cond_wait(pthread_cond_t *cond, pthread_mutex_t *mutex) { pthread_cond_wait(cond, mutex); } -static int +int native_cond_timedwait(pthread_cond_t *cond, pthread_mutex_t *mutex, struct timespec *ts) { return pthread_cond_timedwait(cond, mutex, ts); @@ -507,7 +498,7 @@ RUBY_STACK_MIN_LIMIT), RUBY_STACK_SPACE_LIMIT = 1024 * 1024, RUBY_STACK_SPACE = (RUBY_STACK_MIN/5 > RUBY_STACK_SPACE_LIMIT ? - RUBY_STACK_SPACE_LIMIT : RUBY_STACK_MIN/5), + RUBY_STACK_SPACE_LIMIT : RUBY_STACK_MIN/5) }; #define CHECK_ERR(expr) \ Index: mvm/vm_core.h =================================================================== --- mvm/vm_core.h (revision 25717) +++ mvm/vm_core.h (revision 25718) @@ -267,6 +267,7 @@ typedef struct rb_vm_struct { VALUE self; + rb_thread_cond_t global_vm_waiting; rb_thread_lock_t global_vm_lock; VALUE global_state_version; @@ -669,6 +670,7 @@ int argc, const VALUE *argv, const rb_block_t *blockptr); VALUE rb_vm_make_proc(rb_thread_t *th, const rb_block_t *block, VALUE klass); VALUE rb_vm_make_env_object(rb_thread_t *th, rb_control_frame_t *cfp); +rb_vm_t *ruby_make_bare_vm(void); void *rb_thread_call_with_gvl(void *(*func)(void *), void *data1); int ruby_thread_has_gvl_p(void); @@ -683,6 +685,12 @@ void rb_mark_end_proc(struct end_proc_data **); void rb_exec_end_proc(struct end_proc_data **); +void *ruby_vm_xmalloc(struct rb_objspace *objspace, size_t size); +void *ruby_vm_xmalloc2(struct rb_objspace *objspace, size_t n, size_t size); +void *ruby_vm_xrealloc(struct rb_objspace *objspace, void *ptr, size_t size); +void *ruby_vm_xrealloc2(struct rb_objspace *objspace, void *ptr, size_t n, size_t size); +void ruby_vm_xfree(struct rb_objspace *objspace, void *ptr); + #define sysstack_error rb_errSysStack VALUE rb_str_resurrect(VALUE str); Index: mvm/io.c =================================================================== --- mvm/io.c (revision 25717) +++ mvm/io.c (revision 25718) @@ -4472,7 +4472,7 @@ const struct sysopen_struct *data = ptr; const char *fname = RSTRING_PTR(data->fname); #if USE_OPENAT - return (VALUE)openat(data->base, data->fname, data->oflags, data->perm); + return (VALUE)openat(data->base, RSTRING_PTR(data->fname), data->oflags, data->perm); #else #ifdef _WIN32 if (data->wchar) Index: mvm/pack.c =================================================================== --- mvm/pack.c (revision 25717) +++ mvm/pack.c (revision 25718) @@ -1970,7 +1970,7 @@ break; case 'P': - if (sizeof(char *) <= send - s) { + if (sizeof(char *) <= (size_t)(send - s)) { VALUE tmp = Qnil; char *t; @@ -2010,7 +2010,7 @@ if (len > (long)((send - s) / sizeof(char *))) len = (send - s) / sizeof(char *); while (len-- > 0) { - if (send - s < sizeof(char *)) + if ((size_t)(send - s) < sizeof(char *)) break; else { VALUE tmp = Qnil; Index: mvm/thread.c =================================================================== --- mvm/thread.c (revision 25717) +++ mvm/thread.c (revision 25718) @@ -61,6 +61,14 @@ #define native_mutex_initialize(lock) ruby_native_thread_lock_initialize(lock) #define native_mutex_destroy(lock) ruby_native_thread_lock_destroy(lock) +#define native_mutex_lock(lock) ruby_native_thread_lock(lock) +#define native_mutex_unlock(lock) ruby_native_thread_unlock(lock) +#define native_cond_initialize(cond) ruby_native_cond_initialize(cond) +#define native_cond_destroy(cond) ruby_native_cond_destroy(cond) +#define native_cond_signal(cond) ruby_native_cond_signal(cond) +#define native_cond_broadcast(cond) ruby_native_cond_broadcast(cond) +#define native_cond_wait(cond, lock) ruby_native_cond_wait(cond, lock) +#define native_cond_timedwait(cond, lock, ts) ruby_native_cond_timedwait(cond, lock, ts) static void sleep_timeval(rb_thread_t *th, struct timeval time); static void sleep_wait_for_interrupt(rb_thread_t *th, double sleepsec); @@ -124,6 +132,17 @@ GVL_UNLOCK_END(); \ } while(0); +#define blocking_region_begin(th, region, func, arg) \ + do { \ + (region)->prev_status = (th)->status; \ + (th)->blocking_region_buffer = (region); \ + set_unblock_function((th), (func), (arg), &(region)->oldubf); \ + (th)->status = THREAD_STOPPED; \ + thread_debug("enter blocking region (%p)\n", (void *)(th)); \ + RB_GC_SAVE_MACHINE_CONTEXT(th); \ + native_mutex_unlock(&(th)->vm->global_vm_lock); \ + } while (0) + #define BLOCKING_REGION(exec, ubf, ubfarg) do { \ rb_thread_t *__th = GET_THREAD(); \ struct rb_blocking_region_buffer __region; \ @@ -1007,16 +1026,6 @@ } /* blocking region */ -#define blocking_region_begin(th, region, func, arg) \ - do { \ - (region)->prev_status = (th)->status; \ - (th)->blocking_region_buffer = (region); \ - set_unblock_function((th), (func), (arg), &(region)->oldubf); \ - (th)->status = THREAD_STOPPED; \ - thread_debug("enter blocking region (%p)\n", (void *)(th)); \ - RB_GC_SAVE_MACHINE_CONTEXT(th); \ - native_mutex_unlock(&(th)->vm->global_vm_lock); \ - } while (0) static inline void blocking_region_end(rb_thread_t *th, struct rb_blocking_region_buffer *region) @@ -3397,7 +3406,7 @@ while (mutexes) { mutex = mutexes; rb_warn("mutex #<%p> remains to be locked by terminated thread", - mutexes); + (void *)mutexes); mutexes = mutex->next_mutex; err = mutex_unlock(mutex, th); if (err) rb_bug("invalid keeping_mutexes: %s", err); Index: mvm/common.mk =================================================================== --- mvm/common.mk (revision 25717) +++ mvm/common.mk (revision 25718) @@ -627,7 +627,7 @@ util.$(OBJEXT): {$(VPATH)}util.c $(RUBY_H_INCLUDES) {$(VPATH)}util.h variable.$(OBJEXT): {$(VPATH)}variable.c $(RUBY_H_INCLUDES) \ {$(VPATH)}node.h {$(VPATH)}util.h {$(VPATH)}encoding.h \ - {$(VPATH)}oniguruma.h {$(VPATH)}vm.h + {$(VPATH)}oniguruma.h {$(VPATH)}vm.h {$(VPATH)}vm_core.h version.$(OBJEXT): {$(VPATH)}version.c $(RUBY_H_INCLUDES) \ {$(VPATH)}version.h $(srcdir)/revision.h {$(VPATH)}config.h @@ -638,13 +638,15 @@ $(RUBY_H_INCLUDES) $(VM_CORE_H_INCLUDES) {$(VPATH)}insns.inc \ {$(VPATH)}insns_info.inc {$(VPATH)}node_name.inc {$(VPATH)}debug.h vm.$(OBJEXT): {$(VPATH)}vm.c {$(VPATH)}gc.h {$(VPATH)}iseq.h \ - {$(VPATH)}eval_intern.h $(RUBY_H_INCLUDES) $(ENCODING_H_INCLUDES) \ + {$(VPATH)}eval_intern.h {$(VPATH)}vm.h $(RUBY_H_INCLUDES) $(ENCODING_H_INCLUDES) \ $(VM_CORE_H_INCLUDES) {$(VPATH)}vm_method.c {$(VPATH)}vm_eval.c \ {$(VPATH)}vm_insnhelper.c {$(VPATH)}vm_insnhelper.h {$(VPATH)}vm_exec.c \ {$(VPATH)}vm_exec.h {$(VPATH)}insns.def {$(VPATH)}vmtc.inc \ {$(VPATH)}vm.inc {$(VPATH)}insns.inc {$(VPATH)}debug.h vm_dump.$(OBJEXT): {$(VPATH)}vm_dump.c $(RUBY_H_INCLUDES) \ $(VM_CORE_H_INCLUDES) {$(VPATH)}debug.h +mvm.$(OBJEXT): {$(VPATH)}mvm.c $(RUBY_H_INCLUDES) $(VM_CORE_H_INCLUDES) \ + {$(VPATH)}vm.h {$(VPATH)}eval_intern.h debug.$(OBJEXT): {$(VPATH)}debug.c $(RUBY_H_INCLUDES) \ $(ENCODING_H_INCLUDES) $(VM_CORE_H_INCLUDES) {$(VPATH)}eval_intern.h \ {$(VPATH)}util.h {$(VPATH)}debug.h Index: mvm/dir.c =================================================================== --- mvm/dir.c (revision 25717) +++ mvm/dir.c (revision 25718) @@ -2252,8 +2252,8 @@ rb_raise(rb_eArgError, "wrong number of argument (%d for 1)", argc); } argc -= 2; - arg.owner = NIL_P(*argv) ? -1 : NUM2UIDT(*argv); ++argv; - arg.group = NIL_P(*argv) ? -1 : NUM2GIDT(*argv); ++argv; + arg.owner = NIL_P(*argv) ? (rb_uid_t)-1 : NUM2UIDT(*argv); ++argv; + arg.group = NIL_P(*argv) ? (rb_gid_t)-1 : NUM2GIDT(*argv); ++argv; GetDIR(dir, dp); n = apply2filesat(dp, fchown_internal, argc, argv, &arg); return LONG2NUM(n); @@ -2283,8 +2283,8 @@ rb_raise(rb_eArgError, "wrong number of argument (%d for 1)", argc); } argc -= 2; - arg.owner = NIL_P(*argv) ? -1 : NUM2UIDT(*argv); ++argv; - arg.group = NIL_P(*argv) ? -1 : NUM2GIDT(*argv); ++argv; + arg.owner = NIL_P(*argv) ? (rb_uid_t)-1 : NUM2UIDT(*argv); ++argv; + arg.group = NIL_P(*argv) ? (rb_gid_t)-1 : NUM2GIDT(*argv); ++argv; GetDIR(dir, dp); n = apply2filesat(dp, lchown_internal, argc, argv, &arg); return LONG2NUM(n); Index: mvm/main.c =================================================================== --- mvm/main.c (revision 25717) +++ mvm/main.c (revision 25718) @@ -36,7 +36,6 @@ int ret; RUBY_INIT_STACK; - ruby_init(); vm = ruby_vm_new(argc, argv); ret = ruby_vm_run(vm); ruby_vm_destruct(vm); Index: mvm/eval.c =================================================================== --- mvm/eval.c (revision 25717) +++ mvm/eval.c (revision 25718) @@ -37,27 +37,26 @@ void rb_thread_stop_timer_thread(void); void rb_call_inits(void); -void Init_heap(void); -void Init_BareVM(void); +rb_vm_t *Init_BareVM(void); void rb_vm_call_inits(void); -void InitVM_heap(void); void InitVM_ext(void); void ruby_vm_prog_init(rb_vm_t *vm); void *ruby_vm_process_options(rb_vm_t *vm, int argc, char **argv); static int ruby_vm_cleanup(rb_vm_t *vm, int ex); -void +rb_vm_t * ruby_init(void) { static int initialized = 0; int state; + rb_vm_t *vm; if (initialized) - return; + return 0; initialized = 1; ruby_init_stack((void *)&state); - Init_BareVM(); + vm = Init_BareVM(); PUSH_TAG(); if ((state = EXEC_TAG()) == 0) { @@ -70,6 +69,7 @@ error_print(); exit(EXIT_FAILURE); } + return vm; } int @@ -77,8 +77,6 @@ { int state; - InitVM_heap(); - PUSH_TAG(); if ((state = EXEC_TAG()) == 0) { rb_vm_call_inits(); @@ -145,7 +143,7 @@ void rb_thread_stop_timer_thread(void); -static int +int ruby_vm_cleanup(rb_vm_t *vm, volatile int ex) { int state; @@ -263,35 +261,32 @@ return FALSE; } +#define ruby_vm_exec_internal(vm, n) ruby_exec_internal((vm)->main_thread, n) + int ruby_vm_exec_node(rb_vm_t *vm, void *n) { ruby_init_stack((void *)&n); - return ruby_exec_internal(vm->main_thread, n); + return ruby_vm_exec_internal(vm, n); } int -ruby_vm_run_node(rb_vm_t *vm, void *n) -{ - int status; - if (!ruby_executable_node(n, &status)) { - ruby_vm_cleanup(vm, 0); - return status; - } - return ruby_vm_cleanup(vm, ruby_vm_exec_node(vm, n)); -} - -int ruby_vm_run(rb_vm_t *vm) { int status; + void *n; rb_thread_set_current_raw(vm->main_thread); Init_stack((void *)&vm); if ((status = ruby_vm_init(vm)) != 0) { return ruby_vm_cleanup(vm, status); } - return ruby_vm_run_node(vm, ruby_vm_parse_options(vm)); + n = ruby_vm_parse_options(vm); + if (!ruby_executable_node(n, &status)) { + ruby_vm_cleanup(vm, 0); + return status; + } + return ruby_vm_exec_internal(vm, n); } /* Index: mvm/gc.c =================================================================== --- mvm/gc.c (revision 25717) +++ mvm/gc.c (revision 25718) @@ -738,16 +738,22 @@ } void * -ruby_xmalloc2(size_t n, size_t size) +rb_objspace_xmalloc2(rb_objspace_t *objspace, size_t n, size_t size) { size_t len = size * n; if (n != 0 && size != len / n) { rb_raise(rb_eArgError, "malloc: possible integer overflow"); } - return rb_objspace_xmalloc(&rb_objspace, len); + return rb_objspace_xmalloc(objspace, len); } void * +ruby_xmalloc2(size_t n, size_t size) +{ + return rb_objspace_xmalloc2(&rb_objspace, n, size); +} + +void * ruby_xcalloc(size_t n, size_t size) { void *mem = ruby_xmalloc2(n, size); @@ -763,15 +769,21 @@ } void * -ruby_xrealloc2(void *ptr, size_t n, size_t size) +rb_objspace_xrealloc2(rb_objspace_t *objspace, void *ptr, size_t n, size_t size) { size_t len = size * n; if (n != 0 && size != len / n) { rb_raise(rb_eArgError, "realloc: possible integer overflow"); } - return ruby_xrealloc(ptr, len); + return rb_objspace_xrealloc(objspace, ptr, len); } +void * +ruby_xrealloc2(void *ptr, size_t n, size_t size) +{ + return rb_objspace_xrealloc2(&rb_objspace, ptr, n, size); +} + void ruby_xfree(void *x) { @@ -2284,19 +2296,6 @@ * */ -void -Init_heap(void) -{ -} - -void -InitVM_heap(void) -{ -#if !(defined(ENABLE_VM_OBJSPACE) && ENABLE_VM_OBJSPACE) - init_heap(vm->objspace); -#endif -} - /* * rb_objspace_each_objects() is special C API to walk through * Ruby object space. This C API is too difficult to use it. Index: mvm/parse.y =================================================================== --- mvm/parse.y (revision 25717) +++ mvm/parse.y (revision 25718) @@ -9324,8 +9324,7 @@ { ruby_native_thread_lock_initialize(&global_symbols.lock); ruby_native_thread_lock(&global_symbols.lock); - global_symbols.objspace = rb_objspace_alloc(); - rb_objspace_gc_disable(global_symbols.objspace); + global_symbols.objspace = GET_VM()->objspace; global_symbols.sym_id = st_init_table_with_size(&symhash, 1000); global_symbols.id_str = st_init_numtable_with_size(1000); Init_id(); Index: mvm/util.c =================================================================== --- mvm/util.c (revision 25717) +++ mvm/util.c (revision 25718) @@ -2280,7 +2280,7 @@ #ifdef Honor_FLT_ROUNDS /* round correctly FLT_ROUNDS = 2 or 3 */ if (sign) { - rv = -rv; + dval(rv) = -dval(rv); sign = 0; } #endif @@ -2296,7 +2296,7 @@ #ifdef Honor_FLT_ROUNDS /* round correctly FLT_ROUNDS = 2 or 3 */ if (sign) { - rv = -rv; + dval(rv) = -dval(rv); sign = 0; } #endif @@ -2324,7 +2324,7 @@ #ifdef Honor_FLT_ROUNDS /* round correctly FLT_ROUNDS = 2 or 3 */ if (sign) { - rv = -rv; + dval(rv) = -dval(rv); sign = 0; } #endif @@ -2791,11 +2791,11 @@ #ifdef Check_FLT_ROUNDS switch (Rounding) { case 2: /* towards +infinity */ - aadj1 -= 0.5; + dval(aadj1) -= 0.5; break; case 0: /* towards 0 */ case 3: /* towards -infinity */ - aadj1 += 0.5; + dval(aadj1) += 0.5; } #else if (Flt_Rounds == 0) @@ -2840,7 +2840,7 @@ if ((word0(rv) & Exp_mask) <= P*Exp_msk1) { dval(rv0) = dval(rv); word0(rv) += P*Exp_msk1; - adj = aadj1 * ulp(dval(rv)); + adj = dval(aadj1) * ulp(dval(rv)); dval(rv) += adj; #ifdef IBM if ((word0(rv) & Exp_mask) < P*Exp_msk1) @@ -2858,7 +2858,7 @@ word0(rv) -= P*Exp_msk1; } else { - adj = aadj1 * ulp(dval(rv)); + adj = dval(aadj1) * ulp(dval(rv)); dval(rv) += adj; } #else /*Sudden_Underflow*/ @@ -2870,11 +2870,11 @@ * example: 1.2e-307 . */ if (y <= (P-1)*Exp_msk1 && aadj > 1.) { - aadj1 = (double)(int)(aadj + 0.5); + dval(aadj1) = (double)(int)(aadj + 0.5); if (!dsign) - aadj1 = -aadj1; + dval(aadj1) = -dval(aadj1); } - adj = aadj1 * ulp(dval(rv)); + adj = dval(aadj1) * ulp(dval(rv)); dval(rv) += adj; #endif /*Sudden_Underflow*/ #endif /*Avoid_Underflow*/ Index: mvm/process.c =================================================================== --- mvm/process.c (revision 25717) +++ mvm/process.c (revision 25718) @@ -4084,9 +4084,9 @@ #endif } else { /* unprivileged user */ #if defined(HAVE_SETRESUID) - if (setresuid((getuid() == uid)? -1: uid, - (geteuid() == uid)? -1: uid, - (SAVED_USER_ID == uid)? -1: uid) < 0) rb_sys_fail(0); + if (setresuid((getuid() == uid)? (rb_uid_t)-1: uid, + (geteuid() == uid)? (rb_uid_t)-1: uid, + (SAVED_USER_ID == uid)? (rb_uid_t)-1: uid) < 0) rb_sys_fail(0); SAVED_USER_ID = uid; #elif defined(HAVE_SETREUID) && !defined(OBSOLETE_SETREUID) if (SAVED_USER_ID == uid) { @@ -4702,9 +4702,9 @@ #endif } else { /* unprivileged user */ #if defined(HAVE_SETRESGID) - if (setresgid((getgid() == gid)? -1: gid, - (getegid() == gid)? -1: gid, - (SAVED_GROUP_ID == gid)? -1: gid) < 0) rb_sys_fail(0); + if (setresgid((getgid() == gid)? (rb_gid_t)-1: gid, + (getegid() == gid)? (rb_gid_t)-1: gid, + (SAVED_GROUP_ID == gid)? (rb_gid_t)-1: gid) < 0) rb_sys_fail(0); SAVED_GROUP_ID = gid; #elif defined(HAVE_SETREGID) && !defined(OBSOLETE_SETREGID) if (SAVED_GROUP_ID == gid) { Index: mvm/hash.c =================================================================== --- mvm/hash.c (revision 25717) +++ mvm/hash.c (revision 25718) @@ -2030,24 +2030,24 @@ ruby_setenv(const char *name, const char *value) { #if defined(_WIN32) - /* The sane way to deal with the environment. - * Has these advantages over putenv() & co.: - * * enables us to store a truly empty value in the - * environment (like in UNIX). - * * we don't have to deal with RTL globals, bugs and leaks. - * * Much faster. - * Why you may want to enable USE_WIN32_RTL_ENV: - * * environ[] and RTL functions will not reflect changes, - * which might be an issue if extensions want to access - * the env. via RTL. This cuts both ways, since RTL will - * not see changes made by extensions that call the Win32 - * functions directly, either. - * GSAR 97-06-07 - * - * REMARK: USE_WIN32_RTL_ENV is already obsoleted since we don't use - * RTL's environ global variable directly yet. - */ - SetEnvironmentVariable(name,value); + int len; + char *buf; + if (value) { + len = strlen(name) + 1 + strlen(value) + 1; + buf = ALLOCA_N(char, len); + snprintf(buf, len, "%s=%s", name, value); + putenv(buf); + + /* putenv() doesn't handle empty value */ + if (*value) + SetEnvironmentVariable(name,value); + } + else { + len = strlen(name) + 1 + 1; + buf = ALLOCA_N(char, len); + snprintf(buf, len, "%s=", name); + putenv(buf); + } #elif defined(HAVE_SETENV) && defined(HAVE_UNSETENV) #undef setenv #undef unsetenv @@ -2067,7 +2067,7 @@ for (max = i; environ[max]; max++) ; tmpenv = ALLOC_N(char*, max+2); for (j=0; j<max; j++) /* copy environment */ - tmpenv[j] = strdup(environ[j]); + tmpenv[j] = ruby_strdup(environ[j]); tmpenv[max] = 0; environ = tmpenv; /* tell exec where it is now */ } Index: mvm/.merged-trunk-revision =================================================================== --- mvm/.merged-trunk-revision (revision 25717) +++ mvm/.merged-trunk-revision (revision 25718) @@ -1 +1 @@ -25704 +25717 Index: mvm/mvm.c =================================================================== --- mvm/mvm.c (revision 25717) +++ mvm/mvm.c (revision 25718) @@ -10,20 +10,27 @@ **********************************************************************/ #include "ruby/ruby.h" +#include "ruby/vm.h" #include "vm_core.h" #include "eval_intern.h" static void vmmgr_add(rb_vm_t *vm); static void vmmgr_del(rb_vm_t *vm); -static rb_vm_t *vm_new(int argc, char *argv[]); void rb_vm_free(rb_vm_t *vm); +static int vm_join(rb_vm_t *vm); + /* core API */ rb_vm_t * ruby_vm_new(int argc, char *argv[]) { - rb_vm_t *vm = vm_new(argc, argv); + rb_vm_t *vm = ruby_init(); + + if (!vm) return 0; + if (!(vm = ruby_make_bare_vm())) return 0; + vm->argc = argc; + vm->argv = argv; vmmgr_add(vm); return vm; @@ -39,8 +46,7 @@ int ruby_vm_join(rb_vm_t *vm) { - rb_bug("unsupporeted"); - return 0; + return vm_join(vm); } int @@ -259,7 +265,6 @@ while (entry) { if (func(entry->vm, arg) == 0) { - printf("ruby_vm_foreach: break\n"); break; } entry = entry->next; @@ -268,13 +273,14 @@ } } -rb_vm_t *ruby_make_bare_vm(); +static int +vm_join(rb_vm_t *vm) +{ + st_table *living_threads = vm->living_threads; -static rb_vm_t * -vm_new(int argc, char *argv[]) -{ - rb_vm_t *vm = ruby_make_bare_vm(); - vm->argc = argc; - vm->argv = argv; - return vm; + if (!living_threads) return 0; + MVM_CRITICAL(vm_manager.lock, do { + ruby_native_cond_wait(&vm->global_vm_waiting, &vm_manager.lock); + } while (vm->living_threads)); + return 0; } Index: mvm/vm.c =================================================================== --- mvm/vm.c (revision 25717) +++ mvm/vm.c (revision 25718) @@ -12,6 +12,7 @@ #include "ruby/st.h" #include "ruby/encoding.h" #include "ruby/util.h" +#include "ruby/vm.h" #include "gc.h" #include "vm_core.h" @@ -1531,13 +1532,15 @@ vm_init2(rb_vm_t *vm) { MEMZERO(vm, rb_vm_t, 1); + vm->argc = -1; ruby_native_thread_lock_initialize(&vm->global_vm_lock); vm->objspace = rb_objspace_alloc(); vm->src_encoding_index = -1; vm->global_state_version = 1; vm->specific_storage.len = rb_vm_key_count(); - vm->specific_storage.ptr = calloc(vm->specific_storage.len, sizeof(VALUE)); - vm->cache = malloc(sizeof(struct cache_entry) * CACHE_SIZE); + vm->specific_storage.ptr = rb_objspace_xmalloc2(vm->objspace, vm->specific_storage.len, sizeof(VALUE)); + MEMZERO(vm->specific_storage.ptr, VALUE, vm->specific_storage.len); + vm->cache = rb_objspace_xmalloc2(vm->objspace, CACHE_SIZE, sizeof(struct cache_entry)); } /* Thread */ @@ -1938,6 +1941,56 @@ return ary; } +static VALUE +rb_vm_s_alloc(VALUE klass) +{ + return TypedData_Wrap_Struct(klass, &vm_data_type, 0); +} + +static void +vm_parse_opt(rb_vm_t *vm, VALUE opt) +{ +} + +static VALUE +rb_vm_initialize(int argc, VALUE *argv, VALUE self) +{ + VALUE opt = Qnil; + rb_vm_t *vm; + + GetVMPtr(self, vm); + if (vm) rb_raise(rb_eArgError, "alread initialized VM"); + DATA_PTR(self) = vm = malloc(sizeof(*vm)); + vm_init2(vm); + if (argc > 0 && NIL_P(opt = rb_check_string_type(argv[argc-1]))) { + --argc; + vm_parse_opt(vm, opt); + } + if (argc > 0) { + int i; + char **args, *argp; + VALUE argsval = 0; + size_t len = rb_long2int(argc * sizeof(char *)), total = 0; + for (i = 0; i < argc; ++i) { + StringValue(argv[i]); + argv[i] = rb_str_new_frozen(argv[i]); + rb_long2int(total += RSTRING_LEN(argv[i]) + 1); + } + args = rb_objspace_xmalloc(vm->objspace, len); + argsval = rb_str_wrap((char *)args, len); + RBASIC(argsval)->klass = 0; + argp = (char *)(args + argc); + for (i = 0; i < argc; ++i) { + long n = RSTRING_LEN(argv[i]); + args[i] = argp; + memcpy(argp, RSTRING_PTR(argv[i]), n); + argp += n; + *argp++ = '\0'; + } + } + return self; +} + void Init_VM(void) { @@ -1952,7 +2005,8 @@ /* ::VM */ rb_cRubyVM = rb_define_class("RubyVM", rb_cObject); - rb_undef_alloc_func(rb_cRubyVM); + rb_define_alloc_func(rb_cRubyVM, rb_vm_s_alloc); + rb_define_method(rb_cRubyVM, "initialize", rb_vm_initialize, -1); /* ::VM::FrozenCore */ fcore = rb_class_new(rb_cBasicObject); @@ -2075,7 +2129,6 @@ } void ruby_thread_init_stack(rb_thread_t *th); -void Init_native_thread(void); rb_vm_t * ruby_make_bare_vm(void) @@ -2083,17 +2136,14 @@ /* VM bootstrap: phase 1 */ rb_vm_t *vm = malloc(sizeof(*vm)); rb_thread_t *th = malloc(sizeof(*th)); - rb_thread_t *old_th = GET_THREAD(); if (!vm || !th) { - fprintf(stderr, "[FATAL] failed to allocate memory\n"); - exit(EXIT_FAILURE); + if (vm) free(vm); + if (th) free(th); + return 0; } MEMZERO(th, rb_thread_t, 1); - /* init thread core */ - Init_native_thread(); - th->vm = vm; rb_thread_set_current_raw(th); vm_init2(vm); @@ -2102,17 +2152,25 @@ th_init(th, 0); ruby_thread_init_stack(th); - rb_thread_set_current_raw(old_th); - return vm; } -void +rb_vm_t * Init_BareVM(void) { void Init_vmmgr(void); + void Init_native_thread(void); + rb_vm_t *vm; + + /* init thread core */ + Init_native_thread(); Init_vmmgr(); - ruby_make_bare_vm(); + vm = ruby_make_bare_vm(); + if (!vm) { + fprintf(stderr, "[FATAL] failed to allocate memory\n"); + exit(EXIT_FAILURE); + } + return vm; } /* top self */ Index: mvm/version.h =================================================================== --- mvm/version.h (revision 25717) +++ mvm/version.h (revision 25718) @@ -1,5 +1,5 @@ #define RUBY_VERSION "1.9.2" -#define RUBY_RELEASE_DATE "2009-11-10" +#define RUBY_RELEASE_DATE "2009-11-11" #define RUBY_PATCHLEVEL -1 #define RUBY_BRANCH_NAME "mvm" @@ -8,7 +8,7 @@ #define RUBY_VERSION_TEENY 1 #define RUBY_RELEASE_YEAR 2009 #define RUBY_RELEASE_MONTH 11 -#define RUBY_RELEASE_DAY 10 +#define RUBY_RELEASE_DAY 11 #include "ruby/version.h" Index: mvm/ruby.c =================================================================== --- mvm/ruby.c (revision 25717) +++ mvm/ruby.c (revision 25718) @@ -1829,10 +1829,9 @@ struct cmdline_options opt; VALUE iseq; - if (argv[0]) { /* for the time being */ - RUBY_VM_OBJECT(vm, progname) = rb_tainted_str_new2(argv[0]); + if (argc > 0 && argv[0]) { /* for the time being */ + ruby_script(argv[0]); /* for the time being */ } - ruby_script(argv[0]); /* for the time being */ rb_argv0 = rb_str_new4(rb_progname); rb_gc_register_mark_object(rb_argv0); iseq = process_options(vm, argc, argv, cmdline_options_init(&opt)); Index: mvm/marshal.c =================================================================== --- mvm/marshal.c (revision 25717) +++ mvm/marshal.c (revision 25718) @@ -778,7 +778,7 @@ case T_HASH: w_uclass(obj, rb_cHash, arg); - if (NIL_P(RHASH(obj)->ifnone)) { + if (NIL_P(RHASH_IFNONE(obj))) { w_byte(TYPE_HASH, arg); } else if (FL_TEST(obj, FL_USER2)) { @@ -790,8 +790,8 @@ } w_long(RHASH_SIZE(obj), arg); rb_hash_foreach(obj, hash_each, (st_data_t)&c_arg); - if (!NIL_P(RHASH(obj)->ifnone)) { - w_object(RHASH(obj)->ifnone, arg, limit); + if (!NIL_P(RHASH_IFNONE(obj))) { + w_object(RHASH_IFNONE(obj), arg, limit); } break; @@ -1565,7 +1565,7 @@ rb_hash_aset(v, key, value); } if (type == TYPE_HASH_DEF) { - RHASH(v)->ifnone = r_object(arg); + RHASH_IFNONE(v) = r_object(arg); } v = r_leave(v, arg); } Index: mvm/test/dl/test_func.rb =================================================================== --- mvm/test/dl/test_func.rb (revision 25717) +++ mvm/test/dl/test_func.rb (revision 25718) @@ -33,8 +33,8 @@ def test_strtod() f = Function.new(CFunc.new(@libc['strtod'], TYPE_DOUBLE, 'strtod'), [TYPE_VOIDP, TYPE_VOIDP]) - buff1 = "12.34" - buff2 = " " + buff1 = CPtr["12.34"] + buff2 = buff1 + 4 r = f.call(buff1, buff2) assert_match(12.00..13.00, r) end Index: mvm/test/matrix/test_matrix.rb =================================================================== --- mvm/test/matrix/test_matrix.rb (revision 25717) +++ mvm/test/matrix/test_matrix.rb (revision 25718) @@ -46,4 +46,102 @@ assert_equal @m1.hash, @m2.hash assert_equal @m1.hash, @m3.hash end + + def test_rank + [ + [[0]], + [[0], [0]], + [[0, 0], [0, 0]], + [[0, 0], [0, 0], [0, 0]], + [[0, 0, 0]], + [[0, 0, 0], [0, 0, 0]], + [[0, 0, 0], [0, 0, 0], [0, 0, 0]], + [[0, 0, 0], [0, 0, 0], [0, 0, 0], [0, 0, 0]], + ].each do |rows| + assert_equal 0, Matrix[*rows].rank + end + + [ + [[1], [0]], + [[1, 0], [0, 0]], + [[1, 0], [1, 0]], + [[0, 0], [1, 0]], + [[1, 0], [0, 0], [0, 0]], + [[0, 0], [1, 0], [0, 0]], + [[0, 0], [0, 0], [1, 0]], + [[1, 0], [1, 0], [0, 0]], + [[0, 0], [1, 0], [1, 0]], + [[1, 0], [1, 0], [1, 0]], + [[1, 0, 0]], + [[1, 0, 0], [0, 0, 0]], + [[0, 0, 0], [1, 0, 0]], + [[1, 0, 0], [1, 0, 0]], + [[1, 0, 0], [1, 0, 0]], + [[1, 0, 0], [0, 0, 0], [0, 0, 0]], + [[0, 0, 0], [1, 0, 0], [0, 0, 0]], + [[0, 0, 0], [0, 0, 0], [1, 0, 0]], + [[1, 0, 0], [1, 0, 0], [0, 0, 0]], + [[0, 0, 0], [1, 0, 0], [1, 0, 0]], + [[1, 0, 0], [0, 0, 0], [1, 0, 0]], + [[1, 0, 0], [1, 0, 0], [1, 0, 0]], + [[1, 0, 0], [0, 0, 0], [0, 0, 0], [0, 0, 0]], + [[1, 0, 0], [0, 0, 0], [0, 0, 0], [0, 0, 0]], + [[1, 0, 0], [1, 0, 0], [0, 0, 0], [0, 0, 0]], + [[1, 0, 0], [0, 0, 0], [1, 0, 0], [0, 0, 0]], + [[1, 0, 0], [0, 0, 0], [0, 0, 0], [1, 0, 0]], + [[1, 0, 0], [1, 0, 0], [1, 0, 0], [0, 0, 0]], + [[1, 0, 0], [0, 0, 0], [1, 0, 0], [1, 0, 0]], + [[1, 0, 0], [1, 0, 0], [0, 0, 0], [1, 0, 0]], + [[1, 0, 0], [1, 0, 0], [1, 0, 0], [1, 0, 0]], + + [[1]], + [[1], [1]], + [[1, 1]], + [[1, 1], [1, 1]], + [[1, 1], [1, 1], [1, 1]], + [[1, 1, 1]], + [[1, 1, 1], [1, 1, 1]], + [[1, 1, 1], [1, 1, 1], [1, 1, 1]], + [[1, 1, 1], [1, 1, 1], [1, 1, 1], [1, 1, 1]], + ].each do |rows| + matrix = Matrix[*rows] + assert_equal 1, matrix.rank + assert_equal 1, matrix.transpose.rank + end + + [ + [[1, 0], [0, 1]], + [[1, 0], [0, 1], [0, 0]], + [[1, 0], [0, 1], [0, 1]], + [[1, 0], [0, 1], [1, 1]], + [[1, 0, 0], [0, 1, 0]], + [[1, 0, 0], [0, 0, 1]], + [[1, 0, 0], [0, 1, 0], [0, 0, 0]], + [[1, 0, 0], [0, 0, 1], [0, 0, 0]], + + [[1, 0, 0], [0, 0, 0], [0, 1, 0]], + [[1, 0, 0], [0, 0, 0], [0, 0, 1]], + + [[1, 0], [1, 1]], + [[1, 2], [1, 1]], + [[1, 2], [0, 1], [1, 1]], + ].each do |rows| + m = Matrix[*rows] + assert_equal 2, m.rank + assert_equal 2, m.transpose.rank + end + + [ + [[1, 0, 0], [0, 1, 0], [0, 0, 1]], + [[1, 1, 0], [0, 1, 1], [1, 0, 1]], + [[1, 1, 0], [0, 1, 1], [1, 0, 1]], + [[1, 1, 0], [0, 1, 1], [1, 0, 1], [0, 0, 0]], + [[1, 1, 0], [0, 1, 1], [1, 0, 1], [1, 1, 1]], + [[1, 1, 1], [1, 1, 2], [1, 3, 1], [4, 1, 1]], + ].each do |rows| + m = Matrix[*rows] + assert_equal 3, m.rank + assert_equal 3, m.transpose.rank + end + end end Index: mvm/file.c =================================================================== --- mvm/file.c (revision 25717) +++ mvm/file.c (revision 25718) @@ -2341,8 +2341,7 @@ ruby_readlink(const char *path, ssize_t *len) { char *buf, *tmp; - int size = 100; - int rv; + ssize_t size = 100, rv; buf = malloc(size); if (!buf) return 0; @@ -2377,7 +2376,7 @@ { static const char fdpat[] = "/proc/self/fd/%d"; char fdname[sizeof(fdpat) + sizeof(int) * 5 / 2]; - long len; + ssize_t len; snprintf(fdname, sizeof(fdname), fdpat, fd); return ruby_readlink(fdname, &len); -- ML: ruby-changes@q... Info: http://www.atdot.net/~ko1/quickml/