123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104 |
- package tunnelstate
- import (
- "net"
- "sync"
- "github.com/rs/zerolog"
- "github.com/cloudflare/cloudflared/connection"
- )
- type ConnTracker struct {
- mutex sync.RWMutex
- // int is the connection Index
- connectionInfo map[uint8]ConnectionInfo
- log *zerolog.Logger
- }
- type ConnectionInfo struct {
- IsConnected bool `json:"isConnected,omitempty"`
- Protocol connection.Protocol `json:"protocol,omitempty"`
- EdgeAddress net.IP `json:"edgeAddress,omitempty"`
- }
- // Convinience struct to extend the connection with its index.
- type IndexedConnectionInfo struct {
- ConnectionInfo
- Index uint8 `json:"index,omitempty"`
- }
- func NewConnTracker(
- log *zerolog.Logger,
- ) *ConnTracker {
- return &ConnTracker{
- connectionInfo: make(map[uint8]ConnectionInfo, 0),
- log: log,
- }
- }
- func (ct *ConnTracker) OnTunnelEvent(c connection.Event) {
- switch c.EventType {
- case connection.Connected:
- ct.mutex.Lock()
- ci := ConnectionInfo{
- IsConnected: true,
- Protocol: c.Protocol,
- EdgeAddress: c.EdgeAddress,
- }
- ct.connectionInfo[c.Index] = ci
- ct.mutex.Unlock()
- case connection.Disconnected, connection.Reconnecting, connection.RegisteringTunnel, connection.Unregistering:
- ct.mutex.Lock()
- ci := ct.connectionInfo[c.Index]
- ci.IsConnected = false
- ct.connectionInfo[c.Index] = ci
- ct.mutex.Unlock()
- default:
- ct.log.Error().Msgf("Unknown connection event case %v", c)
- }
- }
- func (ct *ConnTracker) CountActiveConns() uint {
- ct.mutex.RLock()
- defer ct.mutex.RUnlock()
- active := uint(0)
- for _, ci := range ct.connectionInfo {
- if ci.IsConnected {
- active++
- }
- }
- return active
- }
- // HasConnectedWith checks if we've ever had a successful connection to the edge
- // with said protocol.
- func (ct *ConnTracker) HasConnectedWith(protocol connection.Protocol) bool {
- ct.mutex.RLock()
- defer ct.mutex.RUnlock()
- for _, ci := range ct.connectionInfo {
- if ci.Protocol == protocol {
- return true
- }
- }
- return false
- }
- // Returns the connection information iff it is connected this
- // also leverages the [IndexedConnectionInfo] to also provide the connection index
- func (ct *ConnTracker) GetActiveConnections() []IndexedConnectionInfo {
- ct.mutex.RLock()
- defer ct.mutex.RUnlock()
- connections := make([]IndexedConnectionInfo, 0)
- for key, value := range ct.connectionInfo {
- if value.IsConnected {
- info := IndexedConnectionInfo{value, key}
- connections = append(connections, info)
- }
- }
- return connections
- }
|