Merge "Move back networking policy logic into NetworkPolicyManagerService" into oc-dev

am: 1173ec5bbb

Change-Id: I7d7b66cc1dc6888ea28e2b4d83d570fa440c29f2
This commit is contained in:
Hugo Benichi
2017-04-04 00:58:02 +00:00
committed by android-build-merger
2 changed files with 34 additions and 143 deletions

View File

@@ -29,13 +29,6 @@ import static android.net.NetworkCapabilities.NET_CAPABILITY_INTERNET;
import static android.net.NetworkCapabilities.NET_CAPABILITY_NOT_METERED;
import static android.net.NetworkCapabilities.NET_CAPABILITY_NOT_RESTRICTED;
import static android.net.NetworkCapabilities.NET_CAPABILITY_VALIDATED;
import static android.net.NetworkPolicyManager.RULE_ALLOW_ALL;
import static android.net.NetworkPolicyManager.RULE_ALLOW_METERED;
import static android.net.NetworkPolicyManager.RULE_NONE;
import static android.net.NetworkPolicyManager.RULE_REJECT_ALL;
import static android.net.NetworkPolicyManager.RULE_REJECT_METERED;
import static android.net.NetworkPolicyManager.RULE_TEMPORARY_ALLOW_METERED;
import static android.net.NetworkPolicyManager.uidRulesToString;
import android.annotation.Nullable;
import android.app.BroadcastOptions;
@@ -103,7 +96,6 @@ import android.security.Credentials;
import android.security.KeyStore;
import android.telephony.TelephonyManager;
import android.text.TextUtils;
import android.util.ArraySet;
import android.util.LocalLog;
import android.util.LocalLog.ReadOnlyLocalLog;
import android.util.Log;
@@ -129,6 +121,7 @@ import com.android.internal.util.IndentingPrintWriter;
import com.android.internal.util.MessageUtils;
import com.android.internal.util.WakeupMessage;
import com.android.internal.util.XmlUtils;
import com.android.server.LocalServices;
import com.android.server.am.BatteryStatsService;
import com.android.server.connectivity.DataConnectionStats;
import com.android.server.connectivity.KeepaliveTracker;
@@ -146,6 +139,7 @@ import com.android.server.connectivity.Tethering;
import com.android.server.connectivity.Vpn;
import com.android.server.net.BaseNetworkObserver;
import com.android.server.net.LockdownVpnTracker;
import com.android.server.net.NetworkPolicyManagerInternal;
import com.google.android.collect.Lists;
@@ -222,18 +216,6 @@ public class ConnectivityService extends IConnectivityManager.Stub
private boolean mLockdownEnabled;
private LockdownVpnTracker mLockdownTracker;
/** Lock around {@link #mUidRules} and {@link #mMeteredIfaces}. */
private Object mRulesLock = new Object();
/** Currently active network rules by UID. */
@GuardedBy("mRulesLock")
private SparseIntArray mUidRules = new SparseIntArray();
/** Set of ifaces that are costly. */
@GuardedBy("mRulesLock")
private ArraySet<String> mMeteredIfaces = new ArraySet<>();
/** Flag indicating if background data is restricted. */
@GuardedBy("mRulesLock")
private boolean mRestrictBackground;
final private Context mContext;
private int mNetworkPreference;
// 0 is full bad, 100 is full good
@@ -247,6 +229,7 @@ public class ConnectivityService extends IConnectivityManager.Stub
private INetworkManagementService mNetd;
private INetworkStatsService mStatsService;
private INetworkPolicyManager mPolicyManager;
private NetworkPolicyManagerInternal mPolicyManagerInternal;
private String mCurrentTcpBufferSizes;
@@ -718,12 +701,15 @@ public class ConnectivityService extends IConnectivityManager.Stub
mNetd = checkNotNull(netManager, "missing INetworkManagementService");
mStatsService = checkNotNull(statsService, "missing INetworkStatsService");
mPolicyManager = checkNotNull(policyManager, "missing INetworkPolicyManager");
mPolicyManagerInternal = checkNotNull(
LocalServices.getService(NetworkPolicyManagerInternal.class),
"missing NetworkPolicyManagerInternal");
mKeyStore = KeyStore.getInstance();
mTelephonyManager = (TelephonyManager) mContext.getSystemService(Context.TELEPHONY_SERVICE);
try {
mPolicyManager.setConnectivityListener(mPolicyListener);
mRestrictBackground = mPolicyManager.getRestrictBackground();
mPolicyManager.registerListener(mPolicyListener);
} catch (RemoteException e) {
// ouch, no rules updates means some processes may never get network
loge("unable to register INetworkPolicyListener" + e);
@@ -990,51 +976,22 @@ public class ConnectivityService extends IConnectivityManager.Stub
private boolean isNetworkWithLinkPropertiesBlocked(LinkProperties lp, int uid,
boolean ignoreBlocked) {
// Networks aren't blocked when ignoring blocked status
if (ignoreBlocked) return false;
if (ignoreBlocked) {
return false;
}
// Networks are never blocked for system services
if (isSystem(uid)) return false;
final boolean networkMetered;
final int uidRules;
// TODO: consider moving this check to NetworkPolicyManagerInternal.isUidNetworkingBlocked.
if (isSystem(uid)) {
return false;
}
synchronized (mVpns) {
final Vpn vpn = mVpns.get(UserHandle.getUserId(uid));
if (vpn != null && vpn.isBlockingUid(uid)) {
return true;
}
}
final String iface = (lp == null ? "" : lp.getInterfaceName());
synchronized (mRulesLock) {
networkMetered = mMeteredIfaces.contains(iface);
uidRules = mUidRules.get(uid, RULE_NONE);
}
boolean allowed = true;
// Check Data Saver Mode first...
if (networkMetered) {
if ((uidRules & RULE_REJECT_METERED) != 0) {
if (LOGD_RULES) Log.d(TAG, "uid " + uid + " is blacklisted");
// Explicitly blacklisted.
allowed = false;
} else {
allowed = !mRestrictBackground
|| (uidRules & RULE_ALLOW_METERED) != 0
|| (uidRules & RULE_TEMPORARY_ALLOW_METERED) != 0;
if (LOGD_RULES) Log.d(TAG, "allowed status for uid " + uid + " when"
+ " mRestrictBackground=" + mRestrictBackground
+ ", whitelisted=" + ((uidRules & RULE_ALLOW_METERED) != 0)
+ ", tempWhitelist= + ((uidRules & RULE_TEMPORARY_ALLOW_METERED) != 0)"
+ ": " + allowed);
}
}
// ...then power restrictions.
if (allowed) {
allowed = (uidRules & RULE_REJECT_ALL) == 0;
if (LOGD_RULES) Log.d(TAG, "allowed status for uid " + uid + " when"
+ " rule is " + uidRulesToString(uidRules) + ": " + allowed);
}
return !allowed;
return mPolicyManagerInternal.isUidNetworkingBlocked(uid, iface);
}
private void maybeLogBlockedNetworkInfo(NetworkInfo ni, int uid) {
@@ -1477,67 +1434,24 @@ public class ConnectivityService extends IConnectivityManager.Stub
return true;
}
private INetworkPolicyListener mPolicyListener = new INetworkPolicyListener.Stub() {
private final INetworkPolicyListener mPolicyListener = new INetworkPolicyListener.Stub() {
@Override
public void onUidRulesChanged(int uid, int uidRules) {
// caller is NPMS, since we only register with them
if (LOGD_RULES) {
log("onUidRulesChanged(uid=" + uid + ", uidRules=" + uidRules + ")");
}
synchronized (mRulesLock) {
// skip update when we've already applied rules
final int oldRules = mUidRules.get(uid, RULE_NONE);
if (oldRules == uidRules) return;
if (uidRules == RULE_NONE) {
mUidRules.delete(uid);
} else {
mUidRules.put(uid, uidRules);
}
}
// TODO: notify UID when it has requested targeted updates
}
@Override
public void onMeteredIfacesChanged(String[] meteredIfaces) {
// caller is NPMS, since we only register with them
if (LOGD_RULES) {
log("onMeteredIfacesChanged(ifaces=" + Arrays.toString(meteredIfaces) + ")");
}
synchronized (mRulesLock) {
mMeteredIfaces.clear();
for (String iface : meteredIfaces) {
mMeteredIfaces.add(iface);
}
}
}
@Override
public void onRestrictBackgroundChanged(boolean restrictBackground) {
// caller is NPMS, since we only register with them
if (LOGD_RULES) {
log("onRestrictBackgroundChanged(restrictBackground=" + restrictBackground + ")");
}
synchronized (mRulesLock) {
mRestrictBackground = restrictBackground;
}
// TODO: relocate this specific callback in Tethering.
if (restrictBackground) {
log("onRestrictBackgroundChanged(true): disabling tethering");
mTethering.untetherAll();
}
}
@Override
public void onUidPoliciesChanged(int uid, int uidPolicies) {
// caller is NPMS, since we only register with them
if (LOGD_RULES) {
log("onUidRulesChanged(uid=" + uid + ", uidPolicies=" + uidPolicies + ")");
}
}
};
@@ -1973,33 +1887,6 @@ public class ConnectivityService extends IConnectivityManager.Stub
pw.decreaseIndent();
pw.println();
pw.println("Metered Interfaces:");
pw.increaseIndent();
for (String value : mMeteredIfaces) {
pw.println(value);
}
pw.decreaseIndent();
pw.println();
pw.print("Restrict background: ");
pw.println(mRestrictBackground);
pw.println();
pw.println("Status for known UIDs:");
pw.increaseIndent();
final int size = mUidRules.size();
for (int i = 0; i < size; i++) {
final int uid = mUidRules.keyAt(i);
pw.print("UID=");
pw.print(uid);
final int uidRules = mUidRules.get(uid, RULE_NONE);
pw.print(" rules=");
pw.print(uidRulesToString(uidRules));
pw.println();
}
pw.println();
pw.decreaseIndent();
pw.println("Network Requests:");
pw.increaseIndent();
for (NetworkRequestInfo nri : mNetworkRequests.values()) {
@@ -3427,6 +3314,10 @@ public class ConnectivityService extends IConnectivityManager.Stub
Slog.e(TAG, s);
}
private static void loge(String s, Throwable t) {
Slog.e(TAG, s, t);
}
private static <T> T checkNotNull(T value, String message) {
if (value == null) {
throw new NullPointerException(message);
@@ -4176,20 +4067,16 @@ public class ConnectivityService extends IConnectivityManager.Stub
private void enforceMeteredApnPolicy(NetworkCapabilities networkCapabilities) {
final int uid = Binder.getCallingUid();
if (isSystem(uid)) {
// Exemption for system uid.
return;
}
// if UID is restricted, don't allow them to bring up metered APNs
if (networkCapabilities.hasCapability(NET_CAPABILITY_NOT_METERED) == false) {
final int uidRules;
synchronized(mRulesLock) {
uidRules = mUidRules.get(uid, RULE_ALLOW_ALL);
}
if (mRestrictBackground && (uidRules & RULE_ALLOW_METERED) == 0
&& (uidRules & RULE_TEMPORARY_ALLOW_METERED) == 0) {
// we could silently fail or we can filter the available nets to only give
// them those they have access to. Chose the more useful option.
networkCapabilities.addCapability(NET_CAPABILITY_NOT_METERED);
}
if (networkCapabilities.hasCapability(NET_CAPABILITY_NOT_METERED)) {
// Policy already enforced.
return;
}
if (mPolicyManagerInternal.isUidRestrictedOnMeteredNetworks(uid)) {
// If UID is restricted, don't allow them to bring up metered APNs.
networkCapabilities.addCapability(NET_CAPABILITY_NOT_METERED);
}
}

View File

@@ -87,6 +87,7 @@ import com.android.server.connectivity.NetworkAgentInfo;
import com.android.server.connectivity.NetworkMonitor;
import com.android.server.connectivity.NetworkMonitor.CaptivePortalProbeResult;
import com.android.server.net.NetworkPinner;
import com.android.server.net.NetworkPolicyManagerInternal;
import org.mockito.Mock;
import org.mockito.MockitoAnnotations;
@@ -750,6 +751,9 @@ public class ConnectivityServiceTest extends AndroidTestCase {
}
mServiceContext = new MockContext(getContext());
LocalServices.removeServiceForTest(NetworkPolicyManagerInternal.class);
LocalServices.addService(
NetworkPolicyManagerInternal.class, mock(NetworkPolicyManagerInternal.class));
mService = new WrappedConnectivityService(mServiceContext,
mock(INetworkManagementService.class),
mock(INetworkStatsService.class),