Support multiple IPs for a single cloaking rule

Fixes #617
This commit is contained in:
Frank Denis 2019-02-23 15:51:30 +01:00
parent 5dc66adaa9
commit 734483226b
2 changed files with 35 additions and 13 deletions

View File

@ -20,3 +20,4 @@ youtube.googleapis.com restrictmoderate.youtube.com
www.youtube-nocookie.com restrictmoderate.youtube.com www.youtube-nocookie.com restrictmoderate.youtube.com
localhost 127.0.0.1 localhost 127.0.0.1
localhost ::1

View File

@ -1,6 +1,7 @@
package main package main
import ( import (
"math/rand"
"net" "net"
"strings" "strings"
"sync" "sync"
@ -13,9 +14,10 @@ import (
type CloakedName struct { type CloakedName struct {
target string target string
ipv4 *net.IP ipv4 []*net.IP
ipv6 *net.IP ipv6 []*net.IP
lastUpdate *time.Time lastUpdate *time.Time
lineNo int
isIP bool isIP bool
} }
@ -41,6 +43,7 @@ func (plugin *PluginCloak) Init(proxy *Proxy) error {
} }
plugin.ttl = proxy.cacheMinTTL plugin.ttl = proxy.cacheMinTTL
plugin.patternMatcher = NewPatternPatcher() plugin.patternMatcher = NewPatternPatcher()
cloakedNames := make(map[string]*CloakedName)
for lineNo, line := range strings.Split(string(bin), "\n") { for lineNo, line := range strings.Split(string(bin), "\n") {
line = strings.TrimFunc(line, unicode.IsSpace) line = strings.TrimFunc(line, unicode.IsSpace)
if len(line) == 0 || strings.HasPrefix(line, "#") { if len(line) == 0 || strings.HasPrefix(line, "#") {
@ -60,12 +63,15 @@ func (plugin *PluginCloak) Init(proxy *Proxy) error {
continue continue
} }
line = strings.ToLower(line) line = strings.ToLower(line)
cloakedName := CloakedName{} cloakedName, found := cloakedNames[line]
if !found {
cloakedName = &CloakedName{}
}
if ip := net.ParseIP(target); ip != nil { if ip := net.ParseIP(target); ip != nil {
if ipv4 := ip.To4(); ipv4 != nil { if ipv4 := ip.To4(); ipv4 != nil {
cloakedName.ipv4 = &ipv4 cloakedName.ipv4 = append((*cloakedName).ipv4, &ipv4)
} else if ipv6 := ip.To16(); ipv6 != nil { } else if ipv6 := ip.To16(); ipv6 != nil {
cloakedName.ipv6 = &ipv6 cloakedName.ipv6 = append((*cloakedName).ipv6, &ipv6)
} else { } else {
dlog.Errorf("Invalid IP address in cloaking rule at line %d", 1+lineNo) dlog.Errorf("Invalid IP address in cloaking rule at line %d", 1+lineNo)
continue continue
@ -74,7 +80,11 @@ func (plugin *PluginCloak) Init(proxy *Proxy) error {
} else { } else {
cloakedName.target = target cloakedName.target = target
} }
plugin.patternMatcher.Add(line, &cloakedName, lineNo+1) cloakedName.lineNo = lineNo + 1
cloakedNames[line] = cloakedName
}
for line, cloakedName := range cloakedNames {
plugin.patternMatcher.Add(line, cloakedName, cloakedName.lineNo)
} }
return nil return nil
} }
@ -125,15 +135,20 @@ func (plugin *PluginCloak) Eval(pluginsState *PluginsState, msg *dns.Msg) error
} }
plugin.Lock() plugin.Lock()
cloakedName.lastUpdate = &now cloakedName.lastUpdate = &now
cloakedName.ipv4 = nil
cloakedName.ipv6 = nil
for _, foundIP := range foundIPs { for _, foundIP := range foundIPs {
if ipv4 := foundIP.To4(); ipv4 != nil { if ipv4 := foundIP.To4(); ipv4 != nil {
cloakedName.ipv4 = &ipv4 cloakedName.ipv4 = append(cloakedName.ipv4, &foundIP)
} else { if len(cloakedName.ipv4) >= 16 {
cloakedName.ipv6 = &foundIP
}
if cloakedName.ipv4 != nil && cloakedName.ipv6 != nil {
break break
} }
} else {
cloakedName.ipv6 = append(cloakedName.ipv6, &foundIP)
if len(cloakedName.ipv6) >= 16 {
break
}
}
} }
plugin.Unlock() plugin.Unlock()
} else { } else {
@ -141,9 +156,15 @@ func (plugin *PluginCloak) Eval(pluginsState *PluginsState, msg *dns.Msg) error
} }
var ip *net.IP var ip *net.IP
if question.Qtype == dns.TypeA { if question.Qtype == dns.TypeA {
ip = cloakedName.ipv4 ipLen := len(cloakedName.ipv4)
if ipLen > 0 {
ip = cloakedName.ipv4[rand.Intn(ipLen)]
}
} else { } else {
ip = cloakedName.ipv6 ipLen := len(cloakedName.ipv6)
if ipLen > 0 {
ip = cloakedName.ipv6[rand.Intn(ipLen)]
}
} }
synth, err := EmptyResponseFromMessage(msg) synth, err := EmptyResponseFromMessage(msg)
if err != nil { if err != nil {