blockchain: properly set invocation counter for verification ctx
Fix problem noted in #2270.
This commit is contained in:
parent
9f9bd7261c
commit
fc45d3b132
4 changed files with 12 additions and 19 deletions
|
@ -22,7 +22,6 @@ import (
|
|||
"github.com/nspcc-dev/neo-go/pkg/rpc/response/result/subscriptions"
|
||||
"github.com/nspcc-dev/neo-go/pkg/smartcontract/trigger"
|
||||
"github.com/nspcc-dev/neo-go/pkg/util"
|
||||
"github.com/nspcc-dev/neo-go/pkg/vm"
|
||||
uatomic "go.uber.org/atomic"
|
||||
)
|
||||
|
||||
|
@ -104,8 +103,8 @@ func (chain *FakeChain) IsTxStillRelevant(t *transaction.Transaction, txpool *me
|
|||
panic("TODO")
|
||||
}
|
||||
|
||||
// InitVerificationVM initializes VM for witness check.
|
||||
func (chain *FakeChain) InitVerificationVM(v *vm.VM, getContract func(util.Uint160) (*state.Contract, error), hash util.Uint160, witness *transaction.Witness) error {
|
||||
// InitVerificationContext initializes context for witness check.
|
||||
func (chain *FakeChain) InitVerificationContext(ic *interop.Context, hash util.Uint160, witness *transaction.Witness) error {
|
||||
panic("TODO")
|
||||
}
|
||||
|
||||
|
|
|
@ -2160,8 +2160,8 @@ var (
|
|||
ErrInvalidVerificationContract = errors.New("verification contract is missing `verify` method")
|
||||
)
|
||||
|
||||
// InitVerificationVM initializes VM for witness check.
|
||||
func (bc *Blockchain) InitVerificationVM(v *vm.VM, getContract func(util.Uint160) (*state.Contract, error), hash util.Uint160, witness *transaction.Witness) error {
|
||||
// InitVerificationContext initializes context for witness check.
|
||||
func (bc *Blockchain) InitVerificationContext(ic *interop.Context, hash util.Uint160, witness *transaction.Witness) error {
|
||||
if len(witness.VerificationScript) != 0 {
|
||||
if witness.ScriptHash() != hash {
|
||||
return ErrWitnessHashMismatch
|
||||
|
@ -2173,9 +2173,9 @@ func (bc *Blockchain) InitVerificationVM(v *vm.VM, getContract func(util.Uint160
|
|||
if err != nil {
|
||||
return fmt.Errorf("%w: %v", ErrInvalidVerification, err)
|
||||
}
|
||||
v.LoadScriptWithHash(witness.VerificationScript, hash, callflag.ReadOnly)
|
||||
ic.VM.LoadScriptWithHash(witness.VerificationScript, hash, callflag.ReadOnly)
|
||||
} else {
|
||||
cs, err := getContract(hash)
|
||||
cs, err := ic.GetContract(hash)
|
||||
if err != nil {
|
||||
return ErrUnknownVerificationContract
|
||||
}
|
||||
|
@ -2189,7 +2189,8 @@ func (bc *Blockchain) InitVerificationVM(v *vm.VM, getContract func(util.Uint160
|
|||
if md != nil {
|
||||
initOffset = md.Offset
|
||||
}
|
||||
v.LoadNEFMethod(&cs.NEF, util.Uint160{}, hash, callflag.ReadOnly,
|
||||
ic.Invocations[cs.Hash]++
|
||||
ic.VM.LoadNEFMethod(&cs.NEF, util.Uint160{}, hash, callflag.ReadOnly,
|
||||
true, verifyOffset, initOffset)
|
||||
}
|
||||
if len(witness.InvocationScript) != 0 {
|
||||
|
@ -2197,7 +2198,7 @@ func (bc *Blockchain) InitVerificationVM(v *vm.VM, getContract func(util.Uint160
|
|||
if err != nil {
|
||||
return fmt.Errorf("%w: %v", ErrInvalidInvocation, err)
|
||||
}
|
||||
v.LoadScript(witness.InvocationScript)
|
||||
ic.VM.LoadScript(witness.InvocationScript)
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
@ -2221,7 +2222,7 @@ func (bc *Blockchain) verifyHashAgainstScript(hash util.Uint160, witness *transa
|
|||
vm.SetPriceGetter(interopCtx.GetPrice)
|
||||
vm.LoadToken = contract.LoadToken(interopCtx)
|
||||
vm.GasLimit = gas
|
||||
if err := bc.InitVerificationVM(vm, interopCtx.GetContract, hash, witness); err != nil {
|
||||
if err := bc.InitVerificationContext(interopCtx, hash, witness); err != nil {
|
||||
return 0, err
|
||||
}
|
||||
err := interopCtx.Exec()
|
||||
|
|
|
@ -15,7 +15,6 @@ import (
|
|||
"github.com/nspcc-dev/neo-go/pkg/rpc/response/result/subscriptions"
|
||||
"github.com/nspcc-dev/neo-go/pkg/smartcontract/trigger"
|
||||
"github.com/nspcc-dev/neo-go/pkg/util"
|
||||
"github.com/nspcc-dev/neo-go/pkg/vm"
|
||||
)
|
||||
|
||||
// Blockchainer is an interface that abstract the implementation
|
||||
|
@ -26,7 +25,7 @@ type Blockchainer interface {
|
|||
Blockqueuer // Blockqueuer interface
|
||||
CalculateClaimable(h util.Uint160, endHeight uint32) (*big.Int, error)
|
||||
Close()
|
||||
InitVerificationVM(v *vm.VM, getContract func(util.Uint160) (*state.Contract, error), hash util.Uint160, witness *transaction.Witness) error
|
||||
InitVerificationContext(ic *interop.Context, hash util.Uint160, witness *transaction.Witness) error
|
||||
IsTxStillRelevant(t *transaction.Transaction, txpool *mempool.Pool, isPartialTx bool) bool
|
||||
HeaderHeight() uint32
|
||||
GetBlock(hash util.Uint256) (*block.Block, error)
|
||||
|
|
|
@ -1703,13 +1703,7 @@ func (s *Server) runScriptInVM(t trigger.Type, script []byte, contractScriptHash
|
|||
ic.VM.GasLimit = gasPolicy
|
||||
}
|
||||
|
||||
err := s.chain.InitVerificationVM(ic.VM, func(h util.Uint160) (*state.Contract, error) {
|
||||
res := s.chain.GetContractState(h)
|
||||
if res == nil {
|
||||
return nil, fmt.Errorf("unknown contract: %s", h.StringBE())
|
||||
}
|
||||
return res, nil
|
||||
}, contractScriptHash, &transaction.Witness{InvocationScript: script, VerificationScript: []byte{}})
|
||||
err := s.chain.InitVerificationContext(ic, contractScriptHash, &transaction.Witness{InvocationScript: script, VerificationScript: []byte{}})
|
||||
if err != nil {
|
||||
return nil, response.NewInternalServerError("can't prepare verification VM", err)
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue