mirror of
https://github.com/cwinfo/yggdrasil-go.git
synced 2024-11-26 00:11:36 +00:00
add version metadata to key exchange at the start of connections
This commit is contained in:
parent
f5c850f098
commit
8733099516
@ -10,6 +10,10 @@ package yggdrasil
|
|||||||
// Could be used to DoS (connect, give someone else's keys, spew garbage)
|
// Could be used to DoS (connect, give someone else's keys, spew garbage)
|
||||||
// I guess the "peer" part should watch for link packets, disconnect?
|
// I guess the "peer" part should watch for link packets, disconnect?
|
||||||
|
|
||||||
|
// TCP connections start with a metadata exchange.
|
||||||
|
// It involves exchanging version numbers and crypto keys
|
||||||
|
// See version.go for version metadata format
|
||||||
|
|
||||||
import "net"
|
import "net"
|
||||||
import "time"
|
import "time"
|
||||||
import "errors"
|
import "errors"
|
||||||
@ -142,29 +146,43 @@ func (iface *tcpInterface) handler(sock net.Conn, incoming bool) {
|
|||||||
defer sock.Close()
|
defer sock.Close()
|
||||||
// Get our keys
|
// Get our keys
|
||||||
myLinkPub, myLinkPriv := newBoxKeys() // ephemeral link keys
|
myLinkPub, myLinkPriv := newBoxKeys() // ephemeral link keys
|
||||||
keys := []byte{}
|
meta := version_getBaseMetadata()
|
||||||
keys = append(keys, tcp_key[:]...)
|
meta.box = iface.core.boxPub
|
||||||
keys = append(keys, iface.core.boxPub[:]...)
|
meta.sig = iface.core.sigPub
|
||||||
keys = append(keys, iface.core.sigPub[:]...)
|
meta.link = *myLinkPub
|
||||||
keys = append(keys, myLinkPub[:]...)
|
metaBytes := meta.encode()
|
||||||
_, err := sock.Write(keys)
|
_, err := sock.Write(metaBytes)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
timeout := time.Now().Add(6 * time.Second)
|
timeout := time.Now().Add(6 * time.Second)
|
||||||
sock.SetReadDeadline(timeout)
|
sock.SetReadDeadline(timeout)
|
||||||
n, err := sock.Read(keys)
|
n, err := sock.Read(metaBytes)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
if n < len(keys) { /*panic("Partial key packet?") ;*/
|
if n != version_getMetaLength() {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
info := tcpInfo{} // used as a map key, so don't include ephemeral link eys
|
meta = version_metadata{} // Reset to zero value
|
||||||
var theirLinkPub boxPubKey
|
if !meta.decode(metaBytes) {
|
||||||
if !tcp_chop_keys(&info.box, &info.sig, &theirLinkPub, &keys) { /*panic("Invalid key packet?") ;*/
|
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
if !meta.check() {
|
||||||
|
base := version_getBaseMetadata()
|
||||||
|
if meta.meta == base.meta {
|
||||||
|
if meta.ver > base.ver {
|
||||||
|
iface.core.log.Println("Failed to connect to node:", sock.RemoteAddr().String(), "version:", meta.ver)
|
||||||
|
} else if meta.ver == base.ver && meta.minorVer > base.minorVer {
|
||||||
|
iface.core.log.Println("Failed to connect to node:", sock.RemoteAddr().String(), "version:", fmt.Sprintf("%d.%d", meta.ver, meta.minorVer))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return
|
||||||
|
}
|
||||||
|
info := tcpInfo{ // used as a map key, so don't include ephemeral link key
|
||||||
|
box: meta.box,
|
||||||
|
sig: meta.sig,
|
||||||
|
}
|
||||||
// Quit the parent call if this is a connection to ourself
|
// Quit the parent call if this is a connection to ourself
|
||||||
equiv := func(k1, k2 []byte) bool {
|
equiv := func(k1, k2 []byte) bool {
|
||||||
for idx := range k1 {
|
for idx := range k1 {
|
||||||
@ -210,7 +228,7 @@ func (iface *tcpInterface) handler(sock net.Conn, incoming bool) {
|
|||||||
}()
|
}()
|
||||||
// Note that multiple connections to the same node are allowed
|
// Note that multiple connections to the same node are allowed
|
||||||
// E.g. over different interfaces
|
// E.g. over different interfaces
|
||||||
p := iface.core.peers.newPeer(&info.box, &info.sig, getSharedKey(myLinkPriv, &theirLinkPub))
|
p := iface.core.peers.newPeer(&info.box, &info.sig, getSharedKey(myLinkPriv, &meta.link))
|
||||||
p.linkOut = make(chan []byte, 1)
|
p.linkOut = make(chan []byte, 1)
|
||||||
in := func(bs []byte) {
|
in := func(bs []byte) {
|
||||||
p.handlePacket(bs)
|
p.handlePacket(bs)
|
||||||
|
Loading…
Reference in New Issue
Block a user