github.com/jlmucb/cloudproxy@v0.0.0-20170830161738-b5aa0b619bc4/go/apps/mixnet/listener.go (about)

     1  // Copyright (c) 2016, Google Inc. All rights reserved.
     2  //
     3  // Licensed under the Apache License, Version 2.0 (the "License");
     4  // you may not use this file except in compliance with the License.
     5  // You may obtain a copy of the License at
     6  //
     7  //     http://www.apache.org/licenses/LICENSE-2.0
     8  //
     9  // Unless required by applicable law or agreed to in writing, software
    10  // distributed under the License is distributed on an "AS IS" BASIS,
    11  // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    12  // See the License for the specific language governing permissions and
    13  // limitations under the License.
    14  
    15  package mixnet
    16  
    17  import (
    18  	"crypto/tls"
    19  	"net"
    20  
    21  	"github.com/jlmucb/cloudproxy/go/tao"
    22  	"github.com/jlmucb/cloudproxy/go/util"
    23  )
    24  
    25  type mixnetListener struct {
    26  	net.Listener
    27  	guard      tao.Guard
    28  	verifier   *tao.Verifier
    29  	delegation *tao.Attestation
    30  }
    31  
    32  // Listen listens on a TLS connection with RequestClientCert.
    33  func Listen(network, laddr string, config *tls.Config, g tao.Guard, v *tao.Verifier, del *tao.Attestation) (net.Listener, error) {
    34  	config.ClientAuth = tls.RequestClientCert
    35  	inner, err := tls.Listen(network, laddr, config)
    36  	if err != nil {
    37  		return nil, err
    38  	}
    39  
    40  	return &mixnetListener{inner, g, v, del}, nil
    41  }
    42  
    43  // Accept listens for a TLS connection. It performs a handshake, then it checks
    44  // for certs. If certs are not provided, we assume the connection came from a
    45  // proxy. Otherwise, it came from a router, and Accept checks the cert.
    46  func (l *mixnetListener) Accept() (net.Conn, error) {
    47  	c, err := l.Listener.Accept()
    48  	if err != nil {
    49  		return nil, err
    50  	}
    51  
    52  	// Tao handshake Protocol:
    53  	// 0. TLS handshake explicit handshake (so we can check cert first)
    54  	// If cert is presented, there are two optional steps:
    55  	// 1a. Client -> Server: Tao delegation for X.509 certificate.
    56  	// 2a. Server: checks for a Tao-authorized program.
    57  	// Then send back your certs:
    58  	// 3. Server -> Client: Tao delegation for X.509 certificate.
    59  	// 4. Client: checks for a Tao-authorized program.
    60  	err = c.(*tls.Conn).Handshake()
    61  	if err != nil {
    62  		return nil, err
    63  	}
    64  
    65  	ms := util.NewMessageStream(c)
    66  	var a tao.Attestation
    67  	if len(c.(*tls.Conn).ConnectionState().PeerCertificates) > 0 {
    68  		if err := ms.ReadMessage(&a); err != nil {
    69  			c.Close()
    70  			return nil, err
    71  		}
    72  
    73  		if err := tao.AddEndorsements(l.guard, &a, l.verifier); err != nil {
    74  			return nil, err
    75  		}
    76  
    77  		peerCert := c.(*tls.Conn).ConnectionState().PeerCertificates[0]
    78  		if err := tao.ValidatePeerAttestation(&a, peerCert, l.guard); err != nil {
    79  			c.Close()
    80  			return nil, err
    81  		}
    82  	}
    83  	if _, err := ms.WriteMessage(l.delegation); err != nil {
    84  		c.Close()
    85  		return nil, err
    86  	}
    87  
    88  	return c, nil
    89  }