package peer import ( "log" "net" "net/netip" "sync/atomic" "vppn/m" ) type Router struct { conf m.PeerConfig // Routes used by the peer. conns [MAX_IP]*connHandler routes [MAX_IP]*atomic.Pointer[route] addrs [MAX_IP]*atomic.Pointer[netip.AddrPort] mediatorIP *atomic.Pointer[byte] } func NewRouter(conf m.PeerConfig, conn *net.UDPConn) *Router { r := &Router{ conf: conf, mediatorIP: &atomic.Pointer[byte]{}, } for i := range r.routes { r.routes[i] = &atomic.Pointer[route]{} } _, isServer := netip.AddrFromSlice(conf.PublicIP) sender := newConnSender(conn, conf.PeerIP, STREAM_ROUTING) for i := range r.conns { if byte(i) != conf.PeerIP { r.conns[i] = newConnHandler( isServer, byte(i), r.routes, conf.EncPrivKey, newSafeConnSender(sender)) } } go r.pollHub() if !isServer { go r.manageMediator() } return r } // ---------------------------------------------------------------------------- // Peer Methods // ---------------------------------------------------------------------------- func (rm *Router) GetRoute(ip byte) *route { return rm.routes[ip].Load() } func (rm *Router) GetMediator() *route { if ip := rm.mediatorIP.Load(); ip != nil { return rm.GetRoute(*ip) } return nil } func (r *Router) HandlePacket(src netip.AddrPort, nonce Nonce, data []byte) { if nonce.SourceIP == r.conf.PeerIP { log.Printf("Packet to self...") return } packet := unmarshalPacket(nonce, data) if packet == nil { return } r.conns[nonce.SourceIP].HandlePacket(wrapper{ Packet: packet, Nonce: nonce, SrcAddr: src, }) }