3
0
mirror of https://github.com/ergochat/ergo.git synced 2024-11-10 22:19:31 +01:00

certfp: Add certfp retrieval from client

This commit is contained in:
Daniel Oaks 2016-09-05 13:53:39 +10:00
parent d3d88cfa0c
commit 49034cb20e
3 changed files with 34 additions and 0 deletions

View File

@ -51,6 +51,7 @@ type Client struct {
socket *Socket socket *Socket
username Name username Name
isDestroyed bool isDestroyed bool
certfp string
} }
func NewClient(server *Server, conn net.Conn, isTLS bool) *Client { func NewClient(server *Server, conn net.Conn, isTLS bool) *Client {
@ -201,6 +202,11 @@ func (client *Client) Register() {
if client.registered { if client.registered {
return return
} }
if client.flags[TLS] {
// error is not useful to us here anyways, so we can ignore it
client.certfp, _ = client.socket.CertFP()
//TODO(dan): login based on certfp
}
client.registered = true client.registered = true
client.Touch() client.Touch()
} }

View File

@ -261,6 +261,7 @@ func (s *Server) listen(addr string, tlsMap map[Name]*tls.Config) {
tlsString := "plaintext" tlsString := "plaintext"
if listenTLS { if listenTLS {
config.ClientAuth = tls.RequestClientCert
listener = tls.NewListener(listener, config) listener = tls.NewListener(listener, config)
tlsString = "TLS" tlsString = "TLS"
} }

View File

@ -6,11 +6,20 @@ package irc
import ( import (
"bufio" "bufio"
"crypto/sha256"
"crypto/tls"
"encoding/hex"
"errors"
"io" "io"
"net" "net"
"strings" "strings"
) )
var (
errNotTls = errors.New("Not a TLS connection")
errNoPeerCerts = errors.New("Client did not provide a certificate")
)
// Socket represents an IRC socket. // Socket represents an IRC socket.
type Socket struct { type Socket struct {
Closed bool Closed bool
@ -35,6 +44,24 @@ func (socket *Socket) Close() {
socket.conn.Close() socket.conn.Close()
} }
// CertFP returns the fingerprint of the certificate provided by the client.
func (socket *Socket) CertFP() (string, error) {
var tlsConn, isTLS = socket.conn.(*tls.Conn)
if !isTLS {
return "", errNotTls
}
peerCerts := tlsConn.ConnectionState().PeerCertificates
if len(peerCerts) < 1 {
return "", errNoPeerCerts
}
rawCert := sha256.Sum256(peerCerts[0].Raw)
fingerprint := hex.EncodeToString(rawCert[:])
return fingerprint, nil
}
// Read returns a single IRC line from a Socket. // Read returns a single IRC line from a Socket.
func (socket *Socket) Read() (string, error) { func (socket *Socket) Read() (string, error) {
if socket.Closed { if socket.Closed {