mirror of
https://github.com/nspcc-dev/neo-go.git
synced 2024-11-22 19:29:39 +00:00
core: move GetScriptContainer to runtime
It also brings ToStackItem to Block and Transaction, previously this was avoided to separate block and transaction packages from VM. But turns out `transaction` depends on `stackitem` already, so this makes little sense (but can be shuffled in another way if needed). Context.Container is still a hash.Hashable because we have a number of occasions (header or MPT root verification) where there is no ToStackItem implementation possible. Maybe they can go with `nil` Container, but I don't want to have this risk for now.
This commit is contained in:
parent
cdb55740ea
commit
d70caf1da1
6 changed files with 52 additions and 53 deletions
|
@ -4,11 +4,13 @@ import (
|
|||
"encoding/json"
|
||||
"errors"
|
||||
"math"
|
||||
"math/big"
|
||||
|
||||
"github.com/nspcc-dev/neo-go/pkg/core/transaction"
|
||||
"github.com/nspcc-dev/neo-go/pkg/crypto/hash"
|
||||
"github.com/nspcc-dev/neo-go/pkg/io"
|
||||
"github.com/nspcc-dev/neo-go/pkg/util"
|
||||
"github.com/nspcc-dev/neo-go/pkg/vm/stackitem"
|
||||
)
|
||||
|
||||
const (
|
||||
|
@ -211,3 +213,18 @@ func (b *Block) GetExpectedBlockSizeWithoutTransactions(txCount int) int {
|
|||
}
|
||||
return size
|
||||
}
|
||||
|
||||
// ToStackItem converts Block to stackitem.Item.
|
||||
func (b *Block) ToStackItem() stackitem.Item {
|
||||
return stackitem.NewArray([]stackitem.Item{
|
||||
stackitem.NewByteArray(b.Hash().BytesBE()),
|
||||
stackitem.NewBigInteger(big.NewInt(int64(b.Version))),
|
||||
stackitem.NewByteArray(b.PrevHash.BytesBE()),
|
||||
stackitem.NewByteArray(b.MerkleRoot.BytesBE()),
|
||||
stackitem.NewBigInteger(big.NewInt(int64(b.Timestamp))),
|
||||
stackitem.NewBigInteger(new(big.Int).SetUint64(b.Nonce)),
|
||||
stackitem.NewBigInteger(big.NewInt(int64(b.Index))),
|
||||
stackitem.NewByteArray(b.NextConsensus.BytesBE()),
|
||||
stackitem.NewBigInteger(big.NewInt(int64(len(b.Transactions)))),
|
||||
})
|
||||
}
|
||||
|
|
|
@ -10,6 +10,10 @@ import (
|
|||
"go.uber.org/zap"
|
||||
)
|
||||
|
||||
type itemable interface {
|
||||
ToStackItem() stackitem.Item
|
||||
}
|
||||
|
||||
const (
|
||||
// MaxEventNameLen is the maximum length of a name for event.
|
||||
MaxEventNameLen = 32
|
||||
|
@ -37,6 +41,17 @@ func GetEntryScriptHash(ic *interop.Context) error {
|
|||
return ic.VM.PushContextScriptHash(ic.VM.Istack().Len() - 1)
|
||||
}
|
||||
|
||||
// GetScriptContainer returns transaction or block that contains the script
|
||||
// being run.
|
||||
func GetScriptContainer(ic *interop.Context) error {
|
||||
c, ok := ic.Container.(itemable)
|
||||
if !ok {
|
||||
return errors.New("unknown script container")
|
||||
}
|
||||
ic.VM.Estack().PushItem(c.ToStackItem())
|
||||
return nil
|
||||
}
|
||||
|
||||
// Platform returns the name of the platform.
|
||||
func Platform(ic *interop.Context) error {
|
||||
ic.VM.Estack().PushItem(stackitem.NewByteArray([]byte("NEO")))
|
||||
|
|
|
@ -5,12 +5,9 @@ import (
|
|||
"errors"
|
||||
"fmt"
|
||||
|
||||
"github.com/nspcc-dev/neo-go/pkg/core/block"
|
||||
"github.com/nspcc-dev/neo-go/pkg/core/interop"
|
||||
istorage "github.com/nspcc-dev/neo-go/pkg/core/interop/storage"
|
||||
"github.com/nspcc-dev/neo-go/pkg/core/native"
|
||||
"github.com/nspcc-dev/neo-go/pkg/core/storage"
|
||||
"github.com/nspcc-dev/neo-go/pkg/core/transaction"
|
||||
"github.com/nspcc-dev/neo-go/pkg/vm/stackitem"
|
||||
)
|
||||
|
||||
|
@ -26,22 +23,6 @@ type StorageContext struct {
|
|||
ReadOnly bool
|
||||
}
|
||||
|
||||
// engineGetScriptContainer returns transaction or block that contains the script
|
||||
// being run.
|
||||
func engineGetScriptContainer(ic *interop.Context) error {
|
||||
var item stackitem.Item
|
||||
switch t := ic.Container.(type) {
|
||||
case *transaction.Transaction:
|
||||
item = native.TransactionToStackItem(t)
|
||||
case *block.Block:
|
||||
item = native.BlockToStackItem(t)
|
||||
default:
|
||||
return errors.New("unknown script container")
|
||||
}
|
||||
ic.VM.Estack().PushItem(item)
|
||||
return nil
|
||||
}
|
||||
|
||||
// storageDelete deletes stored key-value pair.
|
||||
func storageDelete(ic *interop.Context) error {
|
||||
stcInterface := ic.VM.Estack().Pop().Value()
|
||||
|
|
|
@ -54,7 +54,7 @@ var systemInterops = []interop.Function{
|
|||
{Name: interopnames.SystemRuntimeGetNetwork, Func: runtime.GetNetwork, Price: 1 << 3},
|
||||
{Name: interopnames.SystemRuntimeGetNotifications, Func: runtime.GetNotifications, Price: 1 << 12, ParamCount: 1},
|
||||
{Name: interopnames.SystemRuntimeGetRandom, Func: runtime.GetRandom, Price: 0},
|
||||
{Name: interopnames.SystemRuntimeGetScriptContainer, Func: engineGetScriptContainer, Price: 1 << 3},
|
||||
{Name: interopnames.SystemRuntimeGetScriptContainer, Func: runtime.GetScriptContainer, Price: 1 << 3},
|
||||
{Name: interopnames.SystemRuntimeGetTime, Func: runtime.GetTime, Price: 1 << 3, RequiredFlags: callflag.ReadStates},
|
||||
{Name: interopnames.SystemRuntimeGetTrigger, Func: runtime.GetTrigger, Price: 1 << 3},
|
||||
{Name: interopnames.SystemRuntimeLog, Func: runtime.Log, Price: 1 << 15, RequiredFlags: callflag.AllowNotify,
|
||||
|
|
|
@ -5,7 +5,6 @@ import (
|
|||
"math"
|
||||
"math/big"
|
||||
|
||||
"github.com/nspcc-dev/neo-go/pkg/core/block"
|
||||
"github.com/nspcc-dev/neo-go/pkg/core/dao"
|
||||
"github.com/nspcc-dev/neo-go/pkg/core/interop"
|
||||
"github.com/nspcc-dev/neo-go/pkg/core/native/nativenames"
|
||||
|
@ -117,7 +116,7 @@ func (l *Ledger) getBlock(ic *interop.Context, params []stackitem.Item) stackite
|
|||
if err != nil || !isTraceableBlock(ic, block.Index) {
|
||||
return stackitem.Null{}
|
||||
}
|
||||
return BlockToStackItem(block)
|
||||
return block.ToStackItem()
|
||||
}
|
||||
|
||||
// getTransaction returns transaction to the SC.
|
||||
|
@ -126,7 +125,7 @@ func (l *Ledger) getTransaction(ic *interop.Context, params []stackitem.Item) st
|
|||
if err != nil || !isTraceableBlock(ic, h) {
|
||||
return stackitem.Null{}
|
||||
}
|
||||
return TransactionToStackItem(tx)
|
||||
return tx.ToStackItem()
|
||||
}
|
||||
|
||||
// getTransactionHeight returns transaction height to the SC.
|
||||
|
@ -150,7 +149,7 @@ func (l *Ledger) getTransactionFromBlock(ic *interop.Context, params []stackitem
|
|||
if index >= uint32(len(block.Transactions)) {
|
||||
panic("wrong transaction index")
|
||||
}
|
||||
return TransactionToStackItem(block.Transactions[index])
|
||||
return block.Transactions[index].ToStackItem()
|
||||
}
|
||||
|
||||
// getTransactionSigners returns transaction signers to the SC.
|
||||
|
@ -228,35 +227,6 @@ func getTransactionAndHeight(d *dao.Simple, item stackitem.Item) (*transaction.T
|
|||
return d.GetTransaction(hash)
|
||||
}
|
||||
|
||||
// BlockToStackItem converts block.Block to stackitem.Item.
|
||||
func BlockToStackItem(b *block.Block) stackitem.Item {
|
||||
return stackitem.NewArray([]stackitem.Item{
|
||||
stackitem.NewByteArray(b.Hash().BytesBE()),
|
||||
stackitem.NewBigInteger(big.NewInt(int64(b.Version))),
|
||||
stackitem.NewByteArray(b.PrevHash.BytesBE()),
|
||||
stackitem.NewByteArray(b.MerkleRoot.BytesBE()),
|
||||
stackitem.NewBigInteger(big.NewInt(int64(b.Timestamp))),
|
||||
stackitem.NewBigInteger(new(big.Int).SetUint64(b.Nonce)),
|
||||
stackitem.NewBigInteger(big.NewInt(int64(b.Index))),
|
||||
stackitem.NewByteArray(b.NextConsensus.BytesBE()),
|
||||
stackitem.NewBigInteger(big.NewInt(int64(len(b.Transactions)))),
|
||||
})
|
||||
}
|
||||
|
||||
// TransactionToStackItem converts transaction.Transaction to stackitem.Item.
|
||||
func TransactionToStackItem(t *transaction.Transaction) stackitem.Item {
|
||||
return stackitem.NewArray([]stackitem.Item{
|
||||
stackitem.NewByteArray(t.Hash().BytesBE()),
|
||||
stackitem.NewBigInteger(big.NewInt(int64(t.Version))),
|
||||
stackitem.NewBigInteger(big.NewInt(int64(t.Nonce))),
|
||||
stackitem.NewByteArray(t.Sender().BytesBE()),
|
||||
stackitem.NewBigInteger(big.NewInt(int64(t.SystemFee))),
|
||||
stackitem.NewBigInteger(big.NewInt(int64(t.NetworkFee))),
|
||||
stackitem.NewBigInteger(big.NewInt(int64(t.ValidUntilBlock))),
|
||||
stackitem.NewByteArray(t.Script),
|
||||
})
|
||||
}
|
||||
|
||||
// SignersToStackItem converts transaction.Signers to stackitem.Item.
|
||||
func SignersToStackItem(signers []transaction.Signer) stackitem.Item {
|
||||
res := make([]stackitem.Item, len(signers))
|
||||
|
|
|
@ -6,12 +6,14 @@ import (
|
|||
"errors"
|
||||
"fmt"
|
||||
"math"
|
||||
"math/big"
|
||||
"math/rand"
|
||||
|
||||
"github.com/nspcc-dev/neo-go/pkg/crypto/hash"
|
||||
"github.com/nspcc-dev/neo-go/pkg/encoding/address"
|
||||
"github.com/nspcc-dev/neo-go/pkg/io"
|
||||
"github.com/nspcc-dev/neo-go/pkg/util"
|
||||
"github.com/nspcc-dev/neo-go/pkg/vm/stackitem"
|
||||
)
|
||||
|
||||
const (
|
||||
|
@ -451,3 +453,17 @@ func (t *Transaction) HasSigner(hash util.Uint160) bool {
|
|||
}
|
||||
return false
|
||||
}
|
||||
|
||||
// ToStackItem converts Transaction to stackitem.Item.
|
||||
func (t *Transaction) ToStackItem() stackitem.Item {
|
||||
return stackitem.NewArray([]stackitem.Item{
|
||||
stackitem.NewByteArray(t.Hash().BytesBE()),
|
||||
stackitem.NewBigInteger(big.NewInt(int64(t.Version))),
|
||||
stackitem.NewBigInteger(big.NewInt(int64(t.Nonce))),
|
||||
stackitem.NewByteArray(t.Sender().BytesBE()),
|
||||
stackitem.NewBigInteger(big.NewInt(int64(t.SystemFee))),
|
||||
stackitem.NewBigInteger(big.NewInt(int64(t.NetworkFee))),
|
||||
stackitem.NewBigInteger(big.NewInt(int64(t.ValidUntilBlock))),
|
||||
stackitem.NewByteArray(t.Script),
|
||||
})
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue