mirror of
https://github.com/ruby/ruby.git
synced 2022-11-09 12:17:21 -05:00
Save PC and SP before accessing globals
These instructions are marked as not leaf in insns.def, which indicate that they could raise exceptions and/or call Ruby methods.
This commit is contained in:
parent
b91078ea74
commit
f4f940e5a6
2 changed files with 43 additions and 2 deletions
|
@ -7,6 +7,19 @@ assert_equal 'string', %q{
|
||||||
foo
|
foo
|
||||||
}
|
}
|
||||||
|
|
||||||
|
# Check that exceptions work when setting global variables
|
||||||
|
assert_equal 'rescued', %q{
|
||||||
|
def set_var
|
||||||
|
$var = 100
|
||||||
|
rescue
|
||||||
|
:rescued
|
||||||
|
end
|
||||||
|
|
||||||
|
set_var
|
||||||
|
trace_var(:$var) { raise }
|
||||||
|
set_var
|
||||||
|
}
|
||||||
|
|
||||||
# Check that global variables work
|
# Check that global variables work
|
||||||
assert_equal 'string', %q{
|
assert_equal 'string', %q{
|
||||||
$foo = "string"
|
$foo = "string"
|
||||||
|
@ -18,6 +31,25 @@ assert_equal 'string', %q{
|
||||||
foo
|
foo
|
||||||
}
|
}
|
||||||
|
|
||||||
|
# Check that exceptions work when getting global variable
|
||||||
|
assert_equal 'rescued', %q{
|
||||||
|
module Warning
|
||||||
|
def warn(message)
|
||||||
|
raise
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
def get_var
|
||||||
|
$=
|
||||||
|
rescue
|
||||||
|
:rescued
|
||||||
|
end
|
||||||
|
|
||||||
|
$VERBOSE = true
|
||||||
|
get_var
|
||||||
|
get_var
|
||||||
|
}
|
||||||
|
|
||||||
# Check that global tracepoints work
|
# Check that global tracepoints work
|
||||||
assert_equal 'true', %q{
|
assert_equal 'true', %q{
|
||||||
def foo
|
def foo
|
||||||
|
|
|
@ -149,7 +149,7 @@ jit_type_of_value(VALUE val)
|
||||||
|
|
||||||
// Save the incremented PC on the CFP
|
// Save the incremented PC on the CFP
|
||||||
// This is necessary when calleees can raise or allocate
|
// This is necessary when calleees can raise or allocate
|
||||||
void
|
static void
|
||||||
jit_save_pc(jitstate_t* jit, x86opnd_t scratch_reg)
|
jit_save_pc(jitstate_t* jit, x86opnd_t scratch_reg)
|
||||||
{
|
{
|
||||||
mov(cb, scratch_reg, const_ptr_opnd(jit->pc + insn_len(jit->opcode)));
|
mov(cb, scratch_reg, const_ptr_opnd(jit->pc + insn_len(jit->opcode)));
|
||||||
|
@ -160,7 +160,7 @@ jit_save_pc(jitstate_t* jit, x86opnd_t scratch_reg)
|
||||||
// This realigns the interpreter SP with the JIT SP
|
// This realigns the interpreter SP with the JIT SP
|
||||||
// Note: this will change the current value of REG_SP,
|
// Note: this will change the current value of REG_SP,
|
||||||
// which could invalidate memory operands
|
// which could invalidate memory operands
|
||||||
void
|
static void
|
||||||
jit_save_sp(jitstate_t* jit, ctx_t* ctx)
|
jit_save_sp(jitstate_t* jit, ctx_t* ctx)
|
||||||
{
|
{
|
||||||
if (ctx->sp_offset != 0) {
|
if (ctx->sp_offset != 0) {
|
||||||
|
@ -3431,6 +3431,10 @@ gen_getglobal(jitstate_t* jit, ctx_t* ctx)
|
||||||
{
|
{
|
||||||
ID gid = jit_get_arg(jit, 0);
|
ID gid = jit_get_arg(jit, 0);
|
||||||
|
|
||||||
|
// Save the PC and SP because we might make a Ruby call for warning
|
||||||
|
jit_save_pc(jit, REG0);
|
||||||
|
jit_save_sp(jit, ctx);
|
||||||
|
|
||||||
// Save YJIT registers
|
// Save YJIT registers
|
||||||
yjit_save_regs(cb);
|
yjit_save_regs(cb);
|
||||||
|
|
||||||
|
@ -3452,6 +3456,11 @@ gen_setglobal(jitstate_t* jit, ctx_t* ctx)
|
||||||
{
|
{
|
||||||
ID gid = jit_get_arg(jit, 0);
|
ID gid = jit_get_arg(jit, 0);
|
||||||
|
|
||||||
|
// Save the PC and SP because we might make a Ruby call for
|
||||||
|
// Kernel#set_trace_var
|
||||||
|
jit_save_pc(jit, REG0);
|
||||||
|
jit_save_sp(jit, ctx);
|
||||||
|
|
||||||
// Save YJIT registers
|
// Save YJIT registers
|
||||||
yjit_save_regs(cb);
|
yjit_save_regs(cb);
|
||||||
|
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue