From 80a4c5f4c5b2ea15eaf2a0dc50acd80cb22355bc Mon Sep 17 00:00:00 2001 From: Roy Crihfield Date: Fri, 23 Jun 2023 00:30:34 +0800 Subject: [PATCH] Fix various build errors and bugs - bug in hex decoding in bls12381 package - correct interfaces - missing test variables --- restricted/crypto/bls12381/g1_test.go | 9 ------ restricted/crypto/bls12381/utils.go | 27 ++++++++++++++--- restricted/hasher/statetrie.go | 6 ++-- restricted/params/config.go | 42 +++++++++++++++++++++++---- restricted/params/config_test.go | 31 ++++++++++++++++++++ restricted/types/hashing_test.go | 7 +++-- 6 files changed, 97 insertions(+), 25 deletions(-) diff --git a/restricted/crypto/bls12381/g1_test.go b/restricted/crypto/bls12381/g1_test.go index dd3fea0..36f88da 100644 --- a/restricted/crypto/bls12381/g1_test.go +++ b/restricted/crypto/bls12381/g1_test.go @@ -1,21 +1,12 @@ package bls12381 import ( - "encoding/hex" "bytes" "crypto/rand" "math/big" "testing" ) -func fromHex(s string) []byte { - b, err := hex.DecodeString(s) - if err != nil { - panic(err) - } - return b -} - func (g *G1) one() *PointG1 { one, _ := g.fromBytesUnchecked( fromHex("" + diff --git a/restricted/crypto/bls12381/utils.go b/restricted/crypto/bls12381/utils.go index 0565174..f3739e7 100644 --- a/restricted/crypto/bls12381/utils.go +++ b/restricted/crypto/bls12381/utils.go @@ -17,15 +17,34 @@ package bls12381 import ( - "strings" "encoding/hex" "errors" "math/big" ) -func bigFromHex(hex string) *big.Int { - b, _ := hex.DecodeString(strings.TrimPrefix(hex, "0x")) - return new(big.Int).SetBytes(b) +// fromHex returns the bytes represented by the hexadecimal string s. +// s may be prefixed with "0x". +func fromHex(s string) []byte { + if has0xPrefix(s) { + s = s[2:] + } + if len(s)%2 == 1 { + s = "0" + s + } + h, err := hex.DecodeString(s) + if err != nil { + panic(err) + } + return h +} + +// has0xPrefix validates str begins with '0x' or '0X'. +func has0xPrefix(str string) bool { + return len(str) >= 2 && str[0] == '0' && (str[1] == 'x' || str[1] == 'X') +} + +func bigFromHex(s string) *big.Int { + return new(big.Int).SetBytes(fromHex(s)) } // decodeFieldElement expects 64 byte input with zero top 16 bytes, diff --git a/restricted/hasher/statetrie.go b/restricted/hasher/statetrie.go index 25fff53..53e1428 100644 --- a/restricted/hasher/statetrie.go +++ b/restricted/hasher/statetrie.go @@ -17,11 +17,11 @@ package hasher import ( - "fmt" "bufio" "bytes" "encoding/gob" "errors" + "fmt" "io" "sync" @@ -57,7 +57,7 @@ func returnToPool(st *StackTrie) { // in order. Once it determines that a subtree will no longer be inserted // into, it will hash it and free up the memory it uses. type StackTrie struct { - owner core.Hash // the owner of the trie + owner core.Hash // the owner of the trie nodeType uint8 // node type (as in branch, ext, leaf) val []byte // value contained by this node if it's a leaf key []byte // key chunk covered by this (leaf|ext) node @@ -214,7 +214,7 @@ func (st *StackTrie) TryUpdate(key, value []byte) error { func (st *StackTrie) Update(key, value []byte) { if err := st.TryUpdate(key, value); err != nil { - fmt.Errorf("Unhandled trie error in StackTrie.Update", "err", err) + fmt.Println("Unhandled trie error in StackTrie.Update:", err) } } diff --git a/restricted/params/config.go b/restricted/params/config.go index df46f4b..a8d0332 100644 --- a/restricted/params/config.go +++ b/restricted/params/config.go @@ -34,13 +34,43 @@ var ( CalaverasGenesisHash = core.HexToHash("0xeb9233d066c275efcdfed8037f4fc082770176aefdbcb7691c71da412a5670f2") ) +var ( + // TestChainConfig contains every protocol change (EIPs) introduced + // and accepted by the Ethereum core developers for testing proposes. + TestChainConfig = &ChainConfig{ + ChainID: big.NewInt(1), + HomesteadBlock: big.NewInt(0), + DAOForkBlock: nil, + DAOForkSupport: false, + EIP150Block: big.NewInt(0), + EIP155Block: big.NewInt(0), + EIP158Block: big.NewInt(0), + ByzantiumBlock: big.NewInt(0), + ConstantinopleBlock: big.NewInt(0), + PetersburgBlock: big.NewInt(0), + IstanbulBlock: big.NewInt(0), + MuirGlacierBlock: big.NewInt(0), + BerlinBlock: big.NewInt(0), + LondonBlock: big.NewInt(0), + ArrowGlacierBlock: big.NewInt(0), + GrayGlacierBlock: big.NewInt(0), + MergeNetsplitBlock: nil, + ShanghaiTime: nil, + CancunTime: nil, + PragueTime: nil, + TerminalTotalDifficulty: nil, + TerminalTotalDifficultyPassed: false, + Ethash: new(EthashConfig), + Clique: nil, + } +) // TrustedCheckpoint represents a set of post-processed trie roots (CHT and // BloomTrie) associated with the appropriate section index and head hash. It is // used to start light syncing from this checkpoint and avoid downloading the // entire header chain while still being able to securely access old headers/logs. type TrustedCheckpoint struct { - SectionIndex uint64 `json:"sectionIndex"` + SectionIndex uint64 `json:"sectionIndex"` SectionHead core.Hash `json:"sectionHead"` CHTRoot core.Hash `json:"chtRoot"` BloomRoot core.Hash `json:"bloomRoot"` @@ -80,7 +110,7 @@ func (c *TrustedCheckpoint) Empty() bool { type CheckpointOracleConfig struct { Address core.Address `json:"address"` Signers []core.Address `json:"signers"` - Threshold uint64 `json:"threshold"` + Threshold uint64 `json:"threshold"` } // ChainConfig is the core config which determines the blockchain settings. @@ -97,7 +127,7 @@ type ChainConfig struct { DAOForkSupport bool `json:"daoForkSupport,omitempty"` // Whether the nodes supports or opposes the DAO hard-fork // EIP150 implements the Gas price changes (https://github.com/ethereum/EIPs/issues/150) - EIP150Block *big.Int `json:"eip150Block,omitempty"` // EIP150 HF block (nil = no fork) + EIP150Block *big.Int `json:"eip150Block,omitempty"` // EIP150 HF block (nil = no fork) EIP150Hash core.Hash `json:"eip150Hash,omitempty"` // EIP150 HF hash (needed for header only clients as only gas pricing changed) EIP155Block *big.Int `json:"eip155Block,omitempty"` // EIP155 HF block @@ -111,9 +141,9 @@ type ChainConfig struct { BerlinBlock *big.Int `json:"berlinBlock,omitempty"` // Berlin switch block (nil = no fork, 0 = already on berlin) LondonBlock *big.Int `json:"londonBlock,omitempty"` // London switch block (nil = no fork, 0 = already on london) - ArrowGlacierBlock *big.Int `json:"arrowGlacierBlock,omitempty"` // Eip-4345 (bomb delay) switch block (nil = no fork, 0 = already activated) - GrayGlacierBlock *big.Int `json:"grayGlacierBlock,omitempty"` // Eip-5133 (bomb delay) switch block (nil = no fork, 0 = already activated) - MergeNetsplitBlock *big.Int `json:"mergeNetsplitBlock,omitempty"` // Virtual fork after The Merge to use as a network splitter + ArrowGlacierBlock *big.Int `json:"arrowGlacierBlock,omitempty"` // Eip-4345 (bomb delay) switch block (nil = no fork, 0 = already activated) + GrayGlacierBlock *big.Int `json:"grayGlacierBlock,omitempty"` // Eip-5133 (bomb delay) switch block (nil = no fork, 0 = already activated) + MergeNetsplitBlock *big.Int `json:"mergeNetsplitBlock,omitempty"` // Virtual fork after The Merge to use as a network splitter // Fork scheduling was switched from blocks to timestamps here diff --git a/restricted/params/config_test.go b/restricted/params/config_test.go index 3c8ebaf..bdac80f 100644 --- a/restricted/params/config_test.go +++ b/restricted/params/config_test.go @@ -22,6 +22,37 @@ import ( "testing" ) +var ( + // AllEthashProtocolChanges contains every protocol change (EIPs) introduced + // and accepted by the Ethereum core developers into the Ethash consensus. + AllEthashProtocolChanges = &ChainConfig{ + ChainID: big.NewInt(1337), + HomesteadBlock: big.NewInt(0), + DAOForkBlock: nil, + DAOForkSupport: false, + EIP150Block: big.NewInt(0), + EIP155Block: big.NewInt(0), + EIP158Block: big.NewInt(0), + ByzantiumBlock: big.NewInt(0), + ConstantinopleBlock: big.NewInt(0), + PetersburgBlock: big.NewInt(0), + IstanbulBlock: big.NewInt(0), + MuirGlacierBlock: big.NewInt(0), + BerlinBlock: big.NewInt(0), + LondonBlock: big.NewInt(0), + ArrowGlacierBlock: big.NewInt(0), + GrayGlacierBlock: big.NewInt(0), + MergeNetsplitBlock: nil, + ShanghaiTime: nil, + CancunTime: nil, + PragueTime: nil, + TerminalTotalDifficulty: nil, + TerminalTotalDifficultyPassed: false, + Ethash: new(EthashConfig), + Clique: nil, + } +) + func TestCheckCompatible(t *testing.T) { type test struct { stored, new *ChainConfig diff --git a/restricted/types/hashing_test.go b/restricted/types/hashing_test.go index 8082e77..c0556d1 100644 --- a/restricted/types/hashing_test.go +++ b/restricted/types/hashing_test.go @@ -26,10 +26,10 @@ import ( "testing" "github.com/openrelayxyz/plugeth-utils/core" - "github.com/openrelayxyz/plugeth-utils/restricted/hexutil" - "github.com/openrelayxyz/plugeth-utils/restricted/types" "github.com/openrelayxyz/plugeth-utils/restricted/crypto" + "github.com/openrelayxyz/plugeth-utils/restricted/hexutil" "github.com/openrelayxyz/plugeth-utils/restricted/rlp" + "github.com/openrelayxyz/plugeth-utils/restricted/types" ) func fromHex(data string) []byte { @@ -136,9 +136,10 @@ func (d *hashToHumanReadable) Reset() { d.data = make([]byte, 0) } -func (d *hashToHumanReadable) Update(i []byte, i2 []byte) { +func (d *hashToHumanReadable) Update(i []byte, i2 []byte) error { l := fmt.Sprintf("%x %x\n", i, i2) d.data = append(d.data, []byte(l)...) + return nil } func (d *hashToHumanReadable) Hash() core.Hash {