Merge pull request #540 from nspcc-dev/feature/triggerType_509
core: add trigger types as constants. Closes #509
This commit is contained in:
commit
e251889f7b
5 changed files with 57 additions and 17 deletions
|
@ -16,6 +16,7 @@ import (
|
|||
"github.com/CityOfZion/neo-go/pkg/crypto/keys"
|
||||
"github.com/CityOfZion/neo-go/pkg/io"
|
||||
"github.com/CityOfZion/neo-go/pkg/smartcontract"
|
||||
"github.com/CityOfZion/neo-go/pkg/smartcontract/trigger"
|
||||
"github.com/CityOfZion/neo-go/pkg/util"
|
||||
"github.com/CityOfZion/neo-go/pkg/vm"
|
||||
"github.com/pkg/errors"
|
||||
|
@ -487,7 +488,7 @@ func (bc *Blockchain) storeBlock(block *Block) error {
|
|||
}
|
||||
chainState.contracts[contract.ScriptHash()] = contract
|
||||
case *transaction.InvocationTX:
|
||||
systemInterop := newInteropContext(0x10, bc, chainState.store, block, tx)
|
||||
systemInterop := newInteropContext(trigger.Application, bc, chainState.store, block, tx)
|
||||
v := bc.spawnVMWithInterops(systemInterop)
|
||||
v.SetCheckedHash(tx.VerificationHash().Bytes())
|
||||
v.LoadScript(t.Script)
|
||||
|
@ -530,7 +531,7 @@ func (bc *Blockchain) storeBlock(block *Block) error {
|
|||
}
|
||||
aer := &AppExecResult{
|
||||
TxHash: tx.Hash(),
|
||||
Trigger: 0x10,
|
||||
Trigger: trigger.Application,
|
||||
VMState: v.State(),
|
||||
GasConsumed: util.Fixed8(0),
|
||||
Stack: v.Stack("estack"),
|
||||
|
@ -1418,7 +1419,7 @@ func (bc *Blockchain) spawnVMWithInterops(interopCtx *interopContext) *vm.VM {
|
|||
// GetTestVM returns a VM and a Store setup for a test run of some sort of code.
|
||||
func (bc *Blockchain) GetTestVM() (*vm.VM, storage.Store) {
|
||||
tmpStore := storage.NewMemCachedStore(bc.store)
|
||||
systemInterop := newInteropContext(0x10, bc, tmpStore, nil, nil)
|
||||
systemInterop := newInteropContext(trigger.Application, bc, tmpStore, nil, nil)
|
||||
vm := bc.spawnVMWithInterops(systemInterop)
|
||||
return vm, tmpStore
|
||||
}
|
||||
|
@ -1482,7 +1483,7 @@ func (bc *Blockchain) verifyTxWitnesses(t *transaction.Transaction, block *Block
|
|||
}
|
||||
sort.Slice(hashes, func(i, j int) bool { return hashes[i].Less(hashes[j]) })
|
||||
sort.Slice(witnesses, func(i, j int) bool { return witnesses[i].ScriptHash().Less(witnesses[j].ScriptHash()) })
|
||||
interopCtx := newInteropContext(0, bc, bc.store, block, t)
|
||||
interopCtx := newInteropContext(trigger.Verification, bc, bc.store, block, t)
|
||||
for i := 0; i < len(hashes); i++ {
|
||||
err := bc.verifyHashAgainstScript(hashes[i], witnesses[i], t.VerificationHash(), interopCtx)
|
||||
if err != nil {
|
||||
|
@ -1502,7 +1503,7 @@ func (bc *Blockchain) verifyBlockWitnesses(block *Block, prevHeader *Header) err
|
|||
} else {
|
||||
hash = prevHeader.NextConsensus
|
||||
}
|
||||
interopCtx := newInteropContext(0, bc, bc.store, nil, nil)
|
||||
interopCtx := newInteropContext(trigger.Verification, bc, bc.store, nil, nil)
|
||||
return bc.verifyHashAgainstScript(hash, block.Script, block.VerificationHash(), interopCtx)
|
||||
}
|
||||
|
||||
|
|
|
@ -8,6 +8,7 @@ import (
|
|||
"github.com/CityOfZion/neo-go/pkg/core/transaction"
|
||||
"github.com/CityOfZion/neo-go/pkg/crypto/keys"
|
||||
"github.com/CityOfZion/neo-go/pkg/smartcontract"
|
||||
"github.com/CityOfZion/neo-go/pkg/smartcontract/trigger"
|
||||
"github.com/CityOfZion/neo-go/pkg/util"
|
||||
"github.com/CityOfZion/neo-go/pkg/vm"
|
||||
gherr "github.com/pkg/errors"
|
||||
|
@ -429,7 +430,7 @@ func (ic *interopContext) storageFind(v *vm.VM) error {
|
|||
// evaluation stack, does a lot of checks and returns ContractState if it
|
||||
// succeeds.
|
||||
func (ic *interopContext) createContractStateFromVM(v *vm.VM) (*ContractState, error) {
|
||||
if ic.trigger != 0x10 {
|
||||
if ic.trigger != trigger.Application {
|
||||
return nil, errors.New("can't create contract when not triggered by an application")
|
||||
}
|
||||
script := v.Estack().Pop().Bytes()
|
||||
|
@ -551,7 +552,7 @@ func (ic *interopContext) contractMigrate(v *vm.VM) error {
|
|||
|
||||
// assetCreate creates an asset.
|
||||
func (ic *interopContext) assetCreate(v *vm.VM) error {
|
||||
if ic.trigger != 0x10 {
|
||||
if ic.trigger != trigger.Application {
|
||||
return errors.New("can't create asset when not triggered by an application")
|
||||
}
|
||||
atype := transaction.AssetType(v.Estack().Pop().BigInt().Int64())
|
||||
|
@ -717,7 +718,7 @@ func (ic *interopContext) assetGetPrecision(v *vm.VM) error {
|
|||
|
||||
// assetRenew updates asset expiration date.
|
||||
func (ic *interopContext) assetRenew(v *vm.VM) error {
|
||||
if ic.trigger != 0x10 {
|
||||
if ic.trigger != trigger.Application {
|
||||
return errors.New("can't create asset when not triggered by an application")
|
||||
}
|
||||
asInterface := v.Estack().Pop().Value()
|
||||
|
|
|
@ -8,6 +8,7 @@ import (
|
|||
"github.com/CityOfZion/neo-go/pkg/core/transaction"
|
||||
"github.com/CityOfZion/neo-go/pkg/crypto/keys"
|
||||
"github.com/CityOfZion/neo-go/pkg/smartcontract"
|
||||
"github.com/CityOfZion/neo-go/pkg/smartcontract/trigger"
|
||||
"github.com/CityOfZion/neo-go/pkg/util"
|
||||
"github.com/CityOfZion/neo-go/pkg/vm"
|
||||
"github.com/stretchr/testify/require"
|
||||
|
@ -42,7 +43,7 @@ func TestHeaderGetVersion(t *testing.T) {
|
|||
func TestHeaderGetVersion_Negative(t *testing.T) {
|
||||
v := vm.New()
|
||||
block := newDumbBlock()
|
||||
context := newInteropContext(0x10, newTestChain(t), storage.NewMemoryStore(), block, nil)
|
||||
context := newInteropContext(trigger.Application, newTestChain(t), storage.NewMemoryStore(), block, nil)
|
||||
v.Estack().PushVal(vm.NewBoolItem(false))
|
||||
|
||||
err := context.headerGetVersion(v)
|
||||
|
@ -325,7 +326,7 @@ func TestAssetGetPrecision(t *testing.T) {
|
|||
func createVMAndPushBlock(t *testing.T) (*vm.VM, *Block, *interopContext) {
|
||||
v := vm.New()
|
||||
block := newDumbBlock()
|
||||
context := newInteropContext(0x10, newTestChain(t), storage.NewMemoryStore(), block, nil)
|
||||
context := newInteropContext(trigger.Application, newTestChain(t), storage.NewMemoryStore(), block, nil)
|
||||
v.Estack().PushVal(vm.NewInteropItem(block))
|
||||
return v, block, context
|
||||
}
|
||||
|
@ -354,7 +355,7 @@ func createVMAndAssetState(t *testing.T) (*vm.VM, *AssetState, *interopContext)
|
|||
IsFrozen: false,
|
||||
}
|
||||
|
||||
context := newInteropContext(0x10, newTestChain(t), storage.NewMemoryStore(), nil, nil)
|
||||
context := newInteropContext(trigger.Application, newTestChain(t), storage.NewMemoryStore(), nil, nil)
|
||||
return v, assetState, context
|
||||
}
|
||||
|
||||
|
@ -373,7 +374,7 @@ func createVMAndContractState(t *testing.T) (*vm.VM, *ContractState, *interopCon
|
|||
scriptHash: randomUint160(),
|
||||
}
|
||||
|
||||
context := newInteropContext(0x10, newTestChain(t), storage.NewMemoryStore(), nil, nil)
|
||||
context := newInteropContext(trigger.Application, newTestChain(t), storage.NewMemoryStore(), nil, nil)
|
||||
return v, contractState, context
|
||||
}
|
||||
|
||||
|
@ -387,7 +388,7 @@ func createVMAndAccState(t *testing.T) (*vm.VM, *AccountState, *interopContext)
|
|||
accountState.Votes = []*keys.PublicKey{key}
|
||||
|
||||
require.NoError(t, err)
|
||||
context := newInteropContext(0x10, newTestChain(t), storage.NewMemoryStore(), nil, nil)
|
||||
context := newInteropContext(trigger.Application, newTestChain(t), storage.NewMemoryStore(), nil, nil)
|
||||
return v, accountState, context
|
||||
}
|
||||
|
||||
|
@ -416,6 +417,6 @@ func createVMAndTX(t *testing.T) (*vm.VM, *transaction.Transaction, *interopCont
|
|||
tx.Attributes = attributes
|
||||
tx.Inputs = inputs
|
||||
tx.Outputs = outputs
|
||||
context := newInteropContext(0x10, newTestChain(t), storage.NewMemoryStore(), nil, tx)
|
||||
context := newInteropContext(trigger.Application, newTestChain(t), storage.NewMemoryStore(), nil, tx)
|
||||
return v, tx, context
|
||||
}
|
||||
|
|
|
@ -8,6 +8,7 @@ import (
|
|||
"github.com/CityOfZion/neo-go/pkg/core/transaction"
|
||||
"github.com/CityOfZion/neo-go/pkg/crypto/hash"
|
||||
"github.com/CityOfZion/neo-go/pkg/crypto/keys"
|
||||
"github.com/CityOfZion/neo-go/pkg/smartcontract/trigger"
|
||||
"github.com/CityOfZion/neo-go/pkg/util"
|
||||
"github.com/CityOfZion/neo-go/pkg/vm"
|
||||
gherr "github.com/pkg/errors"
|
||||
|
@ -393,7 +394,7 @@ func (ic *interopContext) checkStorageContext(stc *StorageContext) error {
|
|||
|
||||
// storageDelete deletes stored key-value pair.
|
||||
func (ic *interopContext) storageDelete(v *vm.VM) error {
|
||||
if ic.trigger != 0x10 && ic.trigger != 0x11 {
|
||||
if ic.trigger != trigger.Application && ic.trigger != trigger.ApplicationR {
|
||||
return errors.New("can't delete when the trigger is not application")
|
||||
}
|
||||
stcInterface := v.Estack().Pop().Value()
|
||||
|
@ -464,7 +465,7 @@ func (ic *interopContext) storageGetReadOnlyContext(v *vm.VM) error {
|
|||
}
|
||||
|
||||
func (ic *interopContext) putWithContextAndFlags(stc *StorageContext, key []byte, value []byte, isConst bool) error {
|
||||
if ic.trigger != 0x10 && ic.trigger != 0x11 {
|
||||
if ic.trigger != trigger.Application && ic.trigger != trigger.ApplicationR {
|
||||
return errors.New("can't delete when the trigger is not application")
|
||||
}
|
||||
if len(key) > MaxStorageKeyLen {
|
||||
|
@ -538,7 +539,7 @@ func (ic *interopContext) storageContextAsReadOnly(v *vm.VM) error {
|
|||
|
||||
// contractDestroy destroys a contract.
|
||||
func (ic *interopContext) contractDestroy(v *vm.VM) error {
|
||||
if ic.trigger != 0x10 {
|
||||
if ic.trigger != trigger.Application {
|
||||
return errors.New("can't destroy contract when not triggered by application")
|
||||
}
|
||||
hash := getContextScriptHash(v, 0)
|
||||
|
|
36
pkg/smartcontract/trigger/trigger_type.go
Normal file
36
pkg/smartcontract/trigger/trigger_type.go
Normal file
|
@ -0,0 +1,36 @@
|
|||
package trigger
|
||||
|
||||
// Trigger typed used in C# reference node: https://github.com/neo-project/neo/blob/c64748ecbac3baeb8045b16af0d518398a6ced24/neo/SmartContract/TriggerType.cs#L3
|
||||
const (
|
||||
// The verification trigger indicates that the contract is being invoked as a verification function.
|
||||
// The verification function can accept multiple parameters, and should return a boolean value that indicates the validity of the transaction or block.
|
||||
// The entry point of the contract will be invoked if the contract is triggered by Verification:
|
||||
// main(...);
|
||||
// The entry point of the contract must be able to handle this type of invocation.
|
||||
Verification = 0x00
|
||||
|
||||
// The verificationR trigger indicates that the contract is being invoked as a verification function because it is specified as a target of an output of the transaction.
|
||||
// The verification function accepts no parameter, and should return a boolean value that indicates the validity of the transaction.
|
||||
// The entry point of the contract will be invoked if the contract is triggered by VerificationR:
|
||||
// main("receiving", new object[0]);
|
||||
// The receiving function should have the following signature:
|
||||
// public bool receiving()
|
||||
// The receiving function will be invoked automatically when a contract is receiving assets from a transfer.
|
||||
VerificationR = 0x01
|
||||
|
||||
// The application trigger indicates that the contract is being invoked as an application function.
|
||||
// The application function can accept multiple parameters, change the states of the blockchain, and return any type of value.
|
||||
// The contract can have any form of entry point, but we recommend that all contracts should have the following entry point:
|
||||
// public byte[] main(string operation, params object[] args)
|
||||
// The functions can be invoked by creating an InvocationTransaction.
|
||||
Application = 0x10
|
||||
|
||||
// The ApplicationR trigger indicates that the default function received of the contract is being invoked because it is specified as a target of an output of the transaction.
|
||||
// The received function accepts no parameter, changes the states of the blockchain, and returns any type of value.
|
||||
// The entry point of the contract will be invoked if the contract is triggered by ApplicationR:
|
||||
// main("received", new object[0]);
|
||||
// The received function should have the following signature:
|
||||
// public byte[] received()
|
||||
// The received function will be invoked automatically when a contract is receiving assets from a transfer.
|
||||
ApplicationR = 0x11
|
||||
)
|
Loading…
Reference in a new issue