Merge "Guard mUidBlockedState with a separate lock." into tm-dev

This commit is contained in:
Sudheer Shanka
2022-03-21 09:38:27 +00:00
committed by Android (Google) Code Review

View File

@@ -90,6 +90,8 @@ import static android.net.NetworkPolicyManager.RULE_REJECT_METERED;
import static android.net.NetworkPolicyManager.RULE_REJECT_RESTRICTED_MODE; import static android.net.NetworkPolicyManager.RULE_REJECT_RESTRICTED_MODE;
import static android.net.NetworkPolicyManager.RULE_TEMPORARY_ALLOW_METERED; import static android.net.NetworkPolicyManager.RULE_TEMPORARY_ALLOW_METERED;
import static android.net.NetworkPolicyManager.SUBSCRIPTION_OVERRIDE_UNMETERED; import static android.net.NetworkPolicyManager.SUBSCRIPTION_OVERRIDE_UNMETERED;
import static android.net.NetworkPolicyManager.allowedReasonsToString;
import static android.net.NetworkPolicyManager.blockedReasonsToString;
import static android.net.NetworkPolicyManager.isProcStateAllowedWhileIdleOrPowerSaveMode; import static android.net.NetworkPolicyManager.isProcStateAllowedWhileIdleOrPowerSaveMode;
import static android.net.NetworkPolicyManager.isProcStateAllowedWhileInLowPowerStandby; import static android.net.NetworkPolicyManager.isProcStateAllowedWhileInLowPowerStandby;
import static android.net.NetworkPolicyManager.isProcStateAllowedWhileOnRestrictBackground; import static android.net.NetworkPolicyManager.isProcStateAllowedWhileOnRestrictBackground;
@@ -594,7 +596,7 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub {
@GuardedBy("mUidRulesFirstLock") @GuardedBy("mUidRulesFirstLock")
private final SparseArray<UidState> mUidState = new SparseArray<>(); private final SparseArray<UidState> mUidState = new SparseArray<>();
@GuardedBy("mUidRulesFirstLock") @GuardedBy("mUidBlockedState")
private final SparseArray<UidBlockedState> mUidBlockedState = new SparseArray<>(); private final SparseArray<UidBlockedState> mUidBlockedState = new SparseArray<>();
/** Objects used temporarily while computing the new blocked state for each uid. */ /** Objects used temporarily while computing the new blocked state for each uid. */
@@ -3930,7 +3932,9 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub {
final SparseBooleanArray knownUids = new SparseBooleanArray(); final SparseBooleanArray knownUids = new SparseBooleanArray();
collectKeys(mUidState, knownUids); collectKeys(mUidState, knownUids);
collectKeys(mUidBlockedState, knownUids); synchronized (mUidBlockedState) {
collectKeys(mUidBlockedState, knownUids);
}
fout.println("Status for all known UIDs:"); fout.println("Status for all known UIDs:");
fout.increaseIndent(); fout.increaseIndent();
@@ -3948,12 +3952,14 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub {
fout.print(uidState.toString()); fout.print(uidState.toString());
} }
final UidBlockedState uidBlockedState = mUidBlockedState.get(uid); synchronized (mUidBlockedState) {
if (uidBlockedState == null) { final UidBlockedState uidBlockedState = mUidBlockedState.get(uid);
fout.print(" blocked_state={null}"); if (uidBlockedState == null) {
} else { fout.print(" blocked_state={null}");
fout.print(" blocked_state="); } else {
fout.print(uidBlockedState.toString()); fout.print(" blocked_state=");
fout.print(uidBlockedState);
}
} }
fout.println(); fout.println();
} }
@@ -4128,9 +4134,9 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub {
mUidFirewallRestrictedModeRules.clear(); mUidFirewallRestrictedModeRules.clear();
forEachUid("updateRestrictedModeAllowlist", uid -> { forEachUid("updateRestrictedModeAllowlist", uid -> {
synchronized (mUidRulesFirstLock) { synchronized (mUidRulesFirstLock) {
final UidBlockedState uidBlockedState = updateBlockedReasonsForRestrictedModeUL( final int effectiveBlockedReasons = updateBlockedReasonsForRestrictedModeUL(
uid); uid);
final int newFirewallRule = getRestrictedModeFirewallRule(uidBlockedState); final int newFirewallRule = getRestrictedModeFirewallRule(effectiveBlockedReasons);
// setUidFirewallRulesUL will allowlist all uids that are passed to it, so only add // setUidFirewallRulesUL will allowlist all uids that are passed to it, so only add
// non-default rules. // non-default rules.
@@ -4150,7 +4156,7 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub {
@VisibleForTesting @VisibleForTesting
@GuardedBy("mUidRulesFirstLock") @GuardedBy("mUidRulesFirstLock")
void updateRestrictedModeForUidUL(int uid) { void updateRestrictedModeForUidUL(int uid) {
final UidBlockedState uidBlockedState = updateBlockedReasonsForRestrictedModeUL(uid); final int effectiveBlockedReasons = updateBlockedReasonsForRestrictedModeUL(uid);
// if restricted networking mode is on, and the app has an access exemption, the uid rule // if restricted networking mode is on, and the app has an access exemption, the uid rule
// will not change, but the firewall rule will have to be updated. // will not change, but the firewall rule will have to be updated.
@@ -4158,37 +4164,48 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub {
// Note: setUidFirewallRule also updates mUidFirewallRestrictedModeRules. // Note: setUidFirewallRule also updates mUidFirewallRestrictedModeRules.
// In this case, default firewall rules can also be added. // In this case, default firewall rules can also be added.
setUidFirewallRuleUL(FIREWALL_CHAIN_RESTRICTED, uid, setUidFirewallRuleUL(FIREWALL_CHAIN_RESTRICTED, uid,
getRestrictedModeFirewallRule(uidBlockedState)); getRestrictedModeFirewallRule(effectiveBlockedReasons));
} }
} }
@GuardedBy("mUidRulesFirstLock") @GuardedBy("mUidRulesFirstLock")
private UidBlockedState updateBlockedReasonsForRestrictedModeUL(int uid) { private int updateBlockedReasonsForRestrictedModeUL(int uid) {
final UidBlockedState uidBlockedState = getOrCreateUidBlockedStateForUid( final boolean hasRestrictedModeAccess = hasRestrictedModeAccess(uid);
mUidBlockedState, uid); final int oldEffectiveBlockedReasons;
final int oldEffectiveBlockedReasons = uidBlockedState.effectiveBlockedReasons; final int newEffectiveBlockedReasons;
if (mRestrictedNetworkingMode) { final int uidRules;
uidBlockedState.blockedReasons |= BLOCKED_REASON_RESTRICTED_MODE; synchronized (mUidBlockedState) {
} else { final UidBlockedState uidBlockedState = getOrCreateUidBlockedStateForUid(
uidBlockedState.blockedReasons &= ~BLOCKED_REASON_RESTRICTED_MODE; mUidBlockedState, uid);
} oldEffectiveBlockedReasons = uidBlockedState.effectiveBlockedReasons;
if (hasRestrictedModeAccess(uid)) { if (mRestrictedNetworkingMode) {
uidBlockedState.allowedReasons |= ALLOWED_REASON_RESTRICTED_MODE_PERMISSIONS; uidBlockedState.blockedReasons |= BLOCKED_REASON_RESTRICTED_MODE;
} else { } else {
uidBlockedState.allowedReasons &= ~ALLOWED_REASON_RESTRICTED_MODE_PERMISSIONS; uidBlockedState.blockedReasons &= ~BLOCKED_REASON_RESTRICTED_MODE;
} }
uidBlockedState.updateEffectiveBlockedReasons(); if (hasRestrictedModeAccess) {
if (oldEffectiveBlockedReasons != uidBlockedState.effectiveBlockedReasons) { uidBlockedState.allowedReasons |= ALLOWED_REASON_RESTRICTED_MODE_PERMISSIONS;
postBlockedReasonsChangedMsg(uid, } else {
uidBlockedState.effectiveBlockedReasons, oldEffectiveBlockedReasons); uidBlockedState.allowedReasons &= ~ALLOWED_REASON_RESTRICTED_MODE_PERMISSIONS;
}
uidBlockedState.updateEffectiveBlockedReasons();
postUidRulesChangedMsg(uid, uidBlockedState.deriveUidRules()); newEffectiveBlockedReasons = uidBlockedState.effectiveBlockedReasons;
uidRules = oldEffectiveBlockedReasons == newEffectiveBlockedReasons
? RULE_NONE
: uidBlockedState.deriveUidRules();
} }
return uidBlockedState; if (oldEffectiveBlockedReasons != newEffectiveBlockedReasons) {
postBlockedReasonsChangedMsg(uid,
newEffectiveBlockedReasons, oldEffectiveBlockedReasons);
postUidRulesChangedMsg(uid, uidRules);
}
return newEffectiveBlockedReasons;
} }
private static int getRestrictedModeFirewallRule(UidBlockedState uidBlockedState) { private static int getRestrictedModeFirewallRule(int effectiveBlockedReasons) {
if ((uidBlockedState.effectiveBlockedReasons & BLOCKED_REASON_RESTRICTED_MODE) != 0) { if ((effectiveBlockedReasons & BLOCKED_REASON_RESTRICTED_MODE) != 0) {
// rejected in restricted mode, this is the default behavior. // rejected in restricted mode, this is the default behavior.
return FIREWALL_RULE_DEFAULT; return FIREWALL_RULE_DEFAULT;
} else { } else {
@@ -4292,12 +4309,10 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub {
mUidFirewallLowPowerStandbyModeRules.clear(); mUidFirewallLowPowerStandbyModeRules.clear();
for (int i = mUidState.size() - 1; i >= 0; i--) { for (int i = mUidState.size() - 1; i >= 0; i--) {
final int uid = mUidState.keyAt(i); final int uid = mUidState.keyAt(i);
UidBlockedState uidBlockedState = mUidBlockedState.get(uid); final int effectiveBlockedReasons = getEffectiveBlockedReasons(uid);
if (hasInternetPermissionUL(uid) && uidBlockedState != null if (hasInternetPermissionUL(uid) && (effectiveBlockedReasons
&& (uidBlockedState.effectiveBlockedReasons
& BLOCKED_REASON_LOW_POWER_STANDBY) == 0) { & BLOCKED_REASON_LOW_POWER_STANDBY) == 0) {
mUidFirewallLowPowerStandbyModeRules.put(mUidBlockedState.keyAt(i), mUidFirewallLowPowerStandbyModeRules.put(uid, FIREWALL_RULE_ALLOW);
FIREWALL_RULE_ALLOW);
} }
} }
setUidFirewallRulesUL(FIREWALL_CHAIN_LOW_POWER_STANDBY, setUidFirewallRulesUL(FIREWALL_CHAIN_LOW_POWER_STANDBY,
@@ -4316,10 +4331,9 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub {
return; return;
} }
final UidBlockedState uidBlockedState = mUidBlockedState.get(uid); final int effectiveBlockedReasons = getEffectiveBlockedReasons(uid);
if (mUidState.contains(uid) && uidBlockedState != null if (mUidState.contains(uid)
&& (uidBlockedState.effectiveBlockedReasons & BLOCKED_REASON_LOW_POWER_STANDBY) && (effectiveBlockedReasons & BLOCKED_REASON_LOW_POWER_STANDBY) == 0) {
== 0) {
mUidFirewallLowPowerStandbyModeRules.put(uid, FIREWALL_RULE_ALLOW); mUidFirewallLowPowerStandbyModeRules.put(uid, FIREWALL_RULE_ALLOW);
setUidFirewallRuleUL(FIREWALL_CHAIN_LOW_POWER_STANDBY, uid, FIREWALL_RULE_ALLOW); setUidFirewallRuleUL(FIREWALL_CHAIN_LOW_POWER_STANDBY, uid, FIREWALL_RULE_ALLOW);
} else { } else {
@@ -4448,9 +4462,8 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub {
if (!isUidValidForDenylistRulesUL(uid)) { if (!isUidValidForDenylistRulesUL(uid)) {
continue; continue;
} }
final UidBlockedState uidBlockedState = getOrCreateUidBlockedStateForUid( final int blockedReasons = getBlockedReasons(uid);
mUidBlockedState, uid); if (!enableChain && (blockedReasons & ~BLOCKED_METERED_REASON_MASK)
if (!enableChain && (uidBlockedState.blockedReasons & ~BLOCKED_METERED_REASON_MASK)
== BLOCKED_REASON_NONE) { == BLOCKED_REASON_NONE) {
// Chain isn't enabled and the uid had no restrictions to begin with. // Chain isn't enabled and the uid had no restrictions to begin with.
continue; continue;
@@ -4692,7 +4705,9 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub {
@GuardedBy("mUidRulesFirstLock") @GuardedBy("mUidRulesFirstLock")
private void onUidDeletedUL(int uid) { private void onUidDeletedUL(int uid) {
// First cleanup in-memory state synchronously... // First cleanup in-memory state synchronously...
mUidBlockedState.delete(uid); synchronized (mUidBlockedState) {
mUidBlockedState.delete(uid);
}
mUidPolicy.delete(uid); mUidPolicy.delete(uid);
mUidFirewallStandbyRules.delete(uid); mUidFirewallStandbyRules.delete(uid);
mUidFirewallDozableRules.delete(uid); mUidFirewallDozableRules.delete(uid);
@@ -4804,11 +4819,6 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub {
final int uidPolicy = mUidPolicy.get(uid, POLICY_NONE); final int uidPolicy = mUidPolicy.get(uid, POLICY_NONE);
final boolean isForeground = isUidForegroundOnRestrictBackgroundUL(uid); final boolean isForeground = isUidForegroundOnRestrictBackgroundUL(uid);
final boolean isRestrictedByAdmin = isRestrictedByAdminUL(uid); final boolean isRestrictedByAdmin = isRestrictedByAdminUL(uid);
final UidBlockedState uidBlockedState = getOrCreateUidBlockedStateForUid(
mUidBlockedState, uid);
final UidBlockedState previousUidBlockedState = getOrCreateUidBlockedStateForUid(
mTmpUidBlockedState, uid);
previousUidBlockedState.copyFrom(uidBlockedState);
final boolean isDenied = (uidPolicy & POLICY_REJECT_METERED_BACKGROUND) != 0; final boolean isDenied = (uidPolicy & POLICY_REJECT_METERED_BACKGROUND) != 0;
final boolean isAllowed = (uidPolicy & POLICY_ALLOW_METERED_BACKGROUND) != 0; final boolean isAllowed = (uidPolicy & POLICY_ALLOW_METERED_BACKGROUND) != 0;
@@ -4823,18 +4833,47 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub {
newAllowedReasons |= (isForeground ? ALLOWED_METERED_REASON_FOREGROUND : 0); newAllowedReasons |= (isForeground ? ALLOWED_METERED_REASON_FOREGROUND : 0);
newAllowedReasons |= (isAllowed ? ALLOWED_METERED_REASON_USER_EXEMPTED : 0); newAllowedReasons |= (isAllowed ? ALLOWED_METERED_REASON_USER_EXEMPTED : 0);
uidBlockedState.blockedReasons = (uidBlockedState.blockedReasons final int oldEffectiveBlockedReasons;
& ~BLOCKED_METERED_REASON_MASK) | newBlockedReasons; final int newEffectiveBlockedReasons;
uidBlockedState.allowedReasons = (uidBlockedState.allowedReasons final int oldAllowedReasons;
& ~ALLOWED_METERED_REASON_MASK) | newAllowedReasons; final int uidRules;
uidBlockedState.updateEffectiveBlockedReasons(); synchronized (mUidBlockedState) {
final int oldEffectiveBlockedReasons = previousUidBlockedState.effectiveBlockedReasons; final UidBlockedState uidBlockedState = getOrCreateUidBlockedStateForUid(
final int newEffectiveBlockedReasons = uidBlockedState.effectiveBlockedReasons; mUidBlockedState, uid);
final UidBlockedState previousUidBlockedState = getOrCreateUidBlockedStateForUid(
mTmpUidBlockedState, uid);
previousUidBlockedState.copyFrom(uidBlockedState);
uidBlockedState.blockedReasons = (uidBlockedState.blockedReasons
& ~BLOCKED_METERED_REASON_MASK) | newBlockedReasons;
uidBlockedState.allowedReasons = (uidBlockedState.allowedReasons
& ~ALLOWED_METERED_REASON_MASK) | newAllowedReasons;
uidBlockedState.updateEffectiveBlockedReasons();
oldEffectiveBlockedReasons = previousUidBlockedState.effectiveBlockedReasons;
newEffectiveBlockedReasons = uidBlockedState.effectiveBlockedReasons;
oldAllowedReasons = previousUidBlockedState.allowedReasons;
uidRules = (oldEffectiveBlockedReasons == newEffectiveBlockedReasons)
? RULE_NONE : uidBlockedState.deriveUidRules();
if (LOGV) {
Log.v(TAG, "updateRuleForRestrictBackgroundUL(" + uid + ")"
+ ": isForeground=" + isForeground
+ ", isDenied=" + isDenied
+ ", isAllowed=" + isAllowed
+ ", isRestrictedByAdmin=" + isRestrictedByAdmin
+ ", oldBlockedState=" + previousUidBlockedState
+ ", newBlockedState=" + uidBlockedState
+ ", newBlockedMeteredReasons=" + blockedReasonsToString(newBlockedReasons)
+ ", newAllowedMeteredReasons=" + allowedReasonsToString(
newAllowedReasons));
}
}
if (oldEffectiveBlockedReasons != newEffectiveBlockedReasons) { if (oldEffectiveBlockedReasons != newEffectiveBlockedReasons) {
postBlockedReasonsChangedMsg(uid, postBlockedReasonsChangedMsg(uid,
newEffectiveBlockedReasons, oldEffectiveBlockedReasons); newEffectiveBlockedReasons, oldEffectiveBlockedReasons);
postUidRulesChangedMsg(uid, uidBlockedState.deriveUidRules()); postUidRulesChangedMsg(uid, uidRules);
} }
// Note that the conditionals below are for avoiding unnecessary calls to netd. // Note that the conditionals below are for avoiding unnecessary calls to netd.
@@ -4850,29 +4889,11 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub {
} }
final int allowlistReasons = ALLOWED_METERED_REASON_FOREGROUND final int allowlistReasons = ALLOWED_METERED_REASON_FOREGROUND
| ALLOWED_METERED_REASON_USER_EXEMPTED; | ALLOWED_METERED_REASON_USER_EXEMPTED;
final int oldAllowedReasons = previousUidBlockedState.allowedReasons;
if ((oldAllowedReasons & allowlistReasons) != ALLOWED_REASON_NONE if ((oldAllowedReasons & allowlistReasons) != ALLOWED_REASON_NONE
|| (newAllowedReasons & allowlistReasons) != ALLOWED_REASON_NONE) { || (newAllowedReasons & allowlistReasons) != ALLOWED_REASON_NONE) {
setMeteredNetworkAllowlist(uid, setMeteredNetworkAllowlist(uid,
(newAllowedReasons & allowlistReasons) != ALLOWED_REASON_NONE); (newAllowedReasons & allowlistReasons) != ALLOWED_REASON_NONE);
} }
if (LOGV) {
Log.v(TAG, "updateRuleForRestrictBackgroundUL(" + uid + ")"
+ ": isForeground=" +isForeground
+ ", isDenied=" + isDenied
+ ", isAllowed=" + isAllowed
+ ", isRestrictedByAdmin=" + isRestrictedByAdmin
+ ", oldBlockedState=" + previousUidBlockedState.toString()
+ ", newBlockedState=" + uidBlockedState.toString()
+ ", oldBlockedMeteredReasons=" + NetworkPolicyManager.blockedReasonsToString(
uidBlockedState.blockedReasons & BLOCKED_METERED_REASON_MASK)
+ ", oldBlockedMeteredEffectiveReasons="
+ NetworkPolicyManager.blockedReasonsToString(
uidBlockedState.effectiveBlockedReasons & BLOCKED_METERED_REASON_MASK)
+ ", oldAllowedMeteredReasons=" + NetworkPolicyManager.blockedReasonsToString(
uidBlockedState.allowedReasons & BLOCKED_METERED_REASON_MASK));
}
} }
/** /**
@@ -4932,56 +4953,66 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub {
final boolean isWhitelisted = isWhitelistedFromPowerSaveUL(uid, mDeviceIdleMode); final boolean isWhitelisted = isWhitelistedFromPowerSaveUL(uid, mDeviceIdleMode);
final UidBlockedState uidBlockedState = getOrCreateUidBlockedStateForUid( final int oldEffectiveBlockedReasons;
mUidBlockedState, uid); final int newEffectiveBlockedReasons;
final UidBlockedState previousUidBlockedState = getOrCreateUidBlockedStateForUid( final int uidRules;
mTmpUidBlockedState, uid); synchronized (mUidBlockedState) {
previousUidBlockedState.copyFrom(uidBlockedState); final UidBlockedState uidBlockedState = getOrCreateUidBlockedStateForUid(
mUidBlockedState, uid);
final UidBlockedState previousUidBlockedState = getOrCreateUidBlockedStateForUid(
mTmpUidBlockedState, uid);
previousUidBlockedState.copyFrom(uidBlockedState);
int newBlockedReasons = BLOCKED_REASON_NONE; int newBlockedReasons = BLOCKED_REASON_NONE;
int newAllowedReasons = ALLOWED_REASON_NONE; int newAllowedReasons = ALLOWED_REASON_NONE;
newBlockedReasons |= (mRestrictPower ? BLOCKED_REASON_BATTERY_SAVER : 0); newBlockedReasons |= (mRestrictPower ? BLOCKED_REASON_BATTERY_SAVER : 0);
newBlockedReasons |= (mDeviceIdleMode ? BLOCKED_REASON_DOZE : 0); newBlockedReasons |= (mDeviceIdleMode ? BLOCKED_REASON_DOZE : 0);
newBlockedReasons |= (mLowPowerStandbyActive ? BLOCKED_REASON_LOW_POWER_STANDBY : 0); newBlockedReasons |= (mLowPowerStandbyActive ? BLOCKED_REASON_LOW_POWER_STANDBY : 0);
newBlockedReasons |= (isUidIdle ? BLOCKED_REASON_APP_STANDBY : 0); newBlockedReasons |= (isUidIdle ? BLOCKED_REASON_APP_STANDBY : 0);
newBlockedReasons |= (uidBlockedState.blockedReasons & BLOCKED_REASON_RESTRICTED_MODE); newBlockedReasons |= (uidBlockedState.blockedReasons & BLOCKED_REASON_RESTRICTED_MODE);
newAllowedReasons |= (isSystem(uid) ? ALLOWED_REASON_SYSTEM : 0); newAllowedReasons |= (isSystem(uid) ? ALLOWED_REASON_SYSTEM : 0);
newAllowedReasons |= (isForeground ? ALLOWED_REASON_FOREGROUND : 0); newAllowedReasons |= (isForeground ? ALLOWED_REASON_FOREGROUND : 0);
newAllowedReasons |= (isTop ? ALLOWED_REASON_TOP : 0); newAllowedReasons |= (isTop ? ALLOWED_REASON_TOP : 0);
newAllowedReasons |= (isWhitelistedFromPowerSaveUL(uid, true) newAllowedReasons |= (isWhitelistedFromPowerSaveUL(uid, true)
? ALLOWED_REASON_POWER_SAVE_ALLOWLIST : 0); ? ALLOWED_REASON_POWER_SAVE_ALLOWLIST : 0);
newAllowedReasons |= (isWhitelistedFromPowerSaveExceptIdleUL(uid) newAllowedReasons |= (isWhitelistedFromPowerSaveExceptIdleUL(uid)
? ALLOWED_REASON_POWER_SAVE_EXCEPT_IDLE_ALLOWLIST : 0); ? ALLOWED_REASON_POWER_SAVE_EXCEPT_IDLE_ALLOWLIST : 0);
newAllowedReasons |= (uidBlockedState.allowedReasons newAllowedReasons |= (uidBlockedState.allowedReasons
& ALLOWED_REASON_RESTRICTED_MODE_PERMISSIONS); & ALLOWED_REASON_RESTRICTED_MODE_PERMISSIONS);
newAllowedReasons |= (isAllowlistedFromLowPowerStandbyUL(uid)) newAllowedReasons |= (isAllowlistedFromLowPowerStandbyUL(uid))
? ALLOWED_REASON_LOW_POWER_STANDBY_ALLOWLIST : 0; ? ALLOWED_REASON_LOW_POWER_STANDBY_ALLOWLIST : 0;
uidBlockedState.blockedReasons = (uidBlockedState.blockedReasons uidBlockedState.blockedReasons = (uidBlockedState.blockedReasons
& BLOCKED_METERED_REASON_MASK) | newBlockedReasons; & BLOCKED_METERED_REASON_MASK) | newBlockedReasons;
uidBlockedState.allowedReasons = (uidBlockedState.allowedReasons uidBlockedState.allowedReasons = (uidBlockedState.allowedReasons
& ALLOWED_METERED_REASON_MASK) | newAllowedReasons; & ALLOWED_METERED_REASON_MASK) | newAllowedReasons;
uidBlockedState.updateEffectiveBlockedReasons(); uidBlockedState.updateEffectiveBlockedReasons();
if (previousUidBlockedState.effectiveBlockedReasons
!= uidBlockedState.effectiveBlockedReasons) {
postBlockedReasonsChangedMsg(uid,
uidBlockedState.effectiveBlockedReasons,
previousUidBlockedState.effectiveBlockedReasons);
postUidRulesChangedMsg(uid, uidBlockedState.deriveUidRules()); if (LOGV) {
Log.v(TAG, "updateRulesForPowerRestrictionsUL(" + uid + ")"
+ ", isIdle: " + isUidIdle
+ ", mRestrictPower: " + mRestrictPower
+ ", mDeviceIdleMode: " + mDeviceIdleMode
+ ", isForeground=" + isForeground
+ ", isTop=" + isTop
+ ", isWhitelisted=" + isWhitelisted
+ ", oldUidBlockedState=" + previousUidBlockedState
+ ", newUidBlockedState=" + uidBlockedState);
}
oldEffectiveBlockedReasons = previousUidBlockedState.effectiveBlockedReasons;
newEffectiveBlockedReasons = uidBlockedState.effectiveBlockedReasons;
uidRules = oldEffectiveBlockedReasons == newEffectiveBlockedReasons
? RULE_NONE
: uidBlockedState.deriveUidRules();
} }
if (oldEffectiveBlockedReasons != newEffectiveBlockedReasons) {
postBlockedReasonsChangedMsg(uid,
oldEffectiveBlockedReasons,
newEffectiveBlockedReasons);
if (LOGV) { postUidRulesChangedMsg(uid, uidRules);
Log.v(TAG, "updateRulesForPowerRestrictionsUL(" + uid + ")"
+ ", isIdle: " + isUidIdle
+ ", mRestrictPower: " + mRestrictPower
+ ", mDeviceIdleMode: " + mDeviceIdleMode
+ ", isForeground=" + isForeground
+ ", isTop=" + isTop
+ ", isWhitelisted=" + isWhitelisted
+ ", oldUidBlockedState=" + previousUidBlockedState.toString()
+ ", newUidBlockedState=" + uidBlockedState.toString());
} }
} }
@@ -5766,7 +5797,7 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub {
mContext.enforceCallingOrSelfPermission(OBSERVE_NETWORK_POLICY, TAG); mContext.enforceCallingOrSelfPermission(OBSERVE_NETWORK_POLICY, TAG);
int blockedReasons; int blockedReasons;
synchronized (mUidRulesFirstLock) { synchronized (mUidBlockedState) {
final UidBlockedState uidBlockedState = mUidBlockedState.get(uid); final UidBlockedState uidBlockedState = mUidBlockedState.get(uid);
blockedReasons = uidBlockedState == null blockedReasons = uidBlockedState == null
? BLOCKED_REASON_NONE : uidBlockedState.effectiveBlockedReasons; ? BLOCKED_REASON_NONE : uidBlockedState.effectiveBlockedReasons;
@@ -5784,7 +5815,7 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub {
@Override @Override
public boolean isUidRestrictedOnMeteredNetworks(int uid) { public boolean isUidRestrictedOnMeteredNetworks(int uid) {
mContext.enforceCallingOrSelfPermission(OBSERVE_NETWORK_POLICY, TAG); mContext.enforceCallingOrSelfPermission(OBSERVE_NETWORK_POLICY, TAG);
synchronized (mUidRulesFirstLock) { synchronized (mUidBlockedState) {
final UidBlockedState uidBlockedState = mUidBlockedState.get(uid); final UidBlockedState uidBlockedState = mUidBlockedState.get(uid);
int blockedReasons = uidBlockedState == null int blockedReasons = uidBlockedState == null
? BLOCKED_REASON_NONE : uidBlockedState.effectiveBlockedReasons; ? BLOCKED_REASON_NONE : uidBlockedState.effectiveBlockedReasons;
@@ -6032,10 +6063,6 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub {
return restrictedUids != null && restrictedUids.contains(uid); return restrictedUids != null && restrictedUids.contains(uid);
} }
private static boolean hasRule(int uidRules, int rule) {
return (uidRules & rule) != 0;
}
private static boolean getBooleanDefeatingNullable(@Nullable PersistableBundle bundle, private static boolean getBooleanDefeatingNullable(@Nullable PersistableBundle bundle,
String key, boolean defaultValue) { String key, boolean defaultValue) {
return (bundle != null) ? bundle.getBoolean(key, defaultValue) : defaultValue; return (bundle != null) ? bundle.getBoolean(key, defaultValue) : defaultValue;
@@ -6051,16 +6078,39 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub {
return uidBlockedState; return uidBlockedState;
} }
private int getEffectiveBlockedReasons(int uid) {
synchronized (mUidBlockedState) {
final UidBlockedState uidBlockedState = mUidBlockedState.get(uid);
return uidBlockedState == null
? BLOCKED_REASON_NONE
: uidBlockedState.effectiveBlockedReasons;
}
}
private int getBlockedReasons(int uid) {
synchronized (mUidBlockedState) {
final UidBlockedState uidBlockedState = mUidBlockedState.get(uid);
return uidBlockedState == null
? BLOCKED_REASON_NONE
: uidBlockedState.blockedReasons;
}
}
@VisibleForTesting @VisibleForTesting
static final class UidBlockedState { static final class UidBlockedState {
public int blockedReasons; public int blockedReasons;
public int allowedReasons; public int allowedReasons;
public int effectiveBlockedReasons; public int effectiveBlockedReasons;
private UidBlockedState(int blockedReasons, int allowedReasons,
int effectiveBlockedReasons) {
this.blockedReasons = blockedReasons;
this.allowedReasons = allowedReasons;
this.effectiveBlockedReasons = effectiveBlockedReasons;
}
UidBlockedState() { UidBlockedState() {
blockedReasons = BLOCKED_REASON_NONE; this(BLOCKED_REASON_NONE, ALLOWED_REASON_NONE, BLOCKED_REASON_NONE);
allowedReasons = ALLOWED_REASON_NONE;
effectiveBlockedReasons = BLOCKED_REASON_NONE;
} }
void updateEffectiveBlockedReasons() { void updateEffectiveBlockedReasons() {
@@ -6297,7 +6347,7 @@ public class NetworkPolicyManagerService extends INetworkPolicyManager.Stub {
} }
} }
if (LOGV) { if (LOGV) {
Slog.v(TAG, "uidBlockedState=" + this.toString() Slog.v(TAG, "uidBlockedState=" + this
+ " -> uidRule=" + uidRulesToString(uidRule)); + " -> uidRule=" + uidRulesToString(uidRule));
} }
return uidRule; return uidRule;