|
@@ -42,17 +42,14 @@ type Limiter struct {
|
42
|
42
|
exemptedNets []net.IPNet
|
43
|
43
|
}
|
44
|
44
|
|
45
|
|
-// maskAddr masks the given IPv4/6 address with our cidr limit masks.
|
46
|
|
-func (cl *Limiter) maskAddr(addr net.IP) net.IP {
|
47
|
|
- if addr.To4() == nil {
|
48
|
|
- // IPv6 addr
|
49
|
|
- addr = addr.Mask(cl.ipv6Mask)
|
|
45
|
+// addrToKey canonicalizes `addr` to a string key.
|
|
46
|
+func addrToKey(addr net.IP, v4Mask net.IPMask, v6Mask net.IPMask) string {
|
|
47
|
+ if addr.To4() != nil {
|
|
48
|
+ addr = addr.Mask(v4Mask) // IP.Mask() handles the 4-in-6 mapping for us
|
50
|
49
|
} else {
|
51
|
|
- // IPv4 addr
|
52
|
|
- addr = addr.Mask(cl.ipv4Mask)
|
|
50
|
+ addr = addr.Mask(v6Mask)
|
53
|
51
|
}
|
54
|
|
-
|
55
|
|
- return addr
|
|
52
|
+ return addr.String()
|
56
|
53
|
}
|
57
|
54
|
|
58
|
55
|
// AddClient adds a client to our population if possible. If we can't, throws an error instead.
|
|
@@ -72,8 +69,7 @@ func (cl *Limiter) AddClient(addr net.IP, force bool) error {
|
72
|
69
|
}
|
73
|
70
|
|
74
|
71
|
// check population
|
75
|
|
- cl.maskAddr(addr)
|
76
|
|
- addrString := addr.String()
|
|
72
|
+ addrString := addrToKey(addr, cl.ipv4Mask, cl.ipv6Mask)
|
77
|
73
|
|
78
|
74
|
if cl.population[addrString]+1 > cl.subnetLimit && !force {
|
79
|
75
|
return errTooManyClients
|
|
@@ -93,7 +89,7 @@ func (cl *Limiter) RemoveClient(addr net.IP) {
|
93
|
89
|
return
|
94
|
90
|
}
|
95
|
91
|
|
96
|
|
- addrString := addr.String()
|
|
92
|
+ addrString := addrToKey(addr, cl.ipv4Mask, cl.ipv6Mask)
|
97
|
93
|
cl.population[addrString] = cl.population[addrString] - 1
|
98
|
94
|
|
99
|
95
|
// safety limiter
|