示例#1
0
func (s *XLSuite) TestEncoding(c *C) {
	if VERBOSITY > 0 {
		fmt.Println("TEST_ENCODING")
	}
	const K = 2
	nodes, accs := xn.MockLocalHostCluster(K) // lazy way to get keys
	defer func() {
		for i := 0; i < K; i++ {
			if accs[i] != nil {
				accs[i].Close()
			}
		}
	}()

	peer := nodes[0].GetPeer(0)
	pID := peer.GetNodeID().Value()
	pck, err := xc.RSAPubKeyToWire(peer.GetCommsPublicKey())
	c.Assert(err, IsNil)
	psk, err := xc.RSAPubKeyToWire(peer.GetSigPublicKey())
	c.Assert(err, IsNil)

	cmd := XLatticeMsg_Hello
	one := uint64(1)
	msg := &XLatticeMsg{
		Op:       &cmd,
		MsgN:     &one,
		ID:       pID,
		CommsKey: pck,
		SigKey:   psk,
	}
	wired, err := EncodePacket(msg)
	c.Assert(err, IsNil)
	c.Assert(wired, Not(IsNil))

	backAgain, err := DecodePacket(wired)
	c.Assert(err, IsNil)
	c.Assert(backAgain, Not(IsNil))

	rewired, err := EncodePacket(msg)
	c.Assert(err, IsNil)
	c.Assert(rewired, Not(IsNil))

	c.Assert(len(wired), Equals, len(rewired))
	for i := 0; i < len(wired); i++ {
		c.Assert(wired[i], Equals, rewired[i])
	}

	// DEBUG
	//fmt.Printf("    len ck %d bytes\n", len(msg.GetCommsKey()))	// 294
	//fmt.Printf("    len sk %d bytes\n", len(msg.GetSigKey()))		// 294
	//fmt.Println("    end TestEncoding")
	// END
}
示例#2
0
func (s *XLSuite) TestHelloHandler(c *C) {
	if VERBOSITY > 0 {
		fmt.Println("TEST_HELLO_HANDLER")
	}

	// Create a node and add a mock peer.  This is a cluster of 2.
	nodes, accs := xn.MockLocalHostCluster(2)
	defer func() {
		for i := 0; i < 2; i++ {
			if accs[i] != nil {
				accs[i].Close()
			}
		}
	}()
	myNode, peerNode := nodes[0], nodes[1]
	meAsPeer := peerNode.GetPeer(0)
	myAcc, peerAcc := accs[0], accs[1]
	_ = peerAcc // never used

	c.Assert(myAcc, Not(IsNil))
	myAccEP := myAcc.GetEndPoint()
	myCtor, err := xt.NewTcpConnector(myAccEP)
	c.Assert(err, IsNil)

	// myNode's server side
	stopCh := make(chan bool, 1) // has buffer so won't block
	stoppedCh := make(chan bool, 1)

	go func() {
		for {
			cnx, err := myAcc.Accept()
			if err != nil {
				break
			}

			// each connection handled by a separate goroutine
			go func() {
				_, _ = NewInHandler(myNode, cnx, stopCh, stoppedCh)
			}()
		}
	}()

	// -- WELL-FORMED HELLO -----------------------------------------
	// Known peer sends Hello with all parameters correct.  We reply
	// with an Ack and advance state to open.

	conn, err := myCtor.Connect(xt.ANY_TCP_END_POINT)
	c.Assert(err, IsNil)
	c.Assert(conn, Not(IsNil))
	cnx2 := conn.(*xt.TcpConnection)
	defer cnx2.Close()

	oh := &OutHandler{
		Node:       peerNode,
		CnxHandler: CnxHandler{Cnx: cnx2, Peer: meAsPeer}}

	// manually create and send a hello message -

	// XXX HELLO_MSG IS OBSOLETE; it's done with RSA/AES handshake

	peerHello, err := MakeHelloMsg(peerNode)
	c.Assert(err, IsNil)
	c.Assert(peerHello, Not(IsNil))

	data, err := EncodePacket(peerHello)
	c.Assert(err, IsNil)
	c.Assert(data, Not(IsNil))
	count, err := cnx2.Write(data)
	c.Assert(err, IsNil)
	c.Assert(count, Equals, len(data))
	oh.MsgN = ONE
	// end manual hello -------------------------

	time.Sleep(100 * time.Millisecond)

	// wait for ack
	ack, err := oh.readMsg()
	c.Assert(err, IsNil)
	c.Assert(ack, Not(IsNil))

	// verify msg returned is an ack and has the correct parameters
	c.Assert(ack.GetOp(), Equals, XLatticeMsg_Ack)
	c.Assert(ack.GetMsgN(), Equals, TWO)
	c.Assert(ack.GetYourMsgN(), Equals, ONE) // FOO

	// -- KEEPALIVE -------------------------------------------------
	cmd := XLatticeMsg_KeepAlive
	keepAlive := &XLatticeMsg{
		Op:   &cmd,
		MsgN: &THREE,
	}
	data, err = EncodePacket(keepAlive)
	c.Assert(err, IsNil)
	c.Assert(data, Not(IsNil))
	count, err = cnx2.Write(data)
	c.Assert(err, IsNil)
	c.Assert(count, Equals, len(data))

	// Wait for ack.  In a better world we time out if an ack is not
	// received in some short period rather than blocking forever.
	ack, err = oh.readMsg()
	c.Assert(err, IsNil)
	c.Assert(ack, Not(IsNil))

	// verify msg returned is an ack and has the correct parameters
	c.Assert(ack.GetOp(), Equals, XLatticeMsg_Ack)
	c.Assert(ack.GetMsgN(), Equals, FOUR)
	c.Assert(ack.GetYourMsgN(), Equals, THREE)

	// -- BYE -------------------------------------------------------
	cmd = XLatticeMsg_Bye
	bye := &XLatticeMsg{
		Op:   &cmd,
		MsgN: &FIVE,
	}
	data, err = EncodePacket(bye)
	c.Assert(err, IsNil)
	c.Assert(data, Not(IsNil))
	count, err = cnx2.Write(data)
	c.Assert(err, IsNil)
	c.Assert(count, Equals, len(data))

	// Wait for ack.  In a better world we time out if an ack is not
	// received in some short period rather than blocking forever.
	ack, err = oh.readMsg()
	c.Assert(err, IsNil)
	c.Assert(ack, Not(IsNil))

	// verify msg returned is an ack and has the correct parameters
	c.Assert(ack.GetOp(), Equals, XLatticeMsg_Ack)
	c.Assert(ack.GetMsgN(), Equals, SIX)
	c.Assert(ack.GetYourMsgN(), Equals, FIVE)

	// -- STOP THE SERVER -------------------------------------------
	stopCh <- true
	select {
	case <-stoppedCh:
	case <-time.After(100 * time.Millisecond):
	}
} // END HANDLER
示例#3
0
func (s *XLSuite) TestSecondHello(c *C) {
	if VERBOSITY > 0 {
		fmt.Println("TEST_SECOND_HELLO")
	}
	// Create a node and add a mock peer.  This is a cluster of 2.
	nodes, accs := xn.MockLocalHostCluster(2)
	defer func() {
		for i := 0; i < 2; i++ {
			if accs[i] != nil {
				accs[i].Close()
			}
		}
	}()
	serverNode, clientNode := nodes[0], nodes[1]
	serverAsPeer := clientNode.GetPeer(0)
	serverAcc := accs[0]

	c.Assert(serverAcc, Not(IsNil))
	serverAccEP := serverAcc.GetEndPoint()
	serverCtor, err := xt.NewTcpConnector(serverAccEP)
	c.Assert(err, IsNil)

	// serverNode's server side
	stopCh := make(chan bool, 1)
	stoppedCh := make(chan bool, 1)

	// XXX If you comment out this goroutine, there are no mysterious
	// failures.

	go func() {
		for {
			cnx, err := serverAcc.Accept()
			// ADDING THIS ELIMINATES MYSTERY FAILURES
			if err != nil {
				break
			}

			// each connection handled by a separate goroutine
			go func() {
				_, _ = NewInHandler(serverNode, cnx, stopCh, stoppedCh)
			}()
		}
	}() // END FUNC

	// -- WELL-FORMED HELLO -----------------------------------------
	// Known peer sends Hello with all parameters correct.  Server
	// replies with an Ack and advance state to open.

	conn, err := serverCtor.Connect(xt.ANY_TCP_END_POINT)
	c.Assert(err, IsNil)
	c.Assert(conn, Not(IsNil))
	cnx2 := conn.(*xt.TcpConnection)
	defer cnx2.Close()

	oh := &OutHandler{Node: clientNode,
		CnxHandler: CnxHandler{Cnx: cnx2, Peer: serverAsPeer}}

	err = oh.SendHello()
	c.Assert(err, IsNil)

	// wait for ack
	ack, err := oh.readMsg()
	c.Assert(err, IsNil) // XXX "EOF" instead
	c.Assert(ack, Not(IsNil))

	// verify msg returned is an ack and has the correct parameters
	c.Assert(ack.GetOp(), Equals, XLatticeMsg_Ack)
	c.Assert(ack.GetMsgN(), Equals, TWO)
	c.Assert(ack.GetYourMsgN(), Equals, ONE) // FOO

	// -- SECOND WELL-FORMED HELLO ----------------------------------

	// manually create and send a hello message -

	// XXX HELLO_MSG IS OBSOLETE; it's done with RSA/AES handshake

	peerHello, err := MakeHelloMsg(clientNode)
	c.Assert(err, IsNil)
	c.Assert(peerHello, Not(IsNil))

	data, err := EncodePacket(peerHello)
	c.Assert(err, IsNil)
	c.Assert(data, Not(IsNil))
	count, err := cnx2.Write(data)
	c.Assert(err, IsNil)
	c.Assert(count, Equals, len(data))
	oh.MsgN = ONE
	// end manual hello -------------------------

	// wait for error message
	reply, err := oh.readMsg()
	c.Assert(err, IsNil)
	c.Assert(reply, Not(IsNil))

	// verify msg returned is an reply and has the correct parameters
	c.Assert(reply.GetOp(), Equals, XLatticeMsg_Error)
	c.Assert(reply.GetMsgN(), Equals, FOUR)

	// -- STOP THE SERVER -------------------------------------------
	stopCh <- true
	select {
	case <-stoppedCh:
	case <-time.After(100 * time.Millisecond):
	}
}