1 use super::*; 2 use crate::error::*; 3 use crate::mdns::*; 4 use crate::network_type::*; 5 use crate::udp_network::UDPNetwork; 6 use crate::url::*; 7 8 use util::vnet::net::*; 9 10 use std::net::IpAddr; 11 use std::time::Duration; 12 13 /// The interval at which the agent performs candidate checks in the connecting phase. 14 pub(crate) const DEFAULT_CHECK_INTERVAL: Duration = Duration::from_millis(200); 15 16 /// The interval used to keep candidates alive. 17 pub(crate) const DEFAULT_KEEPALIVE_INTERVAL: Duration = Duration::from_secs(2); 18 19 /// The default time till an Agent transitions disconnected. 20 pub(crate) const DEFAULT_DISCONNECTED_TIMEOUT: Duration = Duration::from_secs(5); 21 22 /// The default time till an Agent transitions to failed after disconnected. 23 pub(crate) const DEFAULT_FAILED_TIMEOUT: Duration = Duration::from_secs(25); 24 25 /// Wait time before nominating a host candidate. 26 pub(crate) const DEFAULT_HOST_ACCEPTANCE_MIN_WAIT: Duration = Duration::from_secs(0); 27 28 /// Wait time before nominating a srflx candidate. 29 pub(crate) const DEFAULT_SRFLX_ACCEPTANCE_MIN_WAIT: Duration = Duration::from_millis(500); 30 31 /// Wait time before nominating a prflx candidate. 32 pub(crate) const DEFAULT_PRFLX_ACCEPTANCE_MIN_WAIT: Duration = Duration::from_millis(1000); 33 34 /// Wait time before nominating a relay candidate. 35 pub(crate) const DEFAULT_RELAY_ACCEPTANCE_MIN_WAIT: Duration = Duration::from_millis(2000); 36 37 /// Max binding request before considering a pair failed. 38 pub(crate) const DEFAULT_MAX_BINDING_REQUESTS: u16 = 7; 39 40 /// The number of bytes that can be buffered before we start to error. 41 pub(crate) const MAX_BUFFER_SIZE: usize = 1000 * 1000; // 1MB 42 43 /// Wait time before binding requests can be deleted. 44 pub(crate) const MAX_BINDING_REQUEST_TIMEOUT: Duration = Duration::from_millis(4000); 45 46 pub(crate) fn default_candidate_types() -> Vec<CandidateType> { 47 vec![ 48 CandidateType::Host, 49 CandidateType::ServerReflexive, 50 CandidateType::Relay, 51 ] 52 } 53 54 pub type InterfaceFilterFn = Box<dyn (Fn(&str) -> bool) + Send + Sync>; 55 pub type IpFilterFn = Box<dyn (Fn(IpAddr) -> bool) + Send + Sync>; 56 57 /// Collects the arguments to `ice::Agent` construction into a single structure, for 58 /// future-proofness of the interface. 59 #[derive(Default)] 60 pub struct AgentConfig { 61 pub urls: Vec<Url>, 62 63 /// Controls how the UDP network stack works. 64 /// See [`UDPNetwork`] 65 pub udp_network: UDPNetwork, 66 67 /// It is used to perform connectivity checks. The values MUST be unguessable, with at least 68 /// 128 bits of random number generator output used to generate the password, and at least 24 69 /// bits of output to generate the username fragment. 70 pub local_ufrag: String, 71 /// It is used to perform connectivity checks. The values MUST be unguessable, with at least 72 /// 128 bits of random number generator output used to generate the password, and at least 24 73 /// bits of output to generate the username fragment. 74 pub local_pwd: String, 75 76 /// Controls mDNS behavior for the ICE agent. 77 pub multicast_dns_mode: MulticastDnsMode, 78 79 /// Controls the hostname for this agent. If none is specified a random one will be generated. 80 pub multicast_dns_host_name: String, 81 82 /// Control mDNS destination address 83 pub multicast_dns_dest_addr: String, 84 85 /// Defaults to 5 seconds when this property is nil. 86 /// If the duration is 0, the ICE Agent will never go to disconnected. 87 pub disconnected_timeout: Option<Duration>, 88 89 /// Defaults to 25 seconds when this property is nil. 90 /// If the duration is 0, we will never go to failed. 91 pub failed_timeout: Option<Duration>, 92 93 /// Determines how often should we send ICE keepalives (should be less then connectiontimeout 94 /// above) when this is nil, it defaults to 10 seconds. 95 /// A keepalive interval of 0 means we never send keepalive packets 96 pub keepalive_interval: Option<Duration>, 97 98 /// An optional configuration for disabling or enabling support for specific network types. 99 pub network_types: Vec<NetworkType>, 100 101 /// An optional configuration for disabling or enabling support for specific candidate types. 102 pub candidate_types: Vec<CandidateType>, 103 104 //LoggerFactory logging.LoggerFactory 105 /// Controls how often our internal task loop runs when in the connecting state. 106 /// Only useful for testing. 107 pub check_interval: Duration, 108 109 /// The max amount of binding requests the agent will send over a candidate pair for validation 110 /// or nomination, if after max_binding_requests the candidate is yet to answer a binding 111 /// request or a nomination we set the pair as failed. 112 pub max_binding_requests: Option<u16>, 113 114 pub is_controlling: bool, 115 116 /// lite agents do not perform connectivity check and only provide host candidates. 117 pub lite: bool, 118 119 /// It is used along with nat1to1ips to specify which candidate type the 1:1 NAT IP addresses 120 /// should be mapped to. If unspecified or CandidateTypeHost, nat1to1ips are used to replace 121 /// host candidate IPs. If CandidateTypeServerReflexive, it will insert a srflx candidate (as 122 /// if it was dervied from a STUN server) with its port number being the one for the actual host 123 /// candidate. Other values will result in an error. 124 pub nat_1to1_ip_candidate_type: CandidateType, 125 126 /// Contains a list of public IP addresses that are to be used as a host candidate or srflx 127 /// candidate. This is used typically for servers that are behind 1:1 D-NAT (e.g. AWS EC2 128 /// instances) and to eliminate the need of server reflexisive candidate gathering. 129 pub nat_1to1_ips: Vec<String>, 130 131 /// Specify a minimum wait time before selecting host candidates. 132 pub host_acceptance_min_wait: Option<Duration>, 133 /// Specify a minimum wait time before selecting srflx candidates. 134 pub srflx_acceptance_min_wait: Option<Duration>, 135 /// Specify a minimum wait time before selecting prflx candidates. 136 pub prflx_acceptance_min_wait: Option<Duration>, 137 /// Specify a minimum wait time before selecting relay candidates. 138 pub relay_acceptance_min_wait: Option<Duration>, 139 140 /// Net is the our abstracted network interface for internal development purpose only 141 /// (see (github.com/pion/transport/vnet)[github.com/pion/transport/vnet]). 142 pub net: Option<Arc<Net>>, 143 144 /// A function that you can use in order to whitelist or blacklist the interfaces which are 145 /// used to gather ICE candidates. 146 pub interface_filter: Arc<Option<InterfaceFilterFn>>, 147 148 /// A function that you can use in order to whitelist or blacklist 149 /// the ips which are used to gather ICE candidates. 150 pub ip_filter: Arc<Option<IpFilterFn>>, 151 152 /// Controls if self-signed certificates are accepted when connecting to TURN servers via TLS or 153 /// DTLS. 154 pub insecure_skip_verify: bool, 155 } 156 157 impl AgentConfig { 158 /// Populates an agent and falls back to defaults if fields are unset. 159 pub(crate) fn init_with_defaults(&self, a: &mut AgentInternal) { 160 if let Some(max_binding_requests) = self.max_binding_requests { 161 a.max_binding_requests = max_binding_requests; 162 } else { 163 a.max_binding_requests = DEFAULT_MAX_BINDING_REQUESTS; 164 } 165 166 if let Some(host_acceptance_min_wait) = self.host_acceptance_min_wait { 167 a.host_acceptance_min_wait = host_acceptance_min_wait; 168 } else { 169 a.host_acceptance_min_wait = DEFAULT_HOST_ACCEPTANCE_MIN_WAIT; 170 } 171 172 if let Some(srflx_acceptance_min_wait) = self.srflx_acceptance_min_wait { 173 a.srflx_acceptance_min_wait = srflx_acceptance_min_wait; 174 } else { 175 a.srflx_acceptance_min_wait = DEFAULT_SRFLX_ACCEPTANCE_MIN_WAIT; 176 } 177 178 if let Some(prflx_acceptance_min_wait) = self.prflx_acceptance_min_wait { 179 a.prflx_acceptance_min_wait = prflx_acceptance_min_wait; 180 } else { 181 a.prflx_acceptance_min_wait = DEFAULT_PRFLX_ACCEPTANCE_MIN_WAIT; 182 } 183 184 if let Some(relay_acceptance_min_wait) = self.relay_acceptance_min_wait { 185 a.relay_acceptance_min_wait = relay_acceptance_min_wait; 186 } else { 187 a.relay_acceptance_min_wait = DEFAULT_RELAY_ACCEPTANCE_MIN_WAIT; 188 } 189 190 if let Some(disconnected_timeout) = self.disconnected_timeout { 191 a.disconnected_timeout = disconnected_timeout; 192 } else { 193 a.disconnected_timeout = DEFAULT_DISCONNECTED_TIMEOUT; 194 } 195 196 if let Some(failed_timeout) = self.failed_timeout { 197 a.failed_timeout = failed_timeout; 198 } else { 199 a.failed_timeout = DEFAULT_FAILED_TIMEOUT; 200 } 201 202 if let Some(keepalive_interval) = self.keepalive_interval { 203 a.keepalive_interval = keepalive_interval; 204 } else { 205 a.keepalive_interval = DEFAULT_KEEPALIVE_INTERVAL; 206 } 207 208 if self.check_interval == Duration::from_secs(0) { 209 a.check_interval = DEFAULT_CHECK_INTERVAL; 210 } else { 211 a.check_interval = self.check_interval; 212 } 213 } 214 215 pub(crate) fn init_ext_ip_mapping( 216 &self, 217 mdns_mode: MulticastDnsMode, 218 candidate_types: &[CandidateType], 219 ) -> Result<Option<ExternalIpMapper>> { 220 if let Some(ext_ip_mapper) = 221 ExternalIpMapper::new(self.nat_1to1_ip_candidate_type, &self.nat_1to1_ips)? 222 { 223 if ext_ip_mapper.candidate_type == CandidateType::Host { 224 if mdns_mode == MulticastDnsMode::QueryAndGather { 225 return Err(Error::ErrMulticastDnsWithNat1to1IpMapping); 226 } 227 let mut candi_host_enabled = false; 228 for candi_type in candidate_types { 229 if *candi_type == CandidateType::Host { 230 candi_host_enabled = true; 231 break; 232 } 233 } 234 if !candi_host_enabled { 235 return Err(Error::ErrIneffectiveNat1to1IpMappingHost); 236 } 237 } else if ext_ip_mapper.candidate_type == CandidateType::ServerReflexive { 238 let mut candi_srflx_enabled = false; 239 for candi_type in candidate_types { 240 if *candi_type == CandidateType::ServerReflexive { 241 candi_srflx_enabled = true; 242 break; 243 } 244 } 245 if !candi_srflx_enabled { 246 return Err(Error::ErrIneffectiveNat1to1IpMappingSrflx); 247 } 248 } 249 250 Ok(Some(ext_ip_mapper)) 251 } else { 252 Ok(None) 253 } 254 } 255 } 256