diff options
author | IWASE Yusuke <iwase.yusuke0@gmail.com> | 2017-07-12 11:54:15 +0900 |
---|---|---|
committer | IWASE Yusuke <iwase.yusuke0@gmail.com> | 2017-07-18 15:11:05 +0900 |
commit | c3d98dac4df7d55fc6aceb4558707f252bbbd765 (patch) | |
tree | 795c27dca84473172484c237209f67e60510b63b | |
parent | 178e65f8f113da82f8dfcc56b5fa7682da1bd932 (diff) |
server: Set incoming TTL before accepting connection
Signed-off-by: IWASE Yusuke <iwase.yusuke0@gmail.com>
-rw-r--r-- | server/server.go | 12 | ||||
-rw-r--r-- | server/sockopt.go | 4 | ||||
-rw-r--r-- | server/sockopt_bsd.go | 16 | ||||
-rw-r--r-- | server/sockopt_linux.go | 16 | ||||
-rw-r--r-- | server/sockopt_openbsd.go | 16 | ||||
-rw-r--r-- | server/util.go | 25 |
6 files changed, 70 insertions, 19 deletions
diff --git a/server/server.go b/server/server.go index 61502ced..f5e00b5f 100644 --- a/server/server.go +++ b/server/server.go @@ -24,10 +24,11 @@ import ( "time" "github.com/eapache/channels" + log "github.com/sirupsen/logrus" + "github.com/osrg/gobgp/config" "github.com/osrg/gobgp/packet/bgp" "github.com/osrg/gobgp/table" - log "github.com/sirupsen/logrus" ) type TCPListener struct { @@ -65,6 +66,15 @@ func NewTCPListener(address string, port uint32, ch chan *net.TCPConn) (*TCPList if err != nil { return nil, err } + // Note: Set TTL=255 for incoming connection listener in order to accept + // connection in case for the neighbor has TTL Security settings. + if err := SetListenTcpTTLSockopt(l, 255); err != nil { + log.WithFields(log.Fields{ + "Topic": "Peer", + "Key": addr, + }).Warnf("cannot set TTL(=%d) for TCPLisnter: %s", 255, err) + } + closeCh := make(chan struct{}) go func() error { for { diff --git a/server/sockopt.go b/server/sockopt.go index e053bef0..4f42e59c 100644 --- a/server/sockopt.go +++ b/server/sockopt.go @@ -27,6 +27,10 @@ func SetTcpMD5SigSockopt(l *net.TCPListener, address string, key string) error { return fmt.Errorf("setting md5 is not supported") } +func SetListenTcpTTLSockopt(l *net.TCPListener, ttl int) error { + return fmt.Errorf("setting ttl is not supported") +} + func SetTcpTTLSockopt(conn *net.TCPConn, ttl int) error { return fmt.Errorf("setting ttl is not supported") } diff --git a/server/sockopt_bsd.go b/server/sockopt_bsd.go index 20644775..108c1458 100644 --- a/server/sockopt_bsd.go +++ b/server/sockopt_bsd.go @@ -36,16 +36,11 @@ func setsockoptTcpMD5Sig(fd int, address string, key string) error { } func SetTcpMD5SigSockopt(l *net.TCPListener, address string, key string) error { - fi, err := l.File() + fi, _, err := extractFileAndFamilyFromTCPListener(l) defer fi.Close() if err != nil { return err } - fl, err := net.FileListener(fi) - defer fl.Close() - if err != nil { - return err - } return setsockoptTcpMD5Sig(int(fi.Fd()), address, key) } @@ -59,6 +54,15 @@ func setsockoptIpTtl(fd int, family int, value int) error { return os.NewSyscallError("setsockopt", syscall.SetsockoptInt(fd, level, name, value)) } +func SetListenTcpTTLSockopt(l *net.TCPListener, ttl int) error { + fi, family, err := extractFileAndFamilyFromTCPListener(l) + defer fi.Close() + if err != nil { + return err + } + return setsockoptIpTtl(int(fi.Fd()), family, ttl) +} + func SetTcpTTLSockopt(conn *net.TCPConn, ttl int) error { fi, family, err := extractFileAndFamilyFromTCPConn(conn) defer fi.Close() diff --git a/server/sockopt_linux.go b/server/sockopt_linux.go index c251f8fd..3c347581 100644 --- a/server/sockopt_linux.go +++ b/server/sockopt_linux.go @@ -65,16 +65,11 @@ func setsockoptTcpMD5Sig(fd int, address string, key string) error { } func SetTcpMD5SigSockopt(l *net.TCPListener, address string, key string) error { - fi, err := l.File() + fi, _, err := extractFileAndFamilyFromTCPListener(l) defer fi.Close() if err != nil { return err } - fl, err := net.FileListener(fi) - defer fl.Close() - if err != nil { - return err - } return setsockoptTcpMD5Sig(int(fi.Fd()), address, key) } @@ -88,6 +83,15 @@ func setsockoptIpTtl(fd int, family int, value int) error { return os.NewSyscallError("setsockopt", syscall.SetsockoptInt(fd, level, name, value)) } +func SetListenTcpTTLSockopt(l *net.TCPListener, ttl int) error { + fi, family, err := extractFileAndFamilyFromTCPListener(l) + defer fi.Close() + if err != nil { + return err + } + return setsockoptIpTtl(int(fi.Fd()), family, ttl) +} + func SetTcpTTLSockopt(conn *net.TCPConn, ttl int) error { fi, family, err := extractFileAndFamilyFromTCPConn(conn) defer fi.Close() diff --git a/server/sockopt_openbsd.go b/server/sockopt_openbsd.go index 1adbaf94..5ce1b7ef 100644 --- a/server/sockopt_openbsd.go +++ b/server/sockopt_openbsd.go @@ -363,16 +363,11 @@ func setsockoptTcpMD5Sig(fd int, address string, key string) error { } func SetTcpMD5SigSockopt(l *net.TCPListener, address string, key string) error { - fi, err := l.File() + fi, _, err := extractFileAndFamilyFromTCPListener(l) defer fi.Close() if err != nil { return err } - fl, err := net.FileListener(fi) - defer fl.Close() - if err != nil { - return err - } return setsockoptTcpMD5Sig(int(fi.Fd()), address, key) } @@ -386,6 +381,15 @@ func setsockoptIpTtl(fd int, family int, value int) error { return os.NewSyscallError("setsockopt", syscall.SetsockoptInt(fd, level, name, value)) } +func SetListenTcpTTLSockopt(l *net.TCPListener, ttl int) error { + fi, family, err := extractFileAndFamilyFromTCPListener(l) + defer fi.Close() + if err != nil { + return err + } + return setsockoptIpTtl(int(fi.Fd()), family, ttl) +} + func SetTcpTTLSockopt(conn *net.TCPConn, ttl int) error { fi, family, err := extractFileAndFamilyFromTCPConn(conn) defer fi.Close() diff --git a/server/util.go b/server/util.go index 92f73504..b122fbdb 100644 --- a/server/util.go +++ b/server/util.go @@ -66,6 +66,31 @@ func decodeAdministrativeCommunication(data []byte) (string, []byte) { return string(data[1 : communicationLen+1]), data[communicationLen+1:] } +func extractFileAndFamilyFromTCPListener(l *net.TCPListener) (*os.File, int, error) { + // Note #1: TCPListener.File() has the unexpected side-effect of putting + // the original socket into blocking mode. See Note #2. + fi, err := l.File() + if err != nil { + return nil, 0, err + } + + // Note #2: Call net.FileListener() to put the original socket back into + // non-blocking mode. + fl, err := net.FileListener(fi) + if err != nil { + fi.Close() + return nil, 0, err + } + fl.Close() + + family := syscall.AF_INET + if strings.Contains(l.Addr().String(), "[") { + family = syscall.AF_INET6 + } + + return fi, family, nil +} + func extractFileAndFamilyFromTCPConn(conn *net.TCPConn) (*os.File, int, error) { // Note #1: TCPConn.File() has the unexpected side-effect of putting // the original socket into blocking mode. See Note #2. |