fix incorrect implementation of .jump and .jump_if_not that could cause a server crash
This commit is contained in:
parent
0ddc42c00f
commit
12101bc6e1
2 changed files with 18 additions and 8 deletions
|
@ -146,8 +146,12 @@ pub const Closure = struct {
|
|||
param_count: u8,
|
||||
impl: Impl,
|
||||
|
||||
pub fn bytecodePtr(c: *const Closure, pc: usize) [*]const u8 {
|
||||
return c.impl.bytecode.chunk.bytecode[c.impl.bytecode.start + pc ..].ptr;
|
||||
pub fn globalBytecodePtr(c: *const Closure, pc: usize) [*]const u8 {
|
||||
return c.impl.bytecode.chunk.bytecode[pc..].ptr;
|
||||
}
|
||||
|
||||
pub fn relBytecodePtr(c: *const Closure, pc: usize) [*]const u8 {
|
||||
return c.globalBytecodePtr(c.impl.bytecode.start + pc);
|
||||
}
|
||||
|
||||
pub fn programCounter(c: *const Closure, ip: [*]const u8) u16 {
|
||||
|
|
|
@ -266,8 +266,10 @@ pub fn run(
|
|||
// system functions should be able to call themselves (like: map (range 1 10) sin)
|
||||
debug.assert(init_closure.impl == .bytecode);
|
||||
|
||||
log.debug("BYTECODE {any}", .{init_closure.impl.bytecode.chunk.bytecode});
|
||||
|
||||
var closure = init_closure;
|
||||
var ip: [*]const u8 = closure.bytecodePtr(0);
|
||||
var ip: [*]const u8 = closure.relBytecodePtr(0);
|
||||
var bottom = init_bottom;
|
||||
var fuel = vm.fuel;
|
||||
|
||||
|
@ -391,7 +393,7 @@ pub fn run(
|
|||
const name = ip[0..name_len];
|
||||
ip += name_len;
|
||||
const body = ip;
|
||||
ip = closure.bytecodePtr(then);
|
||||
ip = closure.globalBytecodePtr(then);
|
||||
|
||||
const local_count = read(u8, &ip);
|
||||
const capture_count = read(u8, &ip);
|
||||
|
@ -418,7 +420,7 @@ pub fn run(
|
|||
.param_count = param_count,
|
||||
.impl = .{ .bytecode = .{
|
||||
.chunk = closure.impl.bytecode.chunk,
|
||||
.start = @truncate(body - closure.bytecodePtr(0)),
|
||||
.start = @truncate(body - closure.relBytecodePtr(0)),
|
||||
.local_count = local_count,
|
||||
.captures = captures,
|
||||
} },
|
||||
|
@ -433,7 +435,8 @@ pub fn run(
|
|||
.jump => {
|
||||
const offset = read(u16, &ip);
|
||||
try vm.consumeFuel(&fuel, 1);
|
||||
ip = closure.bytecodePtr(offset);
|
||||
log.debug("JUMP {}", .{offset});
|
||||
ip = closure.globalBytecodePtr(offset);
|
||||
continue :next vm.readOpcode(&ip);
|
||||
},
|
||||
|
||||
|
@ -442,7 +445,10 @@ pub fn run(
|
|||
try vm.consumeFuel(&fuel, 1);
|
||||
const condition = try vm.pop();
|
||||
if (!condition.isTruthy()) {
|
||||
ip = closure.bytecodePtr(offset);
|
||||
log.debug("CJUMP {} JUMPED", .{offset});
|
||||
ip = closure.globalBytecodePtr(offset);
|
||||
} else {
|
||||
log.debug("CJUMP {} SKIPPED", .{offset});
|
||||
}
|
||||
continue :next vm.readOpcode(&ip);
|
||||
},
|
||||
|
@ -508,7 +514,7 @@ pub fn run(
|
|||
try vm.validateBytecode(overflow == 0, "not enough values on the stack for arguments", .{});
|
||||
|
||||
closure = called_closure;
|
||||
ip = closure.bytecodePtr(0);
|
||||
ip = closure.relBytecodePtr(0);
|
||||
bottom = new_bottom;
|
||||
|
||||
// pushCall before setting vm.closure and vm.ip, such that stack overflow errors are
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue