OLD | NEW |
---|---|
1 /* | 1 /* |
2 * libjingle | 2 * libjingle |
3 * Copyright 2015 Google Inc. | 3 * Copyright 2015 Google Inc. |
4 * | 4 * |
5 * Redistribution and use in source and binary forms, with or without | 5 * Redistribution and use in source and binary forms, with or without |
6 * modification, are permitted provided that the following conditions are met: | 6 * modification, are permitted provided that the following conditions are met: |
7 * | 7 * |
8 * 1. Redistributions of source code must retain the above copyright notice, | 8 * 1. Redistributions of source code must retain the above copyright notice, |
9 * this list of conditions and the following disclaimer. | 9 * this list of conditions and the following disclaimer. |
10 * 2. Redistributions in binary form must reproduce the above copyright notice, | 10 * 2. Redistributions in binary form must reproduce the above copyright notice, |
(...skipping 53 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
64 if (enum_name == "CONNECTION_BLUETOOTH") { | 64 if (enum_name == "CONNECTION_BLUETOOTH") { |
65 return NetworkType::NETWORK_BLUETOOTH; | 65 return NetworkType::NETWORK_BLUETOOTH; |
66 } | 66 } |
67 if (enum_name == "CONNECTION_NONE") { | 67 if (enum_name == "CONNECTION_NONE") { |
68 return NetworkType::NETWORK_NONE; | 68 return NetworkType::NETWORK_NONE; |
69 } | 69 } |
70 ASSERT(false); | 70 ASSERT(false); |
71 return NetworkType::NETWORK_UNKNOWN; | 71 return NetworkType::NETWORK_UNKNOWN; |
72 } | 72 } |
73 | 73 |
74 static rtc::AdapterType NetworkTypeToAdapterType(NetworkType network_type) { | |
75 switch (network_type) { | |
pthatcher1
2016/01/19 02:13:07
I'd prefer AdapterTypeFromNetworkType
honghaiz3
2016/01/21 21:38:36
Done.
| |
76 case NETWORK_UNKNOWN: | |
77 RTC_DCHECK(false) << "Unknown network type "; | |
78 return rtc::ADAPTER_TYPE_UNKNOWN; | |
79 case NETWORK_ETHERNET: | |
80 return rtc::ADAPTER_TYPE_ETHERNET; | |
81 case NETWORK_WIFI: | |
82 return rtc::ADAPTER_TYPE_WIFI; | |
83 case NETWORK_4G: | |
84 case NETWORK_3G: | |
85 case NETWORK_2G: | |
86 return rtc::ADAPTER_TYPE_CELLULAR; | |
87 case NETWORK_BLUETOOTH: | |
88 // There is no corresponding mapping for bluetooth networks. | |
89 // Map it to VPN for now. | |
90 return rtc::ADAPTER_TYPE_VPN; | |
pthatcher1
2016/01/19 02:13:07
Would UNKNOWN be a better map? What does bluetoot
honghaiz3
2016/01/21 21:38:35
It has nothing to do with VPN, except perhaps, VPN
| |
91 default: | |
92 RTC_DCHECK(false) << "Invalid network type " << network_type; | |
93 return rtc::ADAPTER_TYPE_UNKNOWN; | |
94 } | |
95 } | |
96 | |
74 static rtc::IPAddress GetIPAddressFromJava(JNIEnv* jni, jobject j_ip_address) { | 97 static rtc::IPAddress GetIPAddressFromJava(JNIEnv* jni, jobject j_ip_address) { |
75 jclass j_ip_address_class = GetObjectClass(jni, j_ip_address); | 98 jclass j_ip_address_class = GetObjectClass(jni, j_ip_address); |
76 jfieldID j_address_id = GetFieldID(jni, j_ip_address_class, "address", "[B"); | 99 jfieldID j_address_id = GetFieldID(jni, j_ip_address_class, "address", "[B"); |
77 jbyteArray j_addresses = | 100 jbyteArray j_addresses = |
78 static_cast<jbyteArray>(GetObjectField(jni, j_ip_address, j_address_id)); | 101 static_cast<jbyteArray>(GetObjectField(jni, j_ip_address, j_address_id)); |
79 size_t address_length = jni->GetArrayLength(j_addresses); | 102 size_t address_length = jni->GetArrayLength(j_addresses); |
80 jbyte* addr_array = jni->GetByteArrayElements(j_addresses, nullptr); | 103 jbyte* addr_array = jni->GetByteArrayElements(j_addresses, nullptr); |
81 CHECK_EXCEPTION(jni) << "Error during GetIPAddressFromJava"; | 104 CHECK_EXCEPTION(jni) << "Error during GetIPAddressFromJava"; |
82 if (address_length == 4) { | 105 if (address_length == 4) { |
83 // IP4 | 106 // IP4 |
(...skipping 95 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
179 started_ = true; | 202 started_ = true; |
180 | 203 |
181 // This is kind of magic behavior, but doing this allows the SocketServer to | 204 // This is kind of magic behavior, but doing this allows the SocketServer to |
182 // use this as a NetworkBinder to bind sockets on a particular network when | 205 // use this as a NetworkBinder to bind sockets on a particular network when |
183 // it creates sockets. | 206 // it creates sockets. |
184 worker_thread()->socketserver()->set_network_binder(this); | 207 worker_thread()->socketserver()->set_network_binder(this); |
185 | 208 |
186 jmethodID m = | 209 jmethodID m = |
187 GetMethodID(jni(), *j_network_monitor_class_, "startMonitoring", "(J)V"); | 210 GetMethodID(jni(), *j_network_monitor_class_, "startMonitoring", "(J)V"); |
188 jni()->CallVoidMethod(*j_network_monitor_, m, jlongFromPointer(this)); | 211 jni()->CallVoidMethod(*j_network_monitor_, m, jlongFromPointer(this)); |
189 CHECK_EXCEPTION(jni()) << "Error during NetworkMonitor.startMonitoring"; | 212 CHECK_EXCEPTION(jni()) << "Error during CallVoidMethod"; |
213 | |
214 UpdateNetworkInfos(); | |
215 } | |
216 | |
217 void AndroidNetworkMonitor::UpdateNetworkInfos() { | |
218 std::vector<NetworkInformation> network_infos; | |
219 GetAllNetworkInfos(&network_infos); | |
220 for (NetworkInformation& info : network_infos) { | |
221 // This method is already on the worker thread. | |
222 OnNetworkAvailable_w(info); | |
Taylor Brandstetter
2016/01/20 01:51:57
This will add networks to the maps, but not remove
honghaiz3
2016/01/21 21:38:36
Partially it was because we do not have the signal
| |
223 } | |
224 } | |
225 | |
226 void AndroidNetworkMonitor::GetAllNetworkInfos( | |
227 std::vector<NetworkInformation>* network_infos) { | |
228 RTC_CHECK(thread_checker_.CalledOnValidThread()); | |
229 network_infos->clear(); | |
230 jmethodID m = GetMethodID( | |
231 jni(), *j_network_monitor_class_, "getAllNetworkInfos", | |
232 "()[Lorg/webrtc/NetworkMonitorAutoDetect$NetworkInformation;"); | |
233 jobjectArray j_network_infos = static_cast<jobjectArray>( | |
234 jni()->CallObjectMethod(*j_network_monitor_, m)); | |
235 CHECK_EXCEPTION(jni()) << "Error during CallObjectMethod"; | |
236 size_t num_infos = jni()->GetArrayLength(j_network_infos); | |
237 for (size_t i = 0; i < num_infos; ++i) { | |
238 jobject j_network_info = jni()->GetObjectArrayElement(j_network_infos, i); | |
239 CHECK_EXCEPTION(jni()) << "Error during GetObjectArrayElement"; | |
240 network_infos->push_back( | |
241 GetNetworkInformationFromJava(jni(), j_network_info)); | |
242 } | |
190 } | 243 } |
191 | 244 |
192 void AndroidNetworkMonitor::Stop() { | 245 void AndroidNetworkMonitor::Stop() { |
193 RTC_CHECK(thread_checker_.CalledOnValidThread()); | 246 RTC_CHECK(thread_checker_.CalledOnValidThread()); |
194 if (!started_) { | 247 if (!started_) { |
195 return; | 248 return; |
196 } | 249 } |
197 started_ = false; | 250 started_ = false; |
198 | 251 |
199 // Once the network monitor stops, it will clear all network information and | 252 // Once the network monitor stops, it will clear all network information and |
200 // it won't find the network handle to bind anyway. | 253 // it won't find the network handle to bind anyway. |
201 if (worker_thread()->socketserver()->network_binder() == this) { | 254 if (worker_thread()->socketserver()->network_binder() == this) { |
202 worker_thread()->socketserver()->set_network_binder(nullptr); | 255 worker_thread()->socketserver()->set_network_binder(nullptr); |
203 } | 256 } |
204 | 257 |
205 jmethodID m = | 258 jmethodID m = |
206 GetMethodID(jni(), *j_network_monitor_class_, "stopMonitoring", "(J)V"); | 259 GetMethodID(jni(), *j_network_monitor_class_, "stopMonitoring", "(J)V"); |
207 jni()->CallVoidMethod(*j_network_monitor_, m, jlongFromPointer(this)); | 260 jni()->CallVoidMethod(*j_network_monitor_, m, jlongFromPointer(this)); |
208 CHECK_EXCEPTION(jni()) << "Error during NetworkMonitor.stopMonitoring"; | 261 CHECK_EXCEPTION(jni()) << "Error during NetworkMonitor.stopMonitoring"; |
209 | 262 |
210 network_info_by_address_.clear(); | 263 network_info_by_address_.clear(); |
264 adapter_types_.clear(); | |
211 } | 265 } |
212 | 266 |
213 int AndroidNetworkMonitor::BindSocketToNetwork(int socket_fd, | 267 int AndroidNetworkMonitor::BindSocketToNetwork(int socket_fd, |
214 const rtc::IPAddress& address) { | 268 const rtc::IPAddress& address) { |
215 RTC_CHECK(thread_checker_.CalledOnValidThread()); | 269 RTC_CHECK(thread_checker_.CalledOnValidThread()); |
216 auto it = network_info_by_address_.find(address); | 270 auto it = network_info_by_address_.find(address); |
217 if (it == network_info_by_address_.end()) { | 271 if (it == network_info_by_address_.end()) { |
218 return rtc::NETWORK_BIND_ADDRESS_NOT_FOUND; | 272 return rtc::NETWORK_BIND_ADDRESS_NOT_FOUND; |
219 } | 273 } |
220 // Android prior to Lollipop didn't have support for binding sockets to | 274 // Android prior to Lollipop didn't have support for binding sockets to |
(...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
259 | 313 |
260 void AndroidNetworkMonitor::OnNetworkAvailable( | 314 void AndroidNetworkMonitor::OnNetworkAvailable( |
261 const NetworkInformation& network_info) { | 315 const NetworkInformation& network_info) { |
262 worker_thread()->Invoke<void>(rtc::Bind( | 316 worker_thread()->Invoke<void>(rtc::Bind( |
263 &AndroidNetworkMonitor::OnNetworkAvailable_w, this, network_info)); | 317 &AndroidNetworkMonitor::OnNetworkAvailable_w, this, network_info)); |
264 } | 318 } |
265 | 319 |
266 void AndroidNetworkMonitor::OnNetworkAvailable_w( | 320 void AndroidNetworkMonitor::OnNetworkAvailable_w( |
267 const NetworkInformation& network_info) { | 321 const NetworkInformation& network_info) { |
268 LOG(LS_INFO) << "Network available: " << network_info.ToString(); | 322 LOG(LS_INFO) << "Network available: " << network_info.ToString(); |
323 adapter_types_[network_info.interface_name] = | |
324 NetworkTypeToAdapterType(network_info.type); | |
269 for (rtc::IPAddress address : network_info.ip_addresses) { | 325 for (rtc::IPAddress address : network_info.ip_addresses) { |
270 network_info_by_address_[address] = network_info; | 326 network_info_by_address_[address] = network_info; |
271 } | 327 } |
Taylor Brandstetter
2016/01/20 01:51:57
It seems redundant to have two data structures tha
honghaiz3
2016/01/21 21:38:36
I used two structures so speed up the lookup. But
Taylor Brandstetter
2016/01/26 02:35:09
Ah; so the second map exists so you can remember t
| |
272 } | 328 } |
273 | 329 |
330 rtc::AdapterType AndroidNetworkMonitor::GetAdapterType( | |
331 const std::string& if_name) { | |
332 if (adapter_types_.find(if_name) == adapter_types_.end()) { | |
333 UpdateNetworkInfos(); | |
Taylor Brandstetter
2016/01/20 01:51:57
Why is UpdateNetworkInfos necessary here? Won't na
honghaiz3
2016/01/21 21:38:36
There might be some short-term inconsistency betwe
| |
334 } | |
335 return adapter_types_[if_name]; | |
pthatcher1
2016/01/19 02:13:07
You can avoid too lookups by storing the result of
honghaiz3
2016/01/21 21:38:36
I am removing the update here.
It was a little co
| |
336 } | |
337 | |
274 rtc::NetworkMonitorInterface* | 338 rtc::NetworkMonitorInterface* |
275 AndroidNetworkMonitorFactory::CreateNetworkMonitor() { | 339 AndroidNetworkMonitorFactory::CreateNetworkMonitor() { |
276 return new AndroidNetworkMonitor(); | 340 return new AndroidNetworkMonitor(); |
277 } | 341 } |
278 | 342 |
279 JOW(void, NetworkMonitor_nativeNotifyConnectionTypeChanged)( | 343 JOW(void, NetworkMonitor_nativeNotifyConnectionTypeChanged)( |
280 JNIEnv* jni, jobject j_monitor, jlong j_native_monitor) { | 344 JNIEnv* jni, jobject j_monitor, jlong j_native_monitor) { |
281 rtc::NetworkMonitorInterface* network_monitor = | 345 rtc::NetworkMonitorInterface* network_monitor = |
282 reinterpret_cast<rtc::NetworkMonitorInterface*>(j_native_monitor); | 346 reinterpret_cast<rtc::NetworkMonitorInterface*>(j_native_monitor); |
283 network_monitor->OnNetworksChanged(); | 347 network_monitor->OnNetworksChanged(); |
284 } | 348 } |
285 | 349 |
286 JOW(void, NetworkMonitor_nativeNotifyOfNetworkConnect)( | 350 JOW(void, NetworkMonitor_nativeNotifyOfNetworkConnect)( |
Taylor Brandstetter
2016/01/20 01:51:57
Why is there not a corresponding "nativeNotifyOfNe
honghaiz3
2016/01/21 21:40:49
Added now (although BindNetworkToSocket will retur
| |
287 JNIEnv* jni, jobject j_monitor, jlong j_native_monitor, | 351 JNIEnv* jni, jobject j_monitor, jlong j_native_monitor, |
288 jobject j_network_info) { | 352 jobject j_network_info) { |
289 AndroidNetworkMonitor* network_monitor = | 353 AndroidNetworkMonitor* network_monitor = |
290 reinterpret_cast<AndroidNetworkMonitor*>(j_native_monitor); | 354 reinterpret_cast<AndroidNetworkMonitor*>(j_native_monitor); |
291 NetworkInformation network_info = | 355 NetworkInformation network_info = |
292 GetNetworkInformationFromJava(jni, j_network_info); | 356 GetNetworkInformationFromJava(jni, j_network_info); |
293 network_monitor->OnNetworkAvailable(network_info); | 357 network_monitor->OnNetworkAvailable(network_info); |
294 } | 358 } |
295 | 359 |
296 } // namespace webrtc_jni | 360 } // namespace webrtc_jni |
OLD | NEW |