mirror of
https://github.com/go-i2p/sam3.git
synced 2025-07-16 13:42:12 -04:00
added logging to primary.go
-added fromPort, toPort in NewUniqueStreamSubsession
This commit is contained in:
59
primary.go
59
primary.go
@ -3,6 +3,7 @@ package sam3
|
||||
import (
|
||||
"errors"
|
||||
"fmt"
|
||||
"github.com/sirupsen/logrus"
|
||||
"math/rand"
|
||||
"net"
|
||||
"strconv"
|
||||
@ -20,6 +21,8 @@ func randport() string {
|
||||
s := rand.NewSource(time.Now().UnixNano())
|
||||
r := rand.New(s)
|
||||
p := r.Intn(55534) + 10000
|
||||
port := strconv.Itoa(p)
|
||||
log.WithField("port", port).Debug("Generated random port")
|
||||
return strconv.Itoa(p)
|
||||
}
|
||||
|
||||
@ -76,6 +79,7 @@ func (ss *PrimarySession) Keys() i2pkeys.I2PKeys {
|
||||
}
|
||||
|
||||
func (sam *PrimarySession) Dial(network, addr string) (net.Conn, error) {
|
||||
log.WithFields(logrus.Fields{"network": network, "addr": addr}).Debug("Dial() called")
|
||||
if network == "udp" || network == "udp4" || network == "udp6" {
|
||||
//return sam.DialUDPI2P(network, network+addr[0:4], addr)
|
||||
return sam.DialUDPI2P(network, network+addr[0:4], addr)
|
||||
@ -84,16 +88,19 @@ func (sam *PrimarySession) Dial(network, addr string) (net.Conn, error) {
|
||||
//return sam.DialTCPI2P(network, network+addr[0:4], addr)
|
||||
return sam.DialTCPI2P(network, network+addr[0:4], addr)
|
||||
}
|
||||
log.WithField("network", network).Error("Invalid network type")
|
||||
return nil, fmt.Errorf("Error: Must specify a valid network type")
|
||||
}
|
||||
|
||||
// DialTCP implements x/dialer
|
||||
func (sam *PrimarySession) DialTCP(network string, laddr, raddr net.Addr) (net.Conn, error) {
|
||||
log.WithFields(logrus.Fields{"network": network, "laddr": laddr, "raddr": raddr}).Debug("DialTCP() called")
|
||||
ts, ok := sam.stsess[network+raddr.String()[0:4]]
|
||||
var err error
|
||||
if !ok {
|
||||
ts, err = sam.NewUniqueStreamSubSession(network + raddr.String()[0:4])
|
||||
if err != nil {
|
||||
log.WithError(err).Error("Failed to create new unique stream sub-session")
|
||||
return nil, err
|
||||
}
|
||||
sam.stsess[network+raddr.String()[0:4]] = ts
|
||||
@ -103,11 +110,13 @@ func (sam *PrimarySession) DialTCP(network string, laddr, raddr net.Addr) (net.C
|
||||
}
|
||||
|
||||
func (sam *PrimarySession) DialTCPI2P(network string, laddr, raddr string) (net.Conn, error) {
|
||||
log.WithFields(logrus.Fields{"network": network, "laddr": laddr, "raddr": raddr}).Debug("DialTCPI2P() called")
|
||||
ts, ok := sam.stsess[network+raddr[0:4]]
|
||||
var err error
|
||||
if !ok {
|
||||
ts, err = sam.NewUniqueStreamSubSession(network + laddr)
|
||||
if err != nil {
|
||||
log.WithError(err).Error("Failed to create new unique stream sub-session")
|
||||
return nil, err
|
||||
}
|
||||
sam.stsess[network+raddr[0:4]] = ts
|
||||
@ -118,11 +127,13 @@ func (sam *PrimarySession) DialTCPI2P(network string, laddr, raddr string) (net.
|
||||
|
||||
// DialUDP implements x/dialer
|
||||
func (sam *PrimarySession) DialUDP(network string, laddr, raddr net.Addr) (net.PacketConn, error) {
|
||||
log.WithFields(logrus.Fields{"network": network, "laddr": laddr, "raddr": raddr}).Debug("DialUDP() called")
|
||||
ds, ok := sam.dgsess[network+raddr.String()[0:4]]
|
||||
var err error
|
||||
if !ok {
|
||||
ds, err = sam.NewDatagramSubSession(network+raddr.String()[0:4], 0)
|
||||
if err != nil {
|
||||
log.WithError(err).Error("Failed to create new datagram sub-session")
|
||||
return nil, err
|
||||
}
|
||||
sam.dgsess[network+raddr.String()[0:4]] = ds
|
||||
@ -132,11 +143,13 @@ func (sam *PrimarySession) DialUDP(network string, laddr, raddr net.Addr) (net.P
|
||||
}
|
||||
|
||||
func (sam *PrimarySession) DialUDPI2P(network, laddr, raddr string) (*DatagramSession, error) {
|
||||
log.WithFields(logrus.Fields{"network": network, "laddr": laddr, "raddr": raddr}).Debug("DialUDPI2P() called")
|
||||
ds, ok := sam.dgsess[network+raddr[0:4]]
|
||||
var err error
|
||||
if !ok {
|
||||
ds, err = sam.NewDatagramSubSession(network+laddr, 0)
|
||||
if err != nil {
|
||||
log.WithError(err).Error("Failed to create new datagram sub-session")
|
||||
return nil, err
|
||||
}
|
||||
sam.dgsess[network+raddr[0:4]] = ds
|
||||
@ -146,37 +159,51 @@ func (sam *PrimarySession) DialUDPI2P(network, laddr, raddr string) (*DatagramSe
|
||||
}
|
||||
|
||||
func (s *PrimarySession) Lookup(name string) (a net.Addr, err error) {
|
||||
log.WithField("name", name).Debug("Lookup() called")
|
||||
var sam *SAM
|
||||
name = strings.Split(name, ":")[0]
|
||||
sam, err = NewSAM(s.samAddr)
|
||||
if err == nil {
|
||||
log.WithField("addr", a).Debug("Lookup successful")
|
||||
defer sam.Close()
|
||||
a, err = sam.Lookup(name)
|
||||
}
|
||||
log.WithError(err).Error("Lookup failed")
|
||||
return
|
||||
}
|
||||
|
||||
func (sam *PrimarySession) Resolve(network, addr string) (net.Addr, error) {
|
||||
log.WithFields(logrus.Fields{"network": network, "addr": addr}).Debug("Resolve() called")
|
||||
return sam.Lookup(addr)
|
||||
}
|
||||
|
||||
func (sam *PrimarySession) ResolveTCPAddr(network, dest string) (net.Addr, error) {
|
||||
log.WithFields(logrus.Fields{"network": network, "dest": dest}).Debug("ResolveTCPAddr() called")
|
||||
return sam.Lookup(dest)
|
||||
}
|
||||
|
||||
func (sam *PrimarySession) ResolveUDPAddr(network, dest string) (net.Addr, error) {
|
||||
log.WithFields(logrus.Fields{"network": network, "dest": dest}).Debug("ResolveUDPAddr() called")
|
||||
return sam.Lookup(dest)
|
||||
}
|
||||
|
||||
// Creates a new PrimarySession with the I2CP- and streaminglib options as
|
||||
// specified. See the I2P documentation for a full list of options.
|
||||
func (sam *SAM) NewPrimarySession(id string, keys i2pkeys.I2PKeys, options []string) (*PrimarySession, error) {
|
||||
log.WithFields(logrus.Fields{"id": id, "options": options}).Debug("NewPrimarySession() called")
|
||||
return sam.newPrimarySession(PrimarySessionSwitch, id, keys, options)
|
||||
}
|
||||
|
||||
func (sam *SAM) newPrimarySession(primarySessionSwitch string, id string, keys i2pkeys.I2PKeys, options []string) (*PrimarySession, error) {
|
||||
log.WithFields(logrus.Fields{
|
||||
"primarySessionSwitch": primarySessionSwitch,
|
||||
"id": id,
|
||||
"options": options,
|
||||
}).Debug("newPrimarySession() called")
|
||||
|
||||
conn, err := sam.newGenericSession(primarySessionSwitch, id, keys, options, []string{})
|
||||
if err != nil {
|
||||
log.WithError(err).Error("Failed to create new generic session")
|
||||
return nil, err
|
||||
}
|
||||
ssesss := make(map[string]*StreamSession)
|
||||
@ -187,8 +214,15 @@ func (sam *SAM) newPrimarySession(primarySessionSwitch string, id string, keys i
|
||||
// Creates a new PrimarySession with the I2CP- and PRIMARYinglib options as
|
||||
// specified. See the I2P documentation for a full list of options.
|
||||
func (sam *SAM) NewPrimarySessionWithSignature(id string, keys i2pkeys.I2PKeys, options []string, sigType string) (*PrimarySession, error) {
|
||||
log.WithFields(logrus.Fields{
|
||||
"id": id,
|
||||
"options": options,
|
||||
"sigType": sigType,
|
||||
}).Debug("NewPrimarySessionWithSignature() called")
|
||||
|
||||
conn, err := sam.newGenericSessionWithSignature(PrimarySessionSwitch, id, keys, sigType, options, []string{})
|
||||
if err != nil {
|
||||
log.WithError(err).Error("Failed to create new generic session with signature")
|
||||
return nil, err
|
||||
}
|
||||
ssesss := make(map[string]*StreamSession)
|
||||
@ -202,10 +236,12 @@ func (sam *SAM) NewPrimarySessionWithSignature(id string, keys i2pkeys.I2PKeys,
|
||||
// setting extra to something else than []string{}.
|
||||
// This sam3 instance is now a session
|
||||
func (sam *PrimarySession) newGenericSubSession(style, id string, extras []string) (net.Conn, error) {
|
||||
log.WithFields(logrus.Fields{"style": style, "id": id, "extras": extras}).Debug("newGenericSubSession called")
|
||||
return sam.newGenericSubSessionWithSignature(style, id, extras)
|
||||
}
|
||||
|
||||
func (sam *PrimarySession) newGenericSubSessionWithSignature(style, id string, extras []string) (net.Conn, error) {
|
||||
log.WithFields(logrus.Fields{"style": style, "id": id, "extras": extras}).Debug("newGenericSubSessionWithSignature called")
|
||||
return sam.newGenericSubSessionWithSignatureAndPorts(style, id, "0", "0", extras)
|
||||
}
|
||||
|
||||
@ -215,6 +251,7 @@ func (sam *PrimarySession) newGenericSubSessionWithSignature(style, id string, e
|
||||
// setting extra to something else than []string{}.
|
||||
// This sam3 instance is now a session
|
||||
func (sam *PrimarySession) newGenericSubSessionWithSignatureAndPorts(style, id, from, to string, extras []string) (net.Conn, error) {
|
||||
log.WithFields(logrus.Fields{"style": style, "id": id, "from": from, "to": to, "extras": extras}).Debug("newGenericSubSessionWithSignatureAndPorts called")
|
||||
|
||||
conn := sam.conn
|
||||
fp := ""
|
||||
@ -226,13 +263,18 @@ func (sam *PrimarySession) newGenericSubSessionWithSignatureAndPorts(style, id,
|
||||
tp = " TO_PORT=" + to
|
||||
}
|
||||
scmsg := []byte("SESSION ADD STYLE=" + style + " ID=" + id + fp + tp + " " + strings.Join(extras, " ") + "\n")
|
||||
|
||||
log.WithField("message", string(scmsg)).Debug("Sending SESSION ADD message")
|
||||
|
||||
for m, i := 0, 0; m != len(scmsg); i++ {
|
||||
if i == 15 {
|
||||
conn.Close()
|
||||
log.Error("Writing to SAM failed after 15 attempts")
|
||||
return nil, errors.New("writing to SAM failed")
|
||||
}
|
||||
n, err := conn.Write(scmsg[m:])
|
||||
if err != nil {
|
||||
log.WithError(err).Error("Failed to write to SAM connection")
|
||||
conn.Close()
|
||||
return nil, err
|
||||
}
|
||||
@ -241,30 +283,38 @@ func (sam *PrimarySession) newGenericSubSessionWithSignatureAndPorts(style, id,
|
||||
buf := make([]byte, 4096)
|
||||
n, err := conn.Read(buf)
|
||||
if err != nil {
|
||||
log.WithError(err).Error("Failed to read from SAM connection")
|
||||
conn.Close()
|
||||
return nil, err
|
||||
}
|
||||
text := string(buf[:n])
|
||||
log.WithField("response", text).Debug("Received response from SAM")
|
||||
//log.Println("SAM:", text)
|
||||
if strings.HasPrefix(text, session_ADDOK) {
|
||||
//if sam.keys.String() != text[len(session_ADDOK):len(text)-1] {
|
||||
//conn.Close()
|
||||
//return nil, errors.New("SAMv3 created a tunnel with keys other than the ones we asked it for")
|
||||
//}
|
||||
log.Debug("Session added successfully")
|
||||
return conn, nil //&StreamSession{id, conn, keys, nil, sync.RWMutex{}, nil}, nil
|
||||
} else if text == session_DUPLICATE_ID {
|
||||
log.Error("Duplicate tunnel name")
|
||||
conn.Close()
|
||||
return nil, errors.New("Duplicate tunnel name")
|
||||
} else if text == session_DUPLICATE_DEST {
|
||||
log.Error("Duplicate destination")
|
||||
conn.Close()
|
||||
return nil, errors.New("Duplicate destination")
|
||||
} else if text == session_INVALID_KEY {
|
||||
log.Error("Invalid key - Primary Session")
|
||||
conn.Close()
|
||||
return nil, errors.New("Invalid key - Primary Session")
|
||||
} else if strings.HasPrefix(text, session_I2P_ERROR) {
|
||||
log.WithField("error", text[len(session_I2P_ERROR):]).Error("I2P error")
|
||||
conn.Close()
|
||||
return nil, errors.New("I2P error " + text[len(session_I2P_ERROR):])
|
||||
} else {
|
||||
log.WithField("reply", text).Error("Unable to parse SAMv3 reply")
|
||||
conn.Close()
|
||||
return nil, errors.New("Unable to parse SAMv3 reply: " + text)
|
||||
}
|
||||
@ -273,8 +323,10 @@ func (sam *PrimarySession) newGenericSubSessionWithSignatureAndPorts(style, id,
|
||||
// Creates a new StreamSession with the I2CP- and streaminglib options as
|
||||
// specified. See the I2P documentation for a full list of options.
|
||||
func (sam *PrimarySession) NewStreamSubSession(id string) (*StreamSession, error) {
|
||||
log.WithField("id", id).Debug("NewStreamSubSession called")
|
||||
conn, err := sam.newGenericSubSession("STREAM", id, []string{})
|
||||
if err != nil {
|
||||
log.WithError(err).Error("Failed to create new generic sub-session")
|
||||
return nil, err
|
||||
}
|
||||
return &StreamSession{sam.Config.I2PConfig.Sam(), id, conn, sam.keys, time.Duration(600 * time.Second), time.Now(), Sig_NONE, "0", "0"}, nil
|
||||
@ -283,11 +335,16 @@ func (sam *PrimarySession) NewStreamSubSession(id string) (*StreamSession, error
|
||||
// Creates a new StreamSession with the I2CP- and streaminglib options as
|
||||
// specified. See the I2P documentation for a full list of options.
|
||||
func (sam *PrimarySession) NewUniqueStreamSubSession(id string) (*StreamSession, error) {
|
||||
log.WithField("id", id).Debug("NewUniqueStreamSubSession called")
|
||||
conn, err := sam.newGenericSubSession("STREAM", id, []string{})
|
||||
if err != nil {
|
||||
log.WithError(err).Error("Failed to create new generic sub-session")
|
||||
return nil, err
|
||||
}
|
||||
return &StreamSession{sam.Config.I2PConfig.Sam(), id, conn, sam.keys, time.Duration(600 * time.Second), time.Now(), Sig_NONE, randport(), randport()}, nil
|
||||
fromPort, toPort := randport(), randport()
|
||||
log.WithFields(logrus.Fields{"fromPort": fromPort, "toPort": toPort}).Debug("Generated random ports")
|
||||
//return &StreamSession{sam.Config.I2PConfig.Sam(), id, conn, sam.keys, time.Duration(600 * time.Second), time.Now(), Sig_NONE, randport(), randport()}, nil
|
||||
return &StreamSession{sam.Config.I2PConfig.Sam(), id, conn, sam.keys, time.Duration(600 * time.Second), time.Now(), Sig_NONE, fromPort, toPort}, nil
|
||||
}
|
||||
|
||||
// Creates a new StreamSession with the I2CP- and streaminglib options as
|
||||
|
Reference in New Issue
Block a user