1 /* 2 * Copyright (C) 2023 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 package android.security.cts.TestLocationScanningServicesUsingSlices; 18 19 import static android.os.UserManager.DISALLOW_CONFIG_LOCATION; 20 21 import static androidx.test.platform.app.InstrumentationRegistry.getInstrumentation; 22 23 import static org.junit.Assert.assertFalse; 24 import static org.junit.Assume.assumeNoException; 25 import static org.junit.Assume.assumeTrue; 26 27 import android.app.Instrumentation; 28 import android.app.PendingIntent; 29 import android.app.admin.DevicePolicyManager; 30 import android.app.slice.SliceProvider; 31 import android.content.ComponentName; 32 import android.content.ContentResolver; 33 import android.content.Context; 34 import android.content.Intent; 35 import android.content.res.Resources; 36 import android.net.Uri; 37 import android.os.UserManager; 38 import android.provider.Settings; 39 40 import androidx.test.runner.AndroidJUnit4; 41 import androidx.test.uiautomator.By; 42 import androidx.test.uiautomator.UiDevice; 43 import androidx.test.uiautomator.UiObject2; 44 import androidx.test.uiautomator.Until; 45 46 import org.junit.Before; 47 import org.junit.Test; 48 import org.junit.runner.RunWith; 49 50 import java.util.regex.Pattern; 51 52 @RunWith(AndroidJUnit4.class) 53 public class DeviceTest { 54 private final int waitMS = 5_000; 55 private final String mSettingsPackage = "com.android.settings"; 56 private final String mScanningTextResId = mSettingsPackage + ":id/switch_text"; 57 private final String mScanningWidgetResId = "android:id/switch_widget"; 58 private final String mBaseUri = "content://" + mSettingsPackage + ".slices/action/"; 59 60 private Context mContext; 61 private ContentResolver mContentResolver; 62 private UiDevice mDevice; 63 private Resources mSettingsResources; 64 65 @Before setUp()66 public void setUp() { 67 try { 68 Instrumentation instrumentation = getInstrumentation(); 69 mContext = instrumentation.getTargetContext(); 70 mContentResolver = mContext.getContentResolver(); 71 mDevice = UiDevice.getInstance(instrumentation); 72 mSettingsResources = 73 mContext.getPackageManager().getResourcesForApplication(mSettingsPackage); 74 75 // Set DISALLOW_CONFIG_LOCATION restriction for the current user 76 mContext.getSystemService(DevicePolicyManager.class) 77 .addUserRestriction( 78 new ComponentName(mContext, PocDeviceAdminReceiver.class), 79 DISALLOW_CONFIG_LOCATION); 80 assumeTrue( 81 "Failed to set user restriction DISALLOW_CONFIG_LOCATION", 82 mContext.getSystemService(UserManager.class) 83 .getUserRestrictions() 84 .getBoolean(DISALLOW_CONFIG_LOCATION)); 85 Object intent = 86 SliceProvider.createPermissionIntent( 87 mContext, 88 Uri.parse(mBaseUri), 89 "android.security.cts.TestLocationScanningServicesUsingSlices"); 90 91 // For Android SC and SC-V2 createPermissionIntent returns an instance of 92 // PendingIntent 93 if (intent instanceof PendingIntent) { 94 ((PendingIntent) intent).send(); 95 } 96 97 // For Android T and above createPermissionIntent returns an instance of 98 // Intent 99 if (intent instanceof Intent) { 100 mContext.startActivity(((Intent) intent).addFlags(Intent.FLAG_ACTIVITY_NEW_TASK)); 101 } 102 103 // Grant SLICE_PERMISSION by clicking on 'Allow' 104 Pattern allowPattern = Pattern.compile("Allow", Pattern.CASE_INSENSITIVE); 105 assumeTrue(mDevice.wait(Until.hasObject(By.text(allowPattern)), waitMS)); 106 UiObject2 allowButton = mDevice.findObject(By.text(allowPattern)); 107 allowButton.click(); 108 } catch (Exception e) { 109 assumeNoException(e); 110 } 111 } 112 113 @Test testPocCVE_2023_21247()114 public void testPocCVE_2023_21247() { 115 try { 116 final int initialBleScanGlobalSetting = 117 Settings.Global.getInt( 118 mContentResolver, Settings.Global.BLE_SCAN_ALWAYS_AVAILABLE, -1); 119 assumeTrue(initialBleScanGlobalSetting != -1); 120 121 // Launching PocActivity to launch "bluetooth_always_scanning_switch" settings 122 // slice using slice-uri 123 mContext.startActivity( 124 new Intent(mContext, PocActivity.class) 125 .setData(Uri.parse(mBaseUri + "bluetooth_always_scanning_switch")) 126 .addFlags(Intent.FLAG_ACTIVITY_NEW_TASK)); 127 128 // Wait for the slice that contains option to toggle "Bluetooth scanning" 129 String btScanningText = 130 mSettingsResources.getString( 131 mSettingsResources.getIdentifier( 132 "location_scanning_bluetooth_always_scanning_title", 133 "string", 134 mSettingsPackage)); 135 boolean btScanningFound = 136 mDevice.wait( 137 Until.hasObject(By.text(btScanningText).res(mScanningTextResId)), 138 waitMS); 139 assumeTrue( 140 "Timed out waiting on the text \'" + btScanningText + "\' to appear", 141 btScanningFound); 142 143 // Try to toggle "Bluetooth scanning" button, it is supposed to be disabled by the 144 // Device Admin in presence of fix 145 UiObject2 btScanningToggle = mDevice.findObject(By.res(mScanningWidgetResId)); 146 btScanningToggle.click(); 147 148 // Value of isChecked is whether "Bluetooth scanning" button should be checked or 149 // unchecked after click() 150 assumeTrue( 151 "Timed out waiting on the button \'" + btScanningToggle + "\' to toggle", 152 btScanningToggle.wait( 153 Until.checked(initialBleScanGlobalSetting == 0 /* isChecked */), 154 waitMS) 155 || !btScanningToggle.isEnabled()); 156 157 final int finalBleScanGlobalSetting = 158 Settings.Global.getInt( 159 mContentResolver, Settings.Global.BLE_SCAN_ALWAYS_AVAILABLE, -1); 160 assumeTrue(finalBleScanGlobalSetting != -1); 161 162 assertFalse( 163 "Device is vulnerable to b/277333781 !!", 164 finalBleScanGlobalSetting != initialBleScanGlobalSetting); 165 } catch (Exception e) { 166 assumeNoException(e); 167 } 168 } 169 170 @Test testPocCVE_2023_21248()171 public void testPocCVE_2023_21248() { 172 try { 173 final int initialWifiScanGlobalSetting = 174 Settings.Global.getInt( 175 mContentResolver, Settings.Global.WIFI_SCAN_ALWAYS_AVAILABLE, -1); 176 assumeTrue(initialWifiScanGlobalSetting != -1); 177 178 // Launching PocActivity to launch "wifi_always_scanning_switch" settings 179 // slice using slice-uri 180 mContext.startActivity( 181 new Intent(mContext, PocActivity.class) 182 .setData(Uri.parse(mBaseUri + "wifi_always_scanning_switch")) 183 .addFlags(Intent.FLAG_ACTIVITY_NEW_TASK)); 184 185 // Wait for the slice that contains option to toggle "Wifi scanning" 186 String wifiScanningText = 187 mSettingsResources.getString( 188 mSettingsResources.getIdentifier( 189 "location_scanning_wifi_always_scanning_title", 190 "string", 191 mSettingsPackage)); 192 boolean wifiScanningFound = 193 mDevice.wait( 194 Until.hasObject(By.text(wifiScanningText).res(mScanningTextResId)), 195 waitMS); 196 assumeTrue( 197 "Timed out waiting on the text \'" + wifiScanningText + "\' to appear", 198 wifiScanningFound); 199 200 // Try to toggle "Wifi scanning" button, it is supposed to be disabled by the 201 // Device Admin in presence of fix 202 UiObject2 wifiScanningToggle = mDevice.findObject(By.res(mScanningWidgetResId)); 203 wifiScanningToggle.click(); 204 205 // Value of isChecked is whether "Wifi scanning" button should be checked or 206 // unchecked after click() 207 assumeTrue( 208 "Timed out waiting on the button \'" + wifiScanningToggle + "\' to toggle", 209 wifiScanningToggle.wait( 210 Until.checked( 211 initialWifiScanGlobalSetting == 0 /* isChecked */), 212 waitMS) 213 || !wifiScanningToggle.isEnabled()); 214 215 final int finalWifiScanGlobalSetting = 216 Settings.Global.getInt( 217 mContentResolver, Settings.Global.WIFI_SCAN_ALWAYS_AVAILABLE, -1); 218 assumeTrue(finalWifiScanGlobalSetting != -1); 219 220 assertFalse( 221 "Device is vulnerable to b/277333746 !!", 222 finalWifiScanGlobalSetting != initialWifiScanGlobalSetting); 223 } catch (Exception e) { 224 assumeNoException(e); 225 } 226 } 227 } 228