glider/rules.go

103 lines
2.2 KiB
Go
Raw Normal View History

2017-07-30 01:54:19 +08:00
package main
import (
"net"
"strings"
)
// RulesForwarder .
2017-08-16 22:37:42 +08:00
type RulesForwarder struct {
2017-07-30 01:54:19 +08:00
globalForwarder Proxy
domainMap map[string]Proxy
ipMap map[string]Proxy
cidrMap map[string]Proxy
}
2017-08-16 22:37:42 +08:00
// NewRulesForwarder .
func NewRulesForwarder(ruleForwarders []*RuleForwarder, globalForwarder Proxy) Proxy {
if len(ruleForwarders) == 0 {
return globalForwarder
}
2017-08-16 22:37:42 +08:00
p := &RulesForwarder{globalForwarder: globalForwarder}
2017-07-30 01:54:19 +08:00
for _, f := range ruleForwarders {
p.domainMap = make(map[string]Proxy)
for _, domain := range f.Domain {
p.domainMap[domain] = f.Proxy
2017-07-30 01:54:19 +08:00
}
p.ipMap = make(map[string]Proxy)
for _, ip := range f.IP {
p.ipMap[ip] = f.Proxy
2017-07-30 01:54:19 +08:00
}
p.cidrMap = make(map[string]Proxy)
for _, cidr := range f.CIDR {
p.cidrMap[cidr] = f.Proxy
2017-07-30 01:54:19 +08:00
}
}
return p
}
2017-08-16 22:37:42 +08:00
func (p *RulesForwarder) Addr() string { return "rules forwarder" }
func (p *RulesForwarder) ListenAndServe() {}
func (p *RulesForwarder) Serve(c net.Conn) {}
func (p *RulesForwarder) CurrentProxy() Proxy { return p.globalForwarder.CurrentProxy() }
2017-07-30 01:54:19 +08:00
2017-08-16 22:37:42 +08:00
func (p *RulesForwarder) GetProxy(dstAddr string) Proxy {
2017-07-30 01:54:19 +08:00
// TODO: change to index finders
2017-07-30 01:54:19 +08:00
host, _, err := net.SplitHostPort(dstAddr)
if err != nil {
// TODO: check here
logf("SplitHostPort ERROR: %s", err)
2017-07-30 01:54:19 +08:00
return p.globalForwarder.GetProxy(dstAddr)
}
// find ip
if ip := net.ParseIP(host); ip != nil {
// check ip
if proxy, ok := p.ipMap[ip.String()]; ok {
return proxy
}
// check cidr
// TODO: do not parse cidr every time
for cidrStr, proxy := range p.cidrMap {
if _, net, err := net.ParseCIDR(cidrStr); err == nil {
if net.Contains(ip) {
return proxy
}
}
2017-07-30 01:54:19 +08:00
}
}
domainParts := strings.Split(host, ".")
length := len(domainParts)
for i := length - 2; i >= 0; i-- {
domain := strings.Join(domainParts[i:length], ".")
// find in domainMap
if proxy, ok := p.domainMap[domain]; ok {
return proxy
2017-07-30 01:54:19 +08:00
}
}
return p.globalForwarder.GetProxy(dstAddr)
}
2017-08-16 22:37:42 +08:00
func (p *RulesForwarder) NextProxy() Proxy {
2017-07-30 01:54:19 +08:00
return p.globalForwarder.NextProxy()
}
2017-08-16 22:37:42 +08:00
func (p *RulesForwarder) Enabled() bool { return true }
func (p *RulesForwarder) SetEnable(enable bool) {}
2017-07-30 01:54:19 +08:00
2017-08-16 22:37:42 +08:00
func (p *RulesForwarder) Dial(network, addr string) (net.Conn, error) {
2017-07-30 01:54:19 +08:00
return p.GetProxy(addr).Dial(network, addr)
}