@@ -27,6 +27,7 @@ import (
27
27
"github.com/decred/dcrd/gcs/v3"
28
28
blockcf "github.com/decred/dcrd/gcs/v3/blockcf2"
29
29
"github.com/decred/dcrd/wire"
30
+ "github.com/decred/go-socks/socks"
30
31
"golang.org/x/sync/errgroup"
31
32
)
32
33
@@ -125,7 +126,7 @@ type LocalPeer struct {
125
126
atomicPeerIDCounter uint64
126
127
atomicRequireHeight int32
127
128
128
- dialer net. Dialer
129
+ dial DialFunc
129
130
130
131
receivedGetData chan * inMsg
131
132
receivedHeaders chan * inMsg
@@ -143,7 +144,9 @@ type LocalPeer struct {
143
144
// NewLocalPeer creates a LocalPeer that is externally reachable to remote peers
144
145
// through extaddr.
145
146
func NewLocalPeer (params * chaincfg.Params , extaddr * net.TCPAddr , amgr * addrmgr.AddrManager ) * LocalPeer {
147
+ var dialer net.Dialer
146
148
lp := & LocalPeer {
149
+ dial : dialer .DialContext ,
147
150
receivedGetData : make (chan * inMsg ),
148
151
receivedHeaders : make (chan * inMsg ),
149
152
receivedInv : make (chan * inMsg ),
@@ -156,12 +159,46 @@ func NewLocalPeer(params *chaincfg.Params, extaddr *net.TCPAddr, amgr *addrmgr.A
156
159
return lp
157
160
}
158
161
159
- func (lp * LocalPeer ) newMsgVersion (pver uint32 , extaddr net.Addr , c net.Conn ) (* wire.MsgVersion , error ) {
160
- la , err := wire .NewNetAddress (c .LocalAddr (), 0 ) // We provide no services
161
- if err != nil {
162
- return nil , err
162
+ // DialFunc provides a method to dial a network connection.
163
+ type DialFunc func (ctx context.Context , net , addr string ) (net.Conn , error )
164
+
165
+ // SetDialFunc sets the function used to dial peer and seeder connections.
166
+ func (lp * LocalPeer ) SetDialFunc (dial DialFunc ) {
167
+ lp .dial = dial
168
+ }
169
+
170
+ func isCGNAT (ip net.IP ) bool {
171
+ if ip4 := ip .To4 (); ip4 != nil {
172
+ return ip4 [0 ] == 100 && ip4 [1 ]& 0xc0 == 64 // 100.64.0.0/10
173
+ }
174
+ return false
175
+ }
176
+
177
+ func newNetAddress (addr net.Addr , services wire.ServiceFlag ) (* wire.NetAddress , error ) {
178
+ var ip net.IP
179
+ var port uint16
180
+ switch a := addr .(type ) {
181
+ case * net.TCPAddr :
182
+ ip = a .IP
183
+ port = uint16 (a .Port )
184
+ case * socks.ProxiedAddr :
185
+ ip = net .ParseIP (a .Host )
186
+ port = uint16 (a .Port )
187
+ default :
188
+ return nil , fmt .Errorf ("newNetAddress: unsupported address " +
189
+ "type %T" , addr )
163
190
}
164
- ra , err := wire .NewNetAddress (c .RemoteAddr (), 0 )
191
+ switch {
192
+ case ip .IsLoopback (), ip .IsPrivate (), ! ip .IsGlobalUnicast (), isCGNAT (ip ):
193
+ ip = nil
194
+ port = 0
195
+ }
196
+ return wire .NewNetAddressIPPort (ip , port , services ), nil
197
+ }
198
+
199
+ func (lp * LocalPeer ) newMsgVersion (pver uint32 , c net.Conn ) (* wire.MsgVersion , error ) {
200
+ la := new (wire.NetAddress )
201
+ ra , err := newNetAddress (c .RemoteAddr (), 0 )
165
202
if err != nil {
166
203
return nil , err
167
204
}
@@ -302,7 +339,7 @@ func (lp *LocalPeer) SeedPeers(ctx context.Context, services wire.ServiceFlag) {
302
339
resps := make (chan * http.Response )
303
340
client := http.Client {
304
341
Transport : & http.Transport {
305
- DialContext : lp .dialer . DialContext ,
342
+ DialContext : lp .dial ,
306
343
},
307
344
}
308
345
cancels := make ([]func (), 0 , len (seeders ))
@@ -479,7 +516,7 @@ func handshake(ctx context.Context, lp *LocalPeer, id uint64, na *addrmgr.NetAdd
479
516
mw := msgWriter {c , lp .chainParams .Net }
480
517
481
518
// The first message sent must be the version message.
482
- lversion , err := lp .newMsgVersion (rp .pver , lp . extaddr , c )
519
+ lversion , err := lp .newMsgVersion (rp .pver , c )
483
520
if err != nil {
484
521
return nil , errors .E (op , err )
485
522
}
@@ -539,7 +576,7 @@ func (lp *LocalPeer) connectOutbound(ctx context.Context, id uint64, addr string
539
576
540
577
// Dial with a timeout of 10 seconds.
541
578
dialCtx , cancel := context .WithTimeout (ctx , 10 * time .Second )
542
- c , err = lp .dialer . DialContext (dialCtx , "tcp" , addr )
579
+ c , err = lp .dial (dialCtx , "tcp" , addr )
543
580
cancel ()
544
581
if err == nil {
545
582
break
0 commit comments