limits: new package with storage limits

Packages like core/state or core/mpt shouldn't import whole core/storage just
to get some constant value, it's not a good dependency.
This commit is contained in:
Roman Khimov 2022-07-08 19:51:59 +03:00
parent 9987afea4c
commit 8cd7b93208
10 changed files with 36 additions and 25 deletions

View file

@ -0,0 +1,17 @@
/*
Package limits contains a number of system-wide hardcoded constants.
Many of the Neo protocol parameters can be adjusted by the configuration, but
some can not and this package contains hardcoded limits that are relevant for
many applications.
*/
package limits
const (
// MaxStorageKeyLen is the maximum length of a key for storage items.
// Contracts can't use keys longer than that in their requests to the DB.
MaxStorageKeyLen = 64
// MaxStorageValueLen is the maximum length of a value for storage items.
// It is set to be the maximum value for uint16, contracts can't put
// values longer than that into the DB.
MaxStorageValueLen = 65535
)

View file

@ -13,6 +13,7 @@ import (
"time"
"github.com/nspcc-dev/neo-go/pkg/config"
"github.com/nspcc-dev/neo-go/pkg/config/limits"
"github.com/nspcc-dev/neo-go/pkg/core/block"
"github.com/nspcc-dev/neo-go/pkg/core/blockchainer"
"github.com/nspcc-dev/neo-go/pkg/core/blockchainer/services"
@ -1328,7 +1329,7 @@ func (bc *Blockchain) handleNotification(note *state.NotificationEvent, d *dao.S
var id []byte
if len(arr) == 4 {
id, err = arr[3].TryBytes()
if err != nil || len(id) > storage.MaxStorageKeyLen {
if err != nil || len(id) > limits.MaxStorageKeyLen {
return
}
}

View file

@ -10,6 +10,7 @@ import (
"math/big"
"sync"
"github.com/nspcc-dev/neo-go/pkg/config/limits"
"github.com/nspcc-dev/neo-go/pkg/core/block"
"github.com/nspcc-dev/neo-go/pkg/core/state"
"github.com/nspcc-dev/neo-go/pkg/core/storage"
@ -830,7 +831,7 @@ func (dao *Simple) StoreAsTransaction(tx *transaction.Transaction, index uint32,
func (dao *Simple) getKeyBuf(len int) []byte {
if dao.private {
if dao.keyBuf == nil {
dao.keyBuf = make([]byte, 0, 1+4+storage.MaxStorageKeyLen) // Prefix, uint32, key.
dao.keyBuf = make([]byte, 0, 1+4+limits.MaxStorageKeyLen) // Prefix, uint32, key.
}
return dao.keyBuf[:len] // Should have enough capacity.
}

View file

@ -4,8 +4,8 @@ import (
"errors"
"fmt"
"github.com/nspcc-dev/neo-go/pkg/config/limits"
"github.com/nspcc-dev/neo-go/pkg/core/interop"
"github.com/nspcc-dev/neo-go/pkg/core/storage"
"github.com/nspcc-dev/neo-go/pkg/vm/stackitem"
)
@ -81,10 +81,10 @@ func getContextInternal(ic *interop.Context, isReadOnly bool) error {
}
func putWithContext(ic *interop.Context, stc *Context, key []byte, value []byte) error {
if len(key) > storage.MaxStorageKeyLen {
if len(key) > limits.MaxStorageKeyLen {
return errors.New("key is too big")
}
if len(value) > storage.MaxStorageValueLen {
if len(value) > limits.MaxStorageValueLen {
return errors.New("value is too big")
}
if stc.ReadOnly {

View file

@ -5,6 +5,7 @@ import (
"math/big"
"testing"
"github.com/nspcc-dev/neo-go/pkg/config/limits"
"github.com/nspcc-dev/neo-go/pkg/core"
"github.com/nspcc-dev/neo-go/pkg/core/block"
"github.com/nspcc-dev/neo-go/pkg/core/interop"
@ -12,7 +13,6 @@ import (
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/state"
"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/crypto/hash"
"github.com/nspcc-dev/neo-go/pkg/neotest/chain"
@ -61,7 +61,7 @@ func TestPut(t *testing.T) {
})
t.Run("check limits", func(t *testing.T) {
initVM(t, make([]byte, storage.MaxStorageKeyLen), make([]byte, storage.MaxStorageValueLen), -1)
initVM(t, make([]byte, limits.MaxStorageKeyLen), make([]byte, limits.MaxStorageValueLen), -1)
require.NoError(t, istorage.Put(ic))
})
@ -72,11 +72,11 @@ func TestPut(t *testing.T) {
require.Error(t, istorage.Put(ic))
})
t.Run("big key", func(t *testing.T) {
initVM(t, make([]byte, storage.MaxStorageKeyLen+1), []byte{1}, -1)
initVM(t, make([]byte, limits.MaxStorageKeyLen+1), []byte{1}, -1)
require.Error(t, istorage.Put(ic))
})
t.Run("big value", func(t *testing.T) {
initVM(t, []byte{1}, make([]byte, storage.MaxStorageValueLen+1), -1)
initVM(t, []byte{1}, make([]byte, limits.MaxStorageValueLen+1), -1)
require.Error(t, istorage.Put(ic))
})
})

View file

@ -6,14 +6,14 @@ import (
"errors"
"fmt"
"github.com/nspcc-dev/neo-go/pkg/core/storage"
"github.com/nspcc-dev/neo-go/pkg/config/limits"
"github.com/nspcc-dev/neo-go/pkg/io"
"github.com/nspcc-dev/neo-go/pkg/util"
)
const (
// maxPathLength is the max length of the extension node key.
maxPathLength = (storage.MaxStorageKeyLen + 4) * 2
maxPathLength = (limits.MaxStorageKeyLen + 4) * 2
// MaxKeyLength is the max length of the key to put in the trie
// before transforming to nibbles.

View file

@ -5,13 +5,13 @@ import (
"errors"
"fmt"
"github.com/nspcc-dev/neo-go/pkg/core/storage"
"github.com/nspcc-dev/neo-go/pkg/config/limits"
"github.com/nspcc-dev/neo-go/pkg/io"
"github.com/nspcc-dev/neo-go/pkg/util"
)
// MaxValueLength is the max length of a leaf node value.
const MaxValueLength = 3 + storage.MaxStorageValueLen + 1
const MaxValueLength = 3 + limits.MaxStorageValueLen + 1
// LeafNode represents an MPT's leaf node.
type LeafNode struct {

View file

@ -4,7 +4,7 @@ import (
"bytes"
"math/big"
"github.com/nspcc-dev/neo-go/pkg/core/storage"
"github.com/nspcc-dev/neo-go/pkg/config/limits"
"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"
@ -224,5 +224,5 @@ func (t *NEP11Transfer) EncodeBinary(w *io.BinWriter) {
// DecodeBinary implements the io.Serializable interface.
func (t *NEP11Transfer) DecodeBinary(r *io.BinReader) {
t.NEP17Transfer.DecodeBinary(r)
t.ID = r.ReadVarBytes(storage.MaxStorageKeyLen)
t.ID = r.ReadVarBytes(limits.MaxStorageKeyLen)
}

View file

@ -41,14 +41,6 @@ const (
ExecTransaction byte = 2
)
const (
// MaxStorageKeyLen is the maximum length of a key for storage items.
MaxStorageKeyLen = 64
// MaxStorageValueLen is the maximum length of a value for storage items.
// It is set to be the maximum value for uint16.
MaxStorageValueLen = 65535
)
// Operation represents a single KV operation (add/del/change) performed
// in the DB.
type Operation struct {

View file

@ -20,6 +20,7 @@ import (
"github.com/google/uuid"
"github.com/gorilla/websocket"
"github.com/nspcc-dev/neo-go/pkg/config/limits"
"github.com/nspcc-dev/neo-go/pkg/config/netmode"
"github.com/nspcc-dev/neo-go/pkg/core"
"github.com/nspcc-dev/neo-go/pkg/core/block"
@ -31,7 +32,6 @@ import (
"github.com/nspcc-dev/neo-go/pkg/core/mpt"
"github.com/nspcc-dev/neo-go/pkg/core/native"
"github.com/nspcc-dev/neo-go/pkg/core/state"
"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/crypto/hash"
"github.com/nspcc-dev/neo-go/pkg/crypto/keys"
@ -846,7 +846,7 @@ contract_loop:
curAsset := &bs.Balances[len(bs.Balances)-1]
for i := range toks {
id, err := toks[i].TryBytes()
if err != nil || len(id) > storage.MaxStorageKeyLen {
if err != nil || len(id) > limits.MaxStorageKeyLen {
continue
}
var amount = "1"