2016-02-07 13:48:01 -05:00
|
|
|
package transport
|
|
|
|
|
|
|
|
import (
|
2022-07-11 23:41:58 -04:00
|
|
|
"github.com/go-i2p/go-i2p/lib/common/router_info"
|
2024-11-21 17:16:48 -05:00
|
|
|
"github.com/go-i2p/logger"
|
2016-02-07 13:48:01 -05:00
|
|
|
)
|
|
|
|
|
2024-10-23 00:06:06 -04:00
|
|
|
var log = logger.GetGoI2PLogger()
|
2024-10-19 11:18:20 -04:00
|
|
|
|
2016-02-07 13:48:01 -05:00
|
|
|
// muxes multiple transports into 1 Transport
|
|
|
|
// implements transport.Transport
|
|
|
|
type TransportMuxer struct {
|
|
|
|
// the underlying transports we are using in order of most prominant to least
|
|
|
|
trans []Transport
|
|
|
|
}
|
|
|
|
|
|
|
|
// mux a bunch of transports together
|
|
|
|
func Mux(t ...Transport) (tmux *TransportMuxer) {
|
2024-10-19 11:18:20 -04:00
|
|
|
log.WithField("transport_count", len(t)).Debug("Creating new TransportMuxer")
|
2016-02-07 13:48:01 -05:00
|
|
|
tmux = new(TransportMuxer)
|
|
|
|
tmux.trans = append(tmux.trans, t...)
|
2024-10-19 11:18:20 -04:00
|
|
|
log.Debug("TransportMuxer created successfully")
|
2016-02-07 13:48:01 -05:00
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
// set the identity for every transport
|
2024-12-21 22:13:03 -05:00
|
|
|
func (tmux *TransportMuxer) SetIdentity(ident router_info.RouterInfo) (err error) {
|
2024-10-19 11:18:20 -04:00
|
|
|
log.WithField("identity", ident).Debug("TransportMuxer: Setting identity for all transports")
|
|
|
|
for i, t := range tmux.trans {
|
2016-02-07 13:48:01 -05:00
|
|
|
err = t.SetIdentity(ident)
|
|
|
|
if err != nil {
|
2024-10-19 11:18:20 -04:00
|
|
|
log.WithError(err).WithField("transport_index", i).Error("TransportMuxer: Failed to set identity for transport")
|
2016-02-07 13:48:01 -05:00
|
|
|
// an error happened let's return and complain
|
|
|
|
return
|
|
|
|
}
|
2024-10-19 11:18:20 -04:00
|
|
|
log.WithField("transport_index", i).Debug("TransportMuxer: Identity set successfully for transport")
|
2016-02-07 13:48:01 -05:00
|
|
|
}
|
2024-10-19 11:18:20 -04:00
|
|
|
log.Debug("TransportMuxer: Identity set successfully for all transports")
|
2016-02-07 13:48:01 -05:00
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
// close every transport that this transport muxer has
|
|
|
|
func (tmux *TransportMuxer) Close() (err error) {
|
2024-10-19 11:18:20 -04:00
|
|
|
log.Debug("TransportMuxer: Closing all transports")
|
|
|
|
for i, t := range tmux.trans {
|
2016-02-07 13:48:01 -05:00
|
|
|
err = t.Close()
|
|
|
|
if t != nil {
|
|
|
|
// TODO: handle error (?)
|
2024-10-19 11:18:20 -04:00
|
|
|
log.WithError(err).WithField("transport_index", i).Warn("TransportMuxer: Error closing transport")
|
|
|
|
} else {
|
|
|
|
log.WithField("transport_index", i).Debug("TransportMuxer: Transport closed successfully")
|
2016-02-07 13:48:01 -05:00
|
|
|
}
|
|
|
|
}
|
2024-10-19 11:18:20 -04:00
|
|
|
log.Debug("TransportMuxer: All transports closed")
|
2016-02-07 13:48:01 -05:00
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
// the name of this transport with the names of all the ones that we mux
|
|
|
|
func (tmux *TransportMuxer) Name() string {
|
2024-10-19 11:18:20 -04:00
|
|
|
log.Debug("TransportMuxer: Generating muxed transport name")
|
2016-02-07 13:48:01 -05:00
|
|
|
name := "Muxed Transport: "
|
|
|
|
for _, t := range tmux.trans {
|
|
|
|
name += t.Name() + ", "
|
|
|
|
}
|
2024-10-22 17:37:17 -04:00
|
|
|
// return name[len(name)-3:]
|
2024-10-19 11:18:20 -04:00
|
|
|
_name := name[len(name)-3:]
|
|
|
|
log.WithField("name", _name).Debug("TransportMuxer: Muxed transport name generated")
|
|
|
|
return _name
|
2016-02-07 13:48:01 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
// get a transport session given a router info
|
|
|
|
// return session and nil if successful
|
|
|
|
// return nil and ErrNoTransportAvailable if we failed to get a session
|
2022-07-11 23:41:58 -04:00
|
|
|
func (tmux *TransportMuxer) GetSession(routerInfo router_info.RouterInfo) (s TransportSession, err error) {
|
2024-10-19 11:18:20 -04:00
|
|
|
log.WithField("router_info", routerInfo.String()).Debug("TransportMuxer: Attempting to get session")
|
|
|
|
for i, t := range tmux.trans {
|
2016-02-07 13:48:01 -05:00
|
|
|
// pick the first one that is compatable
|
2024-10-05 10:15:31 -04:00
|
|
|
if t.Compatible(routerInfo) {
|
2024-10-19 11:18:20 -04:00
|
|
|
log.WithField("transport_index", i).Debug("TransportMuxer: Found compatible transport, attempting to get session")
|
2016-02-07 13:48:01 -05:00
|
|
|
// try to get a session
|
|
|
|
s, err = t.GetSession(routerInfo)
|
|
|
|
if err != nil {
|
2024-10-19 11:18:20 -04:00
|
|
|
log.WithError(err).WithField("transport_index", i).Warn("TransportMuxer: Failed to get session from compatible transport")
|
2016-02-07 13:48:01 -05:00
|
|
|
// we could not get a session
|
|
|
|
// try the next transport
|
|
|
|
continue
|
|
|
|
}
|
|
|
|
// we got a session
|
2024-10-30 23:29:46 -04:00
|
|
|
log.WithField("transport_index", i).Debug("TransportMuxer: Successfully got session from transport")
|
2016-02-07 13:48:01 -05:00
|
|
|
return
|
|
|
|
}
|
|
|
|
}
|
2024-10-19 11:18:20 -04:00
|
|
|
log.Error("TransportMuxer: Failed to get session, no compatible transport available")
|
2016-02-07 13:48:01 -05:00
|
|
|
// we failed to get a session for this routerInfo
|
|
|
|
err = ErrNoTransportAvailable
|
|
|
|
return
|
|
|
|
}
|
|
|
|
|
|
|
|
// is there a transport that we mux that is compatable with this router info?
|
2024-10-05 10:15:31 -04:00
|
|
|
func (tmux *TransportMuxer) Compatible(routerInfo router_info.RouterInfo) (compat bool) {
|
2024-10-19 11:18:20 -04:00
|
|
|
log.WithField("router_info", routerInfo.String()).Debug("TransportMuxer: Checking compatibility")
|
|
|
|
for i, t := range tmux.trans {
|
2024-10-05 10:15:31 -04:00
|
|
|
if t.Compatible(routerInfo) {
|
2024-10-19 11:18:20 -04:00
|
|
|
log.WithField("transport_index", i).Debug("TransportMuxer: Found compatible transport")
|
2016-02-07 13:48:01 -05:00
|
|
|
compat = true
|
|
|
|
return
|
|
|
|
}
|
|
|
|
}
|
2024-10-19 11:18:20 -04:00
|
|
|
log.Debug("TransportMuxer: No compatible transport found")
|
2016-02-07 13:48:01 -05:00
|
|
|
return
|
|
|
|
}
|