Skip to content
Snippets Groups Projects
Commit 5c1addd7 authored by Josh Brooks's avatar Josh Brooks
Browse files

Further clean up authenticated connections' implementation

parent bd39e4fc
No related branches found
No related tags found
3 merge requests!510Release,!216Xx 3895/authenticated connection,!207WIP: Client Restructure
...@@ -37,9 +37,9 @@ type Connection interface { ...@@ -37,9 +37,9 @@ type Connection interface {
IsAuthenticated() bool IsAuthenticated() bool
} }
// ConnectionCallback is the callback format required to retrieve // Callback is the callback format required to retrieve
// new authenticated.Connection objects as they are established. // new authenticated.Connection objects as they are established.
type ConnectionCallback func(connection Connection) type Callback func(connection Connection)
// ConnectWithAuthentication is called by the client, ie the one establishing // ConnectWithAuthentication is called by the client, ie the one establishing
// connection with the server. Once a connect.Connection has been established // connection with the server. Once a connect.Connection has been established
...@@ -86,10 +86,9 @@ func ConnectWithAuthentication(recipient contact.Contact, myId *id.ID, ...@@ -86,10 +86,9 @@ func ConnectWithAuthentication(recipient contact.Contact, myId *id.ID,
// Record since we first successfully sen the message // Record since we first successfully sen the message
timeStart := netTime.Now() timeStart := netTime.Now()
authConnChan := make(chan Connection, 1)
// Determine that the message is properly sent by tracking the success // Determine that the message is properly sent by tracking the success
// of the round(s) // of the round(s)
authConnChan := make(chan Connection, 1)
roundCb := cmix.RoundEventCallback(func(allRoundsSucceeded, roundCb := cmix.RoundEventCallback(func(allRoundsSucceeded,
timedOut bool, rounds map[id.Round]cmix.RoundResult) { timedOut bool, rounds map[id.Round]cmix.RoundResult) {
if allRoundsSucceeded { if allRoundsSucceeded {
...@@ -102,14 +101,18 @@ func ConnectWithAuthentication(recipient contact.Contact, myId *id.ID, ...@@ -102,14 +101,18 @@ func ConnectWithAuthentication(recipient contact.Contact, myId *id.ID,
} }
}) })
// Find the remaining time in the timeout since we first sent the message
remainingTime := e2eParams.Timeout - netTime.Since(timeStart) remainingTime := e2eParams.Timeout - netTime.Since(timeStart)
// Track the result of the round(s) we sent the
// identity authentication message on
err = net.GetRoundResults(remainingTime, err = net.GetRoundResults(remainingTime,
roundCb, rids...) roundCb, rids...)
if err != nil { if err != nil {
return nil, errors.Errorf("could not track rounds for successful " + return nil, errors.Errorf("could not track rounds for successful " +
"identity confirmation message delivery") "identity confirmation message delivery")
} }
// Block waiting for auth to confirm it timeouts // Block waiting for confirmation of the round(s) success (or timeout
jww.DEBUG.Printf("Connection waiting for authenticated "+ jww.DEBUG.Printf("Connection waiting for authenticated "+
"connection with %s to be established...", recipient.ID.String()) "connection with %s to be established...", recipient.ID.String())
timeout := time.NewTimer(p.Timeout) timeout := time.NewTimer(p.Timeout)
...@@ -134,7 +137,7 @@ func ConnectWithAuthentication(recipient contact.Contact, myId *id.ID, ...@@ -134,7 +137,7 @@ func ConnectWithAuthentication(recipient contact.Contact, myId *id.ID,
// will handle authenticated requests and verify the client's attempt to // will handle authenticated requests and verify the client's attempt to
// authenticate themselves. An established authenticated.Connection will // authenticate themselves. An established authenticated.Connection will
// be passed via the callback. // be passed via the callback.
func StartServer(cb ConnectionCallback, func StartServer(cb Callback,
myId *id.ID, privKey *cyclic.Int, myId *id.ID, privKey *cyclic.Int,
rng *fastRNG.StreamGenerator, grp *cyclic.Group, net cmix.Client, rng *fastRNG.StreamGenerator, grp *cyclic.Group, net cmix.Client,
p connect.Params) error { p connect.Params) error {
...@@ -146,7 +149,7 @@ func StartServer(cb ConnectionCallback, ...@@ -146,7 +149,7 @@ func StartServer(cb ConnectionCallback,
// message is received and validated, an authenticated connection will // message is received and validated, an authenticated connection will
// be passed along via the callback // be passed along via the callback
connection.RegisterListener(catalog.ConnectionAuthenticationRequest, connection.RegisterListener(catalog.ConnectionAuthenticationRequest,
handleAuthConfirmation(cb, connection)) buildAuthConfirmationHandler(cb, connection))
}) })
return connect.StartServer(connCb, myId, privKey, rng, grp, return connect.StartServer(connCb, myId, privKey, rng, grp,
net, p) net, p)
......
///////////////////////////////////////////////////////////////////////////////
// Copyright © 2020 xx network SEZC //
// //
// Use of this source code is governed by a license that can be found in the //
// LICENSE file //
///////////////////////////////////////////////////////////////////////////////
package authenticated package authenticated
import ( import (
...@@ -40,7 +47,6 @@ func makeClientAuthRequest(newPartner partner.Manager, ...@@ -40,7 +47,6 @@ func makeClientAuthRequest(newPartner partner.Manager,
} }
payload, err := proto.Marshal(iar) payload, err := proto.Marshal(iar)
if err != nil { if err != nil {
return nil, errors.Errorf("failed to marshal identity request "+ return nil, errors.Errorf("failed to marshal identity request "+
"message: %+v", err) "message: %+v", err)
} }
......
...@@ -31,42 +31,40 @@ type server interface { ...@@ -31,42 +31,40 @@ type server interface {
type serverListener struct { type serverListener struct {
// connectionCallback allows an authenticated.Connection // connectionCallback allows an authenticated.Connection
// to be passed back upon establishment. // to be passed back upon establishment.
connectionCallback ConnectionCallback connectionCallback Callback
// conn used to retrieve the connection context with the partner. // conn used to retrieve the connection context with the partner.
conn connect.Connection conn connect.Connection
} }
// handleAuthConfirmation returns a serverListener object. // buildAuthConfirmationHandler returns a serverListener object.
func handleAuthConfirmation(cb ConnectionCallback, // This will handle incoming identity authentication confirmations
// via the serverListener.Hear method. A successful authenticated.Connection
// will be passed along via the serverListener.connectionCallback
func buildAuthConfirmationHandler(cb Callback,
connection connect.Connection) server { connection connect.Connection) server {
return serverListener{ return &serverListener{
connectionCallback: cb, connectionCallback: cb,
conn: connection, conn: connection,
} }
} }
// Hear handles the reception of an IdentityAuthentication by the // Hear handles the reception of an IdentityAuthentication by the
// server. // server. It will attempt to verify the identity confirmation of
// the given client.
func (a serverListener) Hear(item receive.Message) { func (a serverListener) Hear(item receive.Message) {
// Process the message data into a protobuf // Process the message data into a protobuf
iar := &IdentityAuthentication{} iar := &IdentityAuthentication{}
err := proto.Unmarshal(item.Payload, iar) err := proto.Unmarshal(item.Payload, iar)
if err != nil { if err != nil {
jww.ERROR.Printf("Unable to build connection with "+ a.handleAuthConfirmationErr(err, item.Sender)
"partner %s: %+v", item.Sender, err)
// Send a nil connection to avoid hold-ups down the line
a.connectionCallback(nil)
return return
} }
// Process the PEM encoded public key to an rsa.PublicKey object // Process the PEM encoded public key to an rsa.PublicKey object
partnerPubKey, err := rsa.LoadPublicKeyFromPem(iar.RsaPubKey) partnerPubKey, err := rsa.LoadPublicKeyFromPem(iar.RsaPubKey)
if err != nil { if err != nil {
jww.ERROR.Printf("Unable to build connection with "+ a.handleAuthConfirmationErr(err, item.Sender)
"partner %s: %+v", item.Sender, err)
// Send a nil connection to avoid hold-ups down the line
a.connectionCallback(nil)
return return
} }
...@@ -77,18 +75,12 @@ func (a serverListener) Hear(item receive.Message) { ...@@ -77,18 +75,12 @@ func (a serverListener) Hear(item receive.Message) {
// along the wire // along the wire
partnerWireId, err := xx.NewID(partnerPubKey, iar.Salt, id.User) partnerWireId, err := xx.NewID(partnerPubKey, iar.Salt, id.User)
if err != nil { if err != nil {
jww.ERROR.Printf("Unable to parse identity information with "+ a.handleAuthConfirmationErr(err, item.Sender)
"partner %s: %+v", item.Sender, err)
// Send a nil connection to avoid hold-ups down the line
a.connectionCallback(nil)
return return
} }
if !newPartner.PartnerId().Cmp(partnerWireId) { if !newPartner.PartnerId().Cmp(partnerWireId) {
jww.ERROR.Printf("Unable to verify identity information with "+ a.handleAuthConfirmationErr(err, item.Sender)
"partner %s: %+v", item.Sender, err)
// Send a nil connection to avoid hold-ups down the line
a.connectionCallback(nil)
return return
} }
...@@ -105,10 +97,8 @@ func (a serverListener) Hear(item receive.Message) { ...@@ -105,10 +97,8 @@ func (a serverListener) Hear(item receive.Message) {
// Verify the signature // Verify the signature
err = rsa.Verify(partnerPubKey, opts.Hash, nonce, iar.Signature, opts) err = rsa.Verify(partnerPubKey, opts.Hash, nonce, iar.Signature, opts)
if err != nil { if err != nil {
jww.ERROR.Printf("Unable to build connection with "+ a.handleAuthConfirmationErr(err, item.Sender)
"partner %s: %+v", item.Sender, err) return
// Send a nil connection to avoid hold-ups down the line
a.connectionCallback(nil)
} }
// If successful, pass along the established authenticated connection // If successful, pass along the established authenticated connection
...@@ -120,6 +110,20 @@ func (a serverListener) Hear(item receive.Message) { ...@@ -120,6 +110,20 @@ func (a serverListener) Hear(item receive.Message) {
a.connectionCallback(authConn) a.connectionCallback(authConn)
} }
// handleAuthConfirmationErr is a helper function which will close the connection
// between the server and the client. It will also print out the passed in error.
func (a serverListener) handleAuthConfirmationErr(err error, sender *id.ID) {
jww.ERROR.Printf("Unable to build connection with "+
"partner %s: %+v", sender, err)
// Send a nil connection to avoid hold-ups down the line
a.connectionCallback(nil)
err = a.conn.Close()
if err != nil {
jww.ERROR.Printf("Failed to close connection with partner %s: %v",
sender, err)
}
}
// Name returns the name of this listener. This is typically for // Name returns the name of this listener. This is typically for
// printing/debugging purposes. // printing/debugging purposes.
func (a serverListener) Name() string { func (a serverListener) Name() string {
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment