Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(445)

Unified Diff: net/udp/udp_socket_posix.cc

Issue 2160263002: Use supported Android network handles in Android M and newer. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: comment parseInt Created 4 years, 5 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
« no previous file with comments | « net/base/network_change_notifier.h ('k') | net/udp/udp_socket_unittest.cc » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: net/udp/udp_socket_posix.cc
diff --git a/net/udp/udp_socket_posix.cc b/net/udp/udp_socket_posix.cc
index b3972625edc48844318ecfba2b9c042080e9a7ba..797e1a0bc1352b5a4a9a43c8c663c7acb05ab374 100644
--- a/net/udp/udp_socket_posix.cc
+++ b/net/udp/udp_socket_posix.cc
@@ -346,27 +346,55 @@ int UDPSocketPosix::BindToNetwork(
base::android::SDK_VERSION_LOLLIPOP) {
return ERR_NOT_IMPLEMENTED;
}
- // NOTE(pauljensen): This does rely on Android implementation details, but
- // these details are unlikely to change.
- typedef int (*SetNetworkForSocket)(unsigned netId, int socketFd);
- static SetNetworkForSocket setNetworkForSocket;
- // This is racy, but all racers should come out with the same answer so it
- // shouldn't matter.
- if (!setNetworkForSocket) {
- // Android's netd client library should always be loaded in our address
- // space as it shims socket() which was used to create |socket_|.
- base::FilePath file(base::GetNativeLibraryName("netd_client"));
- // Use RTLD_NOW to match Android's prior loading of the library:
- // http://androidxref.com/6.0.0_r5/xref/bionic/libc/bionic/NetdClient.cpp#37
- // Use RTLD_NOLOAD to assert that the library is already loaded and
- // avoid doing any disk IO.
- void* dl = dlopen(file.value().c_str(), RTLD_NOW | RTLD_NOLOAD);
- setNetworkForSocket =
- reinterpret_cast<SetNetworkForSocket>(dlsym(dl, "setNetworkForSocket"));
+ int rv;
+ // On Android M and newer releases use supported NDK API. On Android L use
+ // setNetworkForSocket from libnetd_client.so.
+ if (base::android::BuildInfo::GetInstance()->sdk_int() >=
+ base::android::SDK_VERSION_MARSHMALLOW) {
+ // See declaration of android_setsocknetwork() here:
+ // http://androidxref.com/6.0.0_r1/xref/development/ndk/platforms/android-M/include/android/multinetwork.h#65
+ // Function cannot be called directly as it will cause app to fail to load
+ // on pre-marshmallow devices.
+ typedef int (*MarshmallowSetNetworkForSocket)(int64_t netId, int socketFd);
+ static MarshmallowSetNetworkForSocket marshmallowSetNetworkForSocket;
+ // This is racy, but all racers should come out with the same answer so it
+ // shouldn't matter.
+ if (!marshmallowSetNetworkForSocket) {
+ base::FilePath file(base::GetNativeLibraryName("android"));
+ void* dl = dlopen(file.value().c_str(), RTLD_NOW);
+ marshmallowSetNetworkForSocket =
+ reinterpret_cast<MarshmallowSetNetworkForSocket>(
+ dlsym(dl, "android_setsocknetwork"));
+ }
+ if (!marshmallowSetNetworkForSocket)
+ return ERR_NOT_IMPLEMENTED;
+ rv = marshmallowSetNetworkForSocket(network, socket_);
+ if (rv)
+ rv = errno;
+ } else {
+ // NOTE(pauljensen): This does rely on Android implementation details, but
+ // they won't change because Lollipop is already released.
+ typedef int (*LollipopSetNetworkForSocket)(unsigned netId, int socketFd);
+ static LollipopSetNetworkForSocket lollipopSetNetworkForSocket;
+ // This is racy, but all racers should come out with the same answer so it
+ // shouldn't matter.
+ if (!lollipopSetNetworkForSocket) {
+ // Android's netd client library should always be loaded in our address
+ // space as it shims socket() which was used to create |socket_|.
+ base::FilePath file(base::GetNativeLibraryName("netd_client"));
+ // Use RTLD_NOW to match Android's prior loading of the library:
+ // http://androidxref.com/6.0.0_r5/xref/bionic/libc/bionic/NetdClient.cpp#37
+ // Use RTLD_NOLOAD to assert that the library is already loaded and
+ // avoid doing any disk IO.
+ void* dl = dlopen(file.value().c_str(), RTLD_NOW | RTLD_NOLOAD);
+ lollipopSetNetworkForSocket =
+ reinterpret_cast<LollipopSetNetworkForSocket>(
+ dlsym(dl, "setNetworkForSocket"));
+ }
+ if (!lollipopSetNetworkForSocket)
+ return ERR_NOT_IMPLEMENTED;
+ rv = -lollipopSetNetworkForSocket(network, socket_);
}
- if (!setNetworkForSocket)
- return ERR_NOT_IMPLEMENTED;
- int rv = setNetworkForSocket(network, socket_);
// If |network| has since disconnected, |rv| will be ENONET. Surface this as
// ERR_NETWORK_CHANGED, rather than MapSystemError(ENONET) which gives back
// the less descriptive ERR_FAILED.
« no previous file with comments | « net/base/network_change_notifier.h ('k') | net/udp/udp_socket_unittest.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698