OSDN Git Service

Fix P2TP VPNs by adding an exception for VPN user.
[android-x86/system-netd.git] / server / NetdNativeService.cpp
index 97b41b2..5ee8202 100644 (file)
@@ -21,6 +21,7 @@
 #include <android-base/stringprintf.h>
 #include <cutils/log.h>
 #include <utils/Errors.h>
+#include <utils/String16.h>
 
 #include <binder/IPCThreadState.h>
 #include <binder/IServiceManager.h>
@@ -30,6 +31,9 @@
 #include "DumpWriter.h"
 #include "NetdConstants.h"
 #include "NetdNativeService.h"
+#include "RouteController.h"
+#include "SockDiag.h"
+#include "UidRanges.h"
 
 using android::base::StringPrintf;
 
@@ -65,7 +69,6 @@ binder::Status checkPermission(const char *permission) {
     android::RWLock::AutoWLock _lock(lock);
 
 #define NETD_BIG_LOCK_RPC(permission) NETD_LOCKING_RPC((permission), gBigNetdLock)
-
 }  // namespace
 
 
@@ -124,5 +127,79 @@ binder::Status NetdNativeService::bandwidthEnableDataSaver(bool enable, bool *re
     return binder::Status::ok();
 }
 
+binder::Status NetdNativeService::networkRejectNonSecureVpn(bool add,
+        const std::vector<UidRange>& uidRangeArray) {
+    // TODO: elsewhere RouteController is only used from the tethering and network controllers, so
+    // it should be possible to use the same lock as NetworkController. However, every call through
+    // the CommandListener "network" command will need to hold this lock too, not just the ones that
+    // read/modify network internal state (that is sufficient for ::dump() because it doesn't
+    // look at routes, but it's not enough here).
+    NETD_BIG_LOCK_RPC(CONNECTIVITY_INTERNAL);
+
+    UidRanges uidRanges(uidRangeArray);
+
+    int err;
+    if (add) {
+        err = RouteController::addUsersToRejectNonSecureNetworkRule(uidRanges);
+    } else {
+        err = RouteController::removeUsersFromRejectNonSecureNetworkRule(uidRanges);
+    }
+
+    if (err != 0) {
+        return binder::Status::fromServiceSpecificError(-err,
+                String8::format("RouteController error: %s", strerror(-err)));
+    }
+    return binder::Status::ok();
+}
+
+binder::Status NetdNativeService::socketDestroy(const std::vector<UidRange>& uids,
+        const std::vector<int32_t>& skipUids) {
+
+    ENFORCE_PERMISSION(CONNECTIVITY_INTERNAL);
+
+    SockDiag sd;
+    if (!sd.open()) {
+        return binder::Status::fromServiceSpecificError(EIO,
+                String8("Could not open SOCK_DIAG socket"));
+    }
+
+    UidRanges uidRanges(uids);
+    int err = sd.destroySockets(uidRanges, std::set<uid_t>(skipUids.begin(), skipUids.end()));
+
+    if (err) {
+        return binder::Status::fromServiceSpecificError(-err,
+                String8::format("destroySockets: %s", strerror(-err)));
+    }
+    return binder::Status::ok();
+}
+
+binder::Status NetdNativeService::setResolverConfiguration(int32_t netId,
+        const std::vector<std::string>& servers, const std::vector<std::string>& domains,
+        const std::vector<int32_t>& params) {
+    // This function intentionally does not lock within Netd, as Bionic is thread-safe.
+    ENFORCE_PERMISSION(CONNECTIVITY_INTERNAL);
+
+    int err = gCtls->resolverCtrl.setResolverConfiguration(netId, servers, domains, params);
+    if (err != 0) {
+        return binder::Status::fromServiceSpecificError(-err,
+                String8::format("ResolverController error: %s", strerror(-err)));
+    }
+    return binder::Status::ok();
+}
+
+binder::Status NetdNativeService::getResolverInfo(int32_t netId,
+        std::vector<std::string>* servers, std::vector<std::string>* domains,
+        std::vector<int32_t>* params, std::vector<int32_t>* stats) {
+    // This function intentionally does not lock within Netd, as Bionic is thread-safe.
+    ENFORCE_PERMISSION(CONNECTIVITY_INTERNAL);
+
+    int err = gCtls->resolverCtrl.getResolverInfo(netId, servers, domains, params, stats);
+    if (err != 0) {
+        return binder::Status::fromServiceSpecificError(-err,
+                String8::format("ResolverController error: %s", strerror(-err)));
+    }
+    return binder::Status::ok();
+}
+
 }  // namespace net
 }  // namespace android