зеркало из https://github.com/github/ruby.git
Some global variables can be accessed from ractors
Some global variables should be used from non-main Ractors. [Bug #17268] ```ruby # ractor-local (derived from created ractor): debug '$DEBUG' => $DEBUG, '$-d' => $-d, # ractor-local (derived from created ractor): verbose '$VERBOSE' => $VERBOSE, '$-w' => $-w, '$-W' => $-W, '$-v' => $-v, # process-local (readonly): other commandline parameters '$-p' => $-p, '$-l' => $-l, '$-a' => $-a, # process-local (readonly): getpid '$$' => $$, # thread local: process result '$?' => $?, # scope local: match '$~' => $~.inspect, '$&' => $&, '$`' => $`, '$\'' => $', '$+' => $+, '$1' => $1, # scope local: last line '$_' => $_, # scope local: last backtrace '$@' => $@, '$!' => $!, # ractor local: stdin, out, err '$stdin' => $stdin.inspect, '$stdout' => $stdout.inspect, '$stderr' => $stderr.inspect, ```
This commit is contained in:
Родитель
9ced5fae6d
Коммит
99310e3eb5
|
@ -611,6 +611,65 @@ assert_equal 'ok', %q{
|
||||||
'ok'
|
'ok'
|
||||||
}
|
}
|
||||||
|
|
||||||
|
# $DEBUG, $VERBOSE are Ractor local
|
||||||
|
assert_equal 'true', %q{
|
||||||
|
$DEBUG = true
|
||||||
|
$VERBOSE = true
|
||||||
|
|
||||||
|
def ractor_local_globals
|
||||||
|
/a(b)(c)d/ =~ 'abcd' # for $~
|
||||||
|
`echo foo`
|
||||||
|
|
||||||
|
{
|
||||||
|
# ractor-local (derived from created ractor): debug
|
||||||
|
'$DEBUG' => $DEBUG,
|
||||||
|
'$-d' => $-d,
|
||||||
|
|
||||||
|
# ractor-local (derived from created ractor): verbose
|
||||||
|
'$VERBOSE' => $VERBOSE,
|
||||||
|
'$-w' => $-w,
|
||||||
|
'$-W' => $-W,
|
||||||
|
'$-v' => $-v,
|
||||||
|
|
||||||
|
# process-local (readonly): other commandline parameters
|
||||||
|
'$-p' => $-p,
|
||||||
|
'$-l' => $-l,
|
||||||
|
'$-a' => $-a,
|
||||||
|
|
||||||
|
# process-local (readonly): getpid
|
||||||
|
'$$' => $$,
|
||||||
|
|
||||||
|
# thread local: process result
|
||||||
|
'$?' => $?,
|
||||||
|
|
||||||
|
# scope local: match
|
||||||
|
'$~' => $~.inspect,
|
||||||
|
'$&' => $&,
|
||||||
|
'$`' => $`,
|
||||||
|
'$\'' => $',
|
||||||
|
'$+' => $+,
|
||||||
|
'$1' => $1,
|
||||||
|
|
||||||
|
# scope local: last line
|
||||||
|
'$_' => $_,
|
||||||
|
|
||||||
|
# scope local: last backtrace
|
||||||
|
'$@' => $@,
|
||||||
|
'$!' => $!,
|
||||||
|
|
||||||
|
# ractor local: stdin, out, err
|
||||||
|
'$stdin' => $stdin.inspect,
|
||||||
|
'$stdout' => $stdout.inspect,
|
||||||
|
'$stderr' => $stderr.inspect,
|
||||||
|
}
|
||||||
|
end
|
||||||
|
|
||||||
|
h = Ractor.new do
|
||||||
|
ractor_local_globals
|
||||||
|
end.take
|
||||||
|
ractor_local_globals == h #=> true
|
||||||
|
}
|
||||||
|
|
||||||
# selfs are different objects
|
# selfs are different objects
|
||||||
assert_equal 'false', %q{
|
assert_equal 'false', %q{
|
||||||
r = Ractor.new do
|
r = Ractor.new do
|
||||||
|
|
|
@ -10943,6 +10943,7 @@ re.$(OBJEXT): $(top_srcdir)/internal/imemo.h
|
||||||
re.$(OBJEXT): $(top_srcdir)/internal/re.h
|
re.$(OBJEXT): $(top_srcdir)/internal/re.h
|
||||||
re.$(OBJEXT): $(top_srcdir)/internal/static_assert.h
|
re.$(OBJEXT): $(top_srcdir)/internal/static_assert.h
|
||||||
re.$(OBJEXT): $(top_srcdir)/internal/string.h
|
re.$(OBJEXT): $(top_srcdir)/internal/string.h
|
||||||
|
re.$(OBJEXT): $(top_srcdir)/internal/variable.h
|
||||||
re.$(OBJEXT): $(top_srcdir)/internal/warnings.h
|
re.$(OBJEXT): $(top_srcdir)/internal/warnings.h
|
||||||
re.$(OBJEXT): {$(VPATH)}assert.h
|
re.$(OBJEXT): {$(VPATH)}assert.h
|
||||||
re.$(OBJEXT): {$(VPATH)}backward/2/assume.h
|
re.$(OBJEXT): {$(VPATH)}backward/2/assume.h
|
||||||
|
@ -10955,9 +10956,11 @@ re.$(OBJEXT): {$(VPATH)}backward/2/long_long.h
|
||||||
re.$(OBJEXT): {$(VPATH)}backward/2/stdalign.h
|
re.$(OBJEXT): {$(VPATH)}backward/2/stdalign.h
|
||||||
re.$(OBJEXT): {$(VPATH)}backward/2/stdarg.h
|
re.$(OBJEXT): {$(VPATH)}backward/2/stdarg.h
|
||||||
re.$(OBJEXT): {$(VPATH)}config.h
|
re.$(OBJEXT): {$(VPATH)}config.h
|
||||||
|
re.$(OBJEXT): {$(VPATH)}constant.h
|
||||||
re.$(OBJEXT): {$(VPATH)}defines.h
|
re.$(OBJEXT): {$(VPATH)}defines.h
|
||||||
re.$(OBJEXT): {$(VPATH)}encindex.h
|
re.$(OBJEXT): {$(VPATH)}encindex.h
|
||||||
re.$(OBJEXT): {$(VPATH)}encoding.h
|
re.$(OBJEXT): {$(VPATH)}encoding.h
|
||||||
|
re.$(OBJEXT): {$(VPATH)}id_table.h
|
||||||
re.$(OBJEXT): {$(VPATH)}intern.h
|
re.$(OBJEXT): {$(VPATH)}intern.h
|
||||||
re.$(OBJEXT): {$(VPATH)}internal.h
|
re.$(OBJEXT): {$(VPATH)}internal.h
|
||||||
re.$(OBJEXT): {$(VPATH)}internal/anyargs.h
|
re.$(OBJEXT): {$(VPATH)}internal/anyargs.h
|
||||||
|
|
3
eval.c
3
eval.c
|
@ -2084,6 +2084,9 @@ Init_eval(void)
|
||||||
rb_define_virtual_variable("$@", errat_getter, errat_setter);
|
rb_define_virtual_variable("$@", errat_getter, errat_setter);
|
||||||
rb_define_virtual_variable("$!", errinfo_getter, 0);
|
rb_define_virtual_variable("$!", errinfo_getter, 0);
|
||||||
|
|
||||||
|
rb_gvar_ractor_local("$@");
|
||||||
|
rb_gvar_ractor_local("$!");
|
||||||
|
|
||||||
rb_define_global_function("raise", f_raise, -1);
|
rb_define_global_function("raise", f_raise, -1);
|
||||||
rb_define_global_function("fail", f_raise, -1);
|
rb_define_global_function("fail", f_raise, -1);
|
||||||
|
|
||||||
|
|
3
io.c
3
io.c
|
@ -13543,6 +13543,7 @@ Init_IO(void)
|
||||||
rb_define_hooked_variable("$\\", &rb_output_rs, 0, deprecated_str_setter);
|
rb_define_hooked_variable("$\\", &rb_output_rs, 0, deprecated_str_setter);
|
||||||
|
|
||||||
rb_define_virtual_variable("$_", get_LAST_READ_LINE, set_LAST_READ_LINE);
|
rb_define_virtual_variable("$_", get_LAST_READ_LINE, set_LAST_READ_LINE);
|
||||||
|
rb_gvar_ractor_local("$_");
|
||||||
|
|
||||||
rb_define_method(rb_cIO, "initialize_copy", rb_io_init_copy, 1);
|
rb_define_method(rb_cIO, "initialize_copy", rb_io_init_copy, 1);
|
||||||
rb_define_method(rb_cIO, "reopen", rb_io_reopen, -1);
|
rb_define_method(rb_cIO, "reopen", rb_io_reopen, -1);
|
||||||
|
@ -13764,6 +13765,8 @@ Init_IO(void)
|
||||||
ARGF.filename = rb_str_new2("-");
|
ARGF.filename = rb_str_new2("-");
|
||||||
|
|
||||||
rb_define_hooked_variable("$-i", &argf, opt_i_get, opt_i_set);
|
rb_define_hooked_variable("$-i", &argf, opt_i_get, opt_i_set);
|
||||||
|
rb_gvar_ractor_local("$-i");
|
||||||
|
|
||||||
rb_define_hooked_variable("$*", &argf, argf_argv_getter, rb_gvar_readonly_setter);
|
rb_define_hooked_variable("$*", &argf, argf_argv_getter, rb_gvar_readonly_setter);
|
||||||
|
|
||||||
#if defined (_WIN32) || defined(__CYGWIN__)
|
#if defined (_WIN32) || defined(__CYGWIN__)
|
||||||
|
|
|
@ -8445,6 +8445,10 @@ InitVM_process(void)
|
||||||
#define rb_intern(str) rb_intern_const(str)
|
#define rb_intern(str) rb_intern_const(str)
|
||||||
rb_define_virtual_variable("$?", get_CHILD_STATUS, 0);
|
rb_define_virtual_variable("$?", get_CHILD_STATUS, 0);
|
||||||
rb_define_virtual_variable("$$", get_PROCESS_ID, 0);
|
rb_define_virtual_variable("$$", get_PROCESS_ID, 0);
|
||||||
|
|
||||||
|
rb_gvar_ractor_local("$$");
|
||||||
|
rb_gvar_ractor_local("$?");
|
||||||
|
|
||||||
rb_define_global_function("exec", f_exec, -1);
|
rb_define_global_function("exec", f_exec, -1);
|
||||||
rb_define_global_function("fork", rb_f_fork, 0);
|
rb_define_global_function("fork", rb_f_fork, 0);
|
||||||
rb_define_global_function("exit!", rb_f_exit_bang, -1);
|
rb_define_global_function("exit!", rb_f_exit_bang, -1);
|
||||||
|
|
4
ractor.c
4
ractor.c
|
@ -1373,6 +1373,10 @@ ractor_create(rb_execution_context_t *ec, VALUE self, VALUE loc, VALUE name, VAL
|
||||||
r->r_stdout = rb_io_prep_stdout();
|
r->r_stdout = rb_io_prep_stdout();
|
||||||
r->r_stderr = rb_io_prep_stderr();
|
r->r_stderr = rb_io_prep_stderr();
|
||||||
|
|
||||||
|
rb_ractor_t *cr = rb_ec_ractor_ptr(ec);
|
||||||
|
r->verbose = cr->verbose;
|
||||||
|
r->debug = cr->debug;
|
||||||
|
|
||||||
rb_thread_create_ractor(r, args, block);
|
rb_thread_create_ractor(r, args, block);
|
||||||
|
|
||||||
RB_GC_GUARD(rv);
|
RB_GC_GUARD(rv);
|
||||||
|
|
2
ractor.h
2
ractor.h
|
@ -125,6 +125,8 @@ struct rb_ractor_struct {
|
||||||
VALUE r_stdin;
|
VALUE r_stdin;
|
||||||
VALUE r_stdout;
|
VALUE r_stdout;
|
||||||
VALUE r_stderr;
|
VALUE r_stderr;
|
||||||
|
VALUE verbose;
|
||||||
|
VALUE debug;
|
||||||
}; // rb_ractor_t is defined in vm_core.h
|
}; // rb_ractor_t is defined in vm_core.h
|
||||||
|
|
||||||
rb_ractor_t *rb_ractor_main_alloc(void);
|
rb_ractor_t *rb_ractor_main_alloc(void);
|
||||||
|
|
7
re.c
7
re.c
|
@ -19,6 +19,7 @@
|
||||||
#include "internal/imemo.h"
|
#include "internal/imemo.h"
|
||||||
#include "internal/re.h"
|
#include "internal/re.h"
|
||||||
#include "internal/string.h"
|
#include "internal/string.h"
|
||||||
|
#include "internal/variable.h"
|
||||||
#include "regint.h"
|
#include "regint.h"
|
||||||
#include "ruby/encoding.h"
|
#include "ruby/encoding.h"
|
||||||
#include "ruby/re.h"
|
#include "ruby/re.h"
|
||||||
|
@ -4052,6 +4053,12 @@ Init_Regexp(void)
|
||||||
rb_define_virtual_variable("$'", postmatch_getter, 0);
|
rb_define_virtual_variable("$'", postmatch_getter, 0);
|
||||||
rb_define_virtual_variable("$+", last_paren_match_getter, 0);
|
rb_define_virtual_variable("$+", last_paren_match_getter, 0);
|
||||||
|
|
||||||
|
rb_gvar_ractor_local("$~");
|
||||||
|
rb_gvar_ractor_local("$&");
|
||||||
|
rb_gvar_ractor_local("$`");
|
||||||
|
rb_gvar_ractor_local("$'");
|
||||||
|
rb_gvar_ractor_local("$+");
|
||||||
|
|
||||||
rb_define_virtual_variable("$=", ignorecase_getter, ignorecase_setter);
|
rb_define_virtual_variable("$=", ignorecase_getter, ignorecase_setter);
|
||||||
rb_define_virtual_variable("$KCODE", kcode_getter, kcode_setter);
|
rb_define_virtual_variable("$KCODE", kcode_getter, kcode_setter);
|
||||||
rb_define_virtual_variable("$-K", kcode_getter, kcode_setter);
|
rb_define_virtual_variable("$-K", kcode_getter, kcode_setter);
|
||||||
|
|
50
ruby.c
50
ruby.c
|
@ -63,6 +63,7 @@
|
||||||
#include "ruby/thread.h"
|
#include "ruby/thread.h"
|
||||||
#include "ruby/util.h"
|
#include "ruby/util.h"
|
||||||
#include "ruby/version.h"
|
#include "ruby/version.h"
|
||||||
|
#include "ruby/internal/error.h"
|
||||||
|
|
||||||
#ifndef MAXPATHLEN
|
#ifndef MAXPATHLEN
|
||||||
# define MAXPATHLEN 1024
|
# define MAXPATHLEN 1024
|
||||||
|
@ -2021,6 +2022,10 @@ process_options(int argc, char **argv, ruby_cmdline_options_t *opt)
|
||||||
rb_define_readonly_boolean("$-l", opt->do_line);
|
rb_define_readonly_boolean("$-l", opt->do_line);
|
||||||
rb_define_readonly_boolean("$-a", opt->do_split);
|
rb_define_readonly_boolean("$-a", opt->do_split);
|
||||||
|
|
||||||
|
rb_gvar_ractor_local("$-p");
|
||||||
|
rb_gvar_ractor_local("$-l");
|
||||||
|
rb_gvar_ractor_local("$-a");
|
||||||
|
|
||||||
if ((rb_e_script = opt->e_script) != 0) {
|
if ((rb_e_script = opt->e_script) != 0) {
|
||||||
rb_gc_register_mark_object(opt->e_script);
|
rb_gc_register_mark_object(opt->e_script);
|
||||||
}
|
}
|
||||||
|
@ -2430,16 +2435,24 @@ forbid_setid(const char *s, const ruby_cmdline_options_t *opt)
|
||||||
rb_raise(rb_eSecurityError, "no %s allowed while running setgid", s);
|
rb_raise(rb_eSecurityError, "no %s allowed while running setgid", s);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static VALUE
|
||||||
|
verbose_getter(ID id, VALUE *ptr)
|
||||||
|
{
|
||||||
|
return *rb_ruby_verbose_ptr();
|
||||||
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
verbose_setter(VALUE val, ID id, VALUE *variable)
|
verbose_setter(VALUE val, ID id, VALUE *variable)
|
||||||
{
|
{
|
||||||
*variable = RTEST(val) ? Qtrue : val;
|
*rb_ruby_verbose_ptr() = RTEST(val) ? Qtrue : val;
|
||||||
}
|
}
|
||||||
|
|
||||||
static VALUE
|
static VALUE
|
||||||
opt_W_getter(ID id, VALUE *variable)
|
opt_W_getter(ID id, VALUE *dmy)
|
||||||
{
|
{
|
||||||
switch (*variable) {
|
VALUE v = *rb_ruby_verbose_ptr();
|
||||||
|
|
||||||
|
switch (v) {
|
||||||
case Qnil:
|
case Qnil:
|
||||||
return INT2FIX(0);
|
return INT2FIX(0);
|
||||||
case Qfalse:
|
case Qfalse:
|
||||||
|
@ -2451,16 +2464,35 @@ opt_W_getter(ID id, VALUE *variable)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static VALUE
|
||||||
|
debug_getter(ID id, VALUE *dmy)
|
||||||
|
{
|
||||||
|
return *rb_ruby_debug_ptr();
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
debug_setter(VALUE val, ID id, VALUE *dmy)
|
||||||
|
{
|
||||||
|
*rb_ruby_debug_ptr() = val;
|
||||||
|
}
|
||||||
|
|
||||||
/*! Defines built-in variables */
|
/*! Defines built-in variables */
|
||||||
void
|
void
|
||||||
ruby_prog_init(void)
|
ruby_prog_init(void)
|
||||||
{
|
{
|
||||||
rb_define_hooked_variable("$VERBOSE", &ruby_verbose, 0, verbose_setter);
|
rb_define_virtual_variable("$VERBOSE", verbose_getter, verbose_setter);
|
||||||
rb_define_hooked_variable("$-v", &ruby_verbose, 0, verbose_setter);
|
rb_define_virtual_variable("$-v", verbose_getter, verbose_setter);
|
||||||
rb_define_hooked_variable("$-w", &ruby_verbose, 0, verbose_setter);
|
rb_define_virtual_variable("$-w", verbose_getter, verbose_setter);
|
||||||
rb_define_hooked_variable("$-W", &ruby_verbose, opt_W_getter, rb_gvar_readonly_setter);
|
rb_define_virtual_variable("$-W", opt_W_getter, rb_gvar_readonly_setter);
|
||||||
rb_define_variable("$DEBUG", &ruby_debug);
|
rb_define_virtual_variable("$DEBUG", debug_getter, debug_setter);
|
||||||
rb_define_variable("$-d", &ruby_debug);
|
rb_define_virtual_variable("$-d", debug_getter, debug_setter);
|
||||||
|
|
||||||
|
rb_gvar_ractor_local("$VERBOSE");
|
||||||
|
rb_gvar_ractor_local("$-v");
|
||||||
|
rb_gvar_ractor_local("$-w");
|
||||||
|
rb_gvar_ractor_local("$-W");
|
||||||
|
rb_gvar_ractor_local("$DEBUG");
|
||||||
|
rb_gvar_ractor_local("$-d");
|
||||||
|
|
||||||
rb_define_hooked_variable("$0", &rb_progname, 0, set_arg0);
|
rb_define_hooked_variable("$0", &rb_progname, 0, set_arg0);
|
||||||
rb_define_hooked_variable("$PROGRAM_NAME", &rb_progname, 0, set_arg0);
|
rb_define_hooked_variable("$PROGRAM_NAME", &rb_progname, 0, set_arg0);
|
||||||
|
|
18
vm.c
18
vm.c
|
@ -3515,28 +3515,18 @@ Init_top_self(void)
|
||||||
rb_define_alias(rb_singleton_class(rb_vm_top_self()), "inspect", "to_s");
|
rb_define_alias(rb_singleton_class(rb_vm_top_self()), "inspect", "to_s");
|
||||||
}
|
}
|
||||||
|
|
||||||
static VALUE *
|
|
||||||
ruby_vm_verbose_ptr(rb_vm_t *vm)
|
|
||||||
{
|
|
||||||
return &vm->verbose;
|
|
||||||
}
|
|
||||||
|
|
||||||
static VALUE *
|
|
||||||
ruby_vm_debug_ptr(rb_vm_t *vm)
|
|
||||||
{
|
|
||||||
return &vm->debug;
|
|
||||||
}
|
|
||||||
|
|
||||||
VALUE *
|
VALUE *
|
||||||
rb_ruby_verbose_ptr(void)
|
rb_ruby_verbose_ptr(void)
|
||||||
{
|
{
|
||||||
return ruby_vm_verbose_ptr(GET_VM());
|
rb_ractor_t *cr = GET_RACTOR();
|
||||||
|
return &cr->verbose;
|
||||||
}
|
}
|
||||||
|
|
||||||
VALUE *
|
VALUE *
|
||||||
rb_ruby_debug_ptr(void)
|
rb_ruby_debug_ptr(void)
|
||||||
{
|
{
|
||||||
return ruby_vm_debug_ptr(GET_VM());
|
rb_ractor_t *cr = GET_RACTOR();
|
||||||
|
return &cr->debug;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* iseq.c */
|
/* iseq.c */
|
||||||
|
|
|
@ -633,7 +633,7 @@ typedef struct rb_vm_struct {
|
||||||
struct list_head workqueue; /* <=> rb_workqueue_job.jnode */
|
struct list_head workqueue; /* <=> rb_workqueue_job.jnode */
|
||||||
rb_nativethread_lock_t workqueue_lock;
|
rb_nativethread_lock_t workqueue_lock;
|
||||||
|
|
||||||
VALUE verbose, debug, orig_progname, progname;
|
VALUE orig_progname, progname;
|
||||||
VALUE coverages;
|
VALUE coverages;
|
||||||
int coverage_mode;
|
int coverage_mode;
|
||||||
|
|
||||||
|
|
Загрузка…
Ссылка в новой задаче