-
-
Notifications
You must be signed in to change notification settings - Fork 628
/
config.go
255 lines (229 loc) · 10.3 KB
/
config.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
package torrent
import (
"context"
"net"
"net/http"
"net/url"
"time"
"github.com/anacrolix/dht/v2"
"github.com/anacrolix/dht/v2/krpc"
"github.com/anacrolix/log"
"github.com/anacrolix/missinggo/v2"
"github.com/pion/webrtc/v4"
"golang.org/x/time/rate"
"github.com/anacrolix/torrent/iplist"
"github.com/anacrolix/torrent/mse"
"github.com/anacrolix/torrent/storage"
"github.com/anacrolix/torrent/version"
)
// Contains config elements that are exclusive to tracker handling. There may be other fields in
// ClientConfig that are also relevant.
type ClientTrackerConfig struct {
// Don't announce to trackers. This only leaves DHT to discover peers.
DisableTrackers bool `long:"disable-trackers"`
// Defines DialContext func to use for HTTP tracker announcements
TrackerDialContext func(ctx context.Context, network, addr string) (net.Conn, error)
// Defines ListenPacket func to use for UDP tracker announcements
TrackerListenPacket func(network, addr string) (net.PacketConn, error)
// Takes a tracker's hostname and requests DNS A and AAAA records.
// Used in case DNS lookups require a special setup (i.e., dns-over-https)
LookupTrackerIp func(*url.URL) ([]net.IP, error)
}
type ClientDhtConfig struct {
// Don't create a DHT.
NoDHT bool `long:"disable-dht"`
DhtStartingNodes func(network string) dht.StartingNodesGetter
// Called for each anacrolix/dht Server created for the Client.
ConfigureAnacrolixDhtServer func(*dht.ServerConfig)
PeriodicallyAnnounceTorrentsToDht bool
// OnQuery hook func
DHTOnQuery func(query *krpc.Msg, source net.Addr) (propagate bool)
}
// Probably not safe to modify this after it's given to a Client.
type ClientConfig struct {
ClientTrackerConfig
ClientDhtConfig
// Store torrent file data in this directory unless .DefaultStorage is
// specified.
DataDir string `long:"data-dir" description:"directory to store downloaded torrent data"`
// The address to listen for new uTP and TCP BitTorrent protocol connections. DHT shares a UDP
// socket with uTP unless configured otherwise.
ListenHost func(network string) string
ListenPort int
NoDefaultPortForwarding bool
UpnpID string
DisablePEX bool `long:"disable-pex"`
// Never send chunks to peers.
NoUpload bool `long:"no-upload"`
// Disable uploading even when it isn't fair.
DisableAggressiveUpload bool `long:"disable-aggressive-upload"`
// Upload even after there's nothing in it for us. By default uploading is
// not altruistic, we'll only upload to encourage the peer to reciprocate.
Seed bool `long:"seed"`
// Only applies to chunks uploaded to peers, to maintain responsiveness
// communicating local Client state to peers. Each limiter token
// represents one byte. The Limiter's burst must be large enough to fit a
// whole chunk, which is usually 16 KiB (see TorrentSpec.ChunkSize).
UploadRateLimiter *rate.Limiter
// Rate limits all reads from connections to peers. Each limiter token
// represents one byte. The Limiter's burst must be bigger than the
// largest Read performed on a the underlying rate-limiting io.Reader
// minus one. This is likely to be the larger of the main read loop buffer
// (~4096), and the requested chunk size (~16KiB, see
// TorrentSpec.ChunkSize).
DownloadRateLimiter *rate.Limiter
// Maximum unverified bytes across all torrents. Not used if zero.
MaxUnverifiedBytes int64
// User-provided Client peer ID. If not present, one is generated automatically.
PeerID string
// For the bittorrent protocol.
DisableUTP bool
// For the bittorrent protocol.
DisableTCP bool `long:"disable-tcp"`
// Called to instantiate storage for each added torrent. Builtin backends
// are in the storage package. If not set, the "file" implementation is
// used (and Closed when the Client is Closed).
DefaultStorage storage.ClientImpl
HeaderObfuscationPolicy HeaderObfuscationPolicy
// The crypto methods to offer when initiating connections with header obfuscation.
CryptoProvides mse.CryptoMethod
// Chooses the crypto method to use when receiving connections with header obfuscation.
CryptoSelector mse.CryptoSelector
IPBlocklist iplist.Ranger
DisableIPv6 bool `long:"disable-ipv6"`
DisableIPv4 bool
DisableIPv4Peers bool
// Perform logging and any other behaviour that will help debug.
Debug bool `help:"enable debugging"`
Logger log.Logger
// Used for torrent sources and webseeding if set.
WebTransport http.RoundTripper
// Defines proxy for HTTP requests, such as for trackers. It's commonly set from the result of
// "net/http".ProxyURL(HTTPProxy).
HTTPProxy func(*http.Request) (*url.URL, error)
// Defines DialContext func to use for HTTP requests, such as for fetching metainfo and webtorrent seeds
HTTPDialContext func(ctx context.Context, network, addr string) (net.Conn, error)
// HTTPUserAgent changes default UserAgent for HTTP requests
HTTPUserAgent string
// HttpRequestDirector modifies the request before it's sent.
// Useful for adding authentication headers, for example
HttpRequestDirector func(*http.Request) error
// WebsocketTrackerHttpHeader returns a custom header to be used when dialing a websocket connection
// to the tracker. Useful for adding authentication headers
WebsocketTrackerHttpHeader func() http.Header
// Updated occasionally to when there's been some changes to client
// behaviour in case other clients are assuming anything of us. See also
// `bep20`.
ExtendedHandshakeClientVersion string
// Peer ID client identifier prefix. We'll update this occasionally to
// reflect changes to client behaviour that other clients may depend on.
// Also see `extendedHandshakeClientVersion`.
Bep20 string
// Peer dial timeout to use when there are limited peers.
NominalDialTimeout time.Duration
// Minimum peer dial timeout to use (even if we have lots of peers).
MinDialTimeout time.Duration
EstablishedConnsPerTorrent int
HalfOpenConnsPerTorrent int
TotalHalfOpenConns int
// Maximum number of peer addresses in reserve.
TorrentPeersHighWater int
// Minumum number of peers before effort is made to obtain more peers.
TorrentPeersLowWater int
// Limit how long handshake can take. This is to reduce the lingering
// impact of a few bad apples. 4s loses 1% of successful handshakes that
// are obtained with 60s timeout, and 5% of unsuccessful handshakes.
HandshakesTimeout time.Duration
// How long between writes before sending a keep alive message on a peer connection that we want
// to maintain.
KeepAliveTimeout time.Duration
// Maximum bytes to buffer per peer connection for peer request data before it is sent.
MaxAllocPeerRequestDataPerConn int64
// The IP addresses as our peers should see them. May differ from the
// local interfaces due to NAT or other network configurations.
PublicIp4 net.IP
PublicIp6 net.IP
// Accept rate limiting affects excessive connection attempts from IPs that fail during
// handshakes or request torrents that we don't have.
DisableAcceptRateLimiting bool
// Don't add connections that have the same peer ID as an existing
// connection for a given Torrent.
DropDuplicatePeerIds bool
// Drop peers that are complete if we are also complete and have no use for the peer. This is a
// bit of a special case, since a peer could also be useless if they're just not interested, or
// we don't intend to obtain all of a torrent's data.
DropMutuallyCompletePeers bool
// Whether to accept peer connections at all.
AcceptPeerConnections bool
// Whether a Client should want conns without delegating to any attached Torrents. This is
// useful when torrents might be added dynamically in callbacks for example.
AlwaysWantConns bool
Extensions PeerExtensionBits
// Bits that peers must have set to proceed past handshakes.
MinPeerExtensions PeerExtensionBits
DisableWebtorrent bool
DisableWebseeds bool
Callbacks Callbacks
// ICEServerList defines a slice describing servers available to be used by
// ICE, such as STUN and TURN servers.
ICEServerList []webrtc.ICEServer
// Deprecated. ICEServers does not support server authentication and therefore
// it cannot be used with most TURN servers. Use ICEServerList instead.
// ICEServers is kept for legacy support.
ICEServers []string
DialRateLimiter *rate.Limiter
PieceHashersPerTorrent int // default: 2
}
func (cfg *ClientConfig) SetListenAddr(addr string) *ClientConfig {
host, port, err := missinggo.ParseHostPort(addr)
if err != nil {
panic(err)
}
cfg.ListenHost = func(string) string { return host }
cfg.ListenPort = port
return cfg
}
func NewDefaultClientConfig() *ClientConfig {
cc := &ClientConfig{
HTTPUserAgent: version.DefaultHttpUserAgent,
ExtendedHandshakeClientVersion: version.DefaultExtendedHandshakeClientVersion,
Bep20: version.DefaultBep20Prefix,
UpnpID: version.DefaultUpnpId,
NominalDialTimeout: 20 * time.Second,
MinDialTimeout: 3 * time.Second,
EstablishedConnsPerTorrent: 50,
HalfOpenConnsPerTorrent: 25,
TotalHalfOpenConns: 100,
TorrentPeersHighWater: 500,
TorrentPeersLowWater: 50,
HandshakesTimeout: 4 * time.Second,
KeepAliveTimeout: time.Minute,
MaxAllocPeerRequestDataPerConn: 1 << 20,
ListenHost: func(string) string { return "" },
UploadRateLimiter: unlimited,
DownloadRateLimiter: unlimited,
DisableAcceptRateLimiting: true,
DropMutuallyCompletePeers: true,
HeaderObfuscationPolicy: HeaderObfuscationPolicy{
Preferred: true,
RequirePreferred: false,
},
CryptoSelector: mse.DefaultCryptoSelector,
CryptoProvides: mse.AllSupportedCrypto,
ListenPort: 42069,
Extensions: defaultPeerExtensionBytes(),
AcceptPeerConnections: true,
MaxUnverifiedBytes: 64 << 20,
DialRateLimiter: rate.NewLimiter(10, 10),
PieceHashersPerTorrent: 2,
}
cc.DhtStartingNodes = func(network string) dht.StartingNodesGetter {
return func() ([]dht.Addr, error) { return dht.GlobalBootstrapAddrs(network) }
}
cc.PeriodicallyAnnounceTorrentsToDht = true
return cc
}
type HeaderObfuscationPolicy struct {
RequirePreferred bool // Whether the value of Preferred is a strict requirement.
Preferred bool // Whether header obfuscation is preferred.
}