Merge branch 'goeth-1.8.18' into geth-upgrade-1.8.18

# Conflicts:
#	.github/CONTRIBUTING.md
#	.travis.yml
#	core/blockchain.go
#	core/vm/evm.go
#	core/vm/logger_test.go
#	eth/handler_test.go
#	eth/tracers/tracer_test.go
#	internal/ethapi/api.go
#	internal/web3ext/web3ext.go
#	p2p/discover/node.go
#	p2p/server.go
#	swarm/network/simulations/discovery/discovery_test.go
This commit is contained in:
amalraj.manigmail.com 2019-01-29 19:08:50 +08:00
parent bc529a509d
commit 4dbd95947d
33 changed files with 306 additions and 136 deletions

View File

@ -26,13 +26,13 @@ import (
"time"
"unicode"
cli "gopkg.in/urfave/cli.v1"
"gopkg.in/urfave/cli.v1"
"github.com/ethereum/go-ethereum/cmd/utils"
"github.com/ethereum/go-ethereum/dashboard"
"github.com/ethereum/go-ethereum/eth"
"github.com/ethereum/go-ethereum/node"
"github.com/ethereum/go-ethereum/p2p/discover"
"github.com/ethereum/go-ethereum/p2p/enode"
"github.com/ethereum/go-ethereum/params"
"github.com/ethereum/go-ethereum/raft"
whisper "github.com/ethereum/go-ethereum/whisper/whisperv6"
@ -218,7 +218,7 @@ func RegisterRaftService(stack *node.Node, ctx *cli.Context, cfg gethConfig, eth
if err := stack.Register(func(ctx *node.ServiceContext) (node.Service, error) {
privkey := cfg.Node.NodeKey()
strId := discover.PubkeyID(&privkey.PublicKey).String()
strId := enode.PubkeyToIDV4(&privkey.PublicKey).String()
blockTimeNanos := time.Duration(blockTimeMillis) * time.Millisecond
peers := cfg.Node.StaticNodes()
@ -238,7 +238,7 @@ func RegisterRaftService(stack *node.Node, ctx *cli.Context, cfg gethConfig, eth
utils.Fatalf("raftport querystring parameter not specified in static-node enode ID: %v. please check your static-nodes.json file.", peer.String())
}
peerId := peer.ID.String()
peerId := peer.ID().String()
peerIds[peerIdx] = peerId
if peerId == strId {
myId = uint16(peerIdx) + 1

View File

@ -673,7 +673,7 @@ func (ethash *Ethash) SetThreads(threads int) {
// Note the returned hashrate includes local hashrate, but also includes the total
// hashrate of all remote miner.
func (ethash *Ethash) Hashrate() float64 {
if(ethash.hashrate == nil){
if ethash.hashrate == nil {
return 0
}
// Short circuit if we are run the ethash in normal/test mode.

View File

@ -155,21 +155,21 @@ func NewBlockChain(db ethdb.Database, cacheConfig *CacheConfig, chainConfig *par
badBlocks, _ := lru.New(badBlockLimit)
bc := &BlockChain{
chainConfig: chainConfig,
cacheConfig: cacheConfig,
db: db,
triegc: prque.New(nil),
stateCache: state.NewDatabase(db),
quit: make(chan struct{}),
shouldPreserve: shouldPreserve,
bodyCache: bodyCache,
bodyRLPCache: bodyRLPCache,
receiptsCache: receiptsCache,
blockCache: blockCache,
futureBlocks: futureBlocks,
engine: engine,
vmConfig: vmConfig,
badBlocks: badBlocks,
chainConfig: chainConfig,
cacheConfig: cacheConfig,
db: db,
triegc: prque.New(nil),
stateCache: state.NewDatabase(db),
quit: make(chan struct{}),
shouldPreserve: shouldPreserve,
bodyCache: bodyCache,
bodyRLPCache: bodyRLPCache,
receiptsCache: receiptsCache,
blockCache: blockCache,
futureBlocks: futureBlocks,
engine: engine,
vmConfig: vmConfig,
badBlocks: badBlocks,
privateStateCache: state.NewDatabase(db),
}
bc.SetValidator(NewBlockValidator(chainConfig, bc, engine))

View File

@ -428,6 +428,7 @@ func (evm *EVM) create(caller ContractRef, codeAndHash *codeAndHash, gas uint64,
return nil, common.Address{}, gas, ErrInsufficientBalance
}
// Quorum
// Get the right state in case of a dual state environment. If a sender
// is a transaction (depth == 0) use the public state to derive the address
// and increment the nonce of the public state. If the sender is a contract
@ -447,16 +448,15 @@ func (evm *EVM) create(caller ContractRef, codeAndHash *codeAndHash, gas uint64,
creatorStateDb.SetNonce(caller.Address(), nonce+1)
// Ensure there's no existing contract already at the designated address
contractAddr := crypto.CreateAddress(caller.Address(), nonce)
contractHash := evm.StateDB.GetCodeHash(contractAddr)
if evm.StateDB.GetNonce(contractAddr) != 0 || (contractHash != (common.Hash{}) && contractHash != emptyCodeHash) {
contractHash := evm.StateDB.GetCodeHash(address)
if evm.StateDB.GetNonce(address) != 0 || (contractHash != (common.Hash{}) && contractHash != emptyCodeHash) {
return nil, common.Address{}, 0, ErrContractAddressCollision
}
// Create a new account on the state
snapshot := evm.StateDB.Snapshot()
evm.StateDB.CreateAccount(contractAddr)
evm.StateDB.CreateAccount(address)
if evm.ChainConfig().IsEIP158(evm.BlockNumber) {
evm.StateDB.SetNonce(contractAddr, 1)
evm.StateDB.SetNonce(address, 1)
}
if evm.ChainConfig().IsQuorum {
// skip transfer if value /= 0 (see note: Quorum, States, and Value Transfer)
@ -464,10 +464,10 @@ func (evm *EVM) create(caller ContractRef, codeAndHash *codeAndHash, gas uint64,
if evm.quorumReadOnly {
return nil, common.Address{}, gas, ErrReadOnlyValueTransfer
}
evm.Transfer(evm.StateDB, caller.Address(), contractAddr, value)
evm.Transfer(evm.StateDB, caller.Address(), address, value)
}
} else {
evm.Transfer(evm.StateDB, caller.Address(), contractAddr, value)
evm.Transfer(evm.StateDB, caller.Address(), address, value)
}
// initialise a new contract and set the code that is to be used by the
@ -477,7 +477,7 @@ func (evm *EVM) create(caller ContractRef, codeAndHash *codeAndHash, gas uint64,
contract.SetCodeOptionalHash(&address, codeAndHash)
if evm.vmConfig.NoRecursion && evm.depth > 0 {
return nil, contractAddr, gas, nil
return nil, address, gas, nil
}
if evm.vmConfig.Debug && evm.depth == 0 {
@ -496,7 +496,7 @@ func (evm *EVM) create(caller ContractRef, codeAndHash *codeAndHash, gas uint64,
if err == nil && !maxCodeSizeExceeded {
createDataGas := uint64(len(ret)) * params.CreateDataGas
if contract.UseGas(createDataGas) {
evm.StateDB.SetCode(contractAddr, ret)
evm.StateDB.SetCode(address, ret)
} else {
err = ErrCodeStoreOutOfGas
}
@ -518,13 +518,31 @@ func (evm *EVM) create(caller ContractRef, codeAndHash *codeAndHash, gas uint64,
if evm.vmConfig.Debug && evm.depth == 0 {
evm.vmConfig.Tracer.CaptureEnd(ret, gas-contract.Gas, time.Since(start), err)
}
return ret, contractAddr, contract.Gas, err
return ret, address, contract.Gas, err
}
// Create creates a new contract using code as deployment code.
func (evm *EVM) Create(caller ContractRef, code []byte, gas uint64, value *big.Int) (ret []byte, contractAddr common.Address, leftOverGas uint64, err error) {
contractAddr = crypto.CreateAddress(caller.Address(), evm.StateDB.GetNonce(caller.Address()))
// Quorum
// Get the right state in case of a dual state environment. If a sender
// is a transaction (depth == 0) use the public state to derive the address
// and increment the nonce of the public state. If the sender is a contract
// (depth > 0) use the private state to derive the nonce and increment the
// nonce on the private state only.
//
// If the transaction went to a public contract the private and public state
// are the same.
var creatorStateDb StateDB
if evm.depth > 0 {
creatorStateDb = evm.privateState
} else {
creatorStateDb = evm.publicState
}
// Ensure there's no existing contract already at the designated address
nonce := creatorStateDb.GetNonce(caller.Address())
contractAddr = crypto.CreateAddress(caller.Address(), nonce)
return evm.create(caller, &codeAndHash{code: code}, gas, value, contractAddr)
}
@ -582,6 +600,8 @@ func (env *EVM) Pop() {
env.StateDB = env.states[env.currentStateDepth-1]
}
func (env *EVM) Depth() int { return env.depth }
// We only need to revert the current state because when we call from private
// public state it's read only, there wouldn't be anything to reset.
// (A)->(B)->C->(B): A failure in (B) wouldn't need to reset C, as C was flagged

View File

@ -34,9 +34,9 @@ type twoOperandTest struct {
func testTwoOperandOp(t *testing.T, tests []twoOperandTest, opFn func(pc *uint64, interpreter *EVMInterpreter, contract *Contract, memory *Memory, stack *Stack) ([]byte, error)) {
var (
env = NewEVM(Context{}, nil,nil, params.TestChainConfig, Config{})
stack = newstack()
pc = uint64(0)
env = NewEVM(Context{}, nil, nil, params.TestChainConfig, Config{})
stack = newstack()
pc = uint64(0)
evmInterpreter = NewEVMInterpreter(env, env.vmConfig)
)
@ -75,8 +75,8 @@ func testTwoOperandOp(t *testing.T, tests []twoOperandTest, opFn func(pc *uint64
func TestByteOp(t *testing.T) {
var (
env = NewEVM(Context{}, nil, nil,params.TestChainConfig, Config{})
stack = newstack()
env = NewEVM(Context{}, nil, nil, params.TestChainConfig, Config{})
stack = newstack()
evmInterpreter = NewEVMInterpreter(env, env.vmConfig)
)
@ -210,8 +210,8 @@ func TestSLT(t *testing.T) {
func opBenchmark(bench *testing.B, op func(pc *uint64, interpreter *EVMInterpreter, contract *Contract, memory *Memory, stack *Stack) ([]byte, error), args ...string) {
var (
env = NewEVM(Context{}, nil, nil, params.TestChainConfig, Config{})
stack = newstack()
env = NewEVM(Context{}, nil, nil, params.TestChainConfig, Config{})
stack = newstack()
evmInterpreter = NewEVMInterpreter(env, env.vmConfig)
)
@ -445,9 +445,9 @@ func BenchmarkOpIsZero(b *testing.B) {
func TestOpMstore(t *testing.T) {
var (
env = NewEVM(Context{}, nil, nil,params.TestChainConfig, Config{})
stack = newstack()
mem = NewMemory()
env = NewEVM(Context{}, nil, nil, params.TestChainConfig, Config{})
stack = newstack()
mem = NewMemory()
evmInterpreter = NewEVMInterpreter(env, env.vmConfig)
)
@ -471,9 +471,9 @@ func TestOpMstore(t *testing.T) {
func BenchmarkOpMstore(bench *testing.B) {
var (
env = NewEVM(Context{}, nil, nil, params.TestChainConfig, Config{})
stack = newstack()
mem = NewMemory()
env = NewEVM(Context{}, nil, nil, params.TestChainConfig, Config{})
stack = newstack()
mem = NewMemory()
evmInterpreter = NewEVMInterpreter(env, env.vmConfig)
)

View File

@ -20,6 +20,7 @@ import (
"math/big"
"github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/core/state"
"github.com/ethereum/go-ethereum/core/types"
)
@ -30,6 +31,11 @@ type MinimalApiState interface {
GetCode(addr common.Address) []byte
GetState(a common.Address, b common.Hash) common.Hash
GetNonce(addr common.Address) uint64
GetProof(common.Address) ([][]byte, error)
GetStorageProof(common.Address, common.Hash) ([][]byte, error)
StorageTrie(addr common.Address) state.Trie
Error() error
GetCodeHash(common.Address) common.Hash
}
// StateDB is an EVM database for full state querying.
@ -44,7 +50,7 @@ type StateDB interface {
//GetNonce(common.Address) uint64
SetNonce(common.Address, uint64)
GetCodeHash(common.Address) common.Hash
//GetCodeHash(common.Address) common.Hash
//GetCode(common.Address) []byte
SetCode(common.Address, []byte)
GetCodeSize(common.Address) int

View File

@ -89,6 +89,7 @@ func (s *PublicEthereumAPI) StorageRoot(addr common.Address, blockNr *rpc.BlockN
}
return pub.GetStorageRoot(addr)
}
// Hashrate returns the POW hashrate
func (api *PublicEthereumAPI) Hashrate() hexutil.Uint64 {
return hexutil.Uint64(api.e.Miner().HashRate())

View File

@ -255,6 +255,7 @@ func (b *EthAPIBackend) ServiceFilter(ctx context.Context, session *bloombits.Ma
}
}
// used by Quorum
type EthAPIState struct {
state, privateState *state.StateDB
}
@ -287,4 +288,25 @@ func (s EthAPIState) GetNonce(addr common.Address) uint64 {
return s.state.GetNonce(addr)
}
// TODO: implement the following methods for Quorum
func (s EthAPIState) GetProof(common.Address) ([][]byte, error) {
return nil, nil
}
func (s EthAPIState) GetStorageProof(common.Address, common.Hash) ([][]byte, error) {
return nil, nil
}
func (s EthAPIState) StorageTrie(addr common.Address) state.Trie {
return nil
}
func (s EthAPIState) Error() error {
return nil
}
func (s EthAPIState) GetCodeHash(common.Address) common.Hash {
return common.Hash{}
}
//func (s MinimalApiState) Error

View File

@ -360,10 +360,7 @@ func (pm *ProtocolManager) handleMsg(p *peer) error {
return nil
}
} else if handler, ok := pm.engine.(consensus.Handler); ok {
pubKey, err := p.ID().Pubkey()
if err != nil {
return err
}
pubKey := p.Node().Pubkey()
addr := crypto.PubkeyToAddress(*pubKey)
handled, err := handler.HandleMsg(addr, msg)
if handled {
@ -777,7 +774,6 @@ func (pm *ProtocolManager) BroadcastBlock(block *types.Block, propagate bool) {
}
}
// BroadcastTxs will propagate a batch of transactions to all peers which are not known to
// already have the given transaction.
func (pm *ProtocolManager) BroadcastTxs(txs types.Transactions) {
@ -852,10 +848,7 @@ func (pm *ProtocolManager) NodeInfo() *NodeInfo {
func (self *ProtocolManager) FindPeers(targets map[common.Address]bool) map[common.Address]consensus.Peer {
m := make(map[common.Address]consensus.Peer)
for _, p := range self.peers.Peers() {
pubKey, err := p.ID().Pubkey()
if err != nil {
continue
}
pubKey := p.Node().Pubkey()
addr := crypto.PubkeyToAddress(*pubKey)
if targets[addr] {
m[addr] = p

View File

@ -246,10 +246,10 @@ func testGetBlockBodies(t *testing.T, protocol int) {
available []bool // Availability of explicitly requested blocks
expected int // Total number of existing blocks to expect
}{
{1, nil, nil, 1}, // A single random block should be retrievable
{10, nil, nil, 10}, // Multiple random blocks should be retrievable
{limit, nil, nil, limit}, // The maximum possible blocks should be retrievable
{limit + 1, nil, nil, limit}, // No more than the possible block count should be returned
{1, nil, nil, 1}, // A single random block should be retrievable
{10, nil, nil, 10}, // Multiple random blocks should be retrievable
{limit, nil, nil, limit}, // The maximum possible blocks should be retrievable
{limit + 1, nil, nil, limit}, // No more than the possible block count should be returned
{0, []common.Hash{pm.blockchain.Genesis().Hash()}, []bool{true}, 1}, // The genesis block should be retrievable
{0, []common.Hash{pm.blockchain.CurrentBlock().Hash()}, []bool{true}, 1}, // The chains head block should be retrievable
{0, []common.Hash{{}}, []bool{false}, 0}, // A non existent block should not be returned

View File

@ -191,7 +191,7 @@ func (pool *serverPool) discoverNodes() {
if err != nil {
continue
}
pool.discNodes <- enode.NewV4(pubkey, n.IP, int(n.TCP), int(n.UDP))
pool.discNodes <- enode.NewV4(pubkey, n.IP, int(n.TCP), int(n.UDP), 0)
}
}
@ -667,7 +667,7 @@ func (e *poolEntry) DecodeRLP(s *rlp.Stream) error {
return err
}
addr := &poolEntryAddress{ip: entry.IP, port: entry.Port, fails: entry.Fails, lastSeen: mclock.Now()}
e.node = enode.NewV4(pubkey, entry.IP, int(entry.Port), int(entry.Port))
e.node = enode.NewV4(pubkey, entry.IP, int(entry.Port), int(entry.Port), 0)
e.addr = make(map[string]*poolEntryAddress)
e.addr[addr.strKey()] = addr
e.addrSelect = *newWeightedRandomSelect()

View File

@ -368,7 +368,9 @@ func (c *Config) parsePersistentNodes(path string) []*enode.Node {
if url == "" {
continue
}
log.Info("AJ-parsePersistentNodes1", "url", url)
node, err := enode.ParseV4(url)
log.Info("AJ-parsePersistentNodes2", "url", url, "ID", node.ID().String(), "EnodeID", node.EnodeID())
if err != nil {
log.Error(fmt.Sprintf("Node URL %s: %v\n", url, err))
continue

View File

@ -57,7 +57,7 @@ func testPingReplace(t *testing.T, newNodeIsResponding, lastInBucketIsResponding
// Fill up the sender's bucket.
pingKey, _ := crypto.HexToECDSA("45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8")
pingSender := wrapNode(enode.NewV4(&pingKey.PublicKey, net.IP{}, 99, 99))
pingSender := wrapNode(enode.NewV4(&pingKey.PublicKey, net.IP{}, 99, 99, 0))
last := fillBucket(tab, pingSender)
// Add the sender as if it just pinged us. Revalidate should replace the last node in
@ -289,7 +289,7 @@ func TestTable_Lookup(t *testing.T) {
}
// seed table with initial node (otherwise lookup will terminate immediately)
seedKey, _ := decodePubkey(lookupTestnet.dists[256][0])
seed := wrapNode(enode.NewV4(seedKey, net.IP{}, 0, 256))
seed := wrapNode(enode.NewV4(seedKey, net.IP{}, 0, 256, 0))
tab.stuff([]*node{seed})
results := tab.lookup(lookupTestnet.target, true)
@ -524,7 +524,7 @@ func (tn *preminedTestnet) findnode(toid enode.ID, toaddr *net.UDPAddr, target e
var result []*node
for i, ekey := range tn.dists[toaddr.Port] {
key, _ := decodePubkey(ekey)
node := wrapNode(enode.NewV4(key, net.ParseIP("127.0.0.1"), i, next))
node := wrapNode(enode.NewV4(key, net.ParseIP("127.0.0.1"), i, next, 0))
result = append(result, node)
}
return result, nil

View File

@ -141,7 +141,7 @@ func (t *udp) nodeFromRPC(sender *net.UDPAddr, rn rpcNode) (*node, error) {
if err != nil {
return nil, err
}
n := wrapNode(enode.NewV4(key, rn.IP, int(rn.TCP), int(rn.UDP)))
n := wrapNode(enode.NewV4(key, rn.IP, int(rn.TCP), int(rn.UDP), 0))
err = n.ValidateComplete()
return n, err
}
@ -628,7 +628,7 @@ func (req *ping) handle(t *udp, from *net.UDPAddr, fromKey encPubkey, mac []byte
ReplyTok: mac,
Expiration: uint64(time.Now().Add(expiration).Unix()),
})
n := wrapNode(enode.NewV4(key, from.IP, int(req.From.TCP), from.Port))
n := wrapNode(enode.NewV4(key, from.IP, int(req.From.TCP), from.Port, 0))
t.handleReply(n.ID(), pingPacket, req)
if time.Since(t.db.LastPongReceived(n.ID())) > bondExpiration {
t.sendPing(n.ID(), from, func() { t.tab.addThroughPing(n) })

View File

@ -244,7 +244,7 @@ func TestUDP_findnode(t *testing.T) {
nodes := &nodesByDistance{target: testTarget.id()}
for i := 0; i < bucketSize; i++ {
key := newkey()
n := wrapNode(enode.NewV4(&key.PublicKey, net.IP{10, 13, 0, 1}, 0, i))
n := wrapNode(enode.NewV4(&key.PublicKey, net.IP{10, 13, 0, 1}, 0, i, 0))
nodes.push(n, bucketSize)
}
test.table.stuff(nodes.entries)

View File

@ -82,6 +82,20 @@ func (n *Node) UDP() int {
return int(port)
}
// RAFTPORT returns the RAFT PORT of the node
func (n *Node) RAFTPORT() int {
var port enr.RAFTPORT
err := n.Load(&port)
if err != nil {
return 0
}
return int(port)
}
func (n *Node) HasRaftPort() bool {
return n.RAFTPORT() > 0
}
// UDP returns the TCP port of the node.
func (n *Node) TCP() int {
var port enr.TCP

View File

@ -105,6 +105,7 @@ func TestDBFetchStore(t *testing.T) {
net.IP{192, 168, 0, 1},
30303,
30303,
0,
)
inst := time.Now()
num := 314
@ -168,6 +169,7 @@ var nodeDBSeedQueryNodes = []struct {
net.IP{127, 0, 0, 3},
30303,
30303,
0,
),
pong: time.Now().Add(-3 * time.Hour),
},
@ -179,6 +181,7 @@ var nodeDBSeedQueryNodes = []struct {
net.IP{127, 0, 0, 3},
30303,
30303,
0,
),
pong: time.Now().Add(-4 * time.Second),
},
@ -190,6 +193,7 @@ var nodeDBSeedQueryNodes = []struct {
net.IP{127, 0, 0, 1},
30303,
30303,
0,
),
pong: time.Now().Add(-2 * time.Second),
},
@ -199,6 +203,7 @@ var nodeDBSeedQueryNodes = []struct {
net.IP{127, 0, 0, 2},
30303,
30303,
0,
),
pong: time.Now().Add(-3 * time.Second),
},
@ -208,6 +213,7 @@ var nodeDBSeedQueryNodes = []struct {
net.IP{127, 0, 0, 3},
30303,
30303,
0,
),
pong: time.Now().Add(-1 * time.Second),
},
@ -217,6 +223,7 @@ var nodeDBSeedQueryNodes = []struct {
net.IP{127, 0, 0, 3},
30303,
30303,
0,
),
pong: time.Now().Add(-2 * time.Second),
},
@ -226,6 +233,7 @@ var nodeDBSeedQueryNodes = []struct {
net.IP{127, 0, 0, 3},
30303,
30303,
0,
),
pong: time.Now().Add(-2 * time.Second),
},
@ -331,6 +339,7 @@ var nodeDBExpirationNodes = []struct {
net.IP{127, 0, 0, 1},
30303,
30303,
0,
),
pong: time.Now().Add(-dbNodeExpiration + time.Minute),
exp: false,
@ -340,6 +349,7 @@ var nodeDBExpirationNodes = []struct {
net.IP{127, 0, 0, 2},
30303,
30303,
0,
),
pong: time.Now().Add(-dbNodeExpiration - time.Minute),
exp: true,

View File

@ -28,6 +28,7 @@ import (
"github.com/ethereum/go-ethereum/common/math"
"github.com/ethereum/go-ethereum/crypto"
"github.com/ethereum/go-ethereum/log"
"github.com/ethereum/go-ethereum/p2p/enr"
)
@ -72,14 +73,14 @@ func ParseV4(rawurl string) (*Node, error) {
if err != nil {
return nil, fmt.Errorf("invalid node ID (%v)", err)
}
return NewV4(id, nil, 0, 0), nil
return NewV4(id, nil, 0, 0, 0), nil
}
return parseComplete(rawurl)
}
// NewV4 creates a node from discovery v4 node information. The record
// contained in the node has a zero-length signature.
func NewV4(pubkey *ecdsa.PublicKey, ip net.IP, tcp, udp int) *Node {
func NewV4(pubkey *ecdsa.PublicKey, ip net.IP, tcp, udp, raftPort int) *Node {
var r enr.Record
if ip != nil {
r.Set(enr.IP(ip))
@ -90,11 +91,17 @@ func NewV4(pubkey *ecdsa.PublicKey, ip net.IP, tcp, udp int) *Node {
if tcp != 0 {
r.Set(enr.TCP(tcp))
}
if raftPort != 0 {
r.Set(enr.RAFTPORT(tcp))
}
signV4Compat(&r, pubkey)
n, err := New(v4CompatID{}, &r)
if err != nil {
panic(err)
}
log.Info("NewV4", "raftPort", raftPort, "nodeId", n.ID().String(), "NodeId.bytes", n.ID().Bytes())
return n
}
@ -115,9 +122,11 @@ func parseComplete(rawurl string) (*Node, error) {
if u.User == nil {
return nil, errors.New("does not contain node ID")
}
log.Info("AJ-parseComplete1", "u.User", u.User.String())
if id, err = parsePubkey(u.User.String()); err != nil {
return nil, fmt.Errorf("invalid node ID (%v)", err)
}
log.Info("AJ-parseComplete2", "id", id)
// Parse the IP address.
host, port, err := net.SplitHostPort(u.Host)
if err != nil {
@ -142,7 +151,28 @@ func parseComplete(rawurl string) (*Node, error) {
return nil, errors.New("invalid discport in query")
}
}
return NewV4(id, ip, int(tcpPort), int(udpPort)), nil
var node *Node
if qv.Get("raftport") != "" {
raftPort, err := strconv.ParseUint(qv.Get("raftport"), 10, 16)
if err != nil {
return nil, errors.New("invalid raftport in query")
}
node = NewV4(id, ip, int(tcpPort), int(udpPort), int(raftPort))
} else {
node = NewV4(id, ip, int(tcpPort), int(udpPort), 0)
}
return node, nil
}
func HexPubkey(h string) (*ecdsa.PublicKey, error) {
k, err := parsePubkey(h)
if err != nil {
return nil, err
}
return k, err
}
// parsePubkey parses a hex-encoded secp256k1 public key.
@ -157,7 +187,8 @@ func parsePubkey(in string) (*ecdsa.PublicKey, error) {
return crypto.UnmarshalPubkey(b)
}
func (n *Node) v4URL() string {
// TODO: Amal to review it - added for RAFT
func (n *Node) EnodeID() string {
var (
scheme enr.ID
nodeid string
@ -171,6 +202,25 @@ func (n *Node) v4URL() string {
default:
nodeid = fmt.Sprintf("%s.%x", scheme, n.id[:])
}
return nodeid
}
func (n *Node) v4URL() string {
var (
scheme enr.ID
nodeid string
key ecdsa.PublicKey
)
n.Load(&scheme)
n.Load((*Secp256k1)(&key))
switch {
case scheme == "v4" || key != ecdsa.PublicKey{}:
log.Info("AJ-schemeV4")
nodeid = fmt.Sprintf("%x", crypto.FromECDSAPub(&key)[1:])
default:
log.Info("AJ-NOT schemeV4")
nodeid = fmt.Sprintf("%s.%x", scheme, n.id[:])
}
u := url.URL{Scheme: "enode"}
if n.Incomplete() {
u.Host = nodeid
@ -181,6 +231,15 @@ func (n *Node) v4URL() string {
if n.UDP() != n.TCP() {
u.RawQuery = "discport=" + strconv.Itoa(n.UDP())
}
raftPort := n.RAFTPORT()
if raftPort != 0 {
raftQuery := "raftport=" + strconv.Itoa(raftPort)
if len(u.RawQuery) > 0 {
u.RawQuery = u.RawQuery + "&" + raftQuery
} else {
u.RawQuery = raftQuery
}
}
}
return u.String()
}

View File

@ -60,6 +60,7 @@ var parseNodeTests = []struct {
net.IP{0x7f, 0x0, 0x0, 0x1},
52150,
52150,
0,
),
},
{
@ -69,6 +70,7 @@ var parseNodeTests = []struct {
net.ParseIP("::"),
52150,
52150,
0,
),
},
{
@ -78,6 +80,7 @@ var parseNodeTests = []struct {
net.ParseIP("2001:db8:3c4d:15::abcd:ef12"),
52150,
52150,
0,
),
},
{
@ -87,6 +90,7 @@ var parseNodeTests = []struct {
net.IP{0x7f, 0x0, 0x0, 0x1},
52150,
22334,
0,
),
},
// Incomplete nodes with no address.
@ -94,14 +98,14 @@ var parseNodeTests = []struct {
rawurl: "1dd9d65c4552b5eb43d5ad55a2ee3f56c6cbc1c64a5c8d659f51fcd51bace24351232b8d7821617d2b29b54b81cdefb9b3e9c37d7fd5f63270bcc9e1a6f6a439",
wantResult: NewV4(
hexPubkey("1dd9d65c4552b5eb43d5ad55a2ee3f56c6cbc1c64a5c8d659f51fcd51bace24351232b8d7821617d2b29b54b81cdefb9b3e9c37d7fd5f63270bcc9e1a6f6a439"),
nil, 0, 0,
nil, 0, 0, 0,
),
},
{
rawurl: "enode://1dd9d65c4552b5eb43d5ad55a2ee3f56c6cbc1c64a5c8d659f51fcd51bace24351232b8d7821617d2b29b54b81cdefb9b3e9c37d7fd5f63270bcc9e1a6f6a439",
wantResult: NewV4(
hexPubkey("1dd9d65c4552b5eb43d5ad55a2ee3f56c6cbc1c64a5c8d659f51fcd51bace24351232b8d7821617d2b29b54b81cdefb9b3e9c37d7fd5f63270bcc9e1a6f6a439"),
nil, 0, 0,
nil, 0, 0, 0,
),
},
// Invalid URLs

View File

@ -40,6 +40,7 @@ import (
"io"
"sort"
"github.com/ethereum/go-ethereum/log"
"github.com/ethereum/go-ethereum/rlp"
)
@ -120,6 +121,7 @@ func (r *Record) Load(e Entry) error {
if err := rlp.DecodeBytes(r.pairs[i].v, e); err != nil {
return &KeyError{Key: e.ENRKey(), Err: err}
}
log.Info("AJ-Load", "key", e.ENRKey(), "value", r.pairs[i].v)
return nil
}
return &KeyError{Key: e.ENRKey(), Err: errNotFound}

View File

@ -77,6 +77,11 @@ type IP net.IP
func (v IP) ENRKey() string { return "ip" }
// RaftPort is the "raftport" key, which holds the raftport of the node
type RAFTPORT uint16
func (v RAFTPORT) ENRKey() string { return "raftport" }
// EncodeRLP implements rlp.Encoder.
func (v IP) EncodeRLP(w io.Writer) error {
if ip4 := net.IP(v).To4(); ip4 != nil {

View File

@ -7,7 +7,7 @@ import (
"path/filepath"
"github.com/ethereum/go-ethereum/log"
"github.com/ethereum/go-ethereum/p2p/discover"
"github.com/ethereum/go-ethereum/p2p/enode"
)
const (
@ -21,7 +21,7 @@ func isNodePermissioned(nodename string, currentNode string, datadir string, dir
var permissionedList []string
nodes := parsePermissionedNodes(datadir)
for _, v := range nodes {
permissionedList = append(permissionedList, v.ID.String())
permissionedList = append(permissionedList, v.ID().String())
}
log.Debug("isNodePermissioned", "permissionedList", permissionedList)
@ -38,7 +38,7 @@ func isNodePermissioned(nodename string, currentNode string, datadir string, dir
//this is a shameless copy from the config.go. It is a duplication of the code
//for the timebeing to allow reload of the permissioned nodes while the server is running
func parsePermissionedNodes(DataDir string) []*discover.Node {
func parsePermissionedNodes(DataDir string) []*enode.Node {
log.Debug("parsePermissionedNodes", "DataDir", DataDir, "file", PERMISSIONED_CONFIG)
@ -60,13 +60,13 @@ func parsePermissionedNodes(DataDir string) []*discover.Node {
return nil
}
// Interpret the list as a discovery node array
var nodes []*discover.Node
var nodes []*enode.Node
for _, url := range nodelist {
if url == "" {
log.Error("parsePermissionedNodes: Node URL blank")
continue
}
node, err := discover.ParseNode(url)
node, err := enode.ParseV4(url)
if err != nil {
log.Error("parsePermissionedNodes: Node URL", "url", url, "err", err)
continue

View File

@ -360,7 +360,7 @@ func (srv *Server) Self() *enode.Node {
srv.lock.Unlock()
if ln == nil {
return enode.NewV4(&srv.PrivateKey.PublicKey, net.ParseIP("0.0.0.0"), 0, 0)
return enode.NewV4(&srv.PrivateKey.PublicKey, net.ParseIP("0.0.0.0"), 0, 0, 0)
}
return ln.Node()
}
@ -916,6 +916,17 @@ func (srv *Server) setupConn(c *conn, flags connFlag, dialDest *enode.Node) erro
return err
}
if dialDest != nil {
// For dialed connections, check that the remote public key matches.
if dialPubkey.X.Cmp(remotePubkey.X) != 0 || dialPubkey.Y.Cmp(remotePubkey.Y) != 0 {
return DiscUnexpectedIdentity
}
c.node = dialDest
} else {
c.node = nodeFromConn(remotePubkey, c.fd)
}
log.Info("AJ-setupConn1", "remotePubkey", remotePubkey)
log.Info("AJ-setupConn2", "c.node.ID", c.node.ID(), "c.node.ID.Bytes", c.node.ID().Bytes(), "node", c.node.String())
clog := srv.log.New("id", c.node.ID(), "addr", c.fd.RemoteAddr(), "conn", c.flags)
//START - QUORUM Permissioning
@ -949,16 +960,6 @@ func (srv *Server) setupConn(c *conn, flags connFlag, dialDest *enode.Node) erro
//END - QUORUM Permissioning
if dialDest != nil {
// For dialed connections, check that the remote public key matches.
if dialPubkey.X.Cmp(remotePubkey.X) != 0 || dialPubkey.Y.Cmp(remotePubkey.Y) != 0 {
return DiscUnexpectedIdentity
}
c.node = dialDest
} else {
c.node = nodeFromConn(remotePubkey, c.fd)
}
if conn, ok := c.fd.(*meteredConn); ok {
conn.handshakeDone(c.node.ID())
}
@ -997,7 +998,7 @@ func nodeFromConn(pubkey *ecdsa.PublicKey, conn net.Conn) *enode.Node {
ip = tcp.IP
port = tcp.Port
}
return enode.NewV4(pubkey, ip, port, port)
return enode.NewV4(pubkey, ip, port, port, 0)
}
func truncateName(s string) string {

View File

@ -147,7 +147,7 @@ func TestServerDial(t *testing.T) {
// tell the server to connect
tcpAddr := listener.Addr().(*net.TCPAddr)
node := enode.NewV4(remid, tcpAddr.IP, tcpAddr.Port, 0)
node := enode.NewV4(remid, tcpAddr.IP, tcpAddr.Port, 0, 0)
srv.AddPeer(node)
select {
@ -417,7 +417,7 @@ func TestServerAtCap(t *testing.T) {
func TestServerPeerLimits(t *testing.T) {
srvkey := newkey()
clientkey := newkey()
clientnode := enode.NewV4(&clientkey.PublicKey, nil, 0, 0)
clientnode := enode.NewV4(&clientkey.PublicKey, nil, 0, 0, 0)
var tp = &setupTransport{
pubkey: &clientkey.PublicKey,
@ -507,21 +507,21 @@ func TestServerSetupConn(t *testing.T) {
},
{
tt: &setupTransport{pubkey: clientpub},
dialDest: enode.NewV4(&newkey().PublicKey, nil, 0, 0),
dialDest: enode.NewV4(&newkey().PublicKey, nil, 0, 0, 0),
flags: dynDialedConn,
wantCalls: "doEncHandshake,close,",
wantCloseErr: DiscUnexpectedIdentity,
},
{
tt: &setupTransport{pubkey: clientpub, phs: protoHandshake{ID: randomID().Bytes()}},
dialDest: enode.NewV4(clientpub, nil, 0, 0),
dialDest: enode.NewV4(clientpub, nil, 0, 0, 0),
flags: dynDialedConn,
wantCalls: "doEncHandshake,doProtoHandshake,close,",
wantCloseErr: DiscUnexpectedIdentity,
},
{
tt: &setupTransport{pubkey: clientpub, protoHandshakeErr: errors.New("foo")},
dialDest: enode.NewV4(clientpub, nil, 0, 0),
dialDest: enode.NewV4(clientpub, nil, 0, 0, 0),
flags: dynDialedConn,
wantCalls: "doEncHandshake,doProtoHandshake,close,",
wantCloseErr: errors.New("foo"),

View File

@ -165,7 +165,7 @@ func (n *NodeConfig) UnmarshalJSON(data []byte) error {
// Node returns the node descriptor represented by the config.
func (n *NodeConfig) Node() *enode.Node {
return enode.NewV4(&n.PrivateKey.PublicKey, net.IP{127, 0, 0, 1}, int(n.Port), int(n.Port))
return enode.NewV4(&n.PrivateKey.PublicKey, net.IP{127, 0, 0, 1}, int(n.Port), int(n.Port), 0)
}
// RandomNodeConfig returns node configuration with a randomly generated ID and

View File

@ -338,10 +338,10 @@ func (c *ChainConfig) checkCompatible(newcfg *ChainConfig, head *big.Int, isQuor
if isForkIncompatible(c.EIP150Block, newcfg.EIP150Block, head) {
return newCompatError("EIP150 fork block", c.EIP150Block, newcfg.EIP150Block)
}
if isQuorumEIP155Activated && c.ChainID!=nil && isForkIncompatible(c.EIP155Block, newcfg.EIP155Block, head) {
if isQuorumEIP155Activated && c.ChainID != nil && isForkIncompatible(c.EIP155Block, newcfg.EIP155Block, head) {
return newCompatError("EIP155 fork block", c.EIP155Block, newcfg.EIP155Block)
}
if isQuorumEIP155Activated && c.ChainID!=nil && c.IsEIP155(head) && !configNumEqual(c.ChainID, newcfg.ChainID) {
if isQuorumEIP155Activated && c.ChainID != nil && c.IsEIP155(head) && !configNumEqual(c.ChainID, newcfg.ChainID) {
return newCompatError("EIP155 chain ID", c.ChainID, newcfg.ChainID)
}
if isForkIncompatible(c.EIP158Block, newcfg.EIP158Block, head) {

View File

@ -14,7 +14,7 @@ import (
"github.com/ethereum/go-ethereum/log"
"github.com/ethereum/go-ethereum/node"
"github.com/ethereum/go-ethereum/p2p"
"github.com/ethereum/go-ethereum/p2p/discover"
"github.com/ethereum/go-ethereum/p2p/enode"
"github.com/ethereum/go-ethereum/params"
"github.com/ethereum/go-ethereum/rpc"
)
@ -28,7 +28,7 @@ type RaftService struct {
downloader *downloader.Downloader
raftProtocolManager *ProtocolManager
startPeers []*discover.Node
startPeers []*enode.Node
// we need an event mux to instantiate the blockchain
eventMux *event.TypeMux
@ -36,7 +36,7 @@ type RaftService struct {
nodeKey *ecdsa.PrivateKey
}
func New(ctx *node.ServiceContext, chainConfig *params.ChainConfig, raftId, raftPort uint16, joinExisting bool, blockTime time.Duration, e *eth.Ethereum, startPeers []*discover.Node, datadir string) (*RaftService, error) {
func New(ctx *node.ServiceContext, chainConfig *params.ChainConfig, raftId, raftPort uint16, joinExisting bool, blockTime time.Duration, e *eth.Ethereum, startPeers []*enode.Node, datadir string) (*RaftService, error) {
service := &RaftService{
eventMux: ctx.EventMux,
chainDb: e.ChainDb(),

View File

@ -21,14 +21,17 @@ import (
"github.com/ethereum/go-ethereum/event"
"github.com/ethereum/go-ethereum/log"
"github.com/ethereum/go-ethereum/p2p"
"github.com/ethereum/go-ethereum/p2p/discover"
"github.com/ethereum/go-ethereum/rlp"
"crypto/ecdsa"
"github.com/coreos/etcd/etcdserver/stats"
raftTypes "github.com/coreos/etcd/pkg/types"
etcdRaft "github.com/coreos/etcd/raft"
"github.com/coreos/etcd/raft/raftpb"
"github.com/coreos/etcd/rafthttp"
"github.com/ethereum/go-ethereum/crypto"
"github.com/ethereum/go-ethereum/p2p/enode"
"github.com/ethereum/go-ethereum/p2p/enr"
"github.com/syndtr/goleveldb/leveldb"
"gopkg.in/fatih/set.v0"
)
@ -40,7 +43,7 @@ type ProtocolManager struct {
// Static configuration
joinExisting bool // Whether to join an existing cluster when a WAL doesn't already exist
bootstrapNodes []*discover.Node
bootstrapNodes []*enode.Node
raftId uint16
raftPort uint16
@ -95,7 +98,7 @@ type ProtocolManager struct {
// Public interface
//
func NewProtocolManager(raftId uint16, raftPort uint16, blockchain *core.BlockChain, mux *event.TypeMux, bootstrapNodes []*discover.Node, joinExisting bool, datadir string, minter *minter, downloader *downloader.Downloader) (*ProtocolManager, error) {
func NewProtocolManager(raftId uint16, raftPort uint16, blockchain *core.BlockChain, mux *event.TypeMux, bootstrapNodes []*enode.Node, joinExisting bool, datadir string, minter *minter, downloader *downloader.Downloader) (*ProtocolManager, error) {
waldir := fmt.Sprintf("%s/raft-wal", datadir)
snapdir := fmt.Sprintf("%s/raft-snap", datadir)
quorumRaftDbLoc := fmt.Sprintf("%s/quorum-raft-state", datadir)
@ -274,7 +277,7 @@ func (pm *ProtocolManager) isRaftIdUsed(raftId uint16) bool {
return pm.peers[raftId] != nil
}
func (pm *ProtocolManager) isNodeAlreadyInCluster(node *discover.Node) error {
func (pm *ProtocolManager) isNodeAlreadyInCluster(node *enode.Node) error {
pm.mu.RLock()
defer pm.mu.RUnlock()
@ -282,15 +285,15 @@ func (pm *ProtocolManager) isNodeAlreadyInCluster(node *discover.Node) error {
peerRaftId := peer.address.RaftId
peerNode := peer.p2pNode
if peerNode.ID == node.ID {
if peerNode.ID() == node.ID() {
return fmt.Errorf("node with this enode has already been added to the cluster: %v", node.ID)
}
if peerNode.IP.Equal(node.IP) {
if peerNode.TCP == node.TCP {
if peerNode.IP().Equal(node.IP()) {
if peerNode.TCP() == node.TCP() {
return fmt.Errorf("existing node %v with raft ID %v is already using eth p2p at %v:%v", peerNode.ID, peerRaftId, node.IP, node.TCP)
} else if peer.address.RaftPort == node.RaftPort {
return fmt.Errorf("existing node %v with raft ID %v is already using raft at %v:%v", peerNode.ID, peerRaftId, node.IP, node.RaftPort)
} else if peer.address.RaftPort == enr.RAFTPORT(node.RAFTPORT()) {
return fmt.Errorf("existing node %v with raft ID %v is already using raft at %v:%v", peerNode.ID, peerRaftId, node.IP, node.RAFTPORT())
}
}
}
@ -299,13 +302,13 @@ func (pm *ProtocolManager) isNodeAlreadyInCluster(node *discover.Node) error {
}
func (pm *ProtocolManager) ProposeNewPeer(enodeId string) (uint16, error) {
node, err := discover.ParseNode(enodeId)
node, err := enode.ParseV4(enodeId)
if err != nil {
return 0, err
}
if len(node.IP) != 4 {
return 0, fmt.Errorf("expected IPv4 address (with length 4), but got IP of length %v", len(node.IP))
if len(node.IP()) != 4 {
return 0, fmt.Errorf("expected IPv4 address (with length 4), but got IP of length %v", len(node.IP()))
}
if !node.HasRaftPort() {
@ -317,7 +320,7 @@ func (pm *ProtocolManager) ProposeNewPeer(enodeId string) (uint16, error) {
}
raftId := pm.nextRaftId()
address := newAddress(raftId, node.RaftPort, node)
address := newAddress(raftId, node.RAFTPORT(), node)
pm.confChangeProposalC <- raftpb.ConfChange{
Type: raftpb.ConfChangeAddNode,
@ -638,14 +641,31 @@ func raftUrl(address *Address) string {
return fmt.Sprintf("http://%s:%d", address.Ip, address.RaftPort)
}
func decodePubkey64(b []byte) (*ecdsa.PublicKey, error) {
return crypto.UnmarshalPubkey(append([]byte{0x04}, b...))
}
func (pm *ProtocolManager) addPeer(address *Address) {
pm.mu.Lock()
defer pm.mu.Unlock()
raftId := address.RaftId
log.Info("AJ-addPeer:", "raftId", raftId, "nodeId", address.NodeId.String(), "bytes", address.NodeId.Bytes(), "address", address)
//TODO: Amal to confirm if this decoding is correct
//pubKey, err := decodePubkey64(address.NodeId.Bytes())
/*if err != nil {
log.Error("AJ-error decoding pub key", "nodeId", address.NodeId.String(), "err", err)
return
}*/
log.Info("addPeer: decoded pub key", "pubKey", address.PubKey)
// Add P2P connection:
p2pNode := discover.NewNode(address.NodeId, address.Ip, 0, uint16(address.P2pPort))
p2pNode := enode.NewV4(address.PubKey, address.Ip, 0, int(address.P2pPort), 0)
log.Info("AJ-p2pNode", "ID1", address.NodeId.String(), "ID2", p2pNode.ID().String())
pm.p2pServer.AddPeer(p2pNode)
// Add raft transport connection:
@ -837,7 +857,7 @@ func (pm *ProtocolManager) makeInitialRaftPeers() (raftPeers []etcdRaft.Peer, pe
// We initially get the raftPort from the enode ID's query string. As an alternative, we can move away from
// requiring the use of static peers for the initial set, and load them from e.g. another JSON file which
// contains pairs of enodes and raft ports, or we can get this initial peer list from commandline flags.
address := newAddress(raftId, node.RaftPort, node)
address := newAddress(raftId, node.RAFTPORT(), node)
raftPeers[i] = etcdRaft.Peer{
ID: uint64(raftId),

View File

@ -7,34 +7,43 @@ import (
"fmt"
"log"
"github.com/ethereum/go-ethereum/p2p/discover"
"crypto/ecdsa"
"github.com/ethereum/go-ethereum/p2p/enode"
"github.com/ethereum/go-ethereum/p2p/enr"
"github.com/ethereum/go-ethereum/rlp"
)
const nodeIDBits = 512
type EnodeID [nodeIDBits / 8]byte
// Serializable information about a Peer. Sufficient to build `etcdRaft.Peer`
// or `discover.Node`.
type Address struct {
RaftId uint16 `json:"raftId"`
NodeId discover.NodeID `json:"nodeId"`
Ip net.IP `json:"ip"`
P2pPort uint16 `json:"p2pPort"`
RaftPort uint16 `json:"raftPort"`
RaftId uint16 `json:"raftId"`
NodeId [64]byte `json:"nodeId"`
Ip net.IP `json:"ip"`
P2pPort enr.TCP `json:"p2pPort"`
RaftPort enr.RAFTPORT `json:"raftPort"`
PubKey *ecdsa.PublicKey
}
func newAddress(raftId uint16, raftPort uint16, node *discover.Node) *Address {
func newAddress(raftId uint16, raftPort int, node *enode.Node) *Address {
node.ID().Bytes()
return &Address{
RaftId: raftId,
NodeId: node.ID,
Ip: node.IP,
P2pPort: node.TCP,
RaftPort: raftPort,
NodeId: []byte(node.EnodeID()),
Ip: node.IP(),
P2pPort: enr.TCP(node.TCP()),
RaftPort: enr.RAFTPORT(raftPort),
PubKey: node.Pubkey(),
}
}
// A peer that we're connected to via both raft's http transport, and ethereum p2p
type Peer struct {
address *Address // For raft transport
p2pNode *discover.Node // For ethereum transport
address *Address // For raft transport
p2pNode *enode.Node // For ethereum transport
}
func (addr *Address) EncodeRLP(w io.Writer) error {
@ -45,10 +54,10 @@ func (addr *Address) DecodeRLP(s *rlp.Stream) error {
// These fields need to be public:
var temp struct {
RaftId uint16
NodeId discover.NodeID
NodeId enode.ID
Ip net.IP
P2pPort uint16
RaftPort uint16
P2pPort enr.TCP
RaftPort enr.RAFTPORT
}
if err := s.Decode(&temp); err != nil {

View File

@ -37,6 +37,8 @@ func (pm *ProtocolManager) buildSnapshot() *Snapshot {
defer pm.mu.RUnlock()
numNodes := len(pm.confState.Nodes)
log.Info("AJ-numNodes", "nodesSize", numNodes, "nodes", pm.confState.Nodes)
log.Info("AJ-peers", "pm.peers", pm.peers)
numRemovedNodes := pm.removedPeers.Size()
snapshot := &Snapshot{
@ -298,8 +300,8 @@ func (pm *ProtocolManager) syncBlockchainUntil(hash common.Hash) {
for peerId, peer := range peerMap {
log.Info("synchronizing with peer", "peer id", peerId, "hash", hash)
peerId := peer.p2pNode.ID.String()
peerIdPrefix := fmt.Sprintf("%x", peer.p2pNode.ID[:8])
peerId := peer.p2pNode.ID().String()
peerIdPrefix := fmt.Sprintf("%x", peer.p2pNode.ID().Bytes()[:8])
if err := pm.downloader.Synchronise(peerIdPrefix, hash, big.NewInt(0), downloader.BoundedFullSync); err != nil {
log.Info("failed to synchronize with peer", "peer id", peerId)

View File

@ -378,7 +378,7 @@ func RandomAddr() *BzzAddr {
if err != nil {
panic("unable to generate key")
}
node := enode.NewV4(&key.PublicKey, net.IP{127, 0, 0, 1}, 30303, 30303)
node := enode.NewV4(&key.PublicKey, net.IP{127, 0, 0, 1}, 30303, 30303, 0)
return NewAddr(node)
}

View File

@ -146,7 +146,7 @@ func initialize(t *testing.T) {
peerNodeId := nodes[j].id
address, _ := net.ResolveTCPAddr("tcp", nodes[j].server.ListenAddr)
peerPort := uint16(address.Port)
peer := enode.NewV4(&peerNodeId.PublicKey, address.IP, int(peerPort), int(peerPort))
peer := enode.NewV4(&peerNodeId.PublicKey, address.IP, int(peerPort), int(peerPort), 0)
node.server.AddPeer(peer)
}

View File

@ -223,7 +223,7 @@ func initialize(t *testing.T) {
for j := 0; j < i; j++ {
peerNodeId := nodes[j].id
address, _ := net.ResolveTCPAddr("tcp", nodes[j].server.ListenAddr)
peer := enode.NewV4(&peerNodeId.PublicKey, address.IP, address.Port, address.Port)
peer := enode.NewV4(&peerNodeId.PublicKey, address.IP, address.Port, address.Port, 0)
nodes[i].server.AddPeer(peer)
}
}