Loading services/core/java/com/android/server/appop/TEST_MAPPING +8 −0 Original line number Diff line number Diff line Loading @@ -10,6 +10,14 @@ "include-filter": "com.android.server.appop" } ] }, { "name": "FrameworksMockingServicesTests", "options": [ { "include-filter": "com.android.server.appop" } ] } ] } services/tests/servicestests/src/com/android/server/appop/AppOpsServiceTest.java→services/tests/mockingservicestests/src/com/android/server/appop/AppOpsServiceTest.java +97 −56 Original line number Diff line number Diff line Loading @@ -25,13 +25,26 @@ import static android.app.AppOpsManager.OP_READ_SMS; import static android.app.AppOpsManager.OP_WIFI_SCAN; import static android.app.AppOpsManager.OP_WRITE_SMS; import static com.android.dx.mockito.inline.extended.ExtendedMockito.doNothing; import static com.android.dx.mockito.inline.extended.ExtendedMockito.doReturn; import static com.android.dx.mockito.inline.extended.ExtendedMockito.mock; import static com.android.dx.mockito.inline.extended.ExtendedMockito.mockitoSession; import static com.android.dx.mockito.inline.extended.ExtendedMockito.spy; import static com.android.dx.mockito.inline.extended.ExtendedMockito.when; import static com.google.common.truth.Truth.assertThat; import static com.google.common.truth.Truth.assertWithMessage; import static org.mockito.ArgumentMatchers.anyInt; import static org.mockito.ArgumentMatchers.anyString; import static org.mockito.ArgumentMatchers.eq; import static org.mockito.ArgumentMatchers.nullable; import android.app.ActivityManager; import android.app.AppOpsManager.OpEntry; import android.app.AppOpsManager.PackageOps; import android.content.Context; import android.content.pm.PackageManagerInternal; import android.os.Handler; import android.os.HandlerThread; import android.os.Process; Loading @@ -40,12 +53,14 @@ import androidx.test.InstrumentationRegistry; import androidx.test.filters.SmallTest; import androidx.test.runner.AndroidJUnit4; import com.android.server.appop.AppOpsService; import com.android.dx.mockito.inline.extended.StaticMockitoSession; import com.android.server.LocalServices; import org.junit.After; import org.junit.Before; import org.junit.Ignore; import org.junit.Test; import org.junit.runner.RunWith; import org.mockito.quality.Strictness; import java.io.File; import java.util.List; Loading @@ -55,7 +70,6 @@ import java.util.List; * or for which we can write more detailed unit tests than CTS tests (because the internal APIs are * more finegrained data than the public ones). */ @Ignore @SmallTest @RunWith(AndroidJUnit4.class) public class AppOpsServiceTest { Loading @@ -64,18 +78,44 @@ public class AppOpsServiceTest { // State will be persisted into this XML file. private static final String APP_OPS_FILENAME = "appops-service-test.xml"; private static final Context sContext = InstrumentationRegistry.getTargetContext(); private static final String sMyPackageName = sContext.getOpPackageName(); private File mAppOpsFile; private Context mContext; private Handler mHandler; private AppOpsService mAppOpsService; private String mMyPackageName; private int mMyUid; private long mTestStartMillis; private StaticMockitoSession mMockingSession; @Before public void mockPackageManagerInternalGetApplicationInfo() { mMockingSession = mockitoSession() .strictness(Strictness.LENIENT) .spyStatic(LocalServices.class) .startMocking(); // Mock LocalServices.getService(PackageManagerInternal.class).getApplicationInfo dependency // needed by AppOpsService PackageManagerInternal mockPackageManagerInternal = mock(PackageManagerInternal.class); when(mockPackageManagerInternal.getApplicationInfo(eq(sMyPackageName), anyInt(), anyInt(), anyInt())).thenReturn(sContext.getApplicationInfo()); doReturn(mockPackageManagerInternal).when( () -> LocalServices.getService(PackageManagerInternal.class)); } private void setupAppOpsService() { mAppOpsService = new AppOpsService(mAppOpsFile, mHandler); mAppOpsService.mContext = spy(sContext); // Always approve all permission checks doNothing().when(mAppOpsService.mContext).enforcePermission(anyString(), anyInt(), anyInt(), nullable(String.class)); } @Before public void setUp() { mContext = InstrumentationRegistry.getTargetContext(); mAppOpsFile = new File(mContext.getFilesDir(), APP_OPS_FILENAME); mAppOpsFile = new File(sContext.getFilesDir(), APP_OPS_FILENAME); if (mAppOpsFile.exists()) { // Start with a clean state (persisted into XML). mAppOpsFile.delete(); Loading @@ -84,14 +124,17 @@ public class AppOpsServiceTest { HandlerThread handlerThread = new HandlerThread(TAG); handlerThread.start(); mHandler = new Handler(handlerThread.getLooper()); mMyPackageName = mContext.getOpPackageName(); mMyUid = Process.myUid(); mAppOpsService = new AppOpsService(mAppOpsFile, mHandler); mAppOpsService.mContext = mContext; setupAppOpsService(); mTestStartMillis = System.currentTimeMillis(); } @After public void resetStaticMocks() { mMockingSession.finishMocking(); } @Test public void testGetOpsForPackage_noOpsLogged() { assertThat(getLoggedOps()).isNull(); Loading @@ -99,16 +142,16 @@ public class AppOpsServiceTest { @Test public void testNoteOperationAndGetOpsForPackage() { mAppOpsService.setMode(OP_READ_SMS, mMyUid, mMyPackageName, MODE_ALLOWED); mAppOpsService.setMode(OP_WRITE_SMS, mMyUid, mMyPackageName, MODE_ERRORED); mAppOpsService.setMode(OP_READ_SMS, mMyUid, sMyPackageName, MODE_ALLOWED); mAppOpsService.setMode(OP_WRITE_SMS, mMyUid, sMyPackageName, MODE_ERRORED); // Note an op that's allowed. mAppOpsService.noteOperation(OP_READ_SMS, mMyUid, mMyPackageName); mAppOpsService.noteOperation(OP_READ_SMS, mMyUid, sMyPackageName); List<PackageOps> loggedOps = getLoggedOps(); assertContainsOp(loggedOps, OP_READ_SMS, mTestStartMillis, -1, MODE_ALLOWED); // Note another op that's not allowed. mAppOpsService.noteOperation(OP_WRITE_SMS, mMyUid, mMyPackageName); mAppOpsService.noteOperation(OP_WRITE_SMS, mMyUid, sMyPackageName); loggedOps = getLoggedOps(); assertContainsOp(loggedOps, OP_READ_SMS, mTestStartMillis, -1, MODE_ALLOWED); assertContainsOp(loggedOps, OP_WRITE_SMS, -1, mTestStartMillis, MODE_ERRORED); Loading @@ -122,17 +165,17 @@ public class AppOpsServiceTest { @Test public void testNoteOperationAndGetOpsForPackage_controlledByDifferentOp() { // This op controls WIFI_SCAN mAppOpsService.setMode(OP_COARSE_LOCATION, mMyUid, mMyPackageName, MODE_ALLOWED); mAppOpsService.setMode(OP_COARSE_LOCATION, mMyUid, sMyPackageName, MODE_ALLOWED); assertThat(mAppOpsService.noteOperation(OP_WIFI_SCAN, mMyUid, mMyPackageName)) assertThat(mAppOpsService.noteOperation(OP_WIFI_SCAN, mMyUid, sMyPackageName)) .isEqualTo(MODE_ALLOWED); assertContainsOp(getLoggedOps(), OP_WIFI_SCAN, mTestStartMillis, -1, MODE_ALLOWED /* default for WIFI_SCAN; this is not changed or used in this test */); // Now set COARSE_LOCATION to ERRORED -> this will make WIFI_SCAN disabled as well. mAppOpsService.setMode(OP_COARSE_LOCATION, mMyUid, mMyPackageName, MODE_ERRORED); assertThat(mAppOpsService.noteOperation(OP_WIFI_SCAN, mMyUid, mMyPackageName)) mAppOpsService.setMode(OP_COARSE_LOCATION, mMyUid, sMyPackageName, MODE_ERRORED); assertThat(mAppOpsService.noteOperation(OP_WIFI_SCAN, mMyUid, sMyPackageName)) .isEqualTo(MODE_ERRORED); assertContainsOp(getLoggedOps(), OP_WIFI_SCAN, mTestStartMillis, mTestStartMillis, Loading @@ -142,15 +185,14 @@ public class AppOpsServiceTest { // Tests the dumping and restoring of the in-memory state to/from XML. @Test public void testStatePersistence() { mAppOpsService.setMode(OP_READ_SMS, mMyUid, mMyPackageName, MODE_ALLOWED); mAppOpsService.setMode(OP_WRITE_SMS, mMyUid, mMyPackageName, MODE_ERRORED); mAppOpsService.noteOperation(OP_READ_SMS, mMyUid, mMyPackageName); mAppOpsService.noteOperation(OP_WRITE_SMS, mMyUid, mMyPackageName); mAppOpsService.setMode(OP_READ_SMS, mMyUid, sMyPackageName, MODE_ALLOWED); mAppOpsService.setMode(OP_WRITE_SMS, mMyUid, sMyPackageName, MODE_ERRORED); mAppOpsService.noteOperation(OP_READ_SMS, mMyUid, sMyPackageName); mAppOpsService.noteOperation(OP_WRITE_SMS, mMyUid, sMyPackageName); mAppOpsService.writeState(); // Create a new app ops service, and initialize its state from XML. mAppOpsService = new AppOpsService(mAppOpsFile, mHandler); mAppOpsService.mContext = mContext; setupAppOpsService(); mAppOpsService.readState(); // Query the state of the 2nd service. Loading @@ -162,13 +204,12 @@ public class AppOpsServiceTest { // Tests that ops are persisted during shutdown. @Test public void testShutdown() { mAppOpsService.setMode(OP_READ_SMS, mMyUid, mMyPackageName, MODE_ALLOWED); mAppOpsService.noteOperation(OP_READ_SMS, mMyUid, mMyPackageName); mAppOpsService.setMode(OP_READ_SMS, mMyUid, sMyPackageName, MODE_ALLOWED); mAppOpsService.noteOperation(OP_READ_SMS, mMyUid, sMyPackageName); mAppOpsService.shutdown(); // Create a new app ops service, and initialize its state from XML. mAppOpsService = new AppOpsService(mAppOpsFile, mHandler); mAppOpsService.mContext = mContext; setupAppOpsService(); mAppOpsService.readState(); // Query the state of the 2nd service. Loading @@ -178,21 +219,21 @@ public class AppOpsServiceTest { @Test public void testGetOpsForPackage() { mAppOpsService.setMode(OP_READ_SMS, mMyUid, mMyPackageName, MODE_ALLOWED); mAppOpsService.noteOperation(OP_READ_SMS, mMyUid, mMyPackageName); mAppOpsService.setMode(OP_READ_SMS, mMyUid, sMyPackageName, MODE_ALLOWED); mAppOpsService.noteOperation(OP_READ_SMS, mMyUid, sMyPackageName); // Query all ops List<PackageOps> loggedOps = mAppOpsService.getOpsForPackage( mMyUid, mMyPackageName, null /* all ops */); mMyUid, sMyPackageName, null /* all ops */); assertContainsOp(loggedOps, OP_READ_SMS, mTestStartMillis, -1, MODE_ALLOWED); // Query specific ops loggedOps = mAppOpsService.getOpsForPackage( mMyUid, mMyPackageName, new int[]{OP_READ_SMS, OP_WRITE_SMS}); mMyUid, sMyPackageName, new int[]{OP_READ_SMS, OP_WRITE_SMS}); assertContainsOp(loggedOps, OP_READ_SMS, mTestStartMillis, -1, MODE_ALLOWED); // Query unknown UID loggedOps = mAppOpsService.getOpsForPackage(mMyUid + 1, mMyPackageName, null /* all ops */); loggedOps = mAppOpsService.getOpsForPackage(mMyUid + 1, sMyPackageName, null /* all ops */); assertThat(loggedOps).isNull(); // Query unknown package name Loading @@ -200,27 +241,27 @@ public class AppOpsServiceTest { assertThat(loggedOps).isNull(); // Query op code that's not been logged loggedOps = mAppOpsService.getOpsForPackage(mMyUid, mMyPackageName, loggedOps = mAppOpsService.getOpsForPackage(mMyUid, sMyPackageName, new int[]{OP_WRITE_SMS}); assertThat(loggedOps).isNull(); } @Test public void testPackageRemoved() { mAppOpsService.setMode(OP_READ_SMS, mMyUid, mMyPackageName, MODE_ALLOWED); mAppOpsService.noteOperation(OP_READ_SMS, mMyUid, mMyPackageName); mAppOpsService.setMode(OP_READ_SMS, mMyUid, sMyPackageName, MODE_ALLOWED); mAppOpsService.noteOperation(OP_READ_SMS, mMyUid, sMyPackageName); List<PackageOps> loggedOps = getLoggedOps(); assertContainsOp(loggedOps, OP_READ_SMS, mTestStartMillis, -1, MODE_ALLOWED); mAppOpsService.packageRemoved(mMyUid, mMyPackageName); mAppOpsService.packageRemoved(mMyUid, sMyPackageName); assertThat(getLoggedOps()).isNull(); } @Test public void testUidRemoved() { mAppOpsService.setMode(OP_READ_SMS, mMyUid, mMyPackageName, MODE_ALLOWED); mAppOpsService.noteOperation(OP_READ_SMS, mMyUid, mMyPackageName); mAppOpsService.setMode(OP_READ_SMS, mMyUid, sMyPackageName, MODE_ALLOWED); mAppOpsService.noteOperation(OP_READ_SMS, mMyUid, sMyPackageName); List<PackageOps> loggedOps = getLoggedOps(); assertContainsOp(loggedOps, OP_READ_SMS, mTestStartMillis, -1, MODE_ALLOWED); Loading @@ -231,7 +272,7 @@ public class AppOpsServiceTest { private void setupProcStateTests() { // For the location proc state tests mAppOpsService.setMode(OP_COARSE_LOCATION, mMyUid, mMyPackageName, MODE_FOREGROUND); mAppOpsService.setMode(OP_COARSE_LOCATION, mMyUid, sMyPackageName, MODE_FOREGROUND); mAppOpsService.mConstants.FG_SERVICE_STATE_SETTLE_TIME = 0; mAppOpsService.mConstants.TOP_STATE_SETTLE_TIME = 0; mAppOpsService.mConstants.BG_STATE_SETTLE_TIME = 0; Loading @@ -242,18 +283,18 @@ public class AppOpsServiceTest { setupProcStateTests(); mAppOpsService.updateUidProcState(mMyUid, ActivityManager.PROCESS_STATE_CACHED_EMPTY); assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, mMyPackageName)) assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, sMyPackageName)) .isNotEqualTo(MODE_ALLOWED); mAppOpsService.updateUidProcState(mMyUid, ActivityManager.PROCESS_STATE_TOP); assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, mMyPackageName)) assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, sMyPackageName)) .isEqualTo(MODE_ALLOWED); mAppOpsService.updateUidProcState(mMyUid, ActivityManager.PROCESS_STATE_CACHED_EMPTY); // Second time to make sure that settle time is overcome Thread.sleep(50); mAppOpsService.updateUidProcState(mMyUid, ActivityManager.PROCESS_STATE_CACHED_EMPTY); assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, mMyPackageName)) assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, sMyPackageName)) .isNotEqualTo(MODE_ALLOWED); } Loading @@ -262,11 +303,11 @@ public class AppOpsServiceTest { setupProcStateTests(); mAppOpsService.updateUidProcState(mMyUid, ActivityManager.PROCESS_STATE_CACHED_EMPTY); assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, mMyPackageName)) assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, sMyPackageName)) .isNotEqualTo(MODE_ALLOWED); mAppOpsService.updateUidProcState(mMyUid, PROCESS_STATE_FOREGROUND_SERVICE); assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, mMyPackageName)) assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, sMyPackageName)) .isNotEqualTo(MODE_ALLOWED); } Loading @@ -275,12 +316,12 @@ public class AppOpsServiceTest { setupProcStateTests(); mAppOpsService.updateUidProcState(mMyUid, ActivityManager.PROCESS_STATE_CACHED_EMPTY); assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, mMyPackageName)) assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, sMyPackageName)) .isNotEqualTo(MODE_ALLOWED); mAppOpsService.updateUidProcState(mMyUid, PROCESS_STATE_FOREGROUND_SERVICE_LOCATION); assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, mMyPackageName)) assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, sMyPackageName)) .isEqualTo(MODE_ALLOWED); } Loading @@ -289,18 +330,18 @@ public class AppOpsServiceTest { setupProcStateTests(); mAppOpsService.updateUidProcState(mMyUid, ActivityManager.PROCESS_STATE_CACHED_EMPTY); assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, mMyPackageName)) assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, sMyPackageName)) .isNotEqualTo(MODE_ALLOWED); mAppOpsService.updateUidProcState(mMyUid, ActivityManager.PROCESS_STATE_TOP); assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, mMyPackageName)) assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, sMyPackageName)) .isEqualTo(MODE_ALLOWED); mAppOpsService.updateUidProcState(mMyUid, PROCESS_STATE_FOREGROUND_SERVICE); // Second time to make sure that settle time is overcome Thread.sleep(50); mAppOpsService.updateUidProcState(mMyUid, PROCESS_STATE_FOREGROUND_SERVICE); assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, mMyPackageName)) assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, sMyPackageName)) .isNotEqualTo(MODE_ALLOWED); } Loading @@ -309,30 +350,30 @@ public class AppOpsServiceTest { setupProcStateTests(); mAppOpsService.updateUidProcState(mMyUid, ActivityManager.PROCESS_STATE_CACHED_EMPTY); assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, mMyPackageName)) assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, sMyPackageName)) .isNotEqualTo(MODE_ALLOWED); mAppOpsService.updateUidProcState(mMyUid, ActivityManager.PROCESS_STATE_TOP); assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, mMyPackageName)) assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, sMyPackageName)) .isEqualTo(MODE_ALLOWED); mAppOpsService.updateUidProcState(mMyUid, PROCESS_STATE_FOREGROUND_SERVICE_LOCATION); // Second time to make sure that settle time is overcome Thread.sleep(50); mAppOpsService.updateUidProcState(mMyUid, PROCESS_STATE_FOREGROUND_SERVICE_LOCATION); assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, mMyPackageName)) assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, sMyPackageName)) .isEqualTo(MODE_ALLOWED); mAppOpsService.updateUidProcState(mMyUid, PROCESS_STATE_FOREGROUND_SERVICE); // Second time to make sure that settle time is overcome Thread.sleep(50); mAppOpsService.updateUidProcState(mMyUid, PROCESS_STATE_FOREGROUND_SERVICE); assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, mMyPackageName)) assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, sMyPackageName)) .isNotEqualTo(MODE_ALLOWED); } private List<PackageOps> getLoggedOps() { return mAppOpsService.getOpsForPackage(mMyUid, mMyPackageName, null /* all ops */); return mAppOpsService.getOpsForPackage(mMyUid, sMyPackageName, null /* all ops */); } private void assertContainsOp(List<PackageOps> loggedOps, int opCode, long minMillis, Loading @@ -341,7 +382,7 @@ public class AppOpsServiceTest { boolean opLogged = false; for (PackageOps pkgOps : loggedOps) { assertWithMessage("Unexpected UID").that(mMyUid).isEqualTo(pkgOps.getUid()); assertWithMessage("Unexpected package name").that(mMyPackageName).isEqualTo( assertWithMessage("Unexpected package name").that(sMyPackageName).isEqualTo( pkgOps.getPackageName()); for (OpEntry opEntry : pkgOps.getOps()) { Loading Loading
services/core/java/com/android/server/appop/TEST_MAPPING +8 −0 Original line number Diff line number Diff line Loading @@ -10,6 +10,14 @@ "include-filter": "com.android.server.appop" } ] }, { "name": "FrameworksMockingServicesTests", "options": [ { "include-filter": "com.android.server.appop" } ] } ] }
services/tests/servicestests/src/com/android/server/appop/AppOpsServiceTest.java→services/tests/mockingservicestests/src/com/android/server/appop/AppOpsServiceTest.java +97 −56 Original line number Diff line number Diff line Loading @@ -25,13 +25,26 @@ import static android.app.AppOpsManager.OP_READ_SMS; import static android.app.AppOpsManager.OP_WIFI_SCAN; import static android.app.AppOpsManager.OP_WRITE_SMS; import static com.android.dx.mockito.inline.extended.ExtendedMockito.doNothing; import static com.android.dx.mockito.inline.extended.ExtendedMockito.doReturn; import static com.android.dx.mockito.inline.extended.ExtendedMockito.mock; import static com.android.dx.mockito.inline.extended.ExtendedMockito.mockitoSession; import static com.android.dx.mockito.inline.extended.ExtendedMockito.spy; import static com.android.dx.mockito.inline.extended.ExtendedMockito.when; import static com.google.common.truth.Truth.assertThat; import static com.google.common.truth.Truth.assertWithMessage; import static org.mockito.ArgumentMatchers.anyInt; import static org.mockito.ArgumentMatchers.anyString; import static org.mockito.ArgumentMatchers.eq; import static org.mockito.ArgumentMatchers.nullable; import android.app.ActivityManager; import android.app.AppOpsManager.OpEntry; import android.app.AppOpsManager.PackageOps; import android.content.Context; import android.content.pm.PackageManagerInternal; import android.os.Handler; import android.os.HandlerThread; import android.os.Process; Loading @@ -40,12 +53,14 @@ import androidx.test.InstrumentationRegistry; import androidx.test.filters.SmallTest; import androidx.test.runner.AndroidJUnit4; import com.android.server.appop.AppOpsService; import com.android.dx.mockito.inline.extended.StaticMockitoSession; import com.android.server.LocalServices; import org.junit.After; import org.junit.Before; import org.junit.Ignore; import org.junit.Test; import org.junit.runner.RunWith; import org.mockito.quality.Strictness; import java.io.File; import java.util.List; Loading @@ -55,7 +70,6 @@ import java.util.List; * or for which we can write more detailed unit tests than CTS tests (because the internal APIs are * more finegrained data than the public ones). */ @Ignore @SmallTest @RunWith(AndroidJUnit4.class) public class AppOpsServiceTest { Loading @@ -64,18 +78,44 @@ public class AppOpsServiceTest { // State will be persisted into this XML file. private static final String APP_OPS_FILENAME = "appops-service-test.xml"; private static final Context sContext = InstrumentationRegistry.getTargetContext(); private static final String sMyPackageName = sContext.getOpPackageName(); private File mAppOpsFile; private Context mContext; private Handler mHandler; private AppOpsService mAppOpsService; private String mMyPackageName; private int mMyUid; private long mTestStartMillis; private StaticMockitoSession mMockingSession; @Before public void mockPackageManagerInternalGetApplicationInfo() { mMockingSession = mockitoSession() .strictness(Strictness.LENIENT) .spyStatic(LocalServices.class) .startMocking(); // Mock LocalServices.getService(PackageManagerInternal.class).getApplicationInfo dependency // needed by AppOpsService PackageManagerInternal mockPackageManagerInternal = mock(PackageManagerInternal.class); when(mockPackageManagerInternal.getApplicationInfo(eq(sMyPackageName), anyInt(), anyInt(), anyInt())).thenReturn(sContext.getApplicationInfo()); doReturn(mockPackageManagerInternal).when( () -> LocalServices.getService(PackageManagerInternal.class)); } private void setupAppOpsService() { mAppOpsService = new AppOpsService(mAppOpsFile, mHandler); mAppOpsService.mContext = spy(sContext); // Always approve all permission checks doNothing().when(mAppOpsService.mContext).enforcePermission(anyString(), anyInt(), anyInt(), nullable(String.class)); } @Before public void setUp() { mContext = InstrumentationRegistry.getTargetContext(); mAppOpsFile = new File(mContext.getFilesDir(), APP_OPS_FILENAME); mAppOpsFile = new File(sContext.getFilesDir(), APP_OPS_FILENAME); if (mAppOpsFile.exists()) { // Start with a clean state (persisted into XML). mAppOpsFile.delete(); Loading @@ -84,14 +124,17 @@ public class AppOpsServiceTest { HandlerThread handlerThread = new HandlerThread(TAG); handlerThread.start(); mHandler = new Handler(handlerThread.getLooper()); mMyPackageName = mContext.getOpPackageName(); mMyUid = Process.myUid(); mAppOpsService = new AppOpsService(mAppOpsFile, mHandler); mAppOpsService.mContext = mContext; setupAppOpsService(); mTestStartMillis = System.currentTimeMillis(); } @After public void resetStaticMocks() { mMockingSession.finishMocking(); } @Test public void testGetOpsForPackage_noOpsLogged() { assertThat(getLoggedOps()).isNull(); Loading @@ -99,16 +142,16 @@ public class AppOpsServiceTest { @Test public void testNoteOperationAndGetOpsForPackage() { mAppOpsService.setMode(OP_READ_SMS, mMyUid, mMyPackageName, MODE_ALLOWED); mAppOpsService.setMode(OP_WRITE_SMS, mMyUid, mMyPackageName, MODE_ERRORED); mAppOpsService.setMode(OP_READ_SMS, mMyUid, sMyPackageName, MODE_ALLOWED); mAppOpsService.setMode(OP_WRITE_SMS, mMyUid, sMyPackageName, MODE_ERRORED); // Note an op that's allowed. mAppOpsService.noteOperation(OP_READ_SMS, mMyUid, mMyPackageName); mAppOpsService.noteOperation(OP_READ_SMS, mMyUid, sMyPackageName); List<PackageOps> loggedOps = getLoggedOps(); assertContainsOp(loggedOps, OP_READ_SMS, mTestStartMillis, -1, MODE_ALLOWED); // Note another op that's not allowed. mAppOpsService.noteOperation(OP_WRITE_SMS, mMyUid, mMyPackageName); mAppOpsService.noteOperation(OP_WRITE_SMS, mMyUid, sMyPackageName); loggedOps = getLoggedOps(); assertContainsOp(loggedOps, OP_READ_SMS, mTestStartMillis, -1, MODE_ALLOWED); assertContainsOp(loggedOps, OP_WRITE_SMS, -1, mTestStartMillis, MODE_ERRORED); Loading @@ -122,17 +165,17 @@ public class AppOpsServiceTest { @Test public void testNoteOperationAndGetOpsForPackage_controlledByDifferentOp() { // This op controls WIFI_SCAN mAppOpsService.setMode(OP_COARSE_LOCATION, mMyUid, mMyPackageName, MODE_ALLOWED); mAppOpsService.setMode(OP_COARSE_LOCATION, mMyUid, sMyPackageName, MODE_ALLOWED); assertThat(mAppOpsService.noteOperation(OP_WIFI_SCAN, mMyUid, mMyPackageName)) assertThat(mAppOpsService.noteOperation(OP_WIFI_SCAN, mMyUid, sMyPackageName)) .isEqualTo(MODE_ALLOWED); assertContainsOp(getLoggedOps(), OP_WIFI_SCAN, mTestStartMillis, -1, MODE_ALLOWED /* default for WIFI_SCAN; this is not changed or used in this test */); // Now set COARSE_LOCATION to ERRORED -> this will make WIFI_SCAN disabled as well. mAppOpsService.setMode(OP_COARSE_LOCATION, mMyUid, mMyPackageName, MODE_ERRORED); assertThat(mAppOpsService.noteOperation(OP_WIFI_SCAN, mMyUid, mMyPackageName)) mAppOpsService.setMode(OP_COARSE_LOCATION, mMyUid, sMyPackageName, MODE_ERRORED); assertThat(mAppOpsService.noteOperation(OP_WIFI_SCAN, mMyUid, sMyPackageName)) .isEqualTo(MODE_ERRORED); assertContainsOp(getLoggedOps(), OP_WIFI_SCAN, mTestStartMillis, mTestStartMillis, Loading @@ -142,15 +185,14 @@ public class AppOpsServiceTest { // Tests the dumping and restoring of the in-memory state to/from XML. @Test public void testStatePersistence() { mAppOpsService.setMode(OP_READ_SMS, mMyUid, mMyPackageName, MODE_ALLOWED); mAppOpsService.setMode(OP_WRITE_SMS, mMyUid, mMyPackageName, MODE_ERRORED); mAppOpsService.noteOperation(OP_READ_SMS, mMyUid, mMyPackageName); mAppOpsService.noteOperation(OP_WRITE_SMS, mMyUid, mMyPackageName); mAppOpsService.setMode(OP_READ_SMS, mMyUid, sMyPackageName, MODE_ALLOWED); mAppOpsService.setMode(OP_WRITE_SMS, mMyUid, sMyPackageName, MODE_ERRORED); mAppOpsService.noteOperation(OP_READ_SMS, mMyUid, sMyPackageName); mAppOpsService.noteOperation(OP_WRITE_SMS, mMyUid, sMyPackageName); mAppOpsService.writeState(); // Create a new app ops service, and initialize its state from XML. mAppOpsService = new AppOpsService(mAppOpsFile, mHandler); mAppOpsService.mContext = mContext; setupAppOpsService(); mAppOpsService.readState(); // Query the state of the 2nd service. Loading @@ -162,13 +204,12 @@ public class AppOpsServiceTest { // Tests that ops are persisted during shutdown. @Test public void testShutdown() { mAppOpsService.setMode(OP_READ_SMS, mMyUid, mMyPackageName, MODE_ALLOWED); mAppOpsService.noteOperation(OP_READ_SMS, mMyUid, mMyPackageName); mAppOpsService.setMode(OP_READ_SMS, mMyUid, sMyPackageName, MODE_ALLOWED); mAppOpsService.noteOperation(OP_READ_SMS, mMyUid, sMyPackageName); mAppOpsService.shutdown(); // Create a new app ops service, and initialize its state from XML. mAppOpsService = new AppOpsService(mAppOpsFile, mHandler); mAppOpsService.mContext = mContext; setupAppOpsService(); mAppOpsService.readState(); // Query the state of the 2nd service. Loading @@ -178,21 +219,21 @@ public class AppOpsServiceTest { @Test public void testGetOpsForPackage() { mAppOpsService.setMode(OP_READ_SMS, mMyUid, mMyPackageName, MODE_ALLOWED); mAppOpsService.noteOperation(OP_READ_SMS, mMyUid, mMyPackageName); mAppOpsService.setMode(OP_READ_SMS, mMyUid, sMyPackageName, MODE_ALLOWED); mAppOpsService.noteOperation(OP_READ_SMS, mMyUid, sMyPackageName); // Query all ops List<PackageOps> loggedOps = mAppOpsService.getOpsForPackage( mMyUid, mMyPackageName, null /* all ops */); mMyUid, sMyPackageName, null /* all ops */); assertContainsOp(loggedOps, OP_READ_SMS, mTestStartMillis, -1, MODE_ALLOWED); // Query specific ops loggedOps = mAppOpsService.getOpsForPackage( mMyUid, mMyPackageName, new int[]{OP_READ_SMS, OP_WRITE_SMS}); mMyUid, sMyPackageName, new int[]{OP_READ_SMS, OP_WRITE_SMS}); assertContainsOp(loggedOps, OP_READ_SMS, mTestStartMillis, -1, MODE_ALLOWED); // Query unknown UID loggedOps = mAppOpsService.getOpsForPackage(mMyUid + 1, mMyPackageName, null /* all ops */); loggedOps = mAppOpsService.getOpsForPackage(mMyUid + 1, sMyPackageName, null /* all ops */); assertThat(loggedOps).isNull(); // Query unknown package name Loading @@ -200,27 +241,27 @@ public class AppOpsServiceTest { assertThat(loggedOps).isNull(); // Query op code that's not been logged loggedOps = mAppOpsService.getOpsForPackage(mMyUid, mMyPackageName, loggedOps = mAppOpsService.getOpsForPackage(mMyUid, sMyPackageName, new int[]{OP_WRITE_SMS}); assertThat(loggedOps).isNull(); } @Test public void testPackageRemoved() { mAppOpsService.setMode(OP_READ_SMS, mMyUid, mMyPackageName, MODE_ALLOWED); mAppOpsService.noteOperation(OP_READ_SMS, mMyUid, mMyPackageName); mAppOpsService.setMode(OP_READ_SMS, mMyUid, sMyPackageName, MODE_ALLOWED); mAppOpsService.noteOperation(OP_READ_SMS, mMyUid, sMyPackageName); List<PackageOps> loggedOps = getLoggedOps(); assertContainsOp(loggedOps, OP_READ_SMS, mTestStartMillis, -1, MODE_ALLOWED); mAppOpsService.packageRemoved(mMyUid, mMyPackageName); mAppOpsService.packageRemoved(mMyUid, sMyPackageName); assertThat(getLoggedOps()).isNull(); } @Test public void testUidRemoved() { mAppOpsService.setMode(OP_READ_SMS, mMyUid, mMyPackageName, MODE_ALLOWED); mAppOpsService.noteOperation(OP_READ_SMS, mMyUid, mMyPackageName); mAppOpsService.setMode(OP_READ_SMS, mMyUid, sMyPackageName, MODE_ALLOWED); mAppOpsService.noteOperation(OP_READ_SMS, mMyUid, sMyPackageName); List<PackageOps> loggedOps = getLoggedOps(); assertContainsOp(loggedOps, OP_READ_SMS, mTestStartMillis, -1, MODE_ALLOWED); Loading @@ -231,7 +272,7 @@ public class AppOpsServiceTest { private void setupProcStateTests() { // For the location proc state tests mAppOpsService.setMode(OP_COARSE_LOCATION, mMyUid, mMyPackageName, MODE_FOREGROUND); mAppOpsService.setMode(OP_COARSE_LOCATION, mMyUid, sMyPackageName, MODE_FOREGROUND); mAppOpsService.mConstants.FG_SERVICE_STATE_SETTLE_TIME = 0; mAppOpsService.mConstants.TOP_STATE_SETTLE_TIME = 0; mAppOpsService.mConstants.BG_STATE_SETTLE_TIME = 0; Loading @@ -242,18 +283,18 @@ public class AppOpsServiceTest { setupProcStateTests(); mAppOpsService.updateUidProcState(mMyUid, ActivityManager.PROCESS_STATE_CACHED_EMPTY); assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, mMyPackageName)) assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, sMyPackageName)) .isNotEqualTo(MODE_ALLOWED); mAppOpsService.updateUidProcState(mMyUid, ActivityManager.PROCESS_STATE_TOP); assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, mMyPackageName)) assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, sMyPackageName)) .isEqualTo(MODE_ALLOWED); mAppOpsService.updateUidProcState(mMyUid, ActivityManager.PROCESS_STATE_CACHED_EMPTY); // Second time to make sure that settle time is overcome Thread.sleep(50); mAppOpsService.updateUidProcState(mMyUid, ActivityManager.PROCESS_STATE_CACHED_EMPTY); assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, mMyPackageName)) assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, sMyPackageName)) .isNotEqualTo(MODE_ALLOWED); } Loading @@ -262,11 +303,11 @@ public class AppOpsServiceTest { setupProcStateTests(); mAppOpsService.updateUidProcState(mMyUid, ActivityManager.PROCESS_STATE_CACHED_EMPTY); assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, mMyPackageName)) assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, sMyPackageName)) .isNotEqualTo(MODE_ALLOWED); mAppOpsService.updateUidProcState(mMyUid, PROCESS_STATE_FOREGROUND_SERVICE); assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, mMyPackageName)) assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, sMyPackageName)) .isNotEqualTo(MODE_ALLOWED); } Loading @@ -275,12 +316,12 @@ public class AppOpsServiceTest { setupProcStateTests(); mAppOpsService.updateUidProcState(mMyUid, ActivityManager.PROCESS_STATE_CACHED_EMPTY); assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, mMyPackageName)) assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, sMyPackageName)) .isNotEqualTo(MODE_ALLOWED); mAppOpsService.updateUidProcState(mMyUid, PROCESS_STATE_FOREGROUND_SERVICE_LOCATION); assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, mMyPackageName)) assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, sMyPackageName)) .isEqualTo(MODE_ALLOWED); } Loading @@ -289,18 +330,18 @@ public class AppOpsServiceTest { setupProcStateTests(); mAppOpsService.updateUidProcState(mMyUid, ActivityManager.PROCESS_STATE_CACHED_EMPTY); assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, mMyPackageName)) assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, sMyPackageName)) .isNotEqualTo(MODE_ALLOWED); mAppOpsService.updateUidProcState(mMyUid, ActivityManager.PROCESS_STATE_TOP); assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, mMyPackageName)) assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, sMyPackageName)) .isEqualTo(MODE_ALLOWED); mAppOpsService.updateUidProcState(mMyUid, PROCESS_STATE_FOREGROUND_SERVICE); // Second time to make sure that settle time is overcome Thread.sleep(50); mAppOpsService.updateUidProcState(mMyUid, PROCESS_STATE_FOREGROUND_SERVICE); assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, mMyPackageName)) assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, sMyPackageName)) .isNotEqualTo(MODE_ALLOWED); } Loading @@ -309,30 +350,30 @@ public class AppOpsServiceTest { setupProcStateTests(); mAppOpsService.updateUidProcState(mMyUid, ActivityManager.PROCESS_STATE_CACHED_EMPTY); assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, mMyPackageName)) assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, sMyPackageName)) .isNotEqualTo(MODE_ALLOWED); mAppOpsService.updateUidProcState(mMyUid, ActivityManager.PROCESS_STATE_TOP); assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, mMyPackageName)) assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, sMyPackageName)) .isEqualTo(MODE_ALLOWED); mAppOpsService.updateUidProcState(mMyUid, PROCESS_STATE_FOREGROUND_SERVICE_LOCATION); // Second time to make sure that settle time is overcome Thread.sleep(50); mAppOpsService.updateUidProcState(mMyUid, PROCESS_STATE_FOREGROUND_SERVICE_LOCATION); assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, mMyPackageName)) assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, sMyPackageName)) .isEqualTo(MODE_ALLOWED); mAppOpsService.updateUidProcState(mMyUid, PROCESS_STATE_FOREGROUND_SERVICE); // Second time to make sure that settle time is overcome Thread.sleep(50); mAppOpsService.updateUidProcState(mMyUid, PROCESS_STATE_FOREGROUND_SERVICE); assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, mMyPackageName)) assertThat(mAppOpsService.noteOperation(OP_COARSE_LOCATION, mMyUid, sMyPackageName)) .isNotEqualTo(MODE_ALLOWED); } private List<PackageOps> getLoggedOps() { return mAppOpsService.getOpsForPackage(mMyUid, mMyPackageName, null /* all ops */); return mAppOpsService.getOpsForPackage(mMyUid, sMyPackageName, null /* all ops */); } private void assertContainsOp(List<PackageOps> loggedOps, int opCode, long minMillis, Loading @@ -341,7 +382,7 @@ public class AppOpsServiceTest { boolean opLogged = false; for (PackageOps pkgOps : loggedOps) { assertWithMessage("Unexpected UID").that(mMyUid).isEqualTo(pkgOps.getUid()); assertWithMessage("Unexpected package name").that(mMyPackageName).isEqualTo( assertWithMessage("Unexpected package name").that(sMyPackageName).isEqualTo( pkgOps.getPackageName()); for (OpEntry opEntry : pkgOps.getOps()) { Loading