forked from cosmos/ibc-go
-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Copy share package into Rollkit (cosmos#888)
Closes: cosmos#887 Copy parts of [share package](https://github.com/celestiaorg/celestia-app/tree/main/pkg/shares) relating to compact shares. We plan to later extract common code into a separate repo that both `celestia-app` and `rollkit` can use. Changes needed to this code for use in rollkit will be handled in a later PR. Also, extracts parts needed to resolve dependencies, specifically, `namespace`, `appconsts`, and `testfactory.
- Loading branch information
1 parent
acf0090
commit c788fb1
Showing
26 changed files
with
3,335 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,101 @@ | ||
package appconsts | ||
|
||
// These constants were originally sourced from: | ||
// https://github.com/celestiaorg/celestia-specs/blob/master/src/specs/consensus.md#constants | ||
const ( | ||
// NamespaveVersionSize is the size of a namespace version in bytes. | ||
NamespaceVersionSize = 1 | ||
|
||
// NamespaceIDSize is the size of a namespace ID in bytes. | ||
NamespaceIDSize = 32 | ||
|
||
// NamespaceSize is the size of a namespace (version + ID) in bytes. | ||
NamespaceSize = NamespaceVersionSize + NamespaceIDSize | ||
|
||
// ShareSize is the size of a share in bytes. | ||
ShareSize = 512 | ||
|
||
// ShareInfoBytes is the number of bytes reserved for information. The info | ||
// byte contains the share version and a sequence start idicator. | ||
ShareInfoBytes = 1 | ||
|
||
// SequenceLenBytes is the number of bytes reserved for the sequence length | ||
// that is present in the first share of a sequence. | ||
SequenceLenBytes = 4 | ||
|
||
// ShareVersionZero is the first share version format. | ||
ShareVersionZero = uint8(0) | ||
|
||
// DefaultShareVersion is the defacto share version. Use this if you are | ||
// unsure of which version to use. | ||
DefaultShareVersion = ShareVersionZero | ||
|
||
// CompactShareReservedBytes is the number of bytes reserved for the location of | ||
// the first unit (transaction, ISR) in a compact share. | ||
CompactShareReservedBytes = 4 | ||
|
||
// FirstCompactShareContentSize is the number of bytes usable for data in | ||
// the first compact share of a sequence. | ||
FirstCompactShareContentSize = ShareSize - NamespaceSize - ShareInfoBytes - SequenceLenBytes - CompactShareReservedBytes | ||
|
||
// ContinuationCompactShareContentSize is the number of bytes usable for | ||
// data in a continuation compact share of a sequence. | ||
ContinuationCompactShareContentSize = ShareSize - NamespaceSize - ShareInfoBytes - CompactShareReservedBytes | ||
|
||
// FirstSparseShareContentSize is the number of bytes usable for data in the | ||
// first sparse share of a sequence. | ||
FirstSparseShareContentSize = ShareSize - NamespaceSize - ShareInfoBytes - SequenceLenBytes | ||
|
||
// ContinuationSparseShareContentSize is the number of bytes usable for data | ||
// in a continuation sparse share of a sequence. | ||
ContinuationSparseShareContentSize = ShareSize - NamespaceSize - ShareInfoBytes | ||
|
||
// DefaultMaxSquareSize is the maximum original square width. | ||
// | ||
// Note: 128 shares in a row * 128 shares in a column * 512 bytes in a share | ||
// = 8 MiB | ||
DefaultMaxSquareSize = 128 | ||
|
||
// MaxShareCount is the maximum number of shares allowed in the original | ||
// data square. | ||
MaxShareCount = DefaultMaxSquareSize * DefaultMaxSquareSize | ||
|
||
// DefaultMinSquareSize is the smallest original square width. | ||
DefaultMinSquareSize = 1 | ||
|
||
// MinshareCount is the minimum number of shares allowed in the original | ||
// data square. | ||
MinShareCount = DefaultMinSquareSize * DefaultMinSquareSize | ||
|
||
// MaxShareVersion is the maximum value a share version can be. | ||
MaxShareVersion = 127 | ||
|
||
// DefaultGasPerBlobByte is the default gas cost deducted per byte of blob | ||
// included in a PayForBlobs txn | ||
DefaultGasPerBlobByte = 8 | ||
|
||
// TransactionsPerBlockLimit is the maximum number of transactions a block | ||
// producer will include in a block. | ||
// | ||
// NOTE: Currently this value is set at roughly the number of PFBs that | ||
// would fill one quarter of the max square size. | ||
TransactionsPerBlockLimit = 5090 | ||
) | ||
|
||
var ( | ||
|
||
// TODO: Consider commenting back in. Removed to reduce unneeded dependency | ||
|
||
// // NewBaseHashFunc is the base hash function used by NMT. Change accordingly | ||
// // if another hash.Hash should be used as a base hasher in the NMT. | ||
// NewBaseHashFunc = consts.NewBaseHashFunc | ||
// // DefaultCodec is the default codec creator used for data erasure. | ||
// DefaultCodec = rsmt2d.NewLeoRSCodec | ||
|
||
// // DataCommitmentBlocksLimit is the limit to the number of blocks we can | ||
// // generate a data commitment for. | ||
// DataCommitmentBlocksLimit = consts.DataCommitmentBlocksLimit | ||
|
||
// SupportedShareVersions is a list of supported share versions. | ||
SupportedShareVersions = []uint8{ShareVersionZero} | ||
) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,8 @@ | ||
package appconsts | ||
|
||
import "time" | ||
|
||
const ( | ||
TimeoutPropose = time.Second * 10 | ||
TimeoutCommit = time.Second * 10 | ||
) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,70 @@ | ||
package namespace | ||
|
||
import ( | ||
"bytes" | ||
"math" | ||
|
||
"github.com/rollkit/rollkit/libs/appconsts" | ||
) | ||
|
||
const ( | ||
// NamespaveVersionSize is the size of a namespace version in bytes. | ||
NamespaceVersionSize = appconsts.NamespaceVersionSize | ||
|
||
// NamespaceIDSize is the size of a namespace ID in bytes. | ||
NamespaceIDSize = appconsts.NamespaceIDSize | ||
|
||
// NamespaceSize is the size of a namespace (version + ID) in bytes. | ||
NamespaceSize = appconsts.NamespaceSize | ||
|
||
// NamespaceVersionZero is the first namespace version. | ||
NamespaceVersionZero = uint8(0) | ||
|
||
// NamespaceVersionMax is the max namespace version. | ||
NamespaceVersionMax = math.MaxUint8 | ||
|
||
// NamespaceZeroPrefixSize is the number of `0` bytes that are prefixed to | ||
// namespace IDs for version 0. | ||
NamespaceVersionZeroPrefixSize = 22 | ||
|
||
// NamespaceVersionZeroIDSize is the number of bytes available for | ||
// user-specified namespace ID in a namespace ID for version 0. | ||
NamespaceVersionZeroIDSize = NamespaceIDSize - NamespaceVersionZeroPrefixSize | ||
) | ||
|
||
var ( | ||
// NamespaceVersionZeroPrefix is the prefix of a namespace ID for version 0. | ||
NamespaceVersionZeroPrefix = bytes.Repeat([]byte{0}, NamespaceVersionZeroPrefixSize) | ||
|
||
// TxNamespace is the namespace reserved for transaction data. | ||
TxNamespace = MustNewV0([]byte{0, 0, 0, 0, 0, 0, 0, 0, 0, 1}) | ||
|
||
// IntermediateStateRootsNamespace is the namespace reserved for | ||
// intermediate state root data. | ||
IntermediateStateRootsNamespace = MustNewV0([]byte{0, 0, 0, 0, 0, 0, 0, 0, 0, 2}) | ||
|
||
// PayForBlobNamespace is the namespace reserved for PayForBlobs transactions. | ||
PayForBlobNamespace = MustNewV0([]byte{0, 0, 0, 0, 0, 0, 0, 0, 0, 4}) | ||
|
||
// ReservedPaddingNamespace is the namespace used for padding after all | ||
// reserved namespaces. In practice this padding is after transactions | ||
// (ordinary and PFBs) but before blobs. | ||
ReservedPaddingNamespace = MustNewV0([]byte{0, 0, 0, 0, 0, 0, 0, 0, 0, 255}) | ||
|
||
// MaxReservedNamespace is lexicographically the largest namespace that is | ||
// reserved for protocol use. | ||
MaxReservedNamespace = MustNewV0([]byte{0, 0, 0, 0, 0, 0, 0, 0, 0, 255}) | ||
|
||
// TailPaddingNamespace is the namespace reserved for tail padding. All data | ||
// with this namespace will be ignored. | ||
TailPaddingNamespace = Namespace{ | ||
Version: math.MaxUint8, | ||
ID: append(bytes.Repeat([]byte{0xFF}, NamespaceIDSize-1), 0xFE), | ||
} | ||
|
||
// ParitySharesNamespace is the namespace reserved for erasure coded data. | ||
ParitySharesNamespace = Namespace{ | ||
Version: math.MaxUint8, | ||
ID: bytes.Repeat([]byte{0xFF}, NamespaceIDSize), | ||
} | ||
) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,130 @@ | ||
package namespace | ||
|
||
import ( | ||
"bytes" | ||
"fmt" | ||
) | ||
|
||
type Namespace struct { | ||
Version uint8 | ||
ID []byte | ||
} | ||
|
||
// New returns a new namespace with the provided version and id. | ||
func New(version uint8, id []byte) (Namespace, error) { | ||
err := validateVersion(version) | ||
if err != nil { | ||
return Namespace{}, err | ||
} | ||
|
||
err = validateID(version, id) | ||
if err != nil { | ||
return Namespace{}, err | ||
} | ||
|
||
return Namespace{ | ||
Version: version, | ||
ID: id, | ||
}, nil | ||
} | ||
|
||
// MustNew returns a new namespace with the provided version and id. It panics | ||
// if the provided version or id are not supported. | ||
func MustNew(version uint8, id []byte) Namespace { | ||
ns, err := New(version, id) | ||
if err != nil { | ||
panic(err) | ||
} | ||
return ns | ||
} | ||
|
||
// MustNewV0 returns a new namespace with version 0 and the provided id. This | ||
// function panics if the provided id is not exactly NamespaceVersionZeroIDSize bytes. | ||
func MustNewV0(id []byte) Namespace { | ||
if len(id) != NamespaceVersionZeroIDSize { | ||
panic(fmt.Sprintf("invalid namespace id length: %v must be %v", len(id), NamespaceVersionZeroIDSize)) | ||
} | ||
|
||
ns, err := New(NamespaceVersionZero, append(NamespaceVersionZeroPrefix, id...)) | ||
if err != nil { | ||
panic(err) | ||
} | ||
return ns | ||
} | ||
|
||
// From returns a namespace from the provided byte slice. | ||
func From(b []byte) (Namespace, error) { | ||
if len(b) != NamespaceSize { | ||
return Namespace{}, fmt.Errorf("invalid namespace length: %v must be %v", len(b), NamespaceSize) | ||
} | ||
rawVersion := b[0] | ||
rawNamespace := b[1:] | ||
return New(rawVersion, rawNamespace) | ||
} | ||
|
||
// Bytes returns this namespace as a byte slice. | ||
func (n Namespace) Bytes() []byte { | ||
return append([]byte{n.Version}, n.ID...) | ||
} | ||
|
||
// ValidateBlobNamespace returns an error if this namespace is not a valid blob namespace. | ||
func (n Namespace) ValidateBlobNamespace() error { | ||
if n.IsReserved() { | ||
return fmt.Errorf("invalid blob namespace: %v cannot use a reserved namespace ID, want > %v", n.Bytes(), MaxReservedNamespace.Bytes()) | ||
} | ||
|
||
if n.IsParityShares() { | ||
return fmt.Errorf("invalid blob namespace: %v cannot use parity shares namespace ID", n.Bytes()) | ||
} | ||
|
||
if n.IsTailPadding() { | ||
return fmt.Errorf("invalid blob namespace: %v cannot use tail padding namespace ID", n.Bytes()) | ||
} | ||
|
||
return nil | ||
} | ||
|
||
// validateVersion returns an error if the version is not supported. | ||
func validateVersion(version uint8) error { | ||
if version != NamespaceVersionZero && version != NamespaceVersionMax { | ||
return fmt.Errorf("unsupported namespace version %v", version) | ||
} | ||
return nil | ||
} | ||
|
||
// validateID returns an error if the provided id does not meet the requirements | ||
// for the provided version. | ||
func validateID(version uint8, id []byte) error { | ||
if len(id) != NamespaceIDSize { | ||
return fmt.Errorf("unsupported namespace id length: id %v must be %v bytes but it was %v bytes", id, NamespaceIDSize, len(id)) | ||
} | ||
|
||
if version == NamespaceVersionZero && !bytes.HasPrefix(id, NamespaceVersionZeroPrefix) { | ||
return fmt.Errorf("unsupported namespace id with version %v. ID %v must start with %v leading zeros", version, id, len(NamespaceVersionZeroPrefix)) | ||
} | ||
return nil | ||
} | ||
|
||
func (n Namespace) IsReserved() bool { | ||
return bytes.Compare(n.Bytes(), MaxReservedNamespace.Bytes()) < 1 | ||
} | ||
|
||
func (n Namespace) IsParityShares() bool { | ||
return bytes.Equal(n.Bytes(), ParitySharesNamespace.Bytes()) | ||
} | ||
|
||
func (n Namespace) IsTailPadding() bool { | ||
return bytes.Equal(n.Bytes(), TailPaddingNamespace.Bytes()) | ||
} | ||
|
||
func (n Namespace) IsReservedPadding() bool { | ||
return bytes.Equal(n.Bytes(), ReservedPaddingNamespace.Bytes()) | ||
} | ||
|
||
func (n Namespace) IsTx() bool { | ||
return bytes.Equal(n.Bytes(), TxNamespace.Bytes()) | ||
} | ||
|
||
func (n Namespace) IsPayForBlob() bool { | ||
return bytes.Equal(n.Bytes(), PayForBlobNamespace.Bytes()) | ||
} |
Oops, something went wrong.