forked from TrueCloudLab/neoneo-go
Merge pull request #1226 from nspcc-dev/fix/pusha
vm: make offset in PUSHA relative
This commit is contained in:
commit
2800179ce0
3 changed files with 7 additions and 17 deletions
|
@ -1533,12 +1533,7 @@ func (c *codegen) writeJumps(b []byte) error {
|
||||||
if int(index) > len(c.l) {
|
if int(index) > len(c.l) {
|
||||||
return fmt.Errorf("unexpected label number: %d (max %d)", index, len(c.l))
|
return fmt.Errorf("unexpected label number: %d (max %d)", index, len(c.l))
|
||||||
}
|
}
|
||||||
var offset int
|
offset := c.l[index] - nextIP + 5
|
||||||
if op == opcode.PUSHA {
|
|
||||||
offset = c.l[index]
|
|
||||||
} else {
|
|
||||||
offset = c.l[index] - nextIP + 5
|
|
||||||
}
|
|
||||||
if offset > math.MaxInt32 || offset < math.MinInt32 {
|
if offset > math.MaxInt32 || offset < math.MinInt32 {
|
||||||
return fmt.Errorf("label offset is too big at the instruction %d: %d (max %d, min %d)",
|
return fmt.Errorf("label offset is too big at the instruction %d: %d (max %d, min %d)",
|
||||||
nextIP-5, offset, math.MaxInt32, math.MinInt32)
|
nextIP-5, offset, math.MaxInt32, math.MinInt32)
|
||||||
|
|
13
pkg/vm/vm.go
13
pkg/vm/vm.go
|
@ -192,16 +192,14 @@ func (v *VM) PrintOps() {
|
||||||
opcode.JMPGT, opcode.JMPGE, opcode.JMPLE, opcode.JMPLT,
|
opcode.JMPGT, opcode.JMPGE, opcode.JMPLE, opcode.JMPLT,
|
||||||
opcode.JMPL, opcode.JMPIFL, opcode.JMPIFNOTL, opcode.CALLL,
|
opcode.JMPL, opcode.JMPIFL, opcode.JMPIFNOTL, opcode.CALLL,
|
||||||
opcode.JMPEQL, opcode.JMPNEL,
|
opcode.JMPEQL, opcode.JMPNEL,
|
||||||
opcode.JMPGTL, opcode.JMPGEL, opcode.JMPLEL, opcode.JMPLTL:
|
opcode.JMPGTL, opcode.JMPGEL, opcode.JMPLEL, opcode.JMPLTL,
|
||||||
|
opcode.PUSHA:
|
||||||
offset, rOffset, err := v.calcJumpOffset(ctx, parameter)
|
offset, rOffset, err := v.calcJumpOffset(ctx, parameter)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
desc = fmt.Sprintf("ERROR: %v", err)
|
desc = fmt.Sprintf("ERROR: %v", err)
|
||||||
} else {
|
} else {
|
||||||
desc = fmt.Sprintf("%d (%d/%x)", offset, rOffset, parameter)
|
desc = fmt.Sprintf("%d (%d/%x)", offset, rOffset, parameter)
|
||||||
}
|
}
|
||||||
case opcode.PUSHA:
|
|
||||||
offset := int32(binary.LittleEndian.Uint32(parameter))
|
|
||||||
desc = fmt.Sprintf("%d (%x)", offset, parameter)
|
|
||||||
case opcode.INITSSLOT:
|
case opcode.INITSSLOT:
|
||||||
desc = fmt.Sprint(parameter[0])
|
desc = fmt.Sprint(parameter[0])
|
||||||
case opcode.INITSLOT:
|
case opcode.INITSLOT:
|
||||||
|
@ -535,11 +533,8 @@ func (v *VM) execute(ctx *Context, op opcode.Opcode, parameter []byte) (err erro
|
||||||
v.estack.PushVal(parameter)
|
v.estack.PushVal(parameter)
|
||||||
|
|
||||||
case opcode.PUSHA:
|
case opcode.PUSHA:
|
||||||
n := int32(binary.LittleEndian.Uint32(parameter))
|
n := v.getJumpOffset(ctx, parameter)
|
||||||
if n < 0 || int(n) > len(ctx.prog) {
|
ptr := stackitem.NewPointer(n, ctx.prog)
|
||||||
panic(fmt.Sprintf("invalid pointer offset (%d)", n))
|
|
||||||
}
|
|
||||||
ptr := stackitem.NewPointer(int(n), ctx.prog)
|
|
||||||
v.estack.PushVal(ptr)
|
v.estack.PushVal(ptr)
|
||||||
|
|
||||||
case opcode.PUSHNULL:
|
case opcode.PUSHNULL:
|
||||||
|
|
|
@ -956,8 +956,8 @@ func TestPUSHA(t *testing.T) {
|
||||||
t.Run("Negative", getTestFuncForVM(makeProgram(opcode.PUSHA, 0xFF, 0xFF, 0xFF, 0xFF), nil))
|
t.Run("Negative", getTestFuncForVM(makeProgram(opcode.PUSHA, 0xFF, 0xFF, 0xFF, 0xFF), nil))
|
||||||
t.Run("TooBig", getTestFuncForVM(makeProgram(opcode.PUSHA, 10, 0, 0, 0), nil))
|
t.Run("TooBig", getTestFuncForVM(makeProgram(opcode.PUSHA, 10, 0, 0, 0), nil))
|
||||||
t.Run("Good", func(t *testing.T) {
|
t.Run("Good", func(t *testing.T) {
|
||||||
prog := makeProgram(opcode.PUSHA, 2, 0, 0, 0)
|
prog := makeProgram(opcode.NOP, opcode.PUSHA, 2, 0, 0, 0)
|
||||||
runWithArgs(t, prog, stackitem.NewPointer(2, prog))
|
runWithArgs(t, prog, stackitem.NewPointer(3, prog))
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue