From d6472d0421251501ca57ae7f73f30bc422c13cc8 Mon Sep 17 00:00:00 2001 From: xvzc Date: Sun, 21 Jul 2024 16:57:47 +0900 Subject: [PATCH 1/4] add options to customize dns server --- build | 2 +- cmd/spoof-dpi/main.go | 2 - dns/dns.go | 89 +++++++++++++++++++++++++++++++ doh/dns.go | 49 ----------------- go.mod | 35 ++++++++---- go.sum | 120 ++++++++++++++++++++++++++++++++++++------ net/conn.go | 19 +++---- proxy/proxy.go | 9 ++-- util/config.go | 14 +++-- 9 files changed, 240 insertions(+), 99 deletions(-) create mode 100644 dns/dns.go delete mode 100644 doh/dns.go diff --git a/build b/build index 848e8cb..ca485d8 100755 --- a/build +++ b/build @@ -4,5 +4,5 @@ docker run --rm \ -it \ --workdir /app/ \ -v $(pwd):/app \ - golang:1.17-alpine \ + golang:1.21-alpine \ sh make-releases.sh diff --git a/cmd/spoof-dpi/main.go b/cmd/spoof-dpi/main.go index 19d019d..7df4c08 100644 --- a/cmd/spoof-dpi/main.go +++ b/cmd/spoof-dpi/main.go @@ -7,7 +7,6 @@ import ( "github.com/sirupsen/logrus" log "github.com/sirupsen/logrus" - "github.com/xvzc/SpoofDPI/doh" "github.com/xvzc/SpoofDPI/proxy" "github.com/xvzc/SpoofDPI/util" ) @@ -17,7 +16,6 @@ func main() { config := util.GetConfig() p := proxy.New(config) - doh.Init(*config.Dns) if *config.Debug { log.SetLevel(log.DebugLevel) } else { diff --git a/dns/dns.go b/dns/dns.go new file mode 100644 index 0000000..1b15c63 --- /dev/null +++ b/dns/dns.go @@ -0,0 +1,89 @@ +package dns + +import ( + "context" + "errors" + "regexp" + "time" + + "github.com/likexian/doh" + dohDns "github.com/likexian/doh/dns" + "github.com/miekg/dns" + log "github.com/sirupsen/logrus" + "github.com/xvzc/SpoofDPI/util" +) + +type DnsResolver struct { + host string + port string + enableDoh bool +} + +func NewResolver(config *util.Config) *DnsResolver { + return &DnsResolver{ + host: *config.DnsAddr, + port: *config.DnsPort, + enableDoh: *config.EnableDoh, + } +} + +func (d *DnsResolver) Lookup(domain string) (string, error) { + ipRegex := "^(?:(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\.){3}(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)$" + + if r, _ := regexp.MatchString(ipRegex, domain); r { + return domain, nil + } + + if d.enableDoh { + return dohLookup(domain) + } + + dnsServer := d.host + ":" + d.port + + msg := new(dns.Msg) + msg.SetQuestion(dns.Fqdn(domain), dns.TypeA) + + c := new(dns.Client) + + response, _, err := c.Exchange(msg, dnsServer) + if err != nil { + return "", errors.New(" couldn't resolve the domain") + } + + for _, answer := range response.Answer { + if record, ok := answer.(*dns.A); ok { + log.Debug("[DNS] resolved dns for "+domain+": ", record.A.String()) + return record.A.String(), nil + } + } + + return "", errors.New("[DNS] couldn't resolve the domain") +} + +func dohLookup(domain string) (string, error) { + ctx, cancel := context.WithTimeout(context.Background(), 3*time.Second) + defer cancel() + c := doh.Use(doh.CloudflareProvider, doh.GoogleProvider) + + rsp, err := c.Query(ctx, dohDns.Domain(domain), dohDns.TypeA) + if err != nil { + return "", errors.New("[DOH] couldn't resolve the domain") + } + // doh dns answer + answer := rsp.Answer + + // print all answer + for _, a := range answer { + if a.Type != 1 { // Type == 1 -> A Record + continue + } + + log.Debug("[DOH] resolved dns for "+domain+": ", a.Data) + return a.Data, nil + } + + // close the client + c.Close() + + return "", errors.New("[DOH] couldn't resolve the domain") +} diff --git a/doh/dns.go b/doh/dns.go deleted file mode 100644 index b33b3f2..0000000 --- a/doh/dns.go +++ /dev/null @@ -1,49 +0,0 @@ -package doh - -import ( - "errors" - "sync" - - "regexp" - - "github.com/babolivier/go-doh-client" -) - -var resolver *doh.Resolver -var once sync.Once - -func Init(dns string) { - getInstance().Host = dns -} - -func Lookup(domain string) (string, error) { - ipRegex := "^(?:(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\.){3}(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)$" - - if r, _ := regexp.MatchString(ipRegex, domain); r { - return domain, nil - } - - a, _, err := resolver.LookupA(domain) - if err != nil { - return "", err - } - - if len(a) < 1 { - return "", errors.New(" couldn't resolve the domain") - } - - ip := a[0].IP4 - - return ip, nil -} - -func getInstance() *doh.Resolver { - once.Do(func() { - resolver = &doh.Resolver{ - Host: "", - Class: doh.IN, - } - }) - - return resolver -} diff --git a/go.mod b/go.mod index ccb7d1a..4028aac 100644 --- a/go.mod +++ b/go.mod @@ -1,19 +1,32 @@ module github.com/xvzc/SpoofDPI -go 1.17 +go 1.21 + +toolchain go1.21.5 require ( - github.com/babolivier/go-doh-client v0.0.0-20201028162107-a76cff4cb8b6 - github.com/pterm/pterm v0.12.33 - github.com/sirupsen/logrus v1.8.1 + github.com/likexian/doh v0.7.1 + github.com/miekg/dns v1.1.61 + github.com/pterm/pterm v0.12.79 + github.com/sirupsen/logrus v1.9.3 ) require ( - github.com/atomicgo/cursor v0.0.1 // indirect - github.com/gookit/color v1.4.2 // indirect - github.com/mattn/go-runewidth v0.0.13 // indirect - github.com/rivo/uniseg v0.2.0 // indirect - github.com/xo/terminfo v0.0.0-20210125001918-ca9a967f8778 // indirect - golang.org/x/sys v0.0.0-20211013075003-97ac67df715c // indirect - golang.org/x/term v0.0.0-20210927222741-03fcf44c2211 // indirect + atomicgo.dev/cursor v0.2.0 // indirect + atomicgo.dev/keyboard v0.2.9 // indirect + atomicgo.dev/schedule v0.1.0 // indirect + github.com/containerd/console v1.0.3 // indirect + github.com/gookit/color v1.5.4 // indirect + github.com/likexian/gokit v0.25.15 // indirect + github.com/lithammer/fuzzysearch v1.1.8 // indirect + github.com/mattn/go-runewidth v0.0.15 // indirect + github.com/rivo/uniseg v0.4.4 // indirect + github.com/xo/terminfo v0.0.0-20220910002029-abceb7e1c41e // indirect + golang.org/x/mod v0.18.0 // indirect + golang.org/x/net v0.27.0 // indirect + golang.org/x/sync v0.7.0 // indirect + golang.org/x/sys v0.22.0 // indirect + golang.org/x/term v0.22.0 // indirect + golang.org/x/text v0.16.0 // indirect + golang.org/x/tools v0.22.0 // indirect ) diff --git a/go.sum b/go.sum index 4e8f431..0f0fe2d 100644 --- a/go.sum +++ b/go.sum @@ -1,49 +1,135 @@ +atomicgo.dev/assert v0.0.2 h1:FiKeMiZSgRrZsPo9qn/7vmr7mCsh5SZyXY4YGYiYwrg= +atomicgo.dev/assert v0.0.2/go.mod h1:ut4NcI3QDdJtlmAxQULOmA13Gz6e2DWbSAS8RUOmNYQ= +atomicgo.dev/cursor v0.2.0 h1:H6XN5alUJ52FZZUkI7AlJbUc1aW38GWZalpYRPpoPOw= +atomicgo.dev/cursor v0.2.0/go.mod h1:Lr4ZJB3U7DfPPOkbH7/6TOtJ4vFGHlgj1nc+n900IpU= +atomicgo.dev/keyboard v0.2.9 h1:tOsIid3nlPLZ3lwgG8KZMp/SFmr7P0ssEN5JUsm78K8= +atomicgo.dev/keyboard v0.2.9/go.mod h1:BC4w9g00XkxH/f1HXhW2sXmJFOCWbKn9xrOunSFtExQ= +atomicgo.dev/schedule v0.1.0 h1:nTthAbhZS5YZmgYbb2+DH8uQIZcTlIrd4eYr3UQxEjs= +atomicgo.dev/schedule v0.1.0/go.mod h1:xeUa3oAkiuHYh8bKiQBRojqAMq3PXXbJujjb0hw8pEU= github.com/MarvinJWendt/testza v0.1.0/go.mod h1:7AxNvlfeHP7Z/hDQ5JtE3OKYT3XFUeLCDE2DQninSqs= github.com/MarvinJWendt/testza v0.2.1/go.mod h1:God7bhG8n6uQxwdScay+gjm9/LnO4D3kkcZX4hv9Rp8= github.com/MarvinJWendt/testza v0.2.8/go.mod h1:nwIcjmr0Zz+Rcwfh3/4UhBp7ePKVhuBExvZqnKYWlII= -github.com/MarvinJWendt/testza v0.2.10 h1:cX4zE9TofXxe72a6EPIYAxC+8cVWTsmmgsXTZIT+5bQ= github.com/MarvinJWendt/testza v0.2.10/go.mod h1:pd+VWsoGUiFtq+hRKSU1Bktnn+DMCSrDrXDpX2bG66k= -github.com/atomicgo/cursor v0.0.1 h1:xdogsqa6YYlLfM+GyClC/Lchf7aiMerFiZQn7soTOoU= +github.com/MarvinJWendt/testza v0.2.12/go.mod h1:JOIegYyV7rX+7VZ9r77L/eH6CfJHHzXjB69adAhzZkI= +github.com/MarvinJWendt/testza v0.3.0/go.mod h1:eFcL4I0idjtIx8P9C6KkAuLgATNKpX4/2oUqKc6bF2c= +github.com/MarvinJWendt/testza v0.4.2/go.mod h1:mSdhXiKH8sg/gQehJ63bINcCKp7RtYewEjXsvsVUPbE= +github.com/MarvinJWendt/testza v0.5.2 h1:53KDo64C1z/h/d/stCYCPY69bt/OSwjq5KpFNwi+zB4= +github.com/MarvinJWendt/testza v0.5.2/go.mod h1:xu53QFE5sCdjtMCKk8YMQ2MnymimEctc4n3EjyIYvEY= github.com/atomicgo/cursor v0.0.1/go.mod h1:cBON2QmmrysudxNBFthvMtN32r3jxVRIvzkUiF/RuIk= -github.com/babolivier/go-doh-client v0.0.0-20201028162107-a76cff4cb8b6 h1:4NNbNM2Iq/k57qEu7WfL67UrbPq1uFWxW4qODCohi+0= -github.com/babolivier/go-doh-client v0.0.0-20201028162107-a76cff4cb8b6/go.mod h1:J29hk+f9lJrblVIfiJOtTFk+OblBawmib4uz/VdKzlg= +github.com/containerd/console v1.0.3 h1:lIr7SlA5PxZyMV30bDW0MGbiOPXwc63yRuCP0ARubLw= +github.com/containerd/console v1.0.3/go.mod h1:7LqA/THxQ86k76b8c/EMSiaJ3h1eZkMkXar0TQ1gf3U= github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c= github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= -github.com/gookit/color v1.4.2 h1:tXy44JFSFkKnELV6WaMo/lLfu/meqITX3iAV52do7lk= github.com/gookit/color v1.4.2/go.mod h1:fqRyamkC1W8uxl+lxCQxOT09l/vYfZ+QeiX3rKQHCoQ= -github.com/mattn/go-runewidth v0.0.13 h1:lTGmDsbAYt5DmK6OnoV7EuIF1wEIFAcxld6ypU4OSgU= +github.com/gookit/color v1.5.0/go.mod h1:43aQb+Zerm/BWh2GnrgOQm7ffz7tvQXEKV6BFMl7wAo= +github.com/gookit/color v1.5.4 h1:FZmqs7XOyGgCAxmWyPslpiok1k05wmY3SJTytgvYFs0= +github.com/gookit/color v1.5.4/go.mod h1:pZJOeOS8DM43rXbp4AZo1n9zCU2qjpcRko0b6/QJi9w= +github.com/klauspost/cpuid/v2 v2.0.9/go.mod h1:FInQzS24/EEf25PyTYn52gqo7WaD8xa0213Md/qVLRg= +github.com/klauspost/cpuid/v2 v2.0.10/go.mod h1:g2LTdtYhdyuGPqyWyv7qRAmj1WBqxuObKfj5c0PQa7c= +github.com/klauspost/cpuid/v2 v2.0.12/go.mod h1:g2LTdtYhdyuGPqyWyv7qRAmj1WBqxuObKfj5c0PQa7c= +github.com/klauspost/cpuid/v2 v2.2.3 h1:sxCkb+qR91z4vsqw4vGGZlDgPz3G7gjaLyK3V8y70BU= +github.com/klauspost/cpuid/v2 v2.2.3/go.mod h1:RVVoqg1df56z8g3pUjL/3lE5UfnlrJX8tyFgg4nqhuY= +github.com/kr/pretty v0.1.0/go.mod h1:dAy3ld7l9f0ibDNOQOHHMYYIIbhfbHSm3C4ZsoJORNo= +github.com/kr/pty v1.1.1/go.mod h1:pFQYn66WHrOpPYNljwOMqo10TkYh1fy3cYio2l3bCsQ= +github.com/kr/text v0.1.0/go.mod h1:4Jbv+DJW3UT/LiOwJeYQe1efqtUx/iVham/4vfdArNI= +github.com/likexian/doh v0.7.1 h1:0p75orMxXrfGNAOnOEtl2xZ5T9Ctqi++i/WhN6P6hs8= +github.com/likexian/doh v0.7.1/go.mod h1:aIEOK197o6nC82iRo5+5L5ws+X7xRCmuer3M4In91WA= +github.com/likexian/gokit v0.25.15 h1:QjospM1eXhdMMHwZRpMKKAHY/Wig9wgcREmLtf9NslY= +github.com/likexian/gokit v0.25.15/go.mod h1:S2QisdsxLEHWeD/XI0QMVeggp+jbxYqUxMvSBil7MRg= +github.com/lithammer/fuzzysearch v1.1.8 h1:/HIuJnjHuXS8bKaiTMeeDlW2/AyIWk2brx1V8LFgLN4= +github.com/lithammer/fuzzysearch v1.1.8/go.mod h1:IdqeyBClc3FFqSzYq/MXESsS4S0FsZ5ajtkr5xPLts4= github.com/mattn/go-runewidth v0.0.13/go.mod h1:Jdepj2loyihRzMpdS35Xk/zdY8IAYHsh153qUoGf23w= +github.com/mattn/go-runewidth v0.0.15 h1:UNAjwbU9l54TA3KzvqLGxwWjHmMgBUVhBiTjelZgg3U= +github.com/mattn/go-runewidth v0.0.15/go.mod h1:Jdepj2loyihRzMpdS35Xk/zdY8IAYHsh153qUoGf23w= +github.com/miekg/dns v1.1.61 h1:nLxbwF3XxhwVSm8g9Dghm9MHPaUZuqhPiGL+675ZmEs= +github.com/miekg/dns v1.1.61/go.mod h1:mnAarhS3nWaW+NVP2wTkYVIZyHNJ098SJZUki3eykwQ= github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM= github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= github.com/pterm/pterm v0.12.27/go.mod h1:PhQ89w4i95rhgE+xedAoqous6K9X+r6aSOI2eFF7DZI= github.com/pterm/pterm v0.12.29/go.mod h1:WI3qxgvoQFFGKGjGnJR849gU0TsEOvKn5Q8LlY1U7lg= github.com/pterm/pterm v0.12.30/go.mod h1:MOqLIyMOgmTDz9yorcYbcw+HsgoZo3BQfg2wtl3HEFE= github.com/pterm/pterm v0.12.31/go.mod h1:32ZAWZVXD7ZfG0s8qqHXePte42kdz8ECtRyEejaWgXU= -github.com/pterm/pterm v0.12.33 h1:XiT50Pvdqn5O8FAiIqZMpXP6NkVEcmlUa+mkA1yWVCg= github.com/pterm/pterm v0.12.33/go.mod h1:x+h2uL+n7CP/rel9+bImHD5lF3nM9vJj80k9ybiiTTE= -github.com/rivo/uniseg v0.2.0 h1:S1pD9weZBuJdFmowNwbpi7BJ8TNftyUImj/0WQi72jY= +github.com/pterm/pterm v0.12.36/go.mod h1:NjiL09hFhT/vWjQHSj1athJpx6H8cjpHXNAK5bUw8T8= +github.com/pterm/pterm v0.12.40/go.mod h1:ffwPLwlbXxP+rxT0GsgDTzS3y3rmpAO1NMjUkGTYf8s= +github.com/pterm/pterm v0.12.79 h1:lH3yrYMhdpeqX9y5Ep1u7DejyHy7NSQg9qrBjF9dFT4= +github.com/pterm/pterm v0.12.79/go.mod h1:1v/gzOF1N0FsjbgTHZ1wVycRkKiatFvJSJC4IGaQAAo= github.com/rivo/uniseg v0.2.0/go.mod h1:J6wj4VEh+S6ZtnVlnTBMWIodfgj8LQOQFoIToxlJtxc= -github.com/sirupsen/logrus v1.8.1 h1:dJKuHgqk1NNQlqoA6BTlM1Wf9DOH3NBjQyu0h9+AZZE= -github.com/sirupsen/logrus v1.8.1/go.mod h1:yWOB1SBYBC5VeMP7gHvWumXLIWorT60ONWic61uBYv0= +github.com/rivo/uniseg v0.4.4 h1:8TfxU8dW6PdqD27gjM8MVNuicgxIjxpm4K7x4jp8sis= +github.com/rivo/uniseg v0.4.4/go.mod h1:FN3SvrM+Zdj16jyLfmOkMNblXMcoc8DfTHruCPUcx88= +github.com/sergi/go-diff v1.2.0 h1:XU+rvMAioB0UC3q1MFrIQy4Vo5/4VsRDQQXHsEya6xQ= +github.com/sergi/go-diff v1.2.0/go.mod h1:STckp+ISIX8hZLjrqAeVduY0gWCT9IjLuqbuNXdaHfM= +github.com/sirupsen/logrus v1.9.3 h1:dueUQJ1C2q9oE3F7wvmSGAaVtTmUizReu6fjN8uqzbQ= +github.com/sirupsen/logrus v1.9.3/go.mod h1:naHLuLoDiP4jHNo9R0sCBMtWGeIprob74mVsIT4qYEQ= github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= -github.com/stretchr/testify v1.2.2/go.mod h1:a8OnRcib4nhh0OaRAV+Yts87kKdq0PP7pXfy6kDkUVs= +github.com/stretchr/testify v1.4.0/go.mod h1:j7eGeouHqKxXV5pUuKE4zz7dFj8WfuZ+81PSLYec5m4= github.com/stretchr/testify v1.6.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= -github.com/stretchr/testify v1.7.0 h1:nwc3DEeHmmLAfoZucVR881uASk0Mfjw8xYJ99tb5CcY= github.com/stretchr/testify v1.7.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= -github.com/xo/terminfo v0.0.0-20210125001918-ca9a967f8778 h1:QldyIu/L63oPpyvQmHgvgickp1Yw510KJOqX7H24mg8= +github.com/stretchr/testify v1.8.4 h1:CcVxjf3Q8PM0mHUKJCdn+eZZtm5yQwehR5yeSVQQcUk= +github.com/stretchr/testify v1.8.4/go.mod h1:sz/lmYIOXD/1dqDmKjjqLyZ2RngseejIcXlSw2iwfAo= github.com/xo/terminfo v0.0.0-20210125001918-ca9a967f8778/go.mod h1:2MuV+tbUrU1zIOPMxZ5EncGwgmMJsa+9ucAQZXxsObs= -golang.org/x/sys v0.0.0-20191026070338-33540a1f6037/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +github.com/xo/terminfo v0.0.0-20220910002029-abceb7e1c41e h1:JVG44RsyaB9T2KIHavMF/ppJZNG9ZpyihvCd0w101no= +github.com/xo/terminfo v0.0.0-20220910002029-abceb7e1c41e/go.mod h1:RbqR21r5mrJuqunuUZ/Dhy/avygyECGrLceyNeo4LiM= +github.com/yuin/goldmark v1.4.13/go.mod h1:6yULJ656Px+3vBD8DxQVa3kxgyrAnzto9xy5taEt/CY= +golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w= +golang.org/x/crypto v0.0.0-20210921155107-089bfa567519/go.mod h1:GvvjBRRGRdwPK5ydBHafDWAxML/pGHZbMvKqRZ5+Abc= +golang.org/x/exp v0.0.0-20220909182711-5c715a9e8561 h1:MDc5xs78ZrZr3HMQugiXOAkSZtfTpbJLDr/lwfgO53E= +golang.org/x/exp v0.0.0-20220909182711-5c715a9e8561/go.mod h1:cyybsKvd6eL0RnXn6p/Grxp8F5bW7iYuBgsNCOHpMYE= +golang.org/x/mod v0.6.0-dev.0.20220419223038-86c51ed26bb4/go.mod h1:jJ57K6gSWd91VN4djpZkiMVwK6gcyfeH4XE8wZrZaV4= +golang.org/x/mod v0.8.0/go.mod h1:iBbtSCu2XBx23ZKBPSOrRkjjQPZFPuis4dIYUhu/chs= +golang.org/x/mod v0.18.0 h1:5+9lSbEzPSdWkH32vYPBwEpX8KwDbM52Ud9xBUvNlb0= +golang.org/x/mod v0.18.0/go.mod h1:hTbmBsO62+eylJbnUtE2MGJUyE7QWk4xUqPFrRgJ+7c= +golang.org/x/net v0.0.0-20190620200207-3b0461eec859/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= +golang.org/x/net v0.0.0-20210226172049-e18ecbb05110/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg= +golang.org/x/net v0.0.0-20220722155237-a158d28d115b/go.mod h1:XRhObCWvk6IyKnWLug+ECip1KBveYUHfp+8e9klMJ9c= +golang.org/x/net v0.6.0/go.mod h1:2Tu9+aMcznHK/AK1HMvgo6xiTLG5rD5rZLDS+rp2Bjs= +golang.org/x/net v0.27.0 h1:5K3Njcw06/l2y9vpGCSdcxWOYHOUk3dVNGDXN+FvAys= +golang.org/x/net v0.27.0/go.mod h1:dDi0PyhWNoiUOrAS8uXv/vnScO4wnHQO4mj9fn/RytE= +golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= +golang.org/x/sync v0.0.0-20220722155255-886fb9371eb4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= +golang.org/x/sync v0.1.0/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= +golang.org/x/sync v0.7.0 h1:YsImfSBoP9QPYL0xyKJPq0gcaJdG3rInoqxTWbfQu9M= +golang.org/x/sync v0.7.0/go.mod h1:Czt+wKu1gCyEFDUtn0jG5QVvpJ6rzVqr5aXyt9drQfk= +golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20210124154548-22da62e12c0c/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210330210617-4fbd30eecc44/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210615035016-665e8c7367d1/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/sys v0.0.0-20211013075003-97ac67df715c h1:taxlMj0D/1sOAuv/CbSD+MMDof2vbyPTqz5FNYKpXt8= golang.org/x/sys v0.0.0-20211013075003-97ac67df715c/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20220319134239-a9b59b0215f8/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20220520151302-bc2c85ada10a/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20220715151400-c0bba94af5f8/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20220722155257-8c9f86f7a55f/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.5.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.22.0 h1:RI27ohtqKCnwULzJLqkv897zojh5/DwS/ENaMzUOaWI= +golang.org/x/sys v0.22.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= +golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo= golang.org/x/term v0.0.0-20210220032956-6a3ed077a48d/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo= golang.org/x/term v0.0.0-20210615171337-6886f2dfbf5b/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8= -golang.org/x/term v0.0.0-20210927222741-03fcf44c2211 h1:JGgROgKl9N8DuW20oFS5gxc+lE67/N3FcwmBPMe7ArY= golang.org/x/term v0.0.0-20210927222741-03fcf44c2211/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8= +golang.org/x/term v0.5.0/go.mod h1:jMB1sMXY+tzblOD4FWmEbocvup2/aLOaQEp7JmGp78k= +golang.org/x/term v0.22.0 h1:BbsgPEJULsl2fV/AT3v15Mjva5yXKQDyKf+TbDz7QJk= +golang.org/x/term v0.22.0/go.mod h1:F3qCibpT5AMpCRfhfT53vVJwhLtIVHhB9XDjfFvnMI4= +golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= +golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= +golang.org/x/text v0.3.7/go.mod h1:u+2+/6zg+i71rQMx5EYifcz6MCKuco9NR6JIITiCfzQ= +golang.org/x/text v0.7.0/go.mod h1:mrYo+phRRbMaCq/xk9113O4dZlRixOauAjOtrjsXDZ8= +golang.org/x/text v0.9.0/go.mod h1:e1OnstbJyHTd6l/uOt8jFFHp6TRDWZR/bV3emEE/zU8= +golang.org/x/text v0.16.0 h1:a94ExnEXNtEwYLGJSIUxnWoxoRz/ZcCsV63ROupILh4= +golang.org/x/text v0.16.0/go.mod h1:GhwF1Be+LQoKShO3cGOHzqOgRrGaYc9AvblQOmPVHnI= +golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= +golang.org/x/tools v0.0.0-20191119224855-298f0cb1881e/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= +golang.org/x/tools v0.1.12/go.mod h1:hNGJHUnrk76NpqgfD5Aqm5Crs+Hm0VOH/i9J2+nxYbc= +golang.org/x/tools v0.6.0/go.mod h1:Xwgl3UAJ/d3gWutnCtw505GrjyAbvKui8lOU390QaIU= +golang.org/x/tools v0.22.0 h1:gqSGLZqv+AI9lIQzniJ0nZDRG5GBPsSi+DRNHWNz6yA= +golang.org/x/tools v0.22.0/go.mod h1:aCwcsjqvq7Yqt6TNyX7QMU2enbQ/Gt0bo6krSeEri+c= +golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= +gopkg.in/check.v1 v1.0.0-20190902080502-41f04d3bba15/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= +gopkg.in/yaml.v2 v2.2.2/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= +gopkg.in/yaml.v2 v2.2.4/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= -gopkg.in/yaml.v3 v3.0.0-20210107192922-496545a6307b h1:h8qDotaEPuJATrMmW04NCwg7v22aHH28wwpauUhK9Oo= gopkg.in/yaml.v3 v3.0.0-20210107192922-496545a6307b/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= +gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA= +gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= diff --git a/net/conn.go b/net/conn.go index 21f0267..e152854 100644 --- a/net/conn.go +++ b/net/conn.go @@ -7,7 +7,7 @@ import ( "time" log "github.com/sirupsen/logrus" - "github.com/xvzc/SpoofDPI/doh" + "github.com/xvzc/SpoofDPI/dns" "github.com/xvzc/SpoofDPI/packet" ) @@ -59,18 +59,16 @@ func (conn *Conn) ReadBytes() ([]byte, error) { return ret, nil } -func (lConn *Conn) HandleHttp(p *packet.HttpPacket, timeout int) { +func (lConn *Conn) HandleHttp(p *packet.HttpPacket, timeout int, resolver *dns.DnsResolver) { p.Tidy() - ip, err := doh.Lookup(p.Domain()) + ip, err := resolver.Lookup(p.Domain()) if err != nil { - log.Error("[HTTP DOH] Error looking up for domain with ", p.Domain(), " ", err) + log.Error("[HTTP] Error looking up for domain with ", p.Domain(), " ", err) lConn.Write([]byte(p.Version() + " 502 Bad Gateway\r\n\r\n")) return } - log.Debug("[DOH] Found ", ip, " with ", p.Domain()) - // Create connection to server var port = "80" if p.Port() != "" { @@ -107,16 +105,15 @@ func (lConn *Conn) HandleHttp(p *packet.HttpPacket, timeout int) { } -func (lConn *Conn) HandleHttps(p *packet.HttpPacket, timeout int) { - ip, err := doh.Lookup(p.Domain()) +func (lConn *Conn) HandleHttps(p *packet.HttpPacket, timeout int, resolver *dns.DnsResolver) { + ip, err := resolver.Lookup(p.Domain()) + if err != nil { - log.Error("[HTTPS DOH] Error looking up for domain: ", p.Domain(), " ", err) + log.Error("[HTTPS] Error looking up for domain: ", p.Domain(), " ", err) lConn.Write([]byte(p.Version() + " 502 Bad Gateway\r\n\r\n")) return } - log.Debug("[DOH] Found ", ip, " with ", p.Domain()) - // Create a connection to the requested server var port = "443" if p.Port() != "" { diff --git a/proxy/proxy.go b/proxy/proxy.go index 88c8b97..7831f41 100644 --- a/proxy/proxy.go +++ b/proxy/proxy.go @@ -5,6 +5,7 @@ import ( "os" log "github.com/sirupsen/logrus" + "github.com/xvzc/SpoofDPI/dns" "github.com/xvzc/SpoofDPI/net" "github.com/xvzc/SpoofDPI/packet" "github.com/xvzc/SpoofDPI/util" @@ -14,6 +15,7 @@ type Proxy struct { addr string port int timeout int + resolver *dns.DnsResolver } func New(config *util.Config) *Proxy { @@ -21,6 +23,7 @@ func New(config *util.Config) *Proxy { addr: *config.Addr, port: *config.Port, timeout: *config.Timeout, + resolver: dns.NewResolver(config), } } @@ -39,7 +42,7 @@ func (p *Proxy) Start() { os.Exit(1) } - log.Println(fmt.Sprintf("Connection timeout is set to %dms", p.timeout)) + log.Println(fmt.Sprintf("Connection timeout is set to %dms", p.timeout)) log.Println("Created a listener on port", p.Port()) @@ -71,10 +74,10 @@ func (p *Proxy) Start() { if pkt.IsConnectMethod() { log.Debug("[HTTPS] Start") - conn.HandleHttps(pkt, p.timeout) + conn.HandleHttps(pkt, p.timeout, p.resolver) } else { log.Debug("[HTTP] Start") - conn.HandleHttp(pkt, p.timeout) + conn.HandleHttp(pkt, p.timeout, p.resolver) } }() } diff --git a/util/config.go b/util/config.go index be42f35..fc42647 100644 --- a/util/config.go +++ b/util/config.go @@ -13,9 +13,11 @@ import ( type Config struct { Addr *string Port *int - Dns *string + DnsAddr *string + DnsPort *string + EnableDoh *bool Debug *bool - NoBanner *bool + NoBanner *bool Timeout *int AllowedPattern *regexp.Regexp AllowedUrls *regexp.Regexp @@ -53,7 +55,9 @@ func ParseArgs() { config = &Config{} config.Addr = flag.String("addr", "127.0.0.1", "Listen addr") config.Port = flag.Int("port", 8080, "port") - config.Dns = flag.String("dns", "8.8.8.8", "DNS server") + config.DnsAddr = flag.String("dns-addr", "8.8.8.8", "DNS addr") + config.DnsPort = flag.String("dns-port", "53", "DNS port") + config.EnableDoh = flag.Bool("enable-doh", false, "Enable DOH") config.Debug = flag.Bool("debug", false, "true | false") config.NoBanner = flag.Bool("no-banner", false, "true | false") config.Timeout = flag.Int("timeout", 2000, "timeout in milliseconds") @@ -90,7 +94,7 @@ func PrintColoredBanner() { pterm.DefaultBulletList.WithItems([]pterm.BulletListItem{ {Level: 0, Text: "ADDR : " + fmt.Sprint(*config.Addr)}, {Level: 0, Text: "PORT : " + fmt.Sprint(*config.Port)}, - {Level: 0, Text: "DNS : " + fmt.Sprint(*config.Dns)}, + {Level: 0, Text: "DNS : " + fmt.Sprint(*config.DnsAddr)}, {Level: 0, Text: "DEBUG : " + fmt.Sprint(*config.Debug)}, }).Render() @@ -107,7 +111,7 @@ func PrintSimpleInfo() { fmt.Println("") fmt.Println("- ADDR : ", *config.Addr) fmt.Println("- PORT : ", *config.Port) - fmt.Println("- DNS : ", *config.Dns) + fmt.Println("- DNS : ", *config.DnsAddr) fmt.Println("- DEBUG : ", *config.Debug) fmt.Println("") } From d150d03a672d9893975c09648691a5797e2d6058 Mon Sep 17 00:00:00 2001 From: xvzc Date: Sun, 21 Jul 2024 17:12:16 +0900 Subject: [PATCH 2/4] fix type for dns port --- dns/dns.go | 3 ++- util/config.go | 9 +++++---- 2 files changed, 7 insertions(+), 5 deletions(-) diff --git a/dns/dns.go b/dns/dns.go index 1b15c63..7ee0c77 100644 --- a/dns/dns.go +++ b/dns/dns.go @@ -5,6 +5,7 @@ import ( "errors" "regexp" "time" + "strconv" "github.com/likexian/doh" dohDns "github.com/likexian/doh/dns" @@ -22,7 +23,7 @@ type DnsResolver struct { func NewResolver(config *util.Config) *DnsResolver { return &DnsResolver{ host: *config.DnsAddr, - port: *config.DnsPort, + port: strconv.Itoa(*config.DnsPort), enableDoh: *config.EnableDoh, } } diff --git a/util/config.go b/util/config.go index fc42647..05fb9d5 100644 --- a/util/config.go +++ b/util/config.go @@ -7,6 +7,7 @@ import ( "strings" "github.com/pterm/pterm" + "github.com/pterm/pterm/putils" log "github.com/sirupsen/logrus" ) @@ -14,7 +15,7 @@ type Config struct { Addr *string Port *int DnsAddr *string - DnsPort *string + DnsPort *int EnableDoh *bool Debug *bool NoBanner *bool @@ -56,7 +57,7 @@ func ParseArgs() { config.Addr = flag.String("addr", "127.0.0.1", "Listen addr") config.Port = flag.Int("port", 8080, "port") config.DnsAddr = flag.String("dns-addr", "8.8.8.8", "DNS addr") - config.DnsPort = flag.String("dns-port", "53", "DNS port") + config.DnsPort = flag.Int("dns-port", 53, "DNS port") config.EnableDoh = flag.Bool("enable-doh", false, "Enable DOH") config.Debug = flag.Bool("debug", false, "true | false") config.NoBanner = flag.Bool("no-banner", false, "true | false") @@ -87,8 +88,8 @@ func ParseArgs() { } func PrintColoredBanner() { - cyan := pterm.NewLettersFromStringWithStyle("Spoof", pterm.NewStyle(pterm.FgCyan)) - purple := pterm.NewLettersFromStringWithStyle("DPI", pterm.NewStyle(pterm.FgLightMagenta)) + cyan := putils.LettersFromStringWithStyle("Spoof", pterm.NewStyle(pterm.FgCyan)) + purple := putils.LettersFromStringWithStyle("DPI", pterm.NewStyle(pterm.FgLightMagenta)) pterm.DefaultBigText.WithLetters(cyan, purple).Render() pterm.DefaultBulletList.WithItems([]pterm.BulletListItem{ From 97e6cd6355aa989d9511507332d66bd301dbd40e Mon Sep 17 00:00:00 2001 From: xvzc Date: Sun, 21 Jul 2024 17:17:45 +0900 Subject: [PATCH 3/4] update help output --- util/config.go | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/util/config.go b/util/config.go index 05fb9d5..57e82ca 100644 --- a/util/config.go +++ b/util/config.go @@ -59,8 +59,8 @@ func ParseArgs() { config.DnsAddr = flag.String("dns-addr", "8.8.8.8", "DNS addr") config.DnsPort = flag.Int("dns-port", 53, "DNS port") config.EnableDoh = flag.Bool("enable-doh", false, "Enable DOH") - config.Debug = flag.Bool("debug", false, "true | false") - config.NoBanner = flag.Bool("no-banner", false, "true | false") + config.Debug = flag.Bool("debug", false, "Enable debug output") + config.NoBanner = flag.Bool("no-banner", false, "Disable banner") config.Timeout = flag.Int("timeout", 2000, "timeout in milliseconds") flag.Var(&allowedHosts, "url", "Bypass DPI only on this url, can be passed multiple times") From b536597063733b8991dffe6fdec75727a68ff218 Mon Sep 17 00:00:00 2001 From: xvzc Date: Sun, 21 Jul 2024 17:21:56 +0900 Subject: [PATCH 4/4] update readme --- readme.md | 34 +++++++++++++++++++++------------- readme_ko.md | 34 +++++++++++++++++++++------------- readme_ru.md | 34 +++++++++++++++++++++------------- readme_zh-cn.md | 34 +++++++++++++++++++++------------- 4 files changed, 84 insertions(+), 52 deletions(-) diff --git a/readme.md b/readme.md index 042fd73..f8f983e 100644 --- a/readme.md +++ b/readme.md @@ -50,19 +50,27 @@ You can also build your own # Usage ``` Usage: spoof-dpi [options...] ---addr= | default: 127.0.0.1 ---dns= | default: 8.8.8.8 ---port= | default: 8080 ---debug= | default: false ---no-banner= | default: false ---timeout= | default: 0 - | Enforces specific connection timeout. Set 0 to turn off ---url= | Can be used multiple times. If set, - | it will bypass DPI only for this url. - | Example: --url=google.com --url=github.com ---pattern= | If set, it will bypass DPI only for packets - | that matches this regex pattern. - | Example: --pattern="google|github" + -addr string + Listen addr (default "127.0.0.1") + -debug + Enable debug output + -dns-addr string + DNS addr (default "8.8.8.8") + -dns-port int + DNS port (default 53) + -enable-doh + Enable DOH + -no-banner + Disable banner + -pattern string + Bypass DPI only on packets matching this regex pattern + -port int + port (default 8080) + -timeout int + timeout in milliseconds (default 2000) + -url value + Bypass DPI only on this url, can be passed multiple times + ``` > If you are using any vpn extensions such as Hotspot Shield in Chrome browser, go to Settings > Extensions, and disable them. diff --git a/readme_ko.md b/readme_ko.md index c6c9120..110c5db 100644 --- a/readme_ko.md +++ b/readme_ko.md @@ -50,19 +50,27 @@ wget -O - https://raw.githubusercontent.com/xvzc/SpoofDPI/main/install.sh | bash # 사용법 ``` Usage: spoof-dpi [options...] ---addr= | default: 127.0.0.1 ---dns= | default: 8.8.8.8 ---port= | default: 8080 ---debug= | default: false ---no-banner= | default: false ---timeout= | default: 0 - | Enforces specific connection timeout. Set 0 to turn off ---url= | Can be used multiple times. If set, - | it will bypass DPI only for this url. - | Example: --url=google.com --url=github.com ---pattern= | If set, it will bypass DPI only for packets - | that matches this regex pattern. - | Example: --pattern="google|github" + -addr string + Listen addr (default "127.0.0.1") + -debug + Enable debug output + -dns-addr string + DNS addr (default "8.8.8.8") + -dns-port int + DNS port (default 53) + -enable-doh + Enable DOH + -no-banner + Disable banner + -pattern string + Bypass DPI only on packets matching this regex pattern + -port int + port (default 8080) + -timeout int + timeout in milliseconds (default 2000) + -url value + Bypass DPI only on this url, can be passed multiple times + ``` > 만약 브라우저에서 Hotspot Shield와 같은 크롬 VPN 확장프로그램을 사용중이라면 Settings > Extension 으로 이동해 비활성화 해주시기바랍니다. diff --git a/readme_ru.md b/readme_ru.md index d187793..2a3ddf8 100644 --- a/readme_ru.md +++ b/readme_ru.md @@ -51,19 +51,27 @@ wget -O - https://raw.githubusercontent.com/xvzc/SpoofDPI/main/install.sh | bash # Использование ``` Usage: spoof-dpi [options...] ---addr= | default: 127.0.0.1 ---dns= | default: 8.8.8.8 ---port= | default: 8080 ---debug= | default: false ---no-banner= | default: false ---timeout= | default: 0 - | Enforces specific connection timeout. Set 0 to turn off ---url= | Can be used multiple times. If set, - | it will bypass DPI only for this url. - | Example: --url=google.com --url=github.com ---pattern= | If set, it will bypass DPI only for packets - | that matches this regex pattern. - | Example: --pattern="google|github" + -addr string + Listen addr (default "127.0.0.1") + -debug + Enable debug output + -dns-addr string + DNS addr (default "8.8.8.8") + -dns-port int + DNS port (default 53) + -enable-doh + Enable DOH + -no-banner + Disable banner + -pattern string + Bypass DPI only on packets matching this regex pattern + -port int + port (default 8080) + -timeout int + timeout in milliseconds (default 2000) + -url value + Bypass DPI only on this url, can be passed multiple times + ``` **Перевод:** ``` diff --git a/readme_zh-cn.md b/readme_zh-cn.md index c22793c..8f9d528 100644 --- a/readme_zh-cn.md +++ b/readme_zh-cn.md @@ -57,19 +57,27 @@ You can also build your own ``` Usage: spoof-dpi [options...] ---addr= | default: 127.0.0.1 ---dns= | default: 8.8.8.8 ---port= | default: 8080 ---debug= | default: false ---no-banner= | default: false ---timeout= | default: 0 - | Enforces specific connection timeout. Set 0 to turn off ---url= | Can be used multiple times. If set, - | it will bypass DPI only for this url. - | Example: --url=google.com --url=github.com ---pattern= | If set, it will bypass DPI only for packets - | that matches this regex pattern. - | Example: --pattern="google|github" + -addr string + Listen addr (default "127.0.0.1") + -debug + Enable debug output + -dns-addr string + DNS addr (default "8.8.8.8") + -dns-port int + DNS port (default 53) + -enable-doh + Enable DOH + -no-banner + Disable banner + -pattern string + Bypass DPI only on packets matching this regex pattern + -port int + port (default 8080) + -timeout int + timeout in milliseconds (default 2000) + -url value + Bypass DPI only on this url, can be passed multiple times + ``` > 如果你在 Chrome 浏览器使用其他 VPN 扩展比如 Hotspot Shield 请去 设置 > 扩展程序禁用它们