ruby-changes:58197
From: =E5=8D=9C=E9=83=A8=E6=98=8C=E5=B9=B3 <ko1@a...>
Date: Thu, 10 Oct 2019 18:05:03 +0900 (JST)
Subject: [ruby-changes:58197] f1ce4897f2 (master): make rb_raise a GVL-only function again
https://git.ruby-lang.org/ruby.git/commit/?id=f1ce4897f2 From f1ce4897f2eaf9a99c250e4707e3ab6f6bdacb74 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=8D=9C=E9=83=A8=E6=98=8C=E5=B9=B3?= <shyouhei@r...> Date: Thu, 10 Oct 2019 17:04:59 +0900 Subject: make rb_raise a GVL-only function again Requested by ko1 that ability of calling rb_raise from anywhere outside of GVL is "too much". Give up that part, move the GVL aquisition routine into gc.c, and make our new gc_raise(). diff --git a/common.mk b/common.mk index ca03038..ff56a0c 100644 --- a/common.mk +++ b/common.mk @@ -1942,7 +1942,6 @@ error.$(OBJEXT): $(CCAN_DIR)/list/list.h https://github.com/ruby/ruby/blob/trunk/common.mk#L1942 error.$(OBJEXT): $(CCAN_DIR)/str/str.h error.$(OBJEXT): $(hdrdir)/ruby.h error.$(OBJEXT): $(hdrdir)/ruby/ruby.h -error.$(OBJEXT): $(hdrdir)/ruby/thread.h error.$(OBJEXT): {$(VPATH)}assert.h error.$(OBJEXT): {$(VPATH)}config.h error.$(OBJEXT): {$(VPATH)}defines.h @@ -1962,7 +1961,6 @@ error.$(OBJEXT): {$(VPATH)}ruby_assert.h https://github.com/ruby/ruby/blob/trunk/common.mk#L1961 error.$(OBJEXT): {$(VPATH)}ruby_atomic.h error.$(OBJEXT): {$(VPATH)}st.h error.$(OBJEXT): {$(VPATH)}subst.h -error.$(OBJEXT): {$(VPATH)}thread.h error.$(OBJEXT): {$(VPATH)}thread_$(THREAD_MODEL).h error.$(OBJEXT): {$(VPATH)}thread_native.h error.$(OBJEXT): {$(VPATH)}vm_core.h diff --git a/error.c b/error.c index 408a163..0c3633c 100644 --- a/error.c +++ b/error.c @@ -2605,20 +2605,10 @@ rb_enc_raise(rb_encoding *enc, VALUE exc, const char *fmt, ...) https://github.com/ruby/ruby/blob/trunk/error.c#L2605 rb_exc_raise(rb_exc_new3(exc, mesg)); } -struct rb_raise_tag { - VALUE exc; - const char *fmt; - va_list *args; -}; - -static void * -rb_vraise(void *ptr) +void +rb_vraise(VALUE exc, const char *fmt, va_list ap) { - struct rb_raise_tag *argv = ptr; - VALUE msg = rb_vsprintf(argv->fmt, *argv->args); - VALUE exc = rb_exc_new3(argv->exc, msg); - rb_exc_raise(exc); - UNREACHABLE_RETURN(NULL); + rb_exc_raise(rb_exc_new3(exc, rb_vsprintf(fmt, ap))); } void @@ -2626,25 +2616,7 @@ rb_raise(VALUE exc, const char *fmt, ...) https://github.com/ruby/ruby/blob/trunk/error.c#L2616 { va_list args; va_start(args, fmt); - struct rb_raise_tag argv = { - exc, fmt, &args, - }; - - if (ruby_thread_has_gvl_p()) { - rb_vraise(&argv); - UNREACHABLE; - } - else if (ruby_native_thread_p()) { - rb_thread_call_with_gvl(rb_vraise, &argv); - UNREACHABLE; - } - else { - /* Not in a ruby thread */ - fprintf(stderr, "%s", "[FATAL] "); - vfprintf(stderr, fmt, args); - abort(); - } - + rb_vraise(exc, fmt, args); va_end(args); } diff --git a/gc.c b/gc.c index e970ea1..8900279 100644 --- a/gc.c +++ b/gc.c @@ -165,6 +165,8 @@ size_mul_add_mul_overflow(size_t x, size_t y, size_t z, size_t w) /* x * y + z * https://github.com/ruby/ruby/blob/trunk/gc.c#L165 return (struct optional) { t.left || u.left || v.left, v.right }; } +PRINTF_ARGS(NORETURN(static void gc_raise(VALUE, const char*, ...)), 2, 3); + static inline size_t size_mul_or_raise(size_t x, size_t y, VALUE exc) { @@ -176,7 +178,7 @@ size_mul_or_raise(size_t x, size_t y, VALUE exc) https://github.com/ruby/ruby/blob/trunk/gc.c#L178 rb_memerror(); /* or...? */ } else { - rb_raise( + gc_raise( exc, "integer overflow: %"PRIuSIZE " * %"PRIuSIZE @@ -202,7 +204,7 @@ size_mul_add_or_raise(size_t x, size_t y, size_t z, VALUE exc) https://github.com/ruby/ruby/blob/trunk/gc.c#L204 rb_memerror(); /* or...? */ } else { - rb_raise( + gc_raise( exc, "integer overflow: %"PRIuSIZE " * %"PRIuSIZE @@ -229,7 +231,7 @@ size_mul_add_mul_or_raise(size_t x, size_t y, size_t z, size_t w, VALUE exc) https://github.com/ruby/ruby/blob/trunk/gc.c#L231 rb_memerror(); /* or...? */ } else { - rb_raise( + gc_raise( exc, "integer overflow: %"PRIdSIZE " * %"PRIdSIZE @@ -9597,12 +9599,53 @@ objspace_reachable_objects_from_root(rb_objspace_t *objspace, void (func)(const https://github.com/ruby/ruby/blob/trunk/gc.c#L9599 ------------------------ Extended allocator ------------------------ */ +struct gc_raise_tag { + VALUE exc; + const char *fmt; + va_list *ap; +}; + +static void * +gc_vraise(void *ptr) +{ + struct gc_raise_tag *argv = ptr; + rb_vraise(argv->exc, argv->fmt, *argv->ap); + UNREACHABLE_RETURN(NULL); +} + +static void +gc_raise(VALUE exc, const char *fmt, ...) +{ + va_list ap; + va_start(ap, fmt); + struct gc_raise_tag argv = { + exc, fmt, &ap, + }; + + if (ruby_thread_has_gvl_p()) { + gc_vraise(&argv); + UNREACHABLE; + } + else if (ruby_native_thread_p()) { + rb_thread_call_with_gvl(gc_vraise, &argv); + UNREACHABLE; + } + else { + /* Not in a ruby thread */ + fprintf(stderr, "%s", "[FATAL] "); + vfprintf(stderr, fmt, ap); + abort(); + } + + va_end(ap); +} + static void objspace_xfree(rb_objspace_t *objspace, void *ptr, size_t size); static void negative_size_allocation_error(const char *msg) { - rb_raise(rb_eNoMemError, "%s", msg); + gc_raise(rb_eNoMemError, "%s", msg); } static void * diff --git a/internal.h b/internal.h index 6afd21d..6d63bcf 100644 --- a/internal.h +++ b/internal.h @@ -1553,6 +1553,7 @@ NORETURN(void ruby_deprecated_internal_feature(const char *)); https://github.com/ruby/ruby/blob/trunk/internal.h#L1553 (ruby_deprecated_internal_feature(func), UNREACHABLE) VALUE rb_warning_warn(VALUE mod, VALUE str); PRINTF_ARGS(VALUE rb_warning_string(const char *fmt, ...), 1, 2); +NORETURN(void rb_vraise(VALUE, const char *, va_list)); /* eval.c */ VALUE rb_refinement_module_get_refined_class(VALUE module); -- cgit v0.10.2 -- ML: ruby-changes@q... Info: http://www.atdot.net/~ko1/quickml/