mosdns: black_hole: apply Fisher-Yates shuffle algorithm to randomize IP order
* The client seems to always use the first IP address in the response, using a random algorithm to scramble multiple IP addresses so that the client can use all IP addresses as much as possible.
This commit is contained in:
parent
87a987dee8
commit
b8b7d64ba9
@ -0,0 +1,56 @@
|
|||||||
|
From 6c00597904ba487615e3a49626ccbb7d5623283f Mon Sep 17 00:00:00 2001
|
||||||
|
From: sbwml <admin@cooluc.com>
|
||||||
|
Date: Wed, 20 Sep 2023 14:51:19 +0800
|
||||||
|
Subject: [PATCH] black_hole: apply Fisher-Yates shuffle algorithm to randomize
|
||||||
|
IP order
|
||||||
|
|
||||||
|
---
|
||||||
|
plugin/executable/black_hole/black_hole.go | 15 +++++++++++++++
|
||||||
|
1 file changed, 15 insertions(+)
|
||||||
|
|
||||||
|
diff --git a/plugin/executable/black_hole/black_hole.go b/plugin/executable/black_hole/black_hole.go
|
||||||
|
index 775253d..f955019 100644
|
||||||
|
--- a/plugin/executable/black_hole/black_hole.go
|
||||||
|
+++ b/plugin/executable/black_hole/black_hole.go
|
||||||
|
@@ -27,6 +27,8 @@ import (
|
||||||
|
"github.com/miekg/dns"
|
||||||
|
"net/netip"
|
||||||
|
"strings"
|
||||||
|
+ "math/rand"
|
||||||
|
+ "sync"
|
||||||
|
)
|
||||||
|
|
||||||
|
const PluginType = "black_hole"
|
||||||
|
@@ -40,6 +42,7 @@ var _ sequence.Executable = (*BlackHole)(nil)
|
||||||
|
type BlackHole struct {
|
||||||
|
ipv4 []netip.Addr
|
||||||
|
ipv6 []netip.Addr
|
||||||
|
+ shuffleMutex sync.Mutex
|
||||||
|
}
|
||||||
|
|
||||||
|
// QuickSetup format: [ipv4|ipv6] ...
|
||||||
|
@@ -65,9 +68,21 @@ func NewBlackHole(ips []string) (*BlackHole, error) {
|
||||||
|
return b, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
+func (b *BlackHole) shuffleIPs() {
|
||||||
|
+ b.shuffleMutex.Lock()
|
||||||
|
+ defer b.shuffleMutex.Unlock()
|
||||||
|
+ rand.Shuffle(len(b.ipv4), func(i, j int) {
|
||||||
|
+ b.ipv4[i], b.ipv4[j] = b.ipv4[j], b.ipv4[i]
|
||||||
|
+ })
|
||||||
|
+ rand.Shuffle(len(b.ipv6), func(i, j int) {
|
||||||
|
+ b.ipv6[i], b.ipv6[j] = b.ipv6[j], b.ipv6[i]
|
||||||
|
+ })
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
// Exec implements sequence.Executable. It set a response with given ips if
|
||||||
|
// query has corresponding qtypes.
|
||||||
|
func (b *BlackHole) Exec(_ context.Context, qCtx *query_context.Context) error {
|
||||||
|
+ b.shuffleIPs()
|
||||||
|
if r := b.Response(qCtx.Q()); r != nil {
|
||||||
|
qCtx.SetResponse(r)
|
||||||
|
}
|
||||||
|
--
|
||||||
|
2.34.8
|
||||||
|
|
Loading…
Reference in New Issue
Block a user