• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  *  Copyright 2004 The WebRTC Project Authors. All rights reserved.
3  *
4  *  Use of this source code is governed by a BSD-style license
5  *  that can be found in the LICENSE file in the root of the source
6  *  tree. An additional intellectual property rights grant can be found
7  *  in the file PATENTS.  All contributing project authors may
8  *  be found in the AUTHORS file in the root of the source tree.
9  */
10 
11 #ifndef P2P_BASE_PORT_ALLOCATOR_H_
12 #define P2P_BASE_PORT_ALLOCATOR_H_
13 
14 #include <deque>
15 #include <memory>
16 #include <string>
17 #include <vector>
18 
19 #include "api/transport/enums.h"
20 #include "p2p/base/port.h"
21 #include "p2p/base/port_interface.h"
22 #include "rtc_base/helpers.h"
23 #include "rtc_base/proxy_info.h"
24 #include "rtc_base/ssl_certificate.h"
25 #include "rtc_base/system/rtc_export.h"
26 #include "rtc_base/third_party/sigslot/sigslot.h"
27 #include "rtc_base/thread.h"
28 #include "rtc_base/thread_checker.h"
29 
30 namespace webrtc {
31 class TurnCustomizer;
32 }  // namespace webrtc
33 
34 namespace cricket {
35 
36 // PortAllocator is responsible for allocating Port types for a given
37 // P2PSocket. It also handles port freeing.
38 //
39 // Clients can override this class to control port allocation, including
40 // what kinds of ports are allocated.
41 
42 enum {
43   // Disable local UDP ports. This doesn't impact how we connect to relay
44   // servers.
45   PORTALLOCATOR_DISABLE_UDP = 0x01,
46   PORTALLOCATOR_DISABLE_STUN = 0x02,
47   PORTALLOCATOR_DISABLE_RELAY = 0x04,
48   // Disable local TCP ports. This doesn't impact how we connect to relay
49   // servers.
50   PORTALLOCATOR_DISABLE_TCP = 0x08,
51   PORTALLOCATOR_ENABLE_IPV6 = 0x40,
52   PORTALLOCATOR_ENABLE_SHARED_SOCKET = 0x100,
53   PORTALLOCATOR_ENABLE_STUN_RETRANSMIT_ATTRIBUTE = 0x200,
54   // When specified, we'll only allocate the STUN candidate for the public
55   // interface as seen by regular http traffic and the HOST candidate associated
56   // with the default local interface.
57   PORTALLOCATOR_DISABLE_ADAPTER_ENUMERATION = 0x400,
58   // When specified along with PORTALLOCATOR_DISABLE_ADAPTER_ENUMERATION, the
59   // default local candidate mentioned above will not be allocated. Only the
60   // STUN candidate will be.
61   PORTALLOCATOR_DISABLE_DEFAULT_LOCAL_CANDIDATE = 0x800,
62   // Disallow use of UDP when connecting to a relay server. Since proxy servers
63   // usually don't handle UDP, using UDP will leak the IP address.
64   PORTALLOCATOR_DISABLE_UDP_RELAY = 0x1000,
65 
66   // When multiple networks exist, do not gather candidates on the ones with
67   // high cost. So if both Wi-Fi and cellular networks exist, gather only on the
68   // Wi-Fi network. If a network type is "unknown", it has a cost lower than
69   // cellular but higher than Wi-Fi/Ethernet. So if an unknown network exists,
70   // cellular networks will not be used to gather candidates and if a Wi-Fi
71   // network is present, "unknown" networks will not be usd to gather
72   // candidates. Doing so ensures that even if a cellular network type was not
73   // detected initially, it would not be used if a Wi-Fi network is present.
74   PORTALLOCATOR_DISABLE_COSTLY_NETWORKS = 0x2000,
75 
76   // When specified, do not collect IPv6 ICE candidates on Wi-Fi.
77   PORTALLOCATOR_ENABLE_IPV6_ON_WIFI = 0x4000,
78 
79   // When this flag is set, ports not bound to any specific network interface
80   // will be used, in addition to normal ports bound to the enumerated
81   // interfaces. Without this flag, these "any address" ports would only be
82   // used when network enumeration fails or is disabled. But under certain
83   // conditions, these ports may succeed where others fail, so they may allow
84   // the application to work in a wider variety of environments, at the expense
85   // of having to allocate additional candidates.
86   PORTALLOCATOR_ENABLE_ANY_ADDRESS_PORTS = 0x8000,
87 
88   // Exclude link-local network interfaces
89   // from considertaion after adapter enumeration.
90   PORTALLOCATOR_DISABLE_LINK_LOCAL_NETWORKS = 0x10000,
91 };
92 
93 // Defines various reasons that have caused ICE regathering.
94 enum class IceRegatheringReason {
95   NETWORK_CHANGE,      // Network interfaces on the device changed
96   NETWORK_FAILURE,     // Regather only on networks that have failed
97   OCCASIONAL_REFRESH,  // Periodic regather on all networks
98   MAX_VALUE
99 };
100 
101 const uint32_t kDefaultPortAllocatorFlags = 0;
102 
103 const uint32_t kDefaultStepDelay = 1000;  // 1 sec step delay.
104 // As per RFC 5245 Appendix B.1, STUN transactions need to be paced at certain
105 // internal. Less than 20ms is not acceptable. We choose 50ms as our default.
106 const uint32_t kMinimumStepDelay = 50;
107 
108 // Turning on IPv6 could make many IPv6 interfaces available for connectivity
109 // check and delay the call setup time. kDefaultMaxIPv6Networks is the default
110 // upper limit of IPv6 networks but could be changed by
111 // set_max_ipv6_networks().
112 constexpr int kDefaultMaxIPv6Networks = 5;
113 
114 // CF = CANDIDATE FILTER
115 enum : uint32_t {
116   CF_NONE = 0x0,
117   CF_HOST = 0x1,
118   CF_REFLEXIVE = 0x2,
119   CF_RELAY = 0x4,
120   CF_ALL = 0x7,
121 };
122 
123 // TLS certificate policy.
124 enum class TlsCertPolicy {
125   // For TLS based protocols, ensure the connection is secure by not
126   // circumventing certificate validation.
127   TLS_CERT_POLICY_SECURE,
128   // For TLS based protocols, disregard security completely by skipping
129   // certificate validation. This is insecure and should never be used unless
130   // security is irrelevant in that particular context.
131   TLS_CERT_POLICY_INSECURE_NO_CHECK,
132 };
133 
134 // TODO(deadbeef): Rename to TurnCredentials (and username to ufrag).
135 struct RelayCredentials {
RelayCredentialsRelayCredentials136   RelayCredentials() {}
RelayCredentialsRelayCredentials137   RelayCredentials(const std::string& username, const std::string& password)
138       : username(username), password(password) {}
139 
140   bool operator==(const RelayCredentials& o) const {
141     return username == o.username && password == o.password;
142   }
143   bool operator!=(const RelayCredentials& o) const { return !(*this == o); }
144 
145   std::string username;
146   std::string password;
147 };
148 
149 typedef std::vector<ProtocolAddress> PortList;
150 // TODO(deadbeef): Rename to TurnServerConfig.
151 struct RTC_EXPORT RelayServerConfig {
152   RelayServerConfig();
153   RelayServerConfig(const rtc::SocketAddress& address,
154                     const std::string& username,
155                     const std::string& password,
156                     ProtocolType proto);
157   RelayServerConfig(const std::string& address,
158                     int port,
159                     const std::string& username,
160                     const std::string& password,
161                     ProtocolType proto);
162   // Legacy constructor where "secure" and PROTO_TCP implies PROTO_TLS.
163   RelayServerConfig(const std::string& address,
164                     int port,
165                     const std::string& username,
166                     const std::string& password,
167                     ProtocolType proto,
168                     bool secure);
169   RelayServerConfig(const RelayServerConfig&);
170   ~RelayServerConfig();
171 
172   bool operator==(const RelayServerConfig& o) const {
173     return ports == o.ports && credentials == o.credentials &&
174            priority == o.priority;
175   }
176   bool operator!=(const RelayServerConfig& o) const { return !(*this == o); }
177 
178   PortList ports;
179   RelayCredentials credentials;
180   int priority = 0;
181   TlsCertPolicy tls_cert_policy = TlsCertPolicy::TLS_CERT_POLICY_SECURE;
182   std::vector<std::string> tls_alpn_protocols;
183   std::vector<std::string> tls_elliptic_curves;
184   rtc::SSLCertificateVerifier* tls_cert_verifier = nullptr;
185   std::string turn_logging_id;
186 };
187 
188 class RTC_EXPORT PortAllocatorSession : public sigslot::has_slots<> {
189  public:
190   // Content name passed in mostly for logging and debugging.
191   PortAllocatorSession(const std::string& content_name,
192                        int component,
193                        const std::string& ice_ufrag,
194                        const std::string& ice_pwd,
195                        uint32_t flags);
196 
197   // Subclasses should clean up any ports created.
198   ~PortAllocatorSession() override;
199 
flags()200   uint32_t flags() const { return flags_; }
set_flags(uint32_t flags)201   void set_flags(uint32_t flags) { flags_ = flags; }
content_name()202   std::string content_name() const { return content_name_; }
component()203   int component() const { return component_; }
ice_ufrag()204   const std::string& ice_ufrag() const { return ice_ufrag_; }
ice_pwd()205   const std::string& ice_pwd() const { return ice_pwd_; }
pooled()206   bool pooled() const { return pooled_; }
207 
208   // Setting this filter should affect not only candidates gathered in the
209   // future, but candidates already gathered and ports already "ready",
210   // which would be returned by ReadyCandidates() and ReadyPorts().
211   //
212   // Default filter should be CF_ALL.
213   virtual void SetCandidateFilter(uint32_t filter) = 0;
214 
215   // Starts gathering ports and ICE candidates.
216   virtual void StartGettingPorts() = 0;
217   // Completely stops gathering. Will not gather again unless StartGettingPorts
218   // is called again.
219   virtual void StopGettingPorts() = 0;
220   // Whether the session is actively getting ports.
221   virtual bool IsGettingPorts() = 0;
222 
223   //
224   // NOTE: The group of methods below is only used for continual gathering.
225   //
226 
227   // ClearGettingPorts should have the same immediate effect as
228   // StopGettingPorts, but if the implementation supports continual gathering,
229   // ClearGettingPorts allows additional ports/candidates to be gathered if the
230   // network conditions change.
231   virtual void ClearGettingPorts() = 0;
232   // Whether it is in the state where the existing gathering process is stopped,
233   // but new ones may be started (basically after calling ClearGettingPorts).
234   virtual bool IsCleared() const;
235   // Whether the session has completely stopped.
236   virtual bool IsStopped() const;
237   // Re-gathers candidates on networks that do not have any connections. More
238   // precisely, a network interface may have more than one IP addresses (e.g.,
239   // IPv4 and IPv6 addresses). Each address subnet will be used to create a
240   // network. Only if all networks of an interface have no connection, the
241   // implementation should start re-gathering on all networks of that interface.
RegatherOnFailedNetworks()242   virtual void RegatherOnFailedNetworks() {}
243   // Get candidate-level stats from all candidates on the ready ports and return
244   // the stats to the given list.
GetCandidateStatsFromReadyPorts(CandidateStatsList * candidate_stats_list)245   virtual void GetCandidateStatsFromReadyPorts(
246       CandidateStatsList* candidate_stats_list) const {}
247   // Set the interval at which STUN candidates will resend STUN binding requests
248   // on the underlying ports to keep NAT bindings open.
249   // The default value of the interval in implementation is restored if a null
250   // optional value is passed.
SetStunKeepaliveIntervalForReadyPorts(const absl::optional<int> & stun_keepalive_interval)251   virtual void SetStunKeepaliveIntervalForReadyPorts(
252       const absl::optional<int>& stun_keepalive_interval) {}
253   // Another way of getting the information provided by the signals below.
254   //
255   // Ports and candidates are not guaranteed to be in the same order as the
256   // signals were emitted in.
257   virtual std::vector<PortInterface*> ReadyPorts() const = 0;
258   virtual std::vector<Candidate> ReadyCandidates() const = 0;
259   virtual bool CandidatesAllocationDone() const = 0;
260   // Marks all ports in the current session as "pruned" so that they may be
261   // destroyed if no connection is using them.
PruneAllPorts()262   virtual void PruneAllPorts() {}
263 
264   sigslot::signal2<PortAllocatorSession*, PortInterface*> SignalPortReady;
265   // Fires this signal when the network of the ports failed (either because the
266   // interface is down, or because there is no connection on the interface),
267   // or when TURN ports are pruned because a higher-priority TURN port becomes
268   // ready(pairable).
269   sigslot::signal2<PortAllocatorSession*, const std::vector<PortInterface*>&>
270       SignalPortsPruned;
271   sigslot::signal2<PortAllocatorSession*, const std::vector<Candidate>&>
272       SignalCandidatesReady;
273   sigslot::signal2<PortAllocatorSession*, const IceCandidateErrorEvent&>
274       SignalCandidateError;
275   // Candidates should be signaled to be removed when the port that generated
276   // the candidates is removed.
277   sigslot::signal2<PortAllocatorSession*, const std::vector<Candidate>&>
278       SignalCandidatesRemoved;
279   sigslot::signal1<PortAllocatorSession*> SignalCandidatesAllocationDone;
280 
281   sigslot::signal2<PortAllocatorSession*, IceRegatheringReason>
282       SignalIceRegathering;
283 
284   virtual uint32_t generation();
285   virtual void set_generation(uint32_t generation);
286   sigslot::signal1<PortAllocatorSession*> SignalDestroyed;
287 
288  protected:
289   // This method is called when a pooled session (which doesn't have these
290   // properties initially) is returned by PortAllocator::TakePooledSession,
291   // and the content name, component, and ICE ufrag/pwd are updated.
292   //
293   // A subclass may need to override this method to perform additional actions,
294   // such as applying the updated information to ports and candidates.
UpdateIceParametersInternal()295   virtual void UpdateIceParametersInternal() {}
296 
297   // TODO(deadbeef): Get rid of these when everyone switches to ice_ufrag and
298   // ice_pwd.
username()299   const std::string& username() const { return ice_ufrag_; }
password()300   const std::string& password() const { return ice_pwd_; }
301 
302  private:
SetIceParameters(const std::string & content_name,int component,const std::string & ice_ufrag,const std::string & ice_pwd)303   void SetIceParameters(const std::string& content_name,
304                         int component,
305                         const std::string& ice_ufrag,
306                         const std::string& ice_pwd) {
307     content_name_ = content_name;
308     component_ = component;
309     ice_ufrag_ = ice_ufrag;
310     ice_pwd_ = ice_pwd;
311     UpdateIceParametersInternal();
312   }
313 
set_pooled(bool value)314   void set_pooled(bool value) { pooled_ = value; }
315 
316   uint32_t flags_;
317   uint32_t generation_;
318   std::string content_name_;
319   int component_;
320   std::string ice_ufrag_;
321   std::string ice_pwd_;
322 
323   bool pooled_ = false;
324 
325   // SetIceParameters is an implementation detail which only PortAllocator
326   // should be able to call.
327   friend class PortAllocator;
328 };
329 
330 // Every method of PortAllocator (including the destructor) must be called on
331 // the same thread after Initialize is called.
332 //
333 // This allows a PortAllocator subclass to be constructed and configured on one
334 // thread, and passed into an object that uses it on a different thread.
335 class RTC_EXPORT PortAllocator : public sigslot::has_slots<> {
336  public:
337   PortAllocator();
338   ~PortAllocator() override;
339 
340   // This MUST be called on the PortAllocator's thread after finishing
341   // constructing and configuring the PortAllocator subclasses.
342   virtual void Initialize();
343 
344   // Set to true if some Ports need to know the ICE credentials when they are
345   // created. This will ensure that the PortAllocator will only match pooled
346   // allocator sessions to the ICE transport with the same credentials.
347   virtual void set_restrict_ice_credentials_change(bool value);
348 
349   // Set STUN and TURN servers to be used in future sessions, and set
350   // candidate pool size, as described in JSEP.
351   //
352   // If the servers are changing, and the candidate pool size is nonzero, and
353   // FreezeCandidatePool hasn't been called, existing pooled sessions will be
354   // destroyed and new ones created.
355   //
356   // If the servers are not changing but the candidate pool size is, and
357   // FreezeCandidatePool hasn't been called, pooled sessions will be either
358   // created or destroyed as necessary.
359   //
360   // Returns true if the configuration could successfully be changed.
361   // Deprecated
362   bool SetConfiguration(const ServerAddresses& stun_servers,
363                         const std::vector<RelayServerConfig>& turn_servers,
364                         int candidate_pool_size,
365                         bool prune_turn_ports,
366                         webrtc::TurnCustomizer* turn_customizer = nullptr,
367                         const absl::optional<int>&
368                             stun_candidate_keepalive_interval = absl::nullopt);
369   bool SetConfiguration(const ServerAddresses& stun_servers,
370                         const std::vector<RelayServerConfig>& turn_servers,
371                         int candidate_pool_size,
372                         webrtc::PortPrunePolicy turn_port_prune_policy,
373                         webrtc::TurnCustomizer* turn_customizer = nullptr,
374                         const absl::optional<int>&
375                             stun_candidate_keepalive_interval = absl::nullopt);
376 
stun_servers()377   const ServerAddresses& stun_servers() const {
378     CheckRunOnValidThreadIfInitialized();
379     return stun_servers_;
380   }
381 
turn_servers()382   const std::vector<RelayServerConfig>& turn_servers() const {
383     CheckRunOnValidThreadIfInitialized();
384     return turn_servers_;
385   }
386 
candidate_pool_size()387   int candidate_pool_size() const {
388     CheckRunOnValidThreadIfInitialized();
389     return candidate_pool_size_;
390   }
391 
stun_candidate_keepalive_interval()392   const absl::optional<int>& stun_candidate_keepalive_interval() const {
393     CheckRunOnValidThreadIfInitialized();
394     return stun_candidate_keepalive_interval_;
395   }
396 
397   // Sets the network types to ignore.
398   // Values are defined by the AdapterType enum.
399   // For instance, calling this with
400   // ADAPTER_TYPE_ETHERNET | ADAPTER_TYPE_LOOPBACK will ignore Ethernet and
401   // loopback interfaces.
402   virtual void SetNetworkIgnoreMask(int network_ignore_mask) = 0;
403 
404   std::unique_ptr<PortAllocatorSession> CreateSession(
405       const std::string& content_name,
406       int component,
407       const std::string& ice_ufrag,
408       const std::string& ice_pwd);
409 
410   // Get an available pooled session and set the transport information on it.
411   //
412   // Caller takes ownership of the returned session.
413   //
414   // If restrict_ice_credentials_change is TRUE, then it will only
415   //   return a pooled session with matching ice credentials.
416   // If no pooled sessions are available, returns null.
417   std::unique_ptr<PortAllocatorSession> TakePooledSession(
418       const std::string& content_name,
419       int component,
420       const std::string& ice_ufrag,
421       const std::string& ice_pwd);
422 
423   // Returns the next session that would be returned by TakePooledSession
424   // optionally restricting it to sessions with specified ice credentials.
425   const PortAllocatorSession* GetPooledSession(
426       const IceParameters* ice_credentials = nullptr) const;
427 
428   // After FreezeCandidatePool is called, changing the candidate pool size will
429   // no longer be allowed, and changing ICE servers will not cause pooled
430   // sessions to be recreated.
431   //
432   // Expected to be called when SetLocalDescription is called on a
433   // PeerConnection. Can be called safely on any thread as long as not
434   // simultaneously with SetConfiguration.
435   void FreezeCandidatePool();
436 
437   // Discard any remaining pooled sessions.
438   void DiscardCandidatePool();
439 
440   // Clears the address and the related address fields of a local candidate to
441   // avoid IP leakage. This is applicable in several scenarios:
442   // 1. Sanitization is configured via the candidate filter.
443   // 2. Sanitization is configured via the port allocator flags.
444   // 3. mDNS concealment of private IPs is enabled.
445   Candidate SanitizeCandidate(const Candidate& c) const;
446 
flags()447   uint32_t flags() const {
448     CheckRunOnValidThreadIfInitialized();
449     return flags_;
450   }
451 
set_flags(uint32_t flags)452   void set_flags(uint32_t flags) {
453     CheckRunOnValidThreadIfInitialized();
454     flags_ = flags;
455   }
456 
457   // These three methods are deprecated. If connections need to go through a
458   // proxy, the application should create a BasicPortAllocator given a custom
459   // PacketSocketFactory that creates proxy sockets.
user_agent()460   const std::string& user_agent() const {
461     CheckRunOnValidThreadIfInitialized();
462     return agent_;
463   }
464 
proxy()465   const rtc::ProxyInfo& proxy() const {
466     CheckRunOnValidThreadIfInitialized();
467     return proxy_;
468   }
469 
set_proxy(const std::string & agent,const rtc::ProxyInfo & proxy)470   void set_proxy(const std::string& agent, const rtc::ProxyInfo& proxy) {
471     CheckRunOnValidThreadIfInitialized();
472     agent_ = agent;
473     proxy_ = proxy;
474   }
475 
476   // Gets/Sets the port range to use when choosing client ports.
min_port()477   int min_port() const {
478     CheckRunOnValidThreadIfInitialized();
479     return min_port_;
480   }
481 
max_port()482   int max_port() const {
483     CheckRunOnValidThreadIfInitialized();
484     return max_port_;
485   }
486 
SetPortRange(int min_port,int max_port)487   bool SetPortRange(int min_port, int max_port) {
488     CheckRunOnValidThreadIfInitialized();
489     if (min_port > max_port) {
490       return false;
491     }
492 
493     min_port_ = min_port;
494     max_port_ = max_port;
495     return true;
496   }
497 
498   // Can be used to change the default numer of IPv6 network interfaces used
499   // (5). Can set to INT_MAX to effectively disable the limit.
500   //
501   // TODO(deadbeef): Applications shouldn't have to arbitrarily limit the
502   // number of available IPv6 network interfaces just because they could slow
503   // ICE down. We should work on making our ICE logic smarter (for example,
504   // prioritizing pinging connections that are most likely to work) so that
505   // every network interface can be used without impacting ICE's speed.
set_max_ipv6_networks(int networks)506   void set_max_ipv6_networks(int networks) {
507     CheckRunOnValidThreadIfInitialized();
508     max_ipv6_networks_ = networks;
509   }
510 
max_ipv6_networks()511   int max_ipv6_networks() {
512     CheckRunOnValidThreadIfInitialized();
513     return max_ipv6_networks_;
514   }
515 
516   // Delay between different candidate gathering phases (UDP, TURN, TCP).
517   // Defaults to 1 second, but PeerConnection sets it to 50ms.
518   // TODO(deadbeef): Get rid of this. Its purpose is to avoid sending too many
519   // STUN transactions at once, but that's already happening if you configure
520   // multiple STUN servers or have multiple network interfaces. We should
521   // implement some global pacing logic instead if that's our goal.
step_delay()522   uint32_t step_delay() const {
523     CheckRunOnValidThreadIfInitialized();
524     return step_delay_;
525   }
526 
set_step_delay(uint32_t delay)527   void set_step_delay(uint32_t delay) {
528     CheckRunOnValidThreadIfInitialized();
529     step_delay_ = delay;
530   }
531 
allow_tcp_listen()532   bool allow_tcp_listen() const {
533     CheckRunOnValidThreadIfInitialized();
534     return allow_tcp_listen_;
535   }
536 
set_allow_tcp_listen(bool allow_tcp_listen)537   void set_allow_tcp_listen(bool allow_tcp_listen) {
538     CheckRunOnValidThreadIfInitialized();
539     allow_tcp_listen_ = allow_tcp_listen;
540   }
541 
candidate_filter()542   uint32_t candidate_filter() {
543     CheckRunOnValidThreadIfInitialized();
544     return candidate_filter_;
545   }
546 
547   // The new filter value will be populated to future allocation sessions, when
548   // they are created via CreateSession, and also pooled sessions when one is
549   // taken via TakePooledSession.
550   //
551   // A change in the candidate filter also fires a signal
552   // |SignalCandidateFilterChanged|, so that objects subscribed to this signal
553   // can, for example, update the candidate filter for sessions created by this
554   // allocator and already taken by the object.
555   //
556   // Specifically for the session taken by the ICE transport, we currently do
557   // not support removing candidate pairs formed with local candidates from this
558   // session that are disabled by the new candidate filter.
559   void SetCandidateFilter(uint32_t filter);
560   // Deprecated.
561   // TODO(qingsi): Remove this after Chromium migrates to the new method.
set_candidate_filter(uint32_t filter)562   void set_candidate_filter(uint32_t filter) { SetCandidateFilter(filter); }
563 
564   // Deprecated (by the next method).
prune_turn_ports()565   bool prune_turn_ports() const {
566     CheckRunOnValidThreadIfInitialized();
567     return turn_port_prune_policy_ == webrtc::PRUNE_BASED_ON_PRIORITY;
568   }
569 
turn_port_prune_policy()570   webrtc::PortPrunePolicy turn_port_prune_policy() const {
571     CheckRunOnValidThreadIfInitialized();
572     return turn_port_prune_policy_;
573   }
574 
575   // Gets/Sets the Origin value used for WebRTC STUN requests.
origin()576   const std::string& origin() const {
577     CheckRunOnValidThreadIfInitialized();
578     return origin_;
579   }
580 
set_origin(const std::string & origin)581   void set_origin(const std::string& origin) {
582     CheckRunOnValidThreadIfInitialized();
583     origin_ = origin;
584   }
585 
turn_customizer()586   webrtc::TurnCustomizer* turn_customizer() {
587     CheckRunOnValidThreadIfInitialized();
588     return turn_customizer_;
589   }
590 
591   // Collect candidate stats from pooled allocator sessions. This can be used to
592   // collect candidate stats without creating an offer/answer or setting local
593   // description. After the local description is set, the ownership of the
594   // pooled session is taken by P2PTransportChannel, and the
595   // candidate stats can be collected from P2PTransportChannel::GetStats.
596   virtual void GetCandidateStatsFromPooledSessions(
597       CandidateStatsList* candidate_stats_list);
598 
599   // Return IceParameters of the pooled sessions.
600   std::vector<IceParameters> GetPooledIceCredentials();
601 
602   // Fired when |candidate_filter_| changes.
603   sigslot::signal2<uint32_t /* prev_filter */, uint32_t /* cur_filter */>
604       SignalCandidateFilterChanged;
605 
606  protected:
607   virtual PortAllocatorSession* CreateSessionInternal(
608       const std::string& content_name,
609       int component,
610       const std::string& ice_ufrag,
611       const std::string& ice_pwd) = 0;
612 
pooled_sessions()613   const std::vector<std::unique_ptr<PortAllocatorSession>>& pooled_sessions() {
614     return pooled_sessions_;
615   }
616 
617   // Returns true if there is an mDNS responder attached to the network manager.
MdnsObfuscationEnabled()618   virtual bool MdnsObfuscationEnabled() const { return false; }
619 
620   // The following thread checks are only done in DCHECK for the consistency
621   // with the exsiting thread checks.
CheckRunOnValidThreadIfInitialized()622   void CheckRunOnValidThreadIfInitialized() const {
623     RTC_DCHECK(!initialized_ || thread_checker_.IsCurrent());
624   }
625 
CheckRunOnValidThreadAndInitialized()626   void CheckRunOnValidThreadAndInitialized() const {
627     RTC_DCHECK(initialized_ && thread_checker_.IsCurrent());
628   }
629 
630   bool initialized_ = false;
631   uint32_t flags_;
632   std::string agent_;
633   rtc::ProxyInfo proxy_;
634   int min_port_;
635   int max_port_;
636   int max_ipv6_networks_;
637   uint32_t step_delay_;
638   bool allow_tcp_listen_;
639   uint32_t candidate_filter_;
640   std::string origin_;
641   rtc::ThreadChecker thread_checker_;
642 
643  private:
644   ServerAddresses stun_servers_;
645   std::vector<RelayServerConfig> turn_servers_;
646   int candidate_pool_size_ = 0;  // Last value passed into SetConfiguration.
647   std::vector<std::unique_ptr<PortAllocatorSession>> pooled_sessions_;
648   bool candidate_pool_frozen_ = false;
649   webrtc::PortPrunePolicy turn_port_prune_policy_ = webrtc::NO_PRUNE;
650 
651   // Customizer for TURN messages.
652   // The instance is owned by application and will be shared among
653   // all TurnPort(s) created.
654   webrtc::TurnCustomizer* turn_customizer_ = nullptr;
655 
656   absl::optional<int> stun_candidate_keepalive_interval_;
657 
658   // If true, TakePooledSession() will only return sessions that has same ice
659   // credentials as requested.
660   bool restrict_ice_credentials_change_ = false;
661 
662   // Returns iterator to pooled session with specified ice_credentials or first
663   // if ice_credentials is nullptr.
664   std::vector<std::unique_ptr<PortAllocatorSession>>::const_iterator
665   FindPooledSession(const IceParameters* ice_credentials = nullptr) const;
666 };
667 
668 }  // namespace cricket
669 
670 #endif  // P2P_BASE_PORT_ALLOCATOR_H_
671