diff options
6 files changed, 193 insertions, 100 deletions
diff --git a/core/java/android/net/NetworkRecommendationProvider.java b/core/java/android/net/NetworkRecommendationProvider.java index fdb4ba073893..a70c97bac10c 100644 --- a/core/java/android/net/NetworkRecommendationProvider.java +++ b/core/java/android/net/NetworkRecommendationProvider.java @@ -35,6 +35,7 @@ import java.util.concurrent.Executor; * A network recommendation provider is any application which: * <ul> * <li>Is granted the {@link permission#SCORE_NETWORKS} permission. + * <li>Is granted the {@link permission#ACCESS_COARSE_LOCATION} permission. * <li>Includes a Service for the {@link NetworkScoreManager#ACTION_RECOMMEND_NETWORKS} intent * which is protected by the {@link permission#BIND_NETWORK_RECOMMENDATION_SERVICE} permission. * </ul> diff --git a/core/java/android/net/NetworkScoreManager.java b/core/java/android/net/NetworkScoreManager.java index 7e0c9ce33b82..060af0dd1ba1 100644 --- a/core/java/android/net/NetworkScoreManager.java +++ b/core/java/android/net/NetworkScoreManager.java @@ -38,7 +38,8 @@ import java.util.List; * * <p>A network scorer is any application which: * <ul> - * <li>Declares the {@link permission#SCORE_NETWORKS} permission. + * <li>Is granted the {@link permission#SCORE_NETWORKS} permission. + * <li>Is granted the {@link permission#ACCESS_COARSE_LOCATION} permission. * <li>Include a Service for the {@link #ACTION_RECOMMEND_NETWORKS} action * protected by the {@link permission#BIND_NETWORK_RECOMMENDATION_SERVICE} * permission. diff --git a/core/res/res/values/config.xml b/core/res/res/values/config.xml index 40380100121a..b27907d1750b 100644 --- a/core/res/res/values/config.xml +++ b/core/res/res/values/config.xml @@ -1388,6 +1388,7 @@ <!-- The package name of the default network recommendation app. A network recommendation provider must: * Be granted the SCORE_NETWORKS permission. + * Be granted the ACCESS_COARSE_LOCATION permission. * Include a Service for the android.net.scoring.RECOMMEND_NETWORKS action protected by the BIND_NETWORK_RECOMMENDATION_SERVICE permission. diff --git a/services/core/java/com/android/server/NetworkScoreService.java b/services/core/java/com/android/server/NetworkScoreService.java index fdc0bba09a52..d60df83da68e 100644 --- a/services/core/java/com/android/server/NetworkScoreService.java +++ b/services/core/java/com/android/server/NetworkScoreService.java @@ -27,6 +27,7 @@ import android.content.IntentFilter; import android.content.ServiceConnection; import android.content.pm.PackageManager; import android.database.ContentObserver; +import android.location.LocationManager; import android.net.INetworkRecommendationProvider; import android.net.INetworkScoreCache; import android.net.INetworkScoreService; @@ -113,6 +114,16 @@ public class NetworkScoreService extends INetworkScoreService.Stub { } }; + private BroadcastReceiver mLocationModeReceiver = new BroadcastReceiver() { + @Override + public void onReceive(Context context, Intent intent) { + final String action = intent.getAction(); + if (LocationManager.MODE_CHANGED_ACTION.equals(action)) { + refreshBinding(); + } + } + }; + /** * Clears scores when the active scorer package is no longer valid and * manages the service connection. @@ -241,6 +252,10 @@ public class NetworkScoreService extends INetworkScoreService.Stub { mUserIntentReceiver, UserHandle.SYSTEM, filter, null /* broadcastPermission*/, null /* scheduler */); mHandler = new ServiceHandler(looper); + IntentFilter locationModeFilter = new IntentFilter(LocationManager.MODE_CHANGED_ACTION); + mContext.registerReceiverAsUser( + mLocationModeReceiver, UserHandle.SYSTEM, locationModeFilter, + null /* broadcastPermission*/, mHandler); mContentObserver = new DispatchingContentObserver(context, mHandler); mServiceConnProducer = serviceConnProducer; } diff --git a/services/core/java/com/android/server/NetworkScorerAppManager.java b/services/core/java/com/android/server/NetworkScorerAppManager.java index 42777bf33bd3..bfd4247abf40 100644 --- a/services/core/java/com/android/server/NetworkScorerAppManager.java +++ b/services/core/java/com/android/server/NetworkScorerAppManager.java @@ -18,6 +18,7 @@ package com.android.server; import android.Manifest.permission; import android.annotation.Nullable; +import android.app.AppOpsManager; import android.content.ComponentName; import android.content.Context; import android.content.Intent; @@ -79,7 +80,7 @@ public class NetworkScorerAppManager { List<NetworkScorerAppData> appDataList = new ArrayList<>(); for (int i = 0; i < resolveInfos.size(); i++) { final ServiceInfo serviceInfo = resolveInfos.get(i).serviceInfo; - if (hasPermissions(serviceInfo.packageName)) { + if (hasPermissions(serviceInfo.applicationInfo.uid, serviceInfo.packageName)) { if (VERBOSE) { Log.v(TAG, serviceInfo.packageName + " is a valid scorer/recommender."); } @@ -197,12 +198,33 @@ public class NetworkScorerAppManager { return null; } - private boolean hasPermissions(String packageName) { + private boolean hasPermissions(final int uid, final String packageName) { + return hasScoreNetworksPermission(packageName) + && canAccessLocation(uid, packageName); + } + + private boolean hasScoreNetworksPermission(String packageName) { final PackageManager pm = mContext.getPackageManager(); return pm.checkPermission(permission.SCORE_NETWORKS, packageName) == PackageManager.PERMISSION_GRANTED; } + private boolean canAccessLocation(int uid, String packageName) { + final PackageManager pm = mContext.getPackageManager(); + final AppOpsManager appOpsManager = + (AppOpsManager) mContext.getSystemService(Context.APP_OPS_SERVICE); + return isLocationModeEnabled() + && pm.checkPermission(permission.ACCESS_COARSE_LOCATION, packageName) + == PackageManager.PERMISSION_GRANTED + && appOpsManager.noteOp(AppOpsManager.OP_COARSE_LOCATION, uid, packageName) + == AppOpsManager.MODE_ALLOWED; + } + + private boolean isLocationModeEnabled() { + return mSettingsFacade.getSecureInt(mContext, Settings.Secure.LOCATION_MODE, + Settings.Secure.LOCATION_MODE_OFF) != Settings.Secure.LOCATION_MODE_OFF; + } + /** * Set the specified package as the default scorer application. * @@ -270,23 +292,20 @@ public class NetworkScorerAppManager { return; } - // the active scorer isn't valid, revert to the default if it's different + int newEnabledSetting = NetworkScoreManager.RECOMMENDATIONS_ENABLED_OFF; + // the active scorer isn't valid, revert to the default if it's different and valid final String defaultPackageName = getDefaultPackageSetting(); - if (!TextUtils.equals(currentPackageName, defaultPackageName)) { - setNetworkRecommendationsPackage(defaultPackageName); + if (!TextUtils.equals(currentPackageName, defaultPackageName) + && getScorer(defaultPackageName) != null) { if (DEBUG) { - Log.d(TAG, "Defaulted the network recommendations app to: " + defaultPackageName); - } - if (getScorer(defaultPackageName) != null) { // the default is valid - if (DEBUG) Log.d(TAG, defaultPackageName + " is now the active scorer."); - setNetworkRecommendationsEnabledSetting( - NetworkScoreManager.RECOMMENDATIONS_ENABLED_ON); - } else { // the default isn't valid either, we're disabled at this point - if (DEBUG) Log.d(TAG, defaultPackageName + " is not an active scorer."); - setNetworkRecommendationsEnabledSetting( - NetworkScoreManager.RECOMMENDATIONS_ENABLED_OFF); + Log.d(TAG, "Defaulting the network recommendations app to: " + + defaultPackageName); } + setNetworkRecommendationsPackage(defaultPackageName); + newEnabledSetting = NetworkScoreManager.RECOMMENDATIONS_ENABLED_ON; } + + setNetworkRecommendationsEnabledSetting(newEnabledSetting); } /** @@ -352,6 +371,9 @@ public class NetworkScorerAppManager { private void setNetworkRecommendationsPackage(String packageName) { mSettingsFacade.putString(mContext, Settings.Global.NETWORK_RECOMMENDATIONS_PACKAGE, packageName); + if (VERBOSE) { + Log.d(TAG, Settings.Global.NETWORK_RECOMMENDATIONS_PACKAGE + " set to " + packageName); + } } private int getNetworkRecommendationsEnabledSetting() { @@ -361,6 +383,9 @@ public class NetworkScorerAppManager { private void setNetworkRecommendationsEnabledSetting(int value) { mSettingsFacade.putInt(mContext, Settings.Global.NETWORK_RECOMMENDATIONS_ENABLED, value); + if (VERBOSE) { + Log.d(TAG, Settings.Global.NETWORK_RECOMMENDATIONS_ENABLED + " set to " + value); + } } /** @@ -382,5 +407,9 @@ public class NetworkScorerAppManager { public int getInt(Context context, String name, int defaultValue) { return Settings.Global.getInt(context.getContentResolver(), name, defaultValue); } + + public int getSecureInt(Context context, String name, int defaultValue) { + return Settings.Secure.getInt(context.getContentResolver(), name, defaultValue); + } } } diff --git a/services/tests/servicestests/src/com/android/server/NetworkScorerAppManagerTest.java b/services/tests/servicestests/src/com/android/server/NetworkScorerAppManagerTest.java index ceb92dece764..82ff0d835f33 100644 --- a/services/tests/servicestests/src/com/android/server/NetworkScorerAppManagerTest.java +++ b/services/tests/servicestests/src/com/android/server/NetworkScorerAppManagerTest.java @@ -31,6 +31,7 @@ import static org.mockito.Mockito.verify; import static org.mockito.Mockito.when; import android.Manifest.permission; +import android.app.AppOpsManager; import android.content.ComponentName; import android.content.Context; import android.content.Intent; @@ -61,15 +62,18 @@ import java.util.List; @RunWith(AndroidJUnit4.class) public class NetworkScorerAppManagerTest { + private static final int PACKAGE_UID = 924; private static String MOCK_SERVICE_LABEL = "Mock Service"; private static String MOCK_OVERRIDEN_SERVICE_LABEL = "Mock Service Label Override"; private static String MOCK_NETWORK_AVAILABLE_NOTIFICATION_CHANNEL_ID = "Mock Network Available Notification Channel Id"; + private static final ComponentName RECO_COMPONENT = new ComponentName("package1", "class1"); @Mock private Context mMockContext; @Mock private PackageManager mMockPm; @Mock private Resources mResources; @Mock private NetworkScorerAppManager.SettingsFacade mSettingsFacade; + @Mock private AppOpsManager mAppOpsManager; private NetworkScorerAppManager mNetworkScorerAppManager; private List<ResolveInfo> mAvailableServices; @@ -86,45 +90,69 @@ public class NetworkScorerAppManagerTest { } }), eq(PackageManager.GET_META_DATA))).thenReturn(mAvailableServices); when(mMockContext.getResources()).thenReturn(mResources); + when(mMockContext.getSystemService(Context.APP_OPS_SERVICE)).thenReturn(mAppOpsManager); + + mockLocationModeOn(); + mockLocationPermissionGranted(PACKAGE_UID, RECO_COMPONENT.getPackageName()); mNetworkScorerAppManager = new NetworkScorerAppManager(mMockContext, mSettingsFacade); } @Test public void testGetActiveScorer_providerAvailable() throws Exception { - final ComponentName recoComponent = new ComponentName("package1", "class1"); - setNetworkRecoPackageSetting(recoComponent.getPackageName()); - mockScoreNetworksGranted(recoComponent.getPackageName()); - mockRecommendationServiceAvailable(recoComponent, 924 /* packageUid */); + setNetworkRecoPackageSetting(RECO_COMPONENT.getPackageName()); + mockScoreNetworksGranted(RECO_COMPONENT.getPackageName()); + mockRecommendationServiceAvailable(RECO_COMPONENT, PACKAGE_UID /* packageUid */); final NetworkScorerAppData activeScorer = mNetworkScorerAppManager.getActiveScorer(); assertNotNull(activeScorer); - assertEquals(recoComponent, activeScorer.getRecommendationServiceComponent()); - assertEquals(924, activeScorer.packageUid); + assertEquals(RECO_COMPONENT, activeScorer.getRecommendationServiceComponent()); + assertEquals(PACKAGE_UID, activeScorer.packageUid); assertEquals(MOCK_SERVICE_LABEL, activeScorer.getRecommendationServiceLabel()); } @Test public void testGetActiveScorer_providerAvailable_serviceLabelOverride() throws Exception { - final ComponentName recoComponent = new ComponentName("package1", "class1"); - setNetworkRecoPackageSetting(recoComponent.getPackageName()); - mockScoreNetworksGranted(recoComponent.getPackageName()); - mockRecommendationServiceAvailable(recoComponent, 924 /* packageUid */, + setNetworkRecoPackageSetting(RECO_COMPONENT.getPackageName()); + mockScoreNetworksGranted(RECO_COMPONENT.getPackageName()); + mockRecommendationServiceAvailable(RECO_COMPONENT, PACKAGE_UID /* packageUid */, null /* enableUseOpenWifiPackageActivityPackage*/, true /* serviceLabelOverride */); final NetworkScorerAppData activeScorer = mNetworkScorerAppManager.getActiveScorer(); assertNotNull(activeScorer); - assertEquals(recoComponent, activeScorer.getRecommendationServiceComponent()); - assertEquals(924, activeScorer.packageUid); + assertEquals(RECO_COMPONENT, activeScorer.getRecommendationServiceComponent()); + assertEquals(PACKAGE_UID, activeScorer.packageUid); assertEquals(MOCK_OVERRIDEN_SERVICE_LABEL, activeScorer.getRecommendationServiceLabel()); } @Test - public void testGetActiveScorer_permissionMissing() throws Exception { - final ComponentName recoComponent = new ComponentName("package1", "class1"); - setNetworkRecoPackageSetting(recoComponent.getPackageName()); - mockScoreNetworksDenied(recoComponent.getPackageName()); - mockRecommendationServiceAvailable(recoComponent, 924 /* packageUid */); + public void testGetActiveScorer_scoreNetworksPermissionMissing() throws Exception { + setNetworkRecoPackageSetting(RECO_COMPONENT.getPackageName()); + mockScoreNetworksDenied(RECO_COMPONENT.getPackageName()); + mockRecommendationServiceAvailable(RECO_COMPONENT, PACKAGE_UID /* packageUid */); + + final NetworkScorerAppData activeScorer = mNetworkScorerAppManager.getActiveScorer(); + assertNull(activeScorer); + } + + @Test + public void testGetActiveScorer_locationPermissionMissing() throws Exception { + setNetworkRecoPackageSetting(RECO_COMPONENT.getPackageName()); + mockScoreNetworksGranted(RECO_COMPONENT.getPackageName()); + mockLocationPermissionDenied(PACKAGE_UID, RECO_COMPONENT.getPackageName()); + mockRecommendationServiceAvailable(RECO_COMPONENT, PACKAGE_UID /* packageUid */); + + final NetworkScorerAppData activeScorer = mNetworkScorerAppManager.getActiveScorer(); + assertNull(activeScorer); + } + + @Test + public void testGetActiveScorer_locationModeOff() throws Exception { + setNetworkRecoPackageSetting(RECO_COMPONENT.getPackageName()); + mockScoreNetworksGranted(RECO_COMPONENT.getPackageName()); + mockLocationPermissionGranted(PACKAGE_UID, RECO_COMPONENT.getPackageName()); + mockLocationModeOff(); + mockRecommendationServiceAvailable(RECO_COMPONENT, PACKAGE_UID /* packageUid */); final NetworkScorerAppData activeScorer = mNetworkScorerAppManager.getActiveScorer(); assertNull(activeScorer); @@ -133,67 +161,63 @@ public class NetworkScorerAppManagerTest { @Test public void testGetActiveScorer_providerAvailable_enableUseOpenWifiActivityNotSet() throws Exception { - final ComponentName recoComponent = new ComponentName("package1", "class1"); - setNetworkRecoPackageSetting(recoComponent.getPackageName()); - mockScoreNetworksGranted(recoComponent.getPackageName()); - mockRecommendationServiceAvailable(recoComponent, 924 /* packageUid */, + setNetworkRecoPackageSetting(RECO_COMPONENT.getPackageName()); + mockScoreNetworksGranted(RECO_COMPONENT.getPackageName()); + mockRecommendationServiceAvailable(RECO_COMPONENT, PACKAGE_UID /* packageUid */, null /* enableUseOpenWifiPackageActivityPackage*/); final NetworkScorerAppData activeScorer = mNetworkScorerAppManager.getActiveScorer(); assertNotNull(activeScorer); - assertEquals(recoComponent, activeScorer.getRecommendationServiceComponent()); - assertEquals(924, activeScorer.packageUid); + assertEquals(RECO_COMPONENT, activeScorer.getRecommendationServiceComponent()); + assertEquals(PACKAGE_UID, activeScorer.packageUid); assertNull(activeScorer.getEnableUseOpenWifiActivity()); } @Test public void testGetActiveScorer_providerAvailable_enableUseOpenWifiActivityNotResolved() throws Exception { - final ComponentName recoComponent = new ComponentName("package1", "class1"); - setNetworkRecoPackageSetting(recoComponent.getPackageName()); - mockScoreNetworksGranted(recoComponent.getPackageName()); - mockRecommendationServiceAvailable(recoComponent, 924 /* packageUid */, + setNetworkRecoPackageSetting(RECO_COMPONENT.getPackageName()); + mockScoreNetworksGranted(RECO_COMPONENT.getPackageName()); + mockRecommendationServiceAvailable(RECO_COMPONENT, PACKAGE_UID /* packageUid */, "package2" /* enableUseOpenWifiPackageActivityPackage*/); final NetworkScorerAppData activeScorer = mNetworkScorerAppManager.getActiveScorer(); assertNotNull(activeScorer); - assertEquals(recoComponent, activeScorer.getRecommendationServiceComponent()); - assertEquals(924, activeScorer.packageUid); + assertEquals(RECO_COMPONENT, activeScorer.getRecommendationServiceComponent()); + assertEquals(PACKAGE_UID, activeScorer.packageUid); assertNull(activeScorer.getEnableUseOpenWifiActivity()); } @Test public void testGetActiveScorer_providerAvailable_enableUseOpenWifiActivityResolved() throws Exception { - final ComponentName recoComponent = new ComponentName("package1", "class1"); final ComponentName enableUseOpenWifiComponent = new ComponentName("package2", "class2"); - setNetworkRecoPackageSetting(recoComponent.getPackageName()); - mockScoreNetworksGranted(recoComponent.getPackageName()); - mockRecommendationServiceAvailable(recoComponent, 924 /* packageUid */, + setNetworkRecoPackageSetting(RECO_COMPONENT.getPackageName()); + mockScoreNetworksGranted(RECO_COMPONENT.getPackageName()); + mockRecommendationServiceAvailable(RECO_COMPONENT, PACKAGE_UID /* packageUid */, enableUseOpenWifiComponent.getPackageName()); mockEnableUseOpenWifiActivity(enableUseOpenWifiComponent); final NetworkScorerAppData activeScorer = mNetworkScorerAppManager.getActiveScorer(); assertNotNull(activeScorer); - assertEquals(recoComponent, activeScorer.getRecommendationServiceComponent()); - assertEquals(924, activeScorer.packageUid); + assertEquals(RECO_COMPONENT, activeScorer.getRecommendationServiceComponent()); + assertEquals(PACKAGE_UID, activeScorer.packageUid); assertEquals(enableUseOpenWifiComponent, activeScorer.getEnableUseOpenWifiActivity()); assertNull(activeScorer.getNetworkAvailableNotificationChannelId()); } @Test public void testGetActiveScorer_providerAvailable_networkAvailableNotificationChannelIdSet() { - final ComponentName recoComponent = new ComponentName("package1", "class1"); - setNetworkRecoPackageSetting(recoComponent.getPackageName()); - mockScoreNetworksGranted(recoComponent.getPackageName()); - mockRecommendationServiceAvailable(recoComponent, 924 /* packageUid */, + setNetworkRecoPackageSetting(RECO_COMPONENT.getPackageName()); + mockScoreNetworksGranted(RECO_COMPONENT.getPackageName()); + mockRecommendationServiceAvailable(RECO_COMPONENT, PACKAGE_UID /* packageUid */, null /* enableUseOpenWifiActivityPackage */, false /* serviceLabelOverride */, true /* setNotificationChannelId */); final NetworkScorerAppData activeScorer = mNetworkScorerAppManager.getActiveScorer(); assertNotNull(activeScorer); - assertEquals(recoComponent, activeScorer.getRecommendationServiceComponent()); - assertEquals(924, activeScorer.packageUid); + assertEquals(RECO_COMPONENT, activeScorer.getRecommendationServiceComponent()); + assertEquals(PACKAGE_UID, activeScorer.packageUid); assertEquals(MOCK_NETWORK_AVAILABLE_NOTIFICATION_CHANNEL_ID, activeScorer.getNetworkAvailableNotificationChannelId()); } @@ -209,9 +233,8 @@ public class NetworkScorerAppManagerTest { @Test public void testGetActiveScorer_packageSettingIsInvalid() throws Exception { - final ComponentName recoComponent = new ComponentName("package1", "class1"); - setDefaultNetworkRecommendationPackage(recoComponent.getPackageName()); - mockScoreNetworksGranted(recoComponent.getPackageName()); + setDefaultNetworkRecommendationPackage(RECO_COMPONENT.getPackageName()); + mockScoreNetworksGranted(RECO_COMPONENT.getPackageName()); // NETWORK_RECOMMENDATIONS_PACKAGE is set to a package that isn't a recommender. final NetworkScorerAppData activeScorer = mNetworkScorerAppManager.getActiveScorer(); @@ -249,12 +272,12 @@ public class NetworkScorerAppManagerTest { @Test public void testSetActiveScorer_validPackage() throws Exception { - String packageName = "package"; String newPackage = "newPackage"; - setNetworkRecoPackageSetting(packageName); + int newAppUid = 621; final ComponentName recoComponent = new ComponentName(newPackage, "class1"); mockScoreNetworksGranted(recoComponent.getPackageName()); - mockRecommendationServiceAvailable(recoComponent, 924 /* packageUid */, null); + mockRecommendationServiceAvailable(recoComponent, newAppUid, null); + mockLocationPermissionGranted(newAppUid, recoComponent.getPackageName()); assertTrue(mNetworkScorerAppManager.setActiveScorer(newPackage)); verify(mSettingsFacade).putString(mMockContext, @@ -289,11 +312,9 @@ public class NetworkScorerAppManagerTest { @Test public void testUpdateState_currentPackageValid() throws Exception { - String packageName = "package"; - setNetworkRecoPackageSetting(packageName); - final ComponentName recoComponent = new ComponentName(packageName, "class1"); - mockScoreNetworksGranted(recoComponent.getPackageName()); - mockRecommendationServiceAvailable(recoComponent, 924 /* packageUid */, null); + setNetworkRecoPackageSetting(RECO_COMPONENT.getPackageName()); + mockScoreNetworksGranted(RECO_COMPONENT.getPackageName()); + mockRecommendationServiceAvailable(RECO_COMPONENT, PACKAGE_UID , null); mNetworkScorerAppManager.updateState(); @@ -306,11 +327,13 @@ public class NetworkScorerAppManagerTest { @Test public void testUpdateState_currentPackageNotValid_validDefault() throws Exception { - String defaultPackage = "defaultPackage"; - setDefaultNetworkRecommendationPackage(defaultPackage); + final String defaultPackage = "defaultPackage"; + final int defaultAppUid = 621; final ComponentName recoComponent = new ComponentName(defaultPackage, "class1"); + setDefaultNetworkRecommendationPackage(defaultPackage); mockScoreNetworksGranted(recoComponent.getPackageName()); - mockRecommendationServiceAvailable(recoComponent, 924 /* packageUid */, null); + mockRecommendationServiceAvailable(recoComponent, defaultAppUid, null); + mockLocationPermissionGranted(defaultAppUid, defaultPackage); mNetworkScorerAppManager.updateState(); @@ -329,8 +352,6 @@ public class NetworkScorerAppManagerTest { mNetworkScorerAppManager.updateState(); - verify(mSettingsFacade).putString(mMockContext, - Settings.Global.NETWORK_RECOMMENDATIONS_PACKAGE, defaultPackage); verify(mSettingsFacade).putInt(mMockContext, Settings.Global.NETWORK_RECOMMENDATIONS_ENABLED, NetworkScoreManager.RECOMMENDATIONS_ENABLED_OFF); @@ -345,8 +366,9 @@ public class NetworkScorerAppManagerTest { verify(mSettingsFacade, never()).putString(any(), eq(Settings.Global.NETWORK_RECOMMENDATIONS_PACKAGE), anyString()); - verify(mSettingsFacade, never()).putInt(any(), - eq(Settings.Global.NETWORK_RECOMMENDATIONS_ENABLED), anyInt()); + verify(mSettingsFacade).putInt(mMockContext, + Settings.Global.NETWORK_RECOMMENDATIONS_ENABLED, + NetworkScoreManager.RECOMMENDATIONS_ENABLED_OFF); } @Test @@ -358,8 +380,9 @@ public class NetworkScorerAppManagerTest { verify(mSettingsFacade, never()).putString(any(), eq(Settings.Global.NETWORK_RECOMMENDATIONS_PACKAGE), anyString()); - verify(mSettingsFacade, never()).putInt(any(), - eq(Settings.Global.NETWORK_RECOMMENDATIONS_ENABLED), anyInt()); + verify(mSettingsFacade).putInt(mMockContext, + Settings.Global.NETWORK_RECOMMENDATIONS_ENABLED, + NetworkScoreManager.RECOMMENDATIONS_ENABLED_OFF); } @Test @@ -370,8 +393,9 @@ public class NetworkScorerAppManagerTest { mNetworkScorerAppManager.updateState(); - verify(mSettingsFacade, never()).putString(any(), - eq(Settings.Global.NETWORK_RECOMMENDATIONS_PACKAGE), any()); + verify(mSettingsFacade).putInt(mMockContext, + Settings.Global.NETWORK_RECOMMENDATIONS_ENABLED, + NetworkScoreManager.RECOMMENDATIONS_ENABLED_OFF); } @Test @@ -415,11 +439,10 @@ public class NetworkScorerAppManagerTest { @Test public void testMigrateNetworkScorerAppSettingIfNeeded_useOpenWifiSettingIsNotEmpty() throws Exception { - final ComponentName recoComponent = new ComponentName("package1", "class1"); final ComponentName enableUseOpenWifiComponent = new ComponentName("package2", "class2"); - setNetworkRecoPackageSetting(recoComponent.getPackageName()); - mockScoreNetworksGranted(recoComponent.getPackageName()); - mockRecommendationServiceAvailable(recoComponent, 924 /* packageUid */, + setNetworkRecoPackageSetting(RECO_COMPONENT.getPackageName()); + mockScoreNetworksGranted(RECO_COMPONENT.getPackageName()); + mockRecommendationServiceAvailable(RECO_COMPONENT, PACKAGE_UID /* packageUid */, enableUseOpenWifiComponent.getPackageName()); mockEnableUseOpenWifiActivity(enableUseOpenWifiComponent); when(mSettingsFacade.getString(mMockContext, @@ -441,13 +464,12 @@ public class NetworkScorerAppManagerTest { @Test public void testMigrateNetworkScorerAppSettingIfNeeded_useOpenWifiActivityNotAvail() throws Exception { - final ComponentName recoComponent = new ComponentName("package1", "class1"); final ComponentName enableUseOpenWifiComponent = new ComponentName("package2", "class2"); - setNetworkRecoPackageSetting(recoComponent.getPackageName()); - mockScoreNetworksGranted(recoComponent.getPackageName()); + setNetworkRecoPackageSetting(RECO_COMPONENT.getPackageName()); + mockScoreNetworksGranted(RECO_COMPONENT.getPackageName()); // The active component doesn't have an open wifi activity so the migration shouldn't // set USE_OPEN_WIFI_PACKAGE. - mockRecommendationServiceAvailable(recoComponent, 924 /* packageUid */, + mockRecommendationServiceAvailable(RECO_COMPONENT, PACKAGE_UID /* packageUid */, null /*useOpenWifiActivityPackage*/); when(mSettingsFacade.getString(mMockContext, Settings.Global.NETWORK_SCORER_APP)) @@ -466,11 +488,10 @@ public class NetworkScorerAppManagerTest { @Test public void testMigrateNetworkScorerAppSettingIfNeeded_packageMismatch_activity() throws Exception { - final ComponentName recoComponent = new ComponentName("package1", "class1"); final ComponentName enableUseOpenWifiComponent = new ComponentName("package2", "class2"); - setNetworkRecoPackageSetting(recoComponent.getPackageName()); - mockScoreNetworksGranted(recoComponent.getPackageName()); - mockRecommendationServiceAvailable(recoComponent, 924 /* packageUid */, + setNetworkRecoPackageSetting(RECO_COMPONENT.getPackageName()); + mockScoreNetworksGranted(RECO_COMPONENT.getPackageName()); + mockRecommendationServiceAvailable(RECO_COMPONENT, PACKAGE_UID /* packageUid */, enableUseOpenWifiComponent.getPackageName()); mockEnableUseOpenWifiActivity(enableUseOpenWifiComponent); // The older network scorer app setting doesn't match the new use open wifi activity package @@ -492,18 +513,17 @@ public class NetworkScorerAppManagerTest { @Test public void testMigrateNetworkScorerAppSettingIfNeeded_packageMismatch_service() throws Exception { - final ComponentName recoComponent = new ComponentName("package1", "class1"); final ComponentName enableUseOpenWifiComponent = new ComponentName("package2", "class2"); - setNetworkRecoPackageSetting(recoComponent.getPackageName()); - mockScoreNetworksGranted(recoComponent.getPackageName()); - mockRecommendationServiceAvailable(recoComponent, 924 /* packageUid */, + setNetworkRecoPackageSetting(RECO_COMPONENT.getPackageName()); + mockScoreNetworksGranted(RECO_COMPONENT.getPackageName()); + mockRecommendationServiceAvailable(RECO_COMPONENT, PACKAGE_UID /* packageUid */, enableUseOpenWifiComponent.getPackageName()); mockEnableUseOpenWifiActivity(enableUseOpenWifiComponent); // The older network scorer app setting doesn't match the active package so the migration // shouldn't set USE_OPEN_WIFI_PACKAGE. when(mSettingsFacade.getString(mMockContext, Settings.Global.NETWORK_SCORER_APP)) - .thenReturn(recoComponent.getPackageName() + ".diff"); + .thenReturn(RECO_COMPONENT.getPackageName() + ".diff"); when(mSettingsFacade.getString(mMockContext, Settings.Global.USE_OPEN_WIFI_PACKAGE)).thenReturn(null); @@ -518,11 +538,10 @@ public class NetworkScorerAppManagerTest { @Test public void testMigrateNetworkScorerAppSettingIfNeeded_packageMatch_activity() throws Exception { - final ComponentName recoComponent = new ComponentName("package1", "class1"); final ComponentName enableUseOpenWifiComponent = new ComponentName("package2", "class2"); - setNetworkRecoPackageSetting(recoComponent.getPackageName()); - mockScoreNetworksGranted(recoComponent.getPackageName()); - mockRecommendationServiceAvailable(recoComponent, 924 /* packageUid */, + setNetworkRecoPackageSetting(RECO_COMPONENT.getPackageName()); + mockScoreNetworksGranted(RECO_COMPONENT.getPackageName()); + mockRecommendationServiceAvailable(RECO_COMPONENT, PACKAGE_UID /* packageUid */, enableUseOpenWifiComponent.getPackageName()); mockEnableUseOpenWifiActivity(enableUseOpenWifiComponent); // Old setting matches the new activity package, migration should happen. @@ -566,6 +585,33 @@ public class NetworkScorerAppManagerTest { .thenReturn(PackageManager.PERMISSION_DENIED); } + private void mockLocationModeOn() { + mockLocationModeValue(Settings.Secure.LOCATION_MODE_HIGH_ACCURACY); + } + + private void mockLocationModeOff() { + mockLocationModeValue(Settings.Secure.LOCATION_MODE_OFF); + } + + private void mockLocationModeValue(int returnVal) { + when(mSettingsFacade.getSecureInt(eq(mMockContext), + eq(Settings.Secure.LOCATION_MODE), anyInt())).thenReturn(returnVal); + } + + private void mockLocationPermissionGranted(int uid, String packageName) { + when(mMockPm.checkPermission(permission.ACCESS_COARSE_LOCATION, packageName)) + .thenReturn(PackageManager.PERMISSION_GRANTED); + when(mAppOpsManager.noteOp(AppOpsManager.OP_COARSE_LOCATION, uid, packageName)) + .thenReturn(AppOpsManager.MODE_ALLOWED); + } + + private void mockLocationPermissionDenied(int uid, String packageName) { + when(mMockPm.checkPermission(permission.ACCESS_COARSE_LOCATION, packageName)) + .thenReturn(PackageManager.PERMISSION_DENIED); + when(mAppOpsManager.noteOp(AppOpsManager.OP_COARSE_LOCATION, uid, packageName)) + .thenReturn(AppOpsManager.MODE_IGNORED); + } + private void mockRecommendationServiceAvailable(final ComponentName compName, int packageUid) { mockRecommendationServiceAvailable(compName, packageUid, null, false); } |