Merge "Push interface quota rules from NetworkPolicyManager to kernel."

This commit is contained in:
Jeff Sharkey
2011-06-29 10:53:06 -07:00
committed by Android (Google) Code Review
5 changed files with 99 additions and 14 deletions

View File

@@ -209,6 +209,16 @@ interface INetworkManagementService
*/
NetworkStats getNetworkStatsUidDetail(int uid);
/**
* Set an overall quota for a group of interfaces.
*/
void setInterfaceQuota(in String[] iface, long quota);
/**
* Control network activity of a UID over interfaces with a quota limit.
*/
void setUidNetworkRules(int uid, boolean rejectOnQuotaInterfaces);
/**
* Configures bandwidth throttling on an interface.
*/

View File

@@ -919,6 +919,38 @@ class NetworkManagementService extends INetworkManagementService.Stub {
}
@Override
public void setInterfaceQuota(String[] iface, long quota)
throws IllegalStateException {
mContext.enforceCallingOrSelfPermission(
android.Manifest.permission.MANAGE_NETWORK_POLICY, "NetworkManagementService");
try {
// TODO: Add support for clubbing together multiple interfaces under
// one quota. Will need support from the kernel and
// BandwidthController to do this.
mConnector.doCommand(
String.format("bandwidth setquota %s %d", iface[0], quota));
} catch (NativeDaemonConnectorException e) {
throw new IllegalStateException(
"Error communicating to native daemon to set Interface quota",
e);
}
}
@Override
public void setUidNetworkRules(int uid, boolean rejectOnQuotaInterfaces)
throws IllegalStateException {
mContext.enforceCallingOrSelfPermission(
android.Manifest.permission.MANAGE_NETWORK_POLICY, "NetworkManagementService");
try {
// TODO: Connect with BandwidthController
// mConnector.doCommand("");
} catch (NativeDaemonConnectorException e) {
throw new IllegalStateException(
"Error communicating to native daemon to set Interface quota",
e);
}
}
public NetworkStats getNetworkStatsUidDetail(int uid) {
if (Binder.getCallingUid() != uid) {
mContext.enforceCallingOrSelfPermission(

View File

@@ -283,7 +283,8 @@ class ServerThread extends Thread {
try {
Slog.i(TAG, "NetworkPolicy Service");
networkPolicy = new NetworkPolicyManagerService(
context, ActivityManagerService.self(), power, networkStats);
context, ActivityManagerService.self(), power,
networkStats, networkManagement);
ServiceManager.addService(Context.NETWORK_POLICY_SERVICE, networkPolicy);
} catch (Throwable e) {
Slog.e(TAG, "Failure starting NetworkPolicy Service", e);

View File

@@ -71,6 +71,7 @@ import android.net.NetworkTemplate;
import android.os.Environment;
import android.os.Handler;
import android.os.HandlerThread;
import android.os.INetworkManagementService;
import android.os.IPowerManager;
import android.os.Message;
import android.os.RemoteCallbackList;
@@ -156,6 +157,7 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub {
private final IActivityManager mActivityManager;
private final IPowerManager mPowerManager;
private final INetworkStatsService mNetworkStats;
private final INetworkManagementService mNetworkManagement;
private final TrustedTime mTime;
private IConnectivityManager mConnManager;
@@ -193,9 +195,11 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub {
// rules enforced, such as system, phone, and radio UIDs.
public NetworkPolicyManagerService(Context context, IActivityManager activityManager,
IPowerManager powerManager, INetworkStatsService networkStats) {
IPowerManager powerManager, INetworkStatsService networkStats,
INetworkManagementService networkManagement) {
// TODO: move to using cached NtpTrustedTime
this(context, activityManager, powerManager, networkStats, new NtpTrustedTime(),
this(context, activityManager, powerManager, networkStats,
networkManagement, new NtpTrustedTime(),
getSystemDir());
}
@@ -204,12 +208,14 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub {
}
public NetworkPolicyManagerService(Context context, IActivityManager activityManager,
IPowerManager powerManager, INetworkStatsService networkStats, TrustedTime time,
File systemDir) {
IPowerManager powerManager, INetworkStatsService networkStats,
INetworkManagementService networkManagement,
TrustedTime time, File systemDir) {
mContext = checkNotNull(context, "missing context");
mActivityManager = checkNotNull(activityManager, "missing activityManager");
mPowerManager = checkNotNull(powerManager, "missing powerManager");
mNetworkStats = checkNotNull(networkStats, "missing networkStats");
mNetworkManagement = checkNotNull(networkManagement, "missing networkManagementService");
mTime = checkNotNull(time, "missing TrustedTime");
mHandlerThread = new HandlerThread(TAG);
@@ -589,7 +595,13 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub {
if (policy.limitBytes != NetworkPolicy.LIMIT_DISABLED) {
// remaining "quota" is based on usage in current cycle
final long quota = Math.max(0, policy.limitBytes - total);
//kernelSetIfacesQuota(ifaces, quota);
if (LOGD) {
Slog.d(TAG, "Applying quota rules for ifaces=" + Arrays.toString(ifaces)
+ " LIMIT=" + policy.limitBytes + " TOTAL="
+ total + " QUOTA=" + quota);
}
setQuotaOnIfaceList(ifaces, quota);
for (String iface : ifaces) {
mMeteredIfaces.add(iface);
@@ -601,6 +613,32 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub {
mHandler.obtainMessage(MSG_METERED_IFACES_CHANGED, meteredIfaces).sendToTarget();
}
private void setQuotaOnIfaceList(String[] ifaces, long quota) {
try {
mNetworkManagement.setInterfaceQuota(ifaces, quota);
} catch (IllegalStateException e) {
Slog.e(TAG, "IllegalStateException in setQuotaOnIfaceList " + e);
} catch (RemoteException e) {
Slog.e(TAG, "Remote Exception in setQuotaOnIfaceList " + e);
}
}
private void setUidNetworkRules(int uid, boolean rejectOnQuotaInterfaces) {
// TODO: connect over to NMS
// ndc bandwidth app <uid> naughty
try {
if (LOGD) {
Slog.d(TAG, "setUidNetworkRules() with uid=" + uid
+ ", rejectOnQuotaInterfaces=" + rejectOnQuotaInterfaces);
}
mNetworkManagement.setUidNetworkRules(uid, rejectOnQuotaInterfaces);
} catch (IllegalStateException e) {
Slog.e(TAG, "IllegalStateException in setUidNetworkRules " + e);
} catch (RemoteException e) {
Slog.e(TAG, "Remote Exception in setUidNetworkRules " + e);
}
}
/**
* Once any {@link #mNetworkPolicy} are loaded from disk, ensure that we
* have at least a default mobile policy defined.
@@ -955,7 +993,7 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub {
mUidRules.put(uid, uidRules);
final boolean rejectMetered = (uidRules & RULE_REJECT_METERED) != 0;
//kernelSetUidRejectPaid(uid, rejectPaid);
setUidNetworkRules(uid, rejectMetered);
// dispatch changed rule to existing listeners
mHandler.obtainMessage(MSG_RULES_CHANGED, uid, uidRules).sendToTarget();

View File

@@ -56,6 +56,7 @@ import android.net.NetworkState;
import android.net.NetworkStats;
import android.net.NetworkTemplate;
import android.os.Binder;
import android.os.INetworkManagementService;
import android.os.IPowerManager;
import android.test.AndroidTestCase;
import android.test.mock.MockPackageManager;
@@ -95,6 +96,7 @@ public class NetworkPolicyManagerServiceTest extends AndroidTestCase {
private IActivityManager mActivityManager;
private IPowerManager mPowerManager;
private INetworkStatsService mStatsService;
private INetworkManagementService mNetworkManagement;
private INetworkPolicyListener mPolicyListener;
private TrustedTime mTime;
private IConnectivityManager mConnManager;
@@ -150,13 +152,15 @@ public class NetworkPolicyManagerServiceTest extends AndroidTestCase {
mActivityManager = createMock(IActivityManager.class);
mPowerManager = createMock(IPowerManager.class);
mStatsService = createMock(INetworkStatsService.class);
mNetworkManagement = createMock(INetworkManagementService.class);
mPolicyListener = createMock(INetworkPolicyListener.class);
mTime = createMock(TrustedTime.class);
mConnManager = createMock(IConnectivityManager.class);
mNotifManager = createMock(INotificationManager.class);
mService = new NetworkPolicyManagerService(
mServiceContext, mActivityManager, mPowerManager, mStatsService, mTime, mPolicyDir);
mServiceContext, mActivityManager, mPowerManager, mStatsService,
mNetworkManagement, mTime, mPolicyDir);
mService.bindConnectivityManager(mConnManager);
mService.bindNotificationManager(mNotifManager);
@@ -526,14 +530,14 @@ public class NetworkPolicyManagerServiceTest extends AndroidTestCase {
}
private void replay() {
EasyMock.replay(mActivityManager, mPowerManager, mStatsService, mPolicyListener, mTime,
mConnManager, mNotifManager);
EasyMock.replay(mActivityManager, mPowerManager, mStatsService, mPolicyListener,
mNetworkManagement, mTime, mConnManager, mNotifManager);
}
private void verifyAndReset() {
EasyMock.verify(mActivityManager, mPowerManager, mStatsService, mPolicyListener, mTime,
mConnManager, mNotifManager);
EasyMock.reset(mActivityManager, mPowerManager, mStatsService, mPolicyListener, mTime,
mConnManager, mNotifManager);
EasyMock.verify(mActivityManager, mPowerManager, mStatsService, mPolicyListener,
mNetworkManagement, mTime, mConnManager, mNotifManager);
EasyMock.reset(mActivityManager, mPowerManager, mStatsService, mPolicyListener,
mNetworkManagement, mTime, mConnManager, mNotifManager);
}
}