mirror of
https://github.com/Control-D-Inc/ctrld.git
synced 2026-07-04 01:07:49 +02:00
all: include client IP if ctrld is dnsmasq upstream
So ctrld can record the raw/original client IP instead of looking up from MAC to IP, which may not the right choice in some network setup like using wireguard/vpn on Merlin router.
This commit is contained in:
committed by
Cuong Manh Le
parent
ee5eb4fc4e
commit
0f3e8c7ada
@@ -33,6 +33,9 @@ func (a *arpDiscover) String() string {
|
||||
}
|
||||
|
||||
func (a *arpDiscover) List() []string {
|
||||
if a == nil {
|
||||
return nil
|
||||
}
|
||||
var ips []string
|
||||
a.ip.Range(func(key, value any) bool {
|
||||
ips = append(ips, value.(string))
|
||||
|
||||
@@ -74,6 +74,7 @@ type Table struct {
|
||||
ptr *ptrDiscover
|
||||
mdns *mdns
|
||||
hf *hostsFile
|
||||
vpn *vpn
|
||||
cfg *ctrld.Config
|
||||
quitCh chan struct{}
|
||||
selfIP string
|
||||
@@ -117,6 +118,7 @@ func (t *Table) Init() {
|
||||
}
|
||||
|
||||
func (t *Table) init() {
|
||||
// Custom client ID presents, use it as the only source.
|
||||
if _, clientID := controld.ParseRawUID(t.cdUID); clientID != "" {
|
||||
ctrld.ProxyLogger.Load().Debug().Msg("start self discovery")
|
||||
t.dhcp = &dhcp{selfIP: t.selfIP}
|
||||
@@ -126,6 +128,11 @@ func (t *Table) init() {
|
||||
t.hostnameResolvers = append(t.hostnameResolvers, t.dhcp)
|
||||
return
|
||||
}
|
||||
|
||||
// Otherwise, process all possible sources in order, that means
|
||||
// the first result of IP/MAC/Hostname lookup will be used.
|
||||
//
|
||||
// Merlin custom clients.
|
||||
if t.discoverDHCP() || t.discoverARP() {
|
||||
t.merlin = &merlinDiscover{}
|
||||
if err := t.merlin.refresh(); err != nil {
|
||||
@@ -135,6 +142,7 @@ func (t *Table) init() {
|
||||
t.refreshers = append(t.refreshers, t.merlin)
|
||||
}
|
||||
}
|
||||
// Hosts file mapping.
|
||||
if t.discoverHosts() {
|
||||
t.hf = &hostsFile{}
|
||||
ctrld.ProxyLogger.Load().Debug().Msg("start hosts file discovery")
|
||||
@@ -146,6 +154,7 @@ func (t *Table) init() {
|
||||
}
|
||||
go t.hf.watchChanges()
|
||||
}
|
||||
// DHCP lease files.
|
||||
if t.discoverDHCP() {
|
||||
t.dhcp = &dhcp{selfIP: t.selfIP}
|
||||
ctrld.ProxyLogger.Load().Debug().Msg("start dhcp discovery")
|
||||
@@ -158,6 +167,7 @@ func (t *Table) init() {
|
||||
}
|
||||
go t.dhcp.watchChanges()
|
||||
}
|
||||
// ARP table.
|
||||
if t.discoverARP() {
|
||||
t.arp = &arpDiscover{}
|
||||
ctrld.ProxyLogger.Load().Debug().Msg("start arp discovery")
|
||||
@@ -169,6 +179,7 @@ func (t *Table) init() {
|
||||
t.refreshers = append(t.refreshers, t.arp)
|
||||
}
|
||||
}
|
||||
// PTR lookup.
|
||||
if t.discoverPTR() {
|
||||
t.ptr = &ptrDiscover{resolver: ctrld.NewPrivateResolver()}
|
||||
ctrld.ProxyLogger.Load().Debug().Msg("start ptr discovery")
|
||||
@@ -179,6 +190,7 @@ func (t *Table) init() {
|
||||
t.refreshers = append(t.refreshers, t.ptr)
|
||||
}
|
||||
}
|
||||
// mdns.
|
||||
if t.discoverMDNS() {
|
||||
t.mdns = &mdns{}
|
||||
ctrld.ProxyLogger.Load().Debug().Msg("start mdns discovery")
|
||||
@@ -188,6 +200,11 @@ func (t *Table) init() {
|
||||
t.hostnameResolvers = append(t.hostnameResolvers, t.mdns)
|
||||
}
|
||||
}
|
||||
// VPN clients.
|
||||
if t.discoverDHCP() || t.discoverARP() {
|
||||
t.vpn = &vpn{}
|
||||
t.hostnameResolvers = append(t.hostnameResolvers, t.vpn)
|
||||
}
|
||||
}
|
||||
|
||||
func (t *Table) LookupIP(mac string) string {
|
||||
@@ -271,7 +288,7 @@ func (t *Table) ListClients() []*Client {
|
||||
_ = r.refresh()
|
||||
}
|
||||
ipMap := make(map[string]*Client)
|
||||
il := []ipLister{t.dhcp, t.arp, t.ptr, t.mdns}
|
||||
il := []ipLister{t.dhcp, t.arp, t.ptr, t.mdns, t.vpn}
|
||||
for _, ir := range il {
|
||||
for _, ip := range ir.List() {
|
||||
c, ok := ipMap[ip]
|
||||
@@ -312,6 +329,15 @@ func (t *Table) ListClients() []*Client {
|
||||
return clients
|
||||
}
|
||||
|
||||
// StoreVPNClient stores client info for VPN clients.
|
||||
func (t *Table) StoreVPNClient(ci *ctrld.ClientInfo) {
|
||||
if ci == nil || t.vpn == nil {
|
||||
return
|
||||
}
|
||||
t.vpn.mac.Store(ci.IP, ci.Mac)
|
||||
t.vpn.ip2name.Store(ci.IP, ci.Hostname)
|
||||
}
|
||||
|
||||
func (t *Table) discoverDHCP() bool {
|
||||
if t.cfg.Service.DiscoverDHCP == nil {
|
||||
return true
|
||||
|
||||
@@ -119,6 +119,9 @@ func (d *dhcp) String() string {
|
||||
}
|
||||
|
||||
func (d *dhcp) List() []string {
|
||||
if d == nil {
|
||||
return nil
|
||||
}
|
||||
var ips []string
|
||||
d.ip.Range(func(key, value any) bool {
|
||||
ips = append(ips, value.(string))
|
||||
|
||||
@@ -48,6 +48,9 @@ func (m *mdns) String() string {
|
||||
}
|
||||
|
||||
func (m *mdns) List() []string {
|
||||
if m == nil {
|
||||
return nil
|
||||
}
|
||||
var ips []string
|
||||
m.name.Range(func(key, value any) bool {
|
||||
ips = append(ips, key.(string))
|
||||
|
||||
@@ -41,6 +41,9 @@ func (p *ptrDiscover) String() string {
|
||||
}
|
||||
|
||||
func (p *ptrDiscover) List() []string {
|
||||
if p == nil {
|
||||
return nil
|
||||
}
|
||||
var ips []string
|
||||
p.hostname.Range(func(key, value any) bool {
|
||||
ips = append(ips, key.(string))
|
||||
|
||||
@@ -0,0 +1,43 @@
|
||||
package clientinfo
|
||||
|
||||
import (
|
||||
"sync"
|
||||
)
|
||||
|
||||
// vpn is the manager for VPN clients info.
|
||||
type vpn struct {
|
||||
ip2name sync.Map // ip => name
|
||||
mac sync.Map // ip => mac
|
||||
}
|
||||
|
||||
// LookupHostnameByIP returns hostname of the given VPN client ip.
|
||||
func (v *vpn) LookupHostnameByIP(ip string) string {
|
||||
val, ok := v.ip2name.Load(ip)
|
||||
if !ok {
|
||||
return ""
|
||||
}
|
||||
return val.(string)
|
||||
}
|
||||
|
||||
// LookupHostnameByMac always returns empty string.
|
||||
func (v *vpn) LookupHostnameByMac(mac string) string {
|
||||
return ""
|
||||
}
|
||||
|
||||
// String returns the string representation of vpn struct.
|
||||
func (v *vpn) String() string {
|
||||
return "vpn"
|
||||
}
|
||||
|
||||
// List lists all known VPN clients IP.
|
||||
func (v *vpn) List() []string {
|
||||
if v == nil {
|
||||
return nil
|
||||
}
|
||||
var ips []string
|
||||
v.mac.Range(func(key, value any) bool {
|
||||
ips = append(ips, key.(string))
|
||||
return true
|
||||
})
|
||||
return ips
|
||||
}
|
||||
@@ -17,6 +17,7 @@ server={{ .IP }}#{{ .Port }}
|
||||
{{- end}}
|
||||
{{- if .SendClientInfo}}
|
||||
add-mac
|
||||
add-subnet=32,128
|
||||
{{- end}}
|
||||
`
|
||||
|
||||
@@ -39,7 +40,10 @@ if [ -n "$pid" ] && [ -f "/proc/${pid}/cmdline" ]; then
|
||||
pc_append "server={{ .IP }}#{{ .Port }}" "$config_file"
|
||||
{{- end}}
|
||||
{{- if .SendClientInfo}}
|
||||
pc_delete "add-mac" "$config_file"
|
||||
pc_delete "add-subnet" "$config_file"
|
||||
pc_append "add-mac" "$config_file" # add client mac
|
||||
pc_append "add-subnet=32,128" "$config_file" # add client ip
|
||||
{{- end}}
|
||||
pc_delete "dnssec" "$config_file" # disable DNSSEC
|
||||
pc_delete "trust-anchor=" "$config_file" # disable DNSSEC
|
||||
|
||||
Reference in New Issue
Block a user