github.com/codingfuture/orig-energi3@v0.8.4/swarm/network/protocol_test.go (about)

     1  // Copyright 2018 The Energi Core Authors
     2  // Copyright 2014 The go-ethereum Authors
     3  // This file is part of the Energi Core library.
     4  //
     5  // The Energi Core library is free software: you can redistribute it and/or modify
     6  // it under the terms of the GNU Lesser General Public License as published by
     7  // the Free Software Foundation, either version 3 of the License, or
     8  // (at your option) any later version.
     9  //
    10  // The Energi Core library is distributed in the hope that it will be useful,
    11  // but WITHOUT ANY WARRANTY; without even the implied warranty of
    12  // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
    13  // GNU Lesser General Public License for more details.
    14  //
    15  // You should have received a copy of the GNU Lesser General Public License
    16  // along with the Energi Core library. If not, see <http://www.gnu.org/licenses/>.
    17  
    18  package network
    19  
    20  import (
    21  	"flag"
    22  	"fmt"
    23  	"os"
    24  	"testing"
    25  	"time"
    26  
    27  	"github.com/ethereum/go-ethereum/log"
    28  	"github.com/ethereum/go-ethereum/p2p"
    29  	"github.com/ethereum/go-ethereum/p2p/enode"
    30  	"github.com/ethereum/go-ethereum/p2p/protocols"
    31  	p2ptest "github.com/ethereum/go-ethereum/p2p/testing"
    32  )
    33  
    34  const (
    35  	TestProtocolVersion   = 8
    36  	TestProtocolNetworkID = 3
    37  )
    38  
    39  var (
    40  	loglevel = flag.Int("loglevel", 2, "verbosity of logs")
    41  )
    42  
    43  func init() {
    44  	testing.Init()
    45  	flag.Parse()
    46  	log.Root().SetHandler(log.LvlFilterHandler(log.Lvl(*loglevel), log.StreamHandler(os.Stderr, log.TerminalFormat(true))))
    47  }
    48  
    49  func HandshakeMsgExchange(lhs, rhs *HandshakeMsg, id enode.ID) []p2ptest.Exchange {
    50  	return []p2ptest.Exchange{
    51  		{
    52  			Expects: []p2ptest.Expect{
    53  				{
    54  					Code: 0,
    55  					Msg:  lhs,
    56  					Peer: id,
    57  				},
    58  			},
    59  		},
    60  		{
    61  			Triggers: []p2ptest.Trigger{
    62  				{
    63  					Code: 0,
    64  					Msg:  rhs,
    65  					Peer: id,
    66  				},
    67  			},
    68  		},
    69  	}
    70  }
    71  
    72  func newBzzBaseTester(t *testing.T, n int, addr *BzzAddr, spec *protocols.Spec, run func(*BzzPeer) error) *bzzTester {
    73  	cs := make(map[string]chan bool)
    74  
    75  	srv := func(p *BzzPeer) error {
    76  		defer func() {
    77  			if cs[p.ID().String()] != nil {
    78  				close(cs[p.ID().String()])
    79  			}
    80  		}()
    81  		return run(p)
    82  	}
    83  
    84  	protocol := func(p *p2p.Peer, rw p2p.MsgReadWriter) error {
    85  		return srv(&BzzPeer{Peer: protocols.NewPeer(p, rw, spec), BzzAddr: NewAddr(p.Node())})
    86  	}
    87  
    88  	s := p2ptest.NewProtocolTester(addr.ID(), n, protocol)
    89  
    90  	for _, node := range s.Nodes {
    91  		cs[node.ID().String()] = make(chan bool)
    92  	}
    93  
    94  	return &bzzTester{
    95  		addr:           addr,
    96  		ProtocolTester: s,
    97  		cs:             cs,
    98  	}
    99  }
   100  
   101  type bzzTester struct {
   102  	*p2ptest.ProtocolTester
   103  	addr *BzzAddr
   104  	cs   map[string]chan bool
   105  	bzz  *Bzz
   106  }
   107  
   108  func newBzz(addr *BzzAddr, lightNode bool) *Bzz {
   109  	config := &BzzConfig{
   110  		OverlayAddr:  addr.Over(),
   111  		UnderlayAddr: addr.Under(),
   112  		HiveParams:   NewHiveParams(),
   113  		NetworkID:    DefaultNetworkID,
   114  		LightNode:    lightNode,
   115  	}
   116  	kad := NewKademlia(addr.OAddr, NewKadParams())
   117  	bzz := NewBzz(config, kad, nil, nil, nil)
   118  	return bzz
   119  }
   120  
   121  func newBzzHandshakeTester(n int, addr *BzzAddr, lightNode bool) *bzzTester {
   122  	bzz := newBzz(addr, lightNode)
   123  	pt := p2ptest.NewProtocolTester(addr.ID(), n, bzz.runBzz)
   124  
   125  	return &bzzTester{
   126  		addr:           addr,
   127  		ProtocolTester: pt,
   128  		bzz:            bzz,
   129  	}
   130  }
   131  
   132  // should test handshakes in one exchange? parallelisation
   133  func (s *bzzTester) testHandshake(lhs, rhs *HandshakeMsg, disconnects ...*p2ptest.Disconnect) error {
   134  	if err := s.TestExchanges(HandshakeMsgExchange(lhs, rhs, rhs.Addr.ID())...); err != nil {
   135  		return err
   136  	}
   137  
   138  	if len(disconnects) > 0 {
   139  		return s.TestDisconnected(disconnects...)
   140  	}
   141  
   142  	// If we don't expect disconnect, ensure peers remain connected
   143  	err := s.TestDisconnected(&p2ptest.Disconnect{
   144  		Peer:  s.Nodes[0].ID(),
   145  		Error: nil,
   146  	})
   147  
   148  	if err == nil {
   149  		return fmt.Errorf("Unexpected peer disconnect")
   150  	}
   151  
   152  	if err.Error() != "timed out waiting for peers to disconnect" {
   153  		return err
   154  	}
   155  
   156  	return nil
   157  }
   158  
   159  func correctBzzHandshake(addr *BzzAddr, lightNode bool) *HandshakeMsg {
   160  	return &HandshakeMsg{
   161  		Version:   TestProtocolVersion,
   162  		NetworkID: TestProtocolNetworkID,
   163  		Addr:      addr,
   164  		LightNode: lightNode,
   165  	}
   166  }
   167  
   168  func TestBzzHandshakeNetworkIDMismatch(t *testing.T) {
   169  	lightNode := false
   170  	addr := RandomAddr()
   171  	s := newBzzHandshakeTester(1, addr, lightNode)
   172  	node := s.Nodes[0]
   173  
   174  	err := s.testHandshake(
   175  		correctBzzHandshake(addr, lightNode),
   176  		&HandshakeMsg{Version: TestProtocolVersion, NetworkID: 321, Addr: NewAddr(node)},
   177  		&p2ptest.Disconnect{Peer: node.ID(), Error: fmt.Errorf("Handshake error: Message handler error: (msg code 0): network id mismatch 321 (!= 3)")},
   178  	)
   179  
   180  	if err != nil {
   181  		t.Fatal(err)
   182  	}
   183  }
   184  
   185  func TestBzzHandshakeVersionMismatch(t *testing.T) {
   186  	lightNode := false
   187  	addr := RandomAddr()
   188  	s := newBzzHandshakeTester(1, addr, lightNode)
   189  	node := s.Nodes[0]
   190  
   191  	err := s.testHandshake(
   192  		correctBzzHandshake(addr, lightNode),
   193  		&HandshakeMsg{Version: 0, NetworkID: TestProtocolNetworkID, Addr: NewAddr(node)},
   194  		&p2ptest.Disconnect{Peer: node.ID(), Error: fmt.Errorf("Handshake error: Message handler error: (msg code 0): version mismatch 0 (!= %d)", TestProtocolVersion)},
   195  	)
   196  
   197  	if err != nil {
   198  		t.Fatal(err)
   199  	}
   200  }
   201  
   202  func TestBzzHandshakeSuccess(t *testing.T) {
   203  	lightNode := false
   204  	addr := RandomAddr()
   205  	s := newBzzHandshakeTester(1, addr, lightNode)
   206  	node := s.Nodes[0]
   207  
   208  	err := s.testHandshake(
   209  		correctBzzHandshake(addr, lightNode),
   210  		&HandshakeMsg{Version: TestProtocolVersion, NetworkID: TestProtocolNetworkID, Addr: NewAddr(node)},
   211  	)
   212  
   213  	if err != nil {
   214  		t.Fatal(err)
   215  	}
   216  }
   217  
   218  func TestBzzHandshakeLightNode(t *testing.T) {
   219  	var lightNodeTests = []struct {
   220  		name      string
   221  		lightNode bool
   222  	}{
   223  		{"on", true},
   224  		{"off", false},
   225  	}
   226  
   227  	for _, test := range lightNodeTests {
   228  		t.Run(test.name, func(t *testing.T) {
   229  			randomAddr := RandomAddr()
   230  			pt := newBzzHandshakeTester(1, randomAddr, false)
   231  
   232  			node := pt.Nodes[0]
   233  			addr := NewAddr(node)
   234  
   235  			err := pt.testHandshake(
   236  				correctBzzHandshake(randomAddr, false),
   237  				&HandshakeMsg{Version: TestProtocolVersion, NetworkID: TestProtocolNetworkID, Addr: addr, LightNode: test.lightNode},
   238  			)
   239  
   240  			if err != nil {
   241  				t.Fatal(err)
   242  			}
   243  
   244  			select {
   245  
   246  			case <-pt.bzz.handshakes[node.ID()].done:
   247  				if pt.bzz.handshakes[node.ID()].LightNode != test.lightNode {
   248  					t.Fatalf("peer LightNode flag is %v, should be %v", pt.bzz.handshakes[node.ID()].LightNode, test.lightNode)
   249  				}
   250  			case <-time.After(10 * time.Second):
   251  				t.Fatal("test timeout")
   252  			}
   253  		})
   254  	}
   255  }