mirror of
https://github.com/PeernetOfficial/core.git
synced 2026-07-17 02:47:51 +01:00
Detect network changes, initial code. Actions to be developed. #2
This commit is contained in:
@@ -152,6 +152,9 @@ func bootstrap() {
|
||||
|
||||
func autoMulticastBroadcast() {
|
||||
sendMulticastBroadcast := func() {
|
||||
networksMutex.RLock()
|
||||
defer networksMutex.RUnlock()
|
||||
|
||||
for _, network := range networks6 {
|
||||
if err := network.MulticastIPv6Send(); err != nil {
|
||||
log.Printf("bootstrap error multicast from network address '%s': %v", network.address.IP.String(), err.Error())
|
||||
|
||||
@@ -70,6 +70,11 @@ func (peer *PeerInfo) cmdResponse(msg *packet2) {
|
||||
|
||||
// cmdPing handles an incoming ping message
|
||||
func (peer *PeerInfo) cmdPing(msg *packet2) {
|
||||
if peer == nil {
|
||||
// Unexpected incoming ping, reply with announce message
|
||||
// TODO
|
||||
return
|
||||
}
|
||||
peer.send(&PacketRaw{Command: CommandPong})
|
||||
//fmt.Printf("Incoming ping from %s on %s\n", msg.connection.Address.String(), msg.connection.Address.String())
|
||||
}
|
||||
|
||||
@@ -241,6 +241,9 @@ func sendAllNetworks(receiverPublicKey *btcec.PublicKey, packet *PacketRaw, remo
|
||||
|
||||
successCount := 0
|
||||
|
||||
networksMutex.RLock()
|
||||
defer networksMutex.RUnlock()
|
||||
|
||||
if IsIPv6(remote.IP.To16()) {
|
||||
for _, network := range networks6 {
|
||||
// Do not mix link-local unicast targets with non link-local networks (only when iface is known, i.e. not catch all local)
|
||||
|
||||
@@ -7,8 +7,11 @@ Author: Peter Kleissner
|
||||
package core
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"log"
|
||||
"net"
|
||||
"strings"
|
||||
"time"
|
||||
)
|
||||
|
||||
// FindInterfaceByIP finds an interface based on the IP. The IP must be available at the interface.
|
||||
@@ -87,3 +90,111 @@ func IsNetworkErrorFatal(err error) bool {
|
||||
|
||||
return false
|
||||
}
|
||||
|
||||
// changeMonitorFrequency is the frequency in seconds to check for a network change
|
||||
const changeMonitorFrequency = 10
|
||||
|
||||
// networkChangeMonitor() monitors for network changes to act accordingly
|
||||
func networkChangeMonitor() {
|
||||
// If manual IPs are entered, no need for monitoring for any network changes.
|
||||
if len(config.Listen) > 0 {
|
||||
return
|
||||
}
|
||||
|
||||
for {
|
||||
time.Sleep(time.Second * changeMonitorFrequency)
|
||||
|
||||
interfaceList, err := net.Interfaces()
|
||||
if err != nil {
|
||||
log.Printf("networkChangeMonitor enumerating network adapters failed: %s\n", err.Error())
|
||||
continue
|
||||
}
|
||||
|
||||
ifacesNew := make(map[string][]net.Addr)
|
||||
|
||||
for _, iface := range interfaceList {
|
||||
addressesNew, err := iface.Addrs()
|
||||
if err != nil {
|
||||
log.Printf("initNetwork error enumerating IPs for network adapter '%s': %s\n", iface.Name, err.Error())
|
||||
continue
|
||||
}
|
||||
ifacesNew[iface.Name] = addressesNew
|
||||
|
||||
// was the interface added?
|
||||
addressesExist, ok := ifacesExist[iface.Name]
|
||||
if !ok {
|
||||
networkChangeInterfaceNew(iface, addressesNew)
|
||||
} else {
|
||||
// new IPs added for this interface?
|
||||
for _, addr := range addressesNew {
|
||||
exists := false
|
||||
for _, exist := range addressesExist {
|
||||
if exist.String() == addr.String() {
|
||||
exists = true
|
||||
break
|
||||
}
|
||||
}
|
||||
|
||||
if !exists {
|
||||
networkChangeIPNew(iface, addr)
|
||||
}
|
||||
}
|
||||
|
||||
// were IPs removed from this interface
|
||||
for _, exist := range addressesExist {
|
||||
removed := true
|
||||
for _, addr := range addressesNew {
|
||||
if exist.String() == addr.String() {
|
||||
removed = false
|
||||
break
|
||||
}
|
||||
}
|
||||
|
||||
if removed {
|
||||
networkChangeIPRemove(iface, exist)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// was an existing interface removed?
|
||||
for ifaceExist, addressesExist := range ifacesExist {
|
||||
if _, ok := ifacesNew[ifaceExist]; !ok {
|
||||
networkChangeInterfaceRemove(ifaceExist, addressesExist)
|
||||
}
|
||||
}
|
||||
|
||||
ifacesExist = ifacesNew
|
||||
}
|
||||
}
|
||||
|
||||
// networkChangeInterfaceNew is called when a new interface is detected
|
||||
func networkChangeInterfaceNew(iface net.Interface, addresses []net.Addr) {
|
||||
fmt.Printf("Interface new: %s\n", iface.Name)
|
||||
|
||||
for _, addr := range addresses {
|
||||
fmt.Printf(" IP: %s\n", addr.String())
|
||||
}
|
||||
}
|
||||
|
||||
// networkChangeInterfaceRemove is called when an existing interface is removed
|
||||
func networkChangeInterfaceRemove(iface string, addresses []net.Addr) {
|
||||
//networksMutex.RLock()
|
||||
//defer networksMutex.RUnlock()
|
||||
|
||||
fmt.Printf("Interface removed: %s\n", iface)
|
||||
|
||||
for _, addr := range addresses {
|
||||
fmt.Printf(" IP: %s\n", addr.String())
|
||||
}
|
||||
}
|
||||
|
||||
// networkChangeIPNew is called when an existing interface lists a new IP
|
||||
func networkChangeIPNew(iface net.Interface, address net.Addr) {
|
||||
fmt.Printf("IP new on iface: %s address %s\n", iface.Name, address.String())
|
||||
}
|
||||
|
||||
// networkChangeIPRemove is called when an existing interface removes an IP
|
||||
func networkChangeIPRemove(iface net.Interface, address net.Addr) {
|
||||
fmt.Printf("IP removed on iface: %s address %s\n", iface.Name, address.String())
|
||||
}
|
||||
|
||||
@@ -31,14 +31,16 @@ type networkWire struct {
|
||||
}
|
||||
|
||||
var (
|
||||
rawPacketsIncoming chan networkWire // channel for processing incoming decoded packets by workers
|
||||
ipsListen map[string]struct{} // list of IPs currently listening on
|
||||
rawPacketsIncoming chan networkWire // channel for processing incoming decoded packets by workers
|
||||
ipsListen map[string]struct{} // list of IPs currently listening on
|
||||
ifacesExist map[string][]net.Addr // list of currently known interfaces with list of IP addresses
|
||||
)
|
||||
|
||||
// initNetwork sets up the network configuration and starts listening.
|
||||
func initNetwork() {
|
||||
rawPacketsIncoming = make(chan networkWire, 1000) // buffer up to 1000 UDP packets before they get buffered by the OS network stack and eventually dropped
|
||||
ipsListen = make(map[string]struct{})
|
||||
ifacesExist = make(map[string][]net.Addr)
|
||||
rand.Seed(time.Now().UnixNano()) // we are not using "crypto/rand" for speed tradeoff
|
||||
|
||||
if config.ListenWorkers == 0 {
|
||||
@@ -96,6 +98,8 @@ func initNetwork() {
|
||||
continue
|
||||
}
|
||||
|
||||
ifacesExist[iface.Name] = addresses
|
||||
|
||||
for _, address := range addresses {
|
||||
net1 := address.(*net.IPNet)
|
||||
|
||||
|
||||
@@ -10,6 +10,7 @@ import (
|
||||
"errors"
|
||||
"log"
|
||||
"net"
|
||||
"sync"
|
||||
"sync/atomic"
|
||||
"time"
|
||||
)
|
||||
@@ -30,6 +31,9 @@ type Network struct {
|
||||
// networks is a list of all connected networks
|
||||
var networks4, networks6 []*Network
|
||||
|
||||
// single mutex for both network lists. Higher granularity currently not needed.
|
||||
var networksMutex sync.RWMutex
|
||||
|
||||
// Default ports to use. This may be randomized in the future to prevent fingerprinting (and subsequent blocking) by corporate and ISP firewalls.
|
||||
const defaultPort = 'p' // 112
|
||||
|
||||
@@ -115,7 +119,7 @@ func packetWorker(packets <-chan networkWire) {
|
||||
for packet := range packets {
|
||||
decoded, senderPublicKey, err := PacketDecrypt(packet.raw, packet.receiverPublicKey)
|
||||
if err != nil {
|
||||
log.Printf("packetWorker Error decrypting packet from '%s': %s\n", packet.sender.String(), err.Error())
|
||||
//log.Printf("packetWorker Error decrypting packet from '%s': %s\n", packet.sender.String(), err.Error())
|
||||
continue
|
||||
}
|
||||
|
||||
|
||||
@@ -20,4 +20,5 @@ func Connect() {
|
||||
go bootstrap()
|
||||
go autoMulticastBroadcast()
|
||||
go autoPingAll()
|
||||
go networkChangeMonitor()
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user