From f3650e20b024cef3b5b35e98e0705b481f18ef9e Mon Sep 17 00:00:00 2001 From: Evgenii Stratonikov Date: Thu, 13 Aug 2020 10:41:33 +0300 Subject: [PATCH] vm: move InteropNameToID to a separate package --- pkg/compiler/panic_test.go | 4 ++-- pkg/compiler/verify_test.go | 4 ++-- pkg/compiler/vm_test.go | 10 ++++----- pkg/core/interop/callback/callback.go | 4 ++-- pkg/core/interop/crypto/interop.go | 14 ++++++------ pkg/core/interop/interopnames/convert.go | 12 ++++++++++ pkg/core/interop/json/json_test.go | 6 ++--- pkg/core/interops.go | 4 ++-- pkg/smartcontract/contract_test.go | 4 ++-- pkg/vm/contract_checks.go | 6 ++--- pkg/vm/emit/emit.go | 10 ++------- pkg/vm/emit/emit_test.go | 3 ++- pkg/vm/interop.go | 28 ++++++++++++------------ pkg/vm/vm_test.go | 3 ++- 14 files changed, 60 insertions(+), 52 deletions(-) create mode 100644 pkg/core/interop/interopnames/convert.go diff --git a/pkg/compiler/panic_test.go b/pkg/compiler/panic_test.go index 646bca04e..713b41e9f 100644 --- a/pkg/compiler/panic_test.go +++ b/pkg/compiler/panic_test.go @@ -6,8 +6,8 @@ import ( "math/big" "testing" + "github.com/nspcc-dev/neo-go/pkg/core/interop/interopnames" "github.com/nspcc-dev/neo-go/pkg/vm" - "github.com/nspcc-dev/neo-go/pkg/vm/emit" "github.com/stretchr/testify/require" ) @@ -56,7 +56,7 @@ func getPanicSource(need bool, message string) string { } func getLogHandler(logs *[]string) vm.SyscallHandler { - logID := emit.InteropNameToID([]byte("System.Runtime.Log")) + logID := interopnames.ToID([]byte("System.Runtime.Log")) return func(v *vm.VM, id uint32) error { if id != logID { return errors.New("syscall not found") diff --git a/pkg/compiler/verify_test.go b/pkg/compiler/verify_test.go index 329f3e016..1c514f430 100644 --- a/pkg/compiler/verify_test.go +++ b/pkg/compiler/verify_test.go @@ -4,9 +4,9 @@ import ( "fmt" "testing" + "github.com/nspcc-dev/neo-go/pkg/core/interop/interopnames" "github.com/nspcc-dev/neo-go/pkg/crypto/keys" "github.com/nspcc-dev/neo-go/pkg/vm" - "github.com/nspcc-dev/neo-go/pkg/vm/emit" "github.com/stretchr/testify/assert" "github.com/stretchr/testify/require" ) @@ -19,7 +19,7 @@ func TestVerifyGood(t *testing.T) { src := getVerifyProg(pub, sig, msg) v, p := vmAndCompileInterop(t, src) - p.interops[emit.InteropNameToID([]byte("Neo.Crypto.VerifyWithECDsaSecp256r1"))] = func(v *vm.VM) error { + p.interops[interopnames.ToID([]byte("Neo.Crypto.VerifyWithECDsaSecp256r1"))] = func(v *vm.VM) error { assert.Equal(t, msg, v.Estack().Pop().Bytes()) assert.Equal(t, pub, v.Estack().Pop().Bytes()) assert.Equal(t, sig, v.Estack().Pop().Bytes()) diff --git a/pkg/compiler/vm_test.go b/pkg/compiler/vm_test.go index d4a317d36..1a4665199 100644 --- a/pkg/compiler/vm_test.go +++ b/pkg/compiler/vm_test.go @@ -7,11 +7,11 @@ import ( "testing" "github.com/nspcc-dev/neo-go/pkg/compiler" + "github.com/nspcc-dev/neo-go/pkg/core/interop/interopnames" "github.com/nspcc-dev/neo-go/pkg/core/state" "github.com/nspcc-dev/neo-go/pkg/smartcontract" "github.com/nspcc-dev/neo-go/pkg/smartcontract/manifest" "github.com/nspcc-dev/neo-go/pkg/vm" - "github.com/nspcc-dev/neo-go/pkg/vm/emit" "github.com/nspcc-dev/neo-go/pkg/vm/stackitem" "github.com/stretchr/testify/assert" "github.com/stretchr/testify/require" @@ -109,10 +109,10 @@ func newStoragePlugin() *storagePlugin { mem: make(map[string][]byte), interops: make(map[uint32]func(v *vm.VM) error), } - s.interops[emit.InteropNameToID([]byte("System.Storage.Get"))] = s.Get - s.interops[emit.InteropNameToID([]byte("System.Storage.Put"))] = s.Put - s.interops[emit.InteropNameToID([]byte("System.Storage.GetContext"))] = s.GetContext - s.interops[emit.InteropNameToID([]byte("System.Runtime.Notify"))] = s.Notify + s.interops[interopnames.ToID([]byte("System.Storage.Get"))] = s.Get + s.interops[interopnames.ToID([]byte("System.Storage.Put"))] = s.Put + s.interops[interopnames.ToID([]byte("System.Storage.GetContext"))] = s.GetContext + s.interops[interopnames.ToID([]byte("System.Runtime.Notify"))] = s.Notify return s } diff --git a/pkg/core/interop/callback/callback.go b/pkg/core/interop/callback/callback.go index 6ea266341..2cc420bf0 100644 --- a/pkg/core/interop/callback/callback.go +++ b/pkg/core/interop/callback/callback.go @@ -4,8 +4,8 @@ import ( "errors" "github.com/nspcc-dev/neo-go/pkg/core/interop" + "github.com/nspcc-dev/neo-go/pkg/core/interop/interopnames" "github.com/nspcc-dev/neo-go/pkg/vm" - "github.com/nspcc-dev/neo-go/pkg/vm/emit" "github.com/nspcc-dev/neo-go/pkg/vm/stackitem" ) @@ -27,7 +27,7 @@ func Invoke(ic *interop.Context) error { cb.LoadContext(ic.VM, args) switch t := cb.(type) { case *MethodCallback: - id := emit.InteropNameToID([]byte("System.Contract.Call")) + id := interopnames.ToID([]byte("System.Contract.Call")) return ic.SyscallHandler(ic.VM, id) case *SyscallCallback: return ic.SyscallHandler(ic.VM, t.desc.ID) diff --git a/pkg/core/interop/crypto/interop.go b/pkg/core/interop/crypto/interop.go index a27850577..7aece73ae 100644 --- a/pkg/core/interop/crypto/interop.go +++ b/pkg/core/interop/crypto/interop.go @@ -2,16 +2,16 @@ package crypto import ( "github.com/nspcc-dev/neo-go/pkg/core/interop" - "github.com/nspcc-dev/neo-go/pkg/vm/emit" + "github.com/nspcc-dev/neo-go/pkg/core/interop/interopnames" ) var ( - ecdsaSecp256r1VerifyID = emit.InteropNameToID([]byte("Neo.Crypto.VerifyWithECDsaSecp256r1")) - ecdsaSecp256k1VerifyID = emit.InteropNameToID([]byte("Neo.Crypto.VerifyWithECDsaSecp256k1")) - ecdsaSecp256r1CheckMultisigID = emit.InteropNameToID([]byte("Neo.Crypto.CheckMultisigWithECDsaSecp256r1")) - ecdsaSecp256k1CheckMultisigID = emit.InteropNameToID([]byte("Neo.Crypto.CheckMultisigWithECDsaSecp256k1")) - sha256ID = emit.InteropNameToID([]byte("Neo.Crypto.SHA256")) - ripemd160ID = emit.InteropNameToID([]byte("Neo.Crypto.RIPEMD160")) + ecdsaSecp256r1VerifyID = interopnames.ToID([]byte("Neo.Crypto.VerifyWithECDsaSecp256r1")) + ecdsaSecp256k1VerifyID = interopnames.ToID([]byte("Neo.Crypto.VerifyWithECDsaSecp256k1")) + ecdsaSecp256r1CheckMultisigID = interopnames.ToID([]byte("Neo.Crypto.CheckMultisigWithECDsaSecp256r1")) + ecdsaSecp256k1CheckMultisigID = interopnames.ToID([]byte("Neo.Crypto.CheckMultisigWithECDsaSecp256k1")) + sha256ID = interopnames.ToID([]byte("Neo.Crypto.SHA256")) + ripemd160ID = interopnames.ToID([]byte("Neo.Crypto.RIPEMD160")) ) var cryptoInterops = []interop.Function{ diff --git a/pkg/core/interop/interopnames/convert.go b/pkg/core/interop/interopnames/convert.go new file mode 100644 index 000000000..cacd44985 --- /dev/null +++ b/pkg/core/interop/interopnames/convert.go @@ -0,0 +1,12 @@ +package interopnames + +import ( + "crypto/sha256" + "encoding/binary" +) + +// ToID returns an identificator of the method based on its name. +func ToID(name []byte) uint32 { + h := sha256.Sum256(name) + return binary.LittleEndian.Uint32(h[:4]) +} diff --git a/pkg/core/interop/json/json_test.go b/pkg/core/interop/json/json_test.go index 12a86edcc..62067a339 100644 --- a/pkg/core/interop/json/json_test.go +++ b/pkg/core/interop/json/json_test.go @@ -5,15 +5,15 @@ import ( "testing" "github.com/nspcc-dev/neo-go/pkg/core/interop" - "github.com/nspcc-dev/neo-go/pkg/vm/emit" + "github.com/nspcc-dev/neo-go/pkg/core/interop/interopnames" "github.com/nspcc-dev/neo-go/pkg/vm/opcode" "github.com/nspcc-dev/neo-go/pkg/vm/stackitem" "github.com/stretchr/testify/require" ) var ( - serializeID = emit.InteropNameToID([]byte("System.Json.Serialize")) - deserializeID = emit.InteropNameToID([]byte("System.Json.Deserialize")) + serializeID = interopnames.ToID([]byte("System.Json.Serialize")) + deserializeID = interopnames.ToID([]byte("System.Json.Deserialize")) ) var jsonInterops = []interop.Function{ diff --git a/pkg/core/interops.go b/pkg/core/interops.go index 6b92e703d..ea15367b2 100644 --- a/pkg/core/interops.go +++ b/pkg/core/interops.go @@ -12,13 +12,13 @@ import ( "github.com/nspcc-dev/neo-go/pkg/core/interop/callback" "github.com/nspcc-dev/neo-go/pkg/core/interop/crypto" "github.com/nspcc-dev/neo-go/pkg/core/interop/enumerator" + "github.com/nspcc-dev/neo-go/pkg/core/interop/interopnames" "github.com/nspcc-dev/neo-go/pkg/core/interop/iterator" "github.com/nspcc-dev/neo-go/pkg/core/interop/json" "github.com/nspcc-dev/neo-go/pkg/core/interop/runtime" "github.com/nspcc-dev/neo-go/pkg/core/native" "github.com/nspcc-dev/neo-go/pkg/smartcontract" "github.com/nspcc-dev/neo-go/pkg/vm" - "github.com/nspcc-dev/neo-go/pkg/vm/emit" ) // SpawnVM returns a VM with script getter and interop functions set @@ -125,7 +125,7 @@ var neoInterops = []interop.Function{ // Function slice and then sorts it. func initIDinInteropsSlice(iops []interop.Function) { for i := range iops { - iops[i].ID = emit.InteropNameToID([]byte(iops[i].Name)) + iops[i].ID = interopnames.ToID([]byte(iops[i].Name)) } interop.Sort(iops) } diff --git a/pkg/smartcontract/contract_test.go b/pkg/smartcontract/contract_test.go index 1c8e74f9c..2b8c4d8ce 100644 --- a/pkg/smartcontract/contract_test.go +++ b/pkg/smartcontract/contract_test.go @@ -3,9 +3,9 @@ package smartcontract import ( "testing" + "github.com/nspcc-dev/neo-go/pkg/core/interop/interopnames" "github.com/nspcc-dev/neo-go/pkg/crypto/keys" "github.com/nspcc-dev/neo-go/pkg/io" - "github.com/nspcc-dev/neo-go/pkg/vm/emit" "github.com/nspcc-dev/neo-go/pkg/vm/opcode" "github.com/stretchr/testify/assert" "github.com/stretchr/testify/require" @@ -34,7 +34,7 @@ func TestCreateMultiSigRedeemScript(t *testing.T) { assert.Equal(t, opcode.PUSH3, opcode.Opcode(br.ReadB())) assert.Equal(t, opcode.PUSHNULL, opcode.Opcode(br.ReadB())) assert.Equal(t, opcode.SYSCALL, opcode.Opcode(br.ReadB())) - assert.Equal(t, emit.InteropNameToID([]byte("Neo.Crypto.CheckMultisigWithECDsaSecp256r1")), br.ReadU32LE()) + assert.Equal(t, interopnames.ToID([]byte("Neo.Crypto.CheckMultisigWithECDsaSecp256r1")), br.ReadU32LE()) } func TestCreateDefaultMultiSigRedeemScript(t *testing.T) { diff --git a/pkg/vm/contract_checks.go b/pkg/vm/contract_checks.go index cd2f83b52..75da4d11f 100644 --- a/pkg/vm/contract_checks.go +++ b/pkg/vm/contract_checks.go @@ -3,15 +3,15 @@ package vm import ( "encoding/binary" + "github.com/nspcc-dev/neo-go/pkg/core/interop/interopnames" "github.com/nspcc-dev/neo-go/pkg/encoding/bigint" - "github.com/nspcc-dev/neo-go/pkg/vm/emit" "github.com/nspcc-dev/neo-go/pkg/vm/opcode" "github.com/nspcc-dev/neo-go/pkg/vm/stackitem" ) var ( - verifyInteropID = emit.InteropNameToID([]byte("Neo.Crypto.VerifyWithECDsaSecp256r1")) - multisigInteropID = emit.InteropNameToID([]byte("Neo.Crypto.CheckMultisigWithECDsaSecp256r1")) + verifyInteropID = interopnames.ToID([]byte("Neo.Crypto.VerifyWithECDsaSecp256r1")) + multisigInteropID = interopnames.ToID([]byte("Neo.Crypto.CheckMultisigWithECDsaSecp256r1")) ) func getNumOfThingsFromInstr(instr opcode.Opcode, param []byte) (int, bool) { diff --git a/pkg/vm/emit/emit.go b/pkg/vm/emit/emit.go index 84fbad3c5..10c1322b0 100644 --- a/pkg/vm/emit/emit.go +++ b/pkg/vm/emit/emit.go @@ -1,13 +1,13 @@ package emit import ( - "crypto/sha256" "encoding/binary" "errors" "fmt" "math/big" "math/bits" + "github.com/nspcc-dev/neo-go/pkg/core/interop/interopnames" "github.com/nspcc-dev/neo-go/pkg/encoding/bigint" "github.com/nspcc-dev/neo-go/pkg/io" "github.com/nspcc-dev/neo-go/pkg/util" @@ -124,7 +124,7 @@ func Syscall(w *io.BinWriter, api string) { return } buf := make([]byte, 4) - binary.LittleEndian.PutUint32(buf, InteropNameToID([]byte(api))) + binary.LittleEndian.PutUint32(buf, interopnames.ToID([]byte(api))) Instruction(w, opcode.SYSCALL, buf) } @@ -162,9 +162,3 @@ func AppCallWithOperationAndArgs(w *io.BinWriter, scriptHash util.Uint160, opera func isInstructionJmp(op opcode.Opcode) bool { return opcode.JMP <= op && op <= opcode.CALLL } - -// InteropNameToID returns an identificator of the method based on its name. -func InteropNameToID(name []byte) uint32 { - h := sha256.Sum256(name) - return binary.LittleEndian.Uint32(h[:4]) -} diff --git a/pkg/vm/emit/emit_test.go b/pkg/vm/emit/emit_test.go index ddda3e684..5c08f5377 100644 --- a/pkg/vm/emit/emit_test.go +++ b/pkg/vm/emit/emit_test.go @@ -5,6 +5,7 @@ import ( "errors" "testing" + "github.com/nspcc-dev/neo-go/pkg/core/interop/interopnames" "github.com/nspcc-dev/neo-go/pkg/encoding/bigint" "github.com/nspcc-dev/neo-go/pkg/io" "github.com/nspcc-dev/neo-go/pkg/vm/opcode" @@ -201,7 +202,7 @@ func TestEmitSyscall(t *testing.T) { result := buf.Bytes() assert.Equal(t, 5, len(result)) assert.Equal(t, opcode.Opcode(result[0]), opcode.SYSCALL) - assert.Equal(t, binary.LittleEndian.Uint32(result[1:]), InteropNameToID([]byte(syscall))) + assert.Equal(t, binary.LittleEndian.Uint32(result[1:]), interopnames.ToID([]byte(syscall))) buf.Reset() } diff --git a/pkg/vm/interop.go b/pkg/vm/interop.go index ec1cf0ef3..515ce290c 100644 --- a/pkg/vm/interop.go +++ b/pkg/vm/interop.go @@ -5,8 +5,8 @@ import ( "fmt" "sort" + "github.com/nspcc-dev/neo-go/pkg/core/interop/interopnames" "github.com/nspcc-dev/neo-go/pkg/smartcontract" - "github.com/nspcc-dev/neo-go/pkg/vm/emit" "github.com/nspcc-dev/neo-go/pkg/vm/stackitem" ) @@ -19,31 +19,31 @@ type interopIDFuncPrice struct { } var defaultVMInterops = []interopIDFuncPrice{ - {ID: emit.InteropNameToID([]byte("System.Binary.Deserialize")), + {ID: interopnames.ToID([]byte("System.Binary.Deserialize")), Func: RuntimeDeserialize, Price: 500000}, - {ID: emit.InteropNameToID([]byte("System.Binary.Serialize")), + {ID: interopnames.ToID([]byte("System.Binary.Serialize")), Func: RuntimeSerialize, Price: 100000}, - {ID: emit.InteropNameToID([]byte("System.Runtime.Log")), + {ID: interopnames.ToID([]byte("System.Runtime.Log")), Func: runtimeLog, Price: 1000000, RequiredFlags: smartcontract.AllowNotify}, - {ID: emit.InteropNameToID([]byte("System.Runtime.Notify")), + {ID: interopnames.ToID([]byte("System.Runtime.Notify")), Func: runtimeNotify, Price: 1000000, RequiredFlags: smartcontract.AllowNotify}, - {ID: emit.InteropNameToID([]byte("System.Enumerator.Create")), + {ID: interopnames.ToID([]byte("System.Enumerator.Create")), Func: EnumeratorCreate, Price: 400}, - {ID: emit.InteropNameToID([]byte("System.Enumerator.Next")), + {ID: interopnames.ToID([]byte("System.Enumerator.Next")), Func: EnumeratorNext, Price: 1000000}, - {ID: emit.InteropNameToID([]byte("System.Enumerator.Concat")), + {ID: interopnames.ToID([]byte("System.Enumerator.Concat")), Func: EnumeratorConcat, Price: 400}, - {ID: emit.InteropNameToID([]byte("System.Enumerator.Value")), + {ID: interopnames.ToID([]byte("System.Enumerator.Value")), Func: EnumeratorValue, Price: 400}, - {ID: emit.InteropNameToID([]byte("System.Iterator.Create")), + {ID: interopnames.ToID([]byte("System.Iterator.Create")), Func: IteratorCreate, Price: 400}, - {ID: emit.InteropNameToID([]byte("System.Iterator.Concat")), + {ID: interopnames.ToID([]byte("System.Iterator.Concat")), Func: IteratorConcat, Price: 400}, - {ID: emit.InteropNameToID([]byte("System.Iterator.Key")), + {ID: interopnames.ToID([]byte("System.Iterator.Key")), Func: IteratorKey, Price: 400}, - {ID: emit.InteropNameToID([]byte("System.Iterator.Keys")), + {ID: interopnames.ToID([]byte("System.Iterator.Keys")), Func: IteratorKeys, Price: 400}, - {ID: emit.InteropNameToID([]byte("System.Iterator.Values")), + {ID: interopnames.ToID([]byte("System.Iterator.Values")), Func: IteratorValues, Price: 400}, } diff --git a/pkg/vm/vm_test.go b/pkg/vm/vm_test.go index a61b41a4f..8c967d153 100644 --- a/pkg/vm/vm_test.go +++ b/pkg/vm/vm_test.go @@ -11,6 +11,7 @@ import ( "math/rand" "testing" + "github.com/nspcc-dev/neo-go/pkg/core/interop/interopnames" "github.com/nspcc-dev/neo-go/pkg/encoding/bigint" "github.com/nspcc-dev/neo-go/pkg/internal/random" "github.com/nspcc-dev/neo-go/pkg/io" @@ -23,7 +24,7 @@ import ( ) func fooInteropHandler(v *VM, id uint32) error { - if id == emit.InteropNameToID([]byte("foo")) { + if id == interopnames.ToID([]byte("foo")) { if !v.AddGas(1) { return errors.New("invalid gas amount") }