mirror of
https://github.com/nspcc-dev/neo-go.git
synced 2025-05-07 05:07:36 +00:00
vm: simplify slot and make it private
Hiding refcounter inside a slot is actually a good idea, but it makes the structure somewhat bigger, especially given that the refcounter is the same and belongs more to VM or Context. New structure is a bit more efficient: name old time/op new time/op delta ScriptFibonacci-8 672µs ± 2% 644µs ± 0% -4.15% (p=0.008 n=5+5) ScriptNestedRefCount-8 1.08ms ± 1% 1.05ms ± 2% -2.56% (p=0.008 n=5+5) ScriptPushPop/4-8 1.52µs ± 1% 1.47µs ± 1% -3.14% (p=0.008 n=5+5) ScriptPushPop/16-8 3.66µs ± 1% 3.54µs ± 1% -3.24% (p=0.008 n=5+5) ScriptPushPop/128-8 24.7µs ± 1% 23.2µs ± 1% -6.14% (p=0.008 n=5+5) ScriptPushPop/1024-8 183µs ± 1% 173µs ± 1% -5.01% (p=0.008 n=5+5) name old alloc/op new alloc/op delta ScriptFibonacci-8 114kB ± 0% 114kB ± 0% ~ (p=0.079 n=4+5) ScriptNestedRefCount-8 241kB ± 0% 241kB ± 0% ~ (p=0.333 n=5+4) ScriptPushPop/4-8 160B ± 0% 160B ± 0% ~ (all equal) ScriptPushPop/16-8 640B ± 0% 640B ± 0% ~ (all equal) ScriptPushPop/128-8 8.70kB ± 0% 8.70kB ± 0% ~ (all equal) ScriptPushPop/1024-8 73.2kB ± 0% 73.2kB ± 0% ~ (all equal) name old allocs/op new allocs/op delta ScriptFibonacci-8 3.17k ± 0% 3.17k ± 0% -0.03% (p=0.008 n=5+5) ScriptNestedRefCount-8 10.7k ± 0% 10.7k ± 0% ~ (all equal) ScriptPushPop/4-8 8.00 ± 0% 8.00 ± 0% ~ (all equal) ScriptPushPop/16-8 32.0 ± 0% 32.0 ± 0% ~ (all equal) ScriptPushPop/128-8 259 ± 0% 259 ± 0% ~ (all equal) ScriptPushPop/1024-8 2.05k ± 0% 2.05k ± 0% ~ (all equal) It'd be especially nice to internalize static slot, but as we can't compare slices it's not possible.
This commit is contained in:
parent
a0473aca92
commit
ee05f73b6f
6 changed files with 54 additions and 66 deletions
28
pkg/vm/vm.go
28
pkg/vm/vm.go
|
@ -310,13 +310,15 @@ func (v *VM) LoadNEFMethod(exe *nef.File, caller util.Uint160, hash util.Uint160
|
|||
// It should be used for calling from native contracts.
|
||||
func (v *VM) loadScriptWithCallingHash(b []byte, exe *nef.File, caller util.Uint160,
|
||||
hash util.Uint160, f callflag.CallFlag, rvcount int, offset int) {
|
||||
var sl slot
|
||||
|
||||
v.checkInvocationStackSize()
|
||||
ctx := NewContextWithParams(b, rvcount, offset)
|
||||
v.estack = newStack("evaluation", &v.refs)
|
||||
ctx.estack = v.estack
|
||||
initStack(&ctx.tryStack, "exception", nil)
|
||||
ctx.callFlag = f
|
||||
ctx.static = newSlot(&v.refs)
|
||||
ctx.static = &sl
|
||||
ctx.scriptHash = hash
|
||||
ctx.callingScriptHash = caller
|
||||
ctx.NEF = exe
|
||||
|
@ -615,13 +617,13 @@ func (v *VM) execute(ctx *Context, op opcode.Opcode, parameter []byte) (err erro
|
|||
panic("zero argument")
|
||||
}
|
||||
if parameter[0] > 0 {
|
||||
ctx.local = v.newSlot(int(parameter[0]))
|
||||
ctx.local.init(int(parameter[0]))
|
||||
}
|
||||
if parameter[1] > 0 {
|
||||
sz := int(parameter[1])
|
||||
ctx.arguments = v.newSlot(sz)
|
||||
ctx.arguments.init(sz)
|
||||
for i := 0; i < sz; i++ {
|
||||
ctx.arguments.Set(i, v.estack.Pop().Item())
|
||||
ctx.arguments.Set(i, v.estack.Pop().Item(), &v.refs)
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -635,11 +637,11 @@ func (v *VM) execute(ctx *Context, op opcode.Opcode, parameter []byte) (err erro
|
|||
|
||||
case opcode.STSFLD0, opcode.STSFLD1, opcode.STSFLD2, opcode.STSFLD3, opcode.STSFLD4, opcode.STSFLD5, opcode.STSFLD6:
|
||||
item := v.estack.Pop().Item()
|
||||
ctx.static.Set(int(op-opcode.STSFLD0), item)
|
||||
ctx.static.Set(int(op-opcode.STSFLD0), item, &v.refs)
|
||||
|
||||
case opcode.STSFLD:
|
||||
item := v.estack.Pop().Item()
|
||||
ctx.static.Set(int(parameter[0]), item)
|
||||
ctx.static.Set(int(parameter[0]), item, &v.refs)
|
||||
|
||||
case opcode.LDLOC0, opcode.LDLOC1, opcode.LDLOC2, opcode.LDLOC3, opcode.LDLOC4, opcode.LDLOC5, opcode.LDLOC6:
|
||||
item := ctx.local.Get(int(op - opcode.LDLOC0))
|
||||
|
@ -651,11 +653,11 @@ func (v *VM) execute(ctx *Context, op opcode.Opcode, parameter []byte) (err erro
|
|||
|
||||
case opcode.STLOC0, opcode.STLOC1, opcode.STLOC2, opcode.STLOC3, opcode.STLOC4, opcode.STLOC5, opcode.STLOC6:
|
||||
item := v.estack.Pop().Item()
|
||||
ctx.local.Set(int(op-opcode.STLOC0), item)
|
||||
ctx.local.Set(int(op-opcode.STLOC0), item, &v.refs)
|
||||
|
||||
case opcode.STLOC:
|
||||
item := v.estack.Pop().Item()
|
||||
ctx.local.Set(int(parameter[0]), item)
|
||||
ctx.local.Set(int(parameter[0]), item, &v.refs)
|
||||
|
||||
case opcode.LDARG0, opcode.LDARG1, opcode.LDARG2, opcode.LDARG3, opcode.LDARG4, opcode.LDARG5, opcode.LDARG6:
|
||||
item := ctx.arguments.Get(int(op - opcode.LDARG0))
|
||||
|
@ -667,11 +669,11 @@ func (v *VM) execute(ctx *Context, op opcode.Opcode, parameter []byte) (err erro
|
|||
|
||||
case opcode.STARG0, opcode.STARG1, opcode.STARG2, opcode.STARG3, opcode.STARG4, opcode.STARG5, opcode.STARG6:
|
||||
item := v.estack.Pop().Item()
|
||||
ctx.arguments.Set(int(op-opcode.STARG0), item)
|
||||
ctx.arguments.Set(int(op-opcode.STARG0), item, &v.refs)
|
||||
|
||||
case opcode.STARG:
|
||||
item := v.estack.Pop().Item()
|
||||
ctx.arguments.Set(int(parameter[0]), item)
|
||||
ctx.arguments.Set(int(parameter[0]), item, &v.refs)
|
||||
|
||||
case opcode.NEWBUFFER:
|
||||
n := toInt(v.estack.Pop().BigInt())
|
||||
|
@ -1527,14 +1529,14 @@ func (v *VM) execute(ctx *Context, op opcode.Opcode, parameter []byte) (err erro
|
|||
|
||||
func (v *VM) unloadContext(ctx *Context) {
|
||||
if ctx.local != nil {
|
||||
ctx.local.Clear()
|
||||
ctx.local.Clear(&v.refs)
|
||||
}
|
||||
if ctx.arguments != nil {
|
||||
ctx.arguments.Clear()
|
||||
ctx.arguments.Clear(&v.refs)
|
||||
}
|
||||
currCtx := v.Context()
|
||||
if ctx.static != nil && currCtx != nil && ctx.static != currCtx.static {
|
||||
ctx.static.Clear()
|
||||
ctx.static.Clear(&v.refs)
|
||||
}
|
||||
}
|
||||
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue