1/*
2 * Copyright (C) 2016 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
17package com.android.server.wifi;
18
19import static org.junit.Assert.*;
20import static org.mockito.Mockito.*;
21
22import android.app.admin.DeviceAdminInfo;
23import android.app.admin.DevicePolicyManagerInternal;
24import android.app.test.MockAnswerUtil.AnswerWithArguments;
25import android.content.Context;
26import android.content.Intent;
27import android.content.pm.ApplicationInfo;
28import android.content.pm.PackageManager;
29import android.content.pm.UserInfo;
30import android.net.IpConfiguration;
31import android.net.wifi.ScanResult;
32import android.net.wifi.WifiConfiguration;
33import android.net.wifi.WifiConfiguration.NetworkSelectionStatus;
34import android.net.wifi.WifiEnterpriseConfig;
35import android.net.wifi.WifiManager;
36import android.net.wifi.WifiScanner;
37import android.net.wifi.WifiSsid;
38import android.os.Process;
39import android.os.UserHandle;
40import android.os.UserManager;
41import android.telephony.TelephonyManager;
42import android.test.suitebuilder.annotation.SmallTest;
43import android.text.TextUtils;
44import android.util.Pair;
45
46import com.android.internal.R;
47import com.android.server.wifi.WifiConfigStoreLegacy.WifiConfigStoreDataLegacy;
48import com.android.server.wifi.util.WifiPermissionsUtil;
49import com.android.server.wifi.util.WifiPermissionsWrapper;
50
51import org.junit.After;
52import org.junit.Before;
53import org.junit.Test;
54import org.mockito.ArgumentCaptor;
55import org.mockito.InOrder;
56import org.mockito.Mock;
57import org.mockito.MockitoAnnotations;
58
59import java.io.FileDescriptor;
60import java.io.PrintWriter;
61import java.io.StringWriter;
62import java.util.ArrayList;
63import java.util.Arrays;
64import java.util.HashSet;
65import java.util.List;
66import java.util.Random;
67import java.util.Set;
68
69/**
70 * Unit tests for {@link com.android.server.wifi.WifiConfigManager}.
71 */
72@SmallTest
73public class WifiConfigManagerTest {
74
75    private static final String TEST_BSSID = "0a:08:5c:67:89:00";
76    private static final long TEST_WALLCLOCK_CREATION_TIME_MILLIS = 9845637;
77    private static final long TEST_WALLCLOCK_UPDATE_TIME_MILLIS = 75455637;
78    private static final long TEST_ELAPSED_UPDATE_NETWORK_SELECTION_TIME_MILLIS = 29457631;
79    private static final int TEST_CREATOR_UID = WifiConfigurationTestUtil.TEST_UID;
80    private static final int TEST_NO_PERM_UID = 7;
81    private static final int TEST_UPDATE_UID = 4;
82    private static final int TEST_SYSUI_UID = 56;
83    private static final int TEST_DEFAULT_USER = UserHandle.USER_SYSTEM;
84    private static final int TEST_MAX_NUM_ACTIVE_CHANNELS_FOR_PARTIAL_SCAN = 5;
85    private static final Integer[] TEST_FREQ_LIST = {2400, 2450, 5150, 5175, 5650};
86    private static final String TEST_CREATOR_NAME = "com.wificonfigmanager.creator";
87    private static final String TEST_UPDATE_NAME = "com.wificonfigmanager.update";
88    private static final String TEST_NO_PERM_NAME = "com.wificonfigmanager.noperm";
89    private static final String TEST_DEFAULT_GW_MAC_ADDRESS = "0f:67:ad:ef:09:34";
90    private static final String TEST_STATIC_PROXY_HOST_1 = "192.168.48.1";
91    private static final int    TEST_STATIC_PROXY_PORT_1 = 8000;
92    private static final String TEST_STATIC_PROXY_EXCLUSION_LIST_1 = "";
93    private static final String TEST_PAC_PROXY_LOCATION_1 = "http://bleh";
94    private static final String TEST_STATIC_PROXY_HOST_2 = "192.168.1.1";
95    private static final int    TEST_STATIC_PROXY_PORT_2 = 3000;
96    private static final String TEST_STATIC_PROXY_EXCLUSION_LIST_2 = "";
97    private static final String TEST_PAC_PROXY_LOCATION_2 = "http://blah";
98
99    @Mock private Context mContext;
100    @Mock private Clock mClock;
101    @Mock private UserManager mUserManager;
102    @Mock private TelephonyManager mTelephonyManager;
103    @Mock private WifiKeyStore mWifiKeyStore;
104    @Mock private WifiConfigStore mWifiConfigStore;
105    @Mock private WifiConfigStoreLegacy mWifiConfigStoreLegacy;
106    @Mock private PackageManager mPackageManager;
107    @Mock private DevicePolicyManagerInternal mDevicePolicyManagerInternal;
108    @Mock private WifiPermissionsUtil mWifiPermissionsUtil;
109    @Mock private WifiPermissionsWrapper mWifiPermissionsWrapper;
110    @Mock private NetworkListStoreData mNetworkListStoreData;
111    @Mock private DeletedEphemeralSsidsStoreData mDeletedEphemeralSsidsStoreData;
112    @Mock private WifiConfigManager.OnSavedNetworkUpdateListener mWcmListener;
113
114    private MockResources mResources;
115    private InOrder mContextConfigStoreMockOrder;
116    private InOrder mNetworkListStoreDataMockOrder;
117    private WifiConfigManager mWifiConfigManager;
118    private boolean mStoreReadTriggered = false;
119
120    /**
121     * Setup the mocks and an instance of WifiConfigManager before each test.
122     */
123    @Before
124    public void setUp() throws Exception {
125        MockitoAnnotations.initMocks(this);
126
127        // Set up the inorder for verifications. This is needed to verify that the broadcasts,
128        // store writes for network updates followed by network additions are in the expected order.
129        mContextConfigStoreMockOrder = inOrder(mContext, mWifiConfigStore);
130        mNetworkListStoreDataMockOrder = inOrder(mNetworkListStoreData);
131
132        // Set up the package name stuff & permission override.
133        when(mContext.getPackageManager()).thenReturn(mPackageManager);
134        mResources = new MockResources();
135        mResources.setBoolean(
136                R.bool.config_wifi_only_link_same_credential_configurations, true);
137        mResources.setInteger(
138                R.integer.config_wifi_framework_associated_partial_scan_max_num_active_channels,
139                TEST_MAX_NUM_ACTIVE_CHANNELS_FOR_PARTIAL_SCAN);
140        when(mContext.getResources()).thenReturn(mResources);
141
142        // Setup UserManager profiles for the default user.
143        setupUserProfiles(TEST_DEFAULT_USER);
144
145        doAnswer(new AnswerWithArguments() {
146            public String answer(int uid) throws Exception {
147                if (uid == TEST_CREATOR_UID) {
148                    return TEST_CREATOR_NAME;
149                } else if (uid == TEST_UPDATE_UID) {
150                    return TEST_UPDATE_NAME;
151                } else if (uid == TEST_SYSUI_UID) {
152                    return WifiConfigManager.SYSUI_PACKAGE_NAME;
153                } else if (uid == TEST_NO_PERM_UID) {
154                    return TEST_NO_PERM_NAME;
155                }
156                fail("Unexpected UID: " + uid);
157                return "";
158            }
159        }).when(mPackageManager).getNameForUid(anyInt());
160        doAnswer(new AnswerWithArguments() {
161            public int answer(String packageName, int flags, int userId) throws Exception {
162                if (packageName.equals(WifiConfigManager.SYSUI_PACKAGE_NAME)) {
163                    return TEST_SYSUI_UID;
164                } else {
165                    return 0;
166                }
167            }
168        }).when(mPackageManager).getPackageUidAsUser(anyString(), anyInt(), anyInt());
169
170        when(mWifiKeyStore
171                .updateNetworkKeys(any(WifiConfiguration.class), any()))
172                .thenReturn(true);
173
174        when(mWifiConfigStore.areStoresPresent()).thenReturn(true);
175        setupStoreDataForRead(new ArrayList<WifiConfiguration>(),
176                new ArrayList<WifiConfiguration>(), new HashSet<String>());
177
178        when(mDevicePolicyManagerInternal.isActiveAdminWithPolicy(anyInt(), anyInt()))
179                .thenReturn(false);
180        when(mWifiPermissionsUtil.checkConfigOverridePermission(anyInt())).thenReturn(true);
181        when(mWifiPermissionsWrapper.getDevicePolicyManagerInternal())
182                .thenReturn(mDevicePolicyManagerInternal);
183        createWifiConfigManager();
184        mWifiConfigManager.setOnSavedNetworkUpdateListener(mWcmListener);
185    }
186
187    /**
188     * Called after each test
189     */
190    @After
191    public void cleanup() {
192        validateMockitoUsage();
193    }
194
195    /**
196     * Verifies that network retrieval via
197     * {@link WifiConfigManager#getConfiguredNetworks()} and
198     * {@link WifiConfigManager#getConfiguredNetworksWithPasswords()} works even if we have not
199     * yet loaded data from store.
200     */
201    @Test
202    public void testGetConfiguredNetworksBeforeLoadFromStore() {
203        assertTrue(mWifiConfigManager.getConfiguredNetworks().isEmpty());
204        assertTrue(mWifiConfigManager.getConfiguredNetworksWithPasswords().isEmpty());
205    }
206
207    /**
208     * Verifies that network addition via
209     * {@link WifiConfigManager#addOrUpdateNetwork(WifiConfiguration, int)} fails if we have not
210     * yet loaded data from store.
211     */
212    @Test
213    public void testAddNetworkBeforeLoadFromStore() {
214        WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork();
215        assertFalse(
216                mWifiConfigManager.addOrUpdateNetwork(openNetwork, TEST_CREATOR_UID).isSuccess());
217    }
218
219    /**
220     * Verifies the addition of a single network using
221     * {@link WifiConfigManager#addOrUpdateNetwork(WifiConfiguration, int)}
222     */
223    @Test
224    public void testAddSingleOpenNetwork() {
225        WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork();
226        List<WifiConfiguration> networks = new ArrayList<>();
227        networks.add(openNetwork);
228
229        verifyAddNetworkToWifiConfigManager(openNetwork);
230
231        List<WifiConfiguration> retrievedNetworks =
232                mWifiConfigManager.getConfiguredNetworksWithPasswords();
233        WifiConfigurationTestUtil.assertConfigurationsEqualForConfigManagerAddOrUpdate(
234                networks, retrievedNetworks);
235        // Ensure that the newly added network is disabled.
236        assertEquals(WifiConfiguration.Status.DISABLED, retrievedNetworks.get(0).status);
237    }
238
239    /**
240     * Verifies the modification of a single network using
241     * {@link WifiConfigManager#addOrUpdateNetwork(WifiConfiguration, int)}
242     */
243    @Test
244    public void testUpdateSingleOpenNetwork() {
245        WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork();
246        List<WifiConfiguration> networks = new ArrayList<>();
247        networks.add(openNetwork);
248
249        verifyAddNetworkToWifiConfigManager(openNetwork);
250        verify(mWcmListener).onSavedNetworkAdded(openNetwork.networkId);
251        reset(mWcmListener);
252
253        // Now change BSSID for the network.
254        assertAndSetNetworkBSSID(openNetwork, TEST_BSSID);
255        verifyUpdateNetworkToWifiConfigManagerWithoutIpChange(openNetwork);
256
257        // Now verify that the modification has been effective.
258        List<WifiConfiguration> retrievedNetworks =
259                mWifiConfigManager.getConfiguredNetworksWithPasswords();
260        WifiConfigurationTestUtil.assertConfigurationsEqualForConfigManagerAddOrUpdate(
261                networks, retrievedNetworks);
262        verify(mWcmListener).onSavedNetworkUpdated(openNetwork.networkId);
263    }
264
265    /**
266     * Verifies the addition of a single ephemeral network using
267     * {@link WifiConfigManager#addOrUpdateNetwork(WifiConfiguration, int)} and verifies that
268     * the {@link WifiConfigManager#getSavedNetworks()} does not return this network.
269     */
270    @Test
271    public void testAddSingleEphemeralNetwork() throws Exception {
272        WifiConfiguration ephemeralNetwork = WifiConfigurationTestUtil.createOpenNetwork();
273        ephemeralNetwork.ephemeral = true;
274        List<WifiConfiguration> networks = new ArrayList<>();
275        networks.add(ephemeralNetwork);
276
277        verifyAddEphemeralNetworkToWifiConfigManager(ephemeralNetwork);
278
279        List<WifiConfiguration> retrievedNetworks =
280                mWifiConfigManager.getConfiguredNetworksWithPasswords();
281        WifiConfigurationTestUtil.assertConfigurationsEqualForConfigManagerAddOrUpdate(
282                networks, retrievedNetworks);
283
284        // Ensure that this is not returned in the saved network list.
285        assertTrue(mWifiConfigManager.getSavedNetworks().isEmpty());
286        verify(mWcmListener, never()).onSavedNetworkAdded(ephemeralNetwork.networkId);
287    }
288
289    /**
290     * Verifies the addition of 2 networks (1 normal and 1 ephemeral) using
291     * {@link WifiConfigManager#addOrUpdateNetwork(WifiConfiguration, int)} and ensures that
292     * the ephemeral network configuration is not persisted in config store.
293     */
294    @Test
295    public void testAddMultipleNetworksAndEnsureEphemeralNetworkNotPersisted() {
296        WifiConfiguration ephemeralNetwork = WifiConfigurationTestUtil.createOpenNetwork();
297        ephemeralNetwork.ephemeral = true;
298        WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork();
299
300        assertTrue(addNetworkToWifiConfigManager(ephemeralNetwork).isSuccess());
301        assertTrue(addNetworkToWifiConfigManager(openNetwork).isSuccess());
302
303        // The open network addition should trigger a store write.
304        Pair<List<WifiConfiguration>, List<WifiConfiguration>> networkListStoreData =
305                captureWriteNetworksListStoreData();
306        List<WifiConfiguration> networkList = new ArrayList<>();
307        networkList.addAll(networkListStoreData.first);
308        networkList.addAll(networkListStoreData.second);
309        assertFalse(isNetworkInConfigStoreData(ephemeralNetwork, networkList));
310        assertTrue(isNetworkInConfigStoreData(openNetwork, networkList));
311    }
312
313    /**
314     * Verifies that the modification of a single open network using
315     * {@link WifiConfigManager#addOrUpdateNetwork(WifiConfiguration, int)} with a UID which
316     * has no permission to modify the network fails.
317     */
318    @Test
319    public void testUpdateSingleOpenNetworkFailedDueToPermissionDenied() throws Exception {
320        WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork();
321        List<WifiConfiguration> networks = new ArrayList<>();
322        networks.add(openNetwork);
323
324        verifyAddNetworkToWifiConfigManager(openNetwork);
325
326        // Now change BSSID of the network.
327        assertAndSetNetworkBSSID(openNetwork, TEST_BSSID);
328
329        when(mWifiPermissionsUtil.checkConfigOverridePermission(anyInt())).thenReturn(false);
330
331        // Update the same configuration and ensure that the operation failed.
332        NetworkUpdateResult result = updateNetworkToWifiConfigManager(openNetwork);
333        assertTrue(result.getNetworkId() == WifiConfiguration.INVALID_NETWORK_ID);
334    }
335
336    /**
337     * Verifies that the modification of a single open network using
338     * {@link WifiConfigManager#addOrUpdateNetwork(WifiConfiguration, int)} with the creator UID
339     * should always succeed.
340     */
341    @Test
342    public void testUpdateSingleOpenNetworkSuccessWithCreatorUID() throws Exception {
343        WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork();
344        List<WifiConfiguration> networks = new ArrayList<>();
345        networks.add(openNetwork);
346
347        verifyAddNetworkToWifiConfigManager(openNetwork);
348
349        // Now change BSSID of the network.
350        assertAndSetNetworkBSSID(openNetwork, TEST_BSSID);
351
352        // Update the same configuration using the creator UID.
353        NetworkUpdateResult result =
354                mWifiConfigManager.addOrUpdateNetwork(openNetwork, TEST_CREATOR_UID);
355        assertTrue(result.getNetworkId() != WifiConfiguration.INVALID_NETWORK_ID);
356
357        // Now verify that the modification has been effective.
358        List<WifiConfiguration> retrievedNetworks =
359                mWifiConfigManager.getConfiguredNetworksWithPasswords();
360        WifiConfigurationTestUtil.assertConfigurationsEqualForConfigManagerAddOrUpdate(
361                networks, retrievedNetworks);
362    }
363
364    /**
365     * Verifies the addition of a single PSK network using
366     * {@link WifiConfigManager#addOrUpdateNetwork(WifiConfiguration, int)} and verifies that
367     * {@link WifiConfigManager#getSavedNetworks()} masks the password.
368     */
369    @Test
370    public void testAddSinglePskNetwork() {
371        WifiConfiguration pskNetwork = WifiConfigurationTestUtil.createPskNetwork();
372        List<WifiConfiguration> networks = new ArrayList<>();
373        networks.add(pskNetwork);
374
375        verifyAddNetworkToWifiConfigManager(pskNetwork);
376
377        List<WifiConfiguration> retrievedNetworks =
378                mWifiConfigManager.getConfiguredNetworksWithPasswords();
379        WifiConfigurationTestUtil.assertConfigurationsEqualForConfigManagerAddOrUpdate(
380                networks, retrievedNetworks);
381
382        List<WifiConfiguration> retrievedSavedNetworks = mWifiConfigManager.getSavedNetworks();
383        assertEquals(retrievedSavedNetworks.size(), 1);
384        assertEquals(retrievedSavedNetworks.get(0).configKey(), pskNetwork.configKey());
385        assertPasswordsMaskedInWifiConfiguration(retrievedSavedNetworks.get(0));
386    }
387
388    /**
389     * Verifies the addition of a single WEP network using
390     * {@link WifiConfigManager#addOrUpdateNetwork(WifiConfiguration, int)} and verifies that
391     * {@link WifiConfigManager#getSavedNetworks()} masks the password.
392     */
393    @Test
394    public void testAddSingleWepNetwork() {
395        WifiConfiguration wepNetwork = WifiConfigurationTestUtil.createWepNetwork();
396        List<WifiConfiguration> networks = new ArrayList<>();
397        networks.add(wepNetwork);
398
399        verifyAddNetworkToWifiConfigManager(wepNetwork);
400
401        List<WifiConfiguration> retrievedNetworks =
402                mWifiConfigManager.getConfiguredNetworksWithPasswords();
403        WifiConfigurationTestUtil.assertConfigurationsEqualForConfigManagerAddOrUpdate(
404                networks, retrievedNetworks);
405
406        List<WifiConfiguration> retrievedSavedNetworks = mWifiConfigManager.getSavedNetworks();
407        assertEquals(retrievedSavedNetworks.size(), 1);
408        assertEquals(retrievedSavedNetworks.get(0).configKey(), wepNetwork.configKey());
409        assertPasswordsMaskedInWifiConfiguration(retrievedSavedNetworks.get(0));
410    }
411
412    /**
413     * Verifies the modification of an IpConfiguration using
414     * {@link WifiConfigManager#addOrUpdateNetwork(WifiConfiguration, int)}
415     */
416    @Test
417    public void testUpdateIpConfiguration() {
418        WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork();
419        List<WifiConfiguration> networks = new ArrayList<>();
420        networks.add(openNetwork);
421
422        verifyAddNetworkToWifiConfigManager(openNetwork);
423
424        // Now change BSSID of the network.
425        assertAndSetNetworkBSSID(openNetwork, TEST_BSSID);
426
427        // Update the same configuration and ensure that the IP configuration change flags
428        // are not set.
429        verifyUpdateNetworkToWifiConfigManagerWithoutIpChange(openNetwork);
430
431        // Configure mock DevicePolicyManager to give Profile Owner permission so that we can modify
432        // proxy settings on a configuration
433        when(mDevicePolicyManagerInternal.isActiveAdminWithPolicy(anyInt(),
434                eq(DeviceAdminInfo.USES_POLICY_PROFILE_OWNER))).thenReturn(true);
435
436        // Change the IpConfiguration now and ensure that the IP configuration flags are set now.
437        assertAndSetNetworkIpConfiguration(
438                openNetwork,
439                WifiConfigurationTestUtil.createStaticIpConfigurationWithStaticProxy());
440        verifyUpdateNetworkToWifiConfigManagerWithIpChange(openNetwork);
441
442        // Now verify that all the modifications have been effective.
443        List<WifiConfiguration> retrievedNetworks =
444                mWifiConfigManager.getConfiguredNetworksWithPasswords();
445        WifiConfigurationTestUtil.assertConfigurationsEqualForConfigManagerAddOrUpdate(
446                networks, retrievedNetworks);
447    }
448
449    /**
450     * Verifies the removal of a single network using
451     * {@link WifiConfigManager#removeNetwork(int)}
452     */
453    @Test
454    public void testRemoveSingleOpenNetwork() {
455        WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork();
456
457        verifyAddNetworkToWifiConfigManager(openNetwork);
458        verify(mWcmListener).onSavedNetworkAdded(openNetwork.networkId);
459        reset(mWcmListener);
460
461        // Ensure that configured network list is not empty.
462        assertFalse(mWifiConfigManager.getConfiguredNetworks().isEmpty());
463
464        verifyRemoveNetworkFromWifiConfigManager(openNetwork);
465        // Ensure that configured network list is empty now.
466        assertTrue(mWifiConfigManager.getConfiguredNetworks().isEmpty());
467        verify(mWcmListener).onSavedNetworkRemoved(openNetwork.networkId);
468    }
469
470    /**
471     * Verifies the removal of an ephemeral network using
472     * {@link WifiConfigManager#removeNetwork(int)}
473     */
474    @Test
475    public void testRemoveSingleEphemeralNetwork() throws Exception {
476        WifiConfiguration ephemeralNetwork = WifiConfigurationTestUtil.createOpenNetwork();
477        ephemeralNetwork.ephemeral = true;
478
479        verifyAddEphemeralNetworkToWifiConfigManager(ephemeralNetwork);
480        // Ensure that configured network list is not empty.
481        assertFalse(mWifiConfigManager.getConfiguredNetworks().isEmpty());
482        verify(mWcmListener, never()).onSavedNetworkAdded(ephemeralNetwork.networkId);
483
484        verifyRemoveEphemeralNetworkFromWifiConfigManager(ephemeralNetwork);
485        // Ensure that configured network list is empty now.
486        assertTrue(mWifiConfigManager.getConfiguredNetworks().isEmpty());
487        verify(mWcmListener, never()).onSavedNetworkRemoved(ephemeralNetwork.networkId);
488    }
489
490    /**
491     * Verifies the removal of a Passpoint network using
492     * {@link WifiConfigManager#removeNetwork(int)}
493     */
494    @Test
495    public void testRemoveSinglePasspointNetwork() throws Exception {
496        WifiConfiguration passpointNetwork = WifiConfigurationTestUtil.createPasspointNetwork();
497
498        verifyAddPasspointNetworkToWifiConfigManager(passpointNetwork);
499        // Ensure that configured network list is not empty.
500        assertFalse(mWifiConfigManager.getConfiguredNetworks().isEmpty());
501        verify(mWcmListener, never()).onSavedNetworkAdded(passpointNetwork.networkId);
502
503        verifyRemovePasspointNetworkFromWifiConfigManager(passpointNetwork);
504        // Ensure that configured network list is empty now.
505        assertTrue(mWifiConfigManager.getConfiguredNetworks().isEmpty());
506        verify(mWcmListener, never()).onSavedNetworkRemoved(passpointNetwork.networkId);
507    }
508
509    /**
510     * Verify that a Passpoint network that's added by an app with {@link #TEST_CREATOR_UID} can
511     * be removed by WiFi Service with {@link Process#WIFI_UID}.
512     *
513     * @throws Exception
514     */
515    @Test
516    public void testRemovePasspointNetworkAddedByOther() throws Exception {
517        WifiConfiguration passpointNetwork = WifiConfigurationTestUtil.createPasspointNetwork();
518
519        // Passpoint network is added using TEST_CREATOR_UID.
520        verifyAddPasspointNetworkToWifiConfigManager(passpointNetwork);
521        // Ensure that configured network list is not empty.
522        assertFalse(mWifiConfigManager.getConfiguredNetworks().isEmpty());
523
524        assertTrue(mWifiConfigManager.removeNetwork(passpointNetwork.networkId, Process.WIFI_UID));
525
526        // Verify keys are not being removed.
527        verify(mWifiKeyStore, never()).removeKeys(any(WifiEnterpriseConfig.class));
528        verifyNetworkRemoveBroadcast(passpointNetwork);
529        // Ensure that the write was not invoked for Passpoint network remove.
530        mContextConfigStoreMockOrder.verify(mWifiConfigStore, never()).write(anyBoolean());
531
532    }
533    /**
534     * Verifies the addition & update of multiple networks using
535     * {@link WifiConfigManager#addOrUpdateNetwork(WifiConfiguration, int)} and the
536     * removal of networks using
537     * {@link WifiConfigManager#removeNetwork(int)}
538     */
539    @Test
540    public void testAddUpdateRemoveMultipleNetworks() {
541        List<WifiConfiguration> networks = new ArrayList<>();
542        WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork();
543        WifiConfiguration pskNetwork = WifiConfigurationTestUtil.createPskNetwork();
544        WifiConfiguration wepNetwork = WifiConfigurationTestUtil.createWepNetwork();
545        networks.add(openNetwork);
546        networks.add(pskNetwork);
547        networks.add(wepNetwork);
548
549        verifyAddNetworkToWifiConfigManager(openNetwork);
550        verifyAddNetworkToWifiConfigManager(pskNetwork);
551        verifyAddNetworkToWifiConfigManager(wepNetwork);
552
553        // Now verify that all the additions has been effective.
554        List<WifiConfiguration> retrievedNetworks =
555                mWifiConfigManager.getConfiguredNetworksWithPasswords();
556        WifiConfigurationTestUtil.assertConfigurationsEqualForConfigManagerAddOrUpdate(
557                networks, retrievedNetworks);
558
559        // Modify all the 3 configurations and update it to WifiConfigManager.
560        assertAndSetNetworkBSSID(openNetwork, TEST_BSSID);
561        assertAndSetNetworkBSSID(pskNetwork, TEST_BSSID);
562        assertAndSetNetworkIpConfiguration(
563                wepNetwork,
564                WifiConfigurationTestUtil.createStaticIpConfigurationWithPacProxy());
565
566        // Configure mock DevicePolicyManager to give Profile Owner permission so that we can modify
567        // proxy settings on a configuration
568        when(mDevicePolicyManagerInternal.isActiveAdminWithPolicy(anyInt(),
569                eq(DeviceAdminInfo.USES_POLICY_PROFILE_OWNER))).thenReturn(true);
570
571        verifyUpdateNetworkToWifiConfigManagerWithoutIpChange(openNetwork);
572        verifyUpdateNetworkToWifiConfigManagerWithoutIpChange(pskNetwork);
573        verifyUpdateNetworkToWifiConfigManagerWithIpChange(wepNetwork);
574        // Now verify that all the modifications has been effective.
575        retrievedNetworks = mWifiConfigManager.getConfiguredNetworksWithPasswords();
576        WifiConfigurationTestUtil.assertConfigurationsEqualForConfigManagerAddOrUpdate(
577                networks, retrievedNetworks);
578
579        // Now remove all 3 networks.
580        verifyRemoveNetworkFromWifiConfigManager(openNetwork);
581        verifyRemoveNetworkFromWifiConfigManager(pskNetwork);
582        verifyRemoveNetworkFromWifiConfigManager(wepNetwork);
583
584        // Ensure that configured network list is empty now.
585        assertTrue(mWifiConfigManager.getConfiguredNetworks().isEmpty());
586    }
587
588    /**
589     * Verifies the update of network status using
590     * {@link WifiConfigManager#updateNetworkSelectionStatus(int, int)}.
591     */
592    @Test
593    public void testNetworkSelectionStatus() {
594        WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork();
595
596        NetworkUpdateResult result = verifyAddNetworkToWifiConfigManager(openNetwork);
597
598        int networkId = result.getNetworkId();
599        // First set it to enabled.
600        verifyUpdateNetworkSelectionStatus(
601                networkId, NetworkSelectionStatus.NETWORK_SELECTION_ENABLE, 0);
602
603        // Now set it to temporarily disabled. The threshold for association rejection is 5, so
604        // disable it 5 times to actually mark it temporarily disabled.
605        int assocRejectReason = NetworkSelectionStatus.DISABLED_ASSOCIATION_REJECTION;
606        int assocRejectThreshold =
607                WifiConfigManager.NETWORK_SELECTION_DISABLE_THRESHOLD[assocRejectReason];
608        for (int i = 1; i <= assocRejectThreshold; i++) {
609            verifyUpdateNetworkSelectionStatus(result.getNetworkId(), assocRejectReason, i);
610        }
611        verify(mWcmListener).onSavedNetworkTemporarilyDisabled(networkId);
612
613        // Now set it to permanently disabled.
614        verifyUpdateNetworkSelectionStatus(
615                result.getNetworkId(), NetworkSelectionStatus.DISABLED_BY_WIFI_MANAGER, 0);
616        verify(mWcmListener).onSavedNetworkPermanentlyDisabled(networkId);
617
618        // Now set it back to enabled.
619        verifyUpdateNetworkSelectionStatus(
620                result.getNetworkId(), NetworkSelectionStatus.NETWORK_SELECTION_ENABLE, 0);
621        verify(mWcmListener, times(2)).onSavedNetworkEnabled(networkId);
622    }
623
624    /**
625     * Verifies the update of network status using
626     * {@link WifiConfigManager#updateNetworkSelectionStatus(int, int)} and ensures that
627     * enabling a network clears out all the temporary disable counters.
628     */
629    @Test
630    public void testNetworkSelectionStatusEnableClearsDisableCounters() {
631        WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork();
632
633        NetworkUpdateResult result = verifyAddNetworkToWifiConfigManager(openNetwork);
634
635        // First set it to enabled.
636        verifyUpdateNetworkSelectionStatus(
637                result.getNetworkId(), NetworkSelectionStatus.NETWORK_SELECTION_ENABLE, 0);
638
639        // Now set it to temporarily disabled 2 times for 2 different reasons.
640        verifyUpdateNetworkSelectionStatus(
641                result.getNetworkId(), NetworkSelectionStatus.DISABLED_ASSOCIATION_REJECTION, 1);
642        verifyUpdateNetworkSelectionStatus(
643                result.getNetworkId(), NetworkSelectionStatus.DISABLED_ASSOCIATION_REJECTION, 2);
644        verifyUpdateNetworkSelectionStatus(
645                result.getNetworkId(), NetworkSelectionStatus.DISABLED_AUTHENTICATION_FAILURE, 1);
646        verifyUpdateNetworkSelectionStatus(
647                result.getNetworkId(), NetworkSelectionStatus.DISABLED_AUTHENTICATION_FAILURE, 2);
648
649        // Now set it back to enabled.
650        verifyUpdateNetworkSelectionStatus(
651                result.getNetworkId(), NetworkSelectionStatus.NETWORK_SELECTION_ENABLE, 0);
652
653        // Ensure that the counters have all been reset now.
654        verifyUpdateNetworkSelectionStatus(
655                result.getNetworkId(), NetworkSelectionStatus.DISABLED_ASSOCIATION_REJECTION, 1);
656        verifyUpdateNetworkSelectionStatus(
657                result.getNetworkId(), NetworkSelectionStatus.DISABLED_AUTHENTICATION_FAILURE, 1);
658    }
659
660    /**
661     * Verifies that {@link WifiConfigManager#updateNetworkNotRecommended(int, boolean)} correctly
662     * updates the {@link NetworkSelectionStatus#mNotRecommended} bit.
663     */
664    @Test
665    public void testUpdateNetworkNotRecommended() {
666        WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork();
667
668        NetworkUpdateResult result = verifyAddNetworkToWifiConfigManager(openNetwork);
669
670        // First retrieve the configuration and check this it does not have this bit set
671        WifiConfiguration retrievedNetwork = mWifiConfigManager.getConfiguredNetwork(result.netId);
672
673        assertFalse(retrievedNetwork.getNetworkSelectionStatus().isNotRecommended());
674
675        // Update the network to be not recommended;
676        assertTrue(mWifiConfigManager.updateNetworkNotRecommended(
677                result.netId, true /* notRecommended*/));
678
679        retrievedNetwork = mWifiConfigManager.getConfiguredNetwork(result.netId);
680
681        assertTrue(retrievedNetwork.getNetworkSelectionStatus().isNotRecommended());
682
683        // Update the network to no longer be not recommended
684        assertTrue(mWifiConfigManager.updateNetworkNotRecommended(
685                result.netId, false/* notRecommended*/));
686
687        retrievedNetwork = mWifiConfigManager.getConfiguredNetwork(result.netId);
688
689        assertFalse(retrievedNetwork.getNetworkSelectionStatus().isNotRecommended());
690    }
691
692    /**
693     * Verifies the enabling of temporarily disabled network using
694     * {@link WifiConfigManager#tryEnableNetwork(int)}.
695     */
696    @Test
697    public void testTryEnableNetwork() {
698        WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork();
699
700        NetworkUpdateResult result = verifyAddNetworkToWifiConfigManager(openNetwork);
701
702        // First set it to enabled.
703        verifyUpdateNetworkSelectionStatus(
704                result.getNetworkId(), NetworkSelectionStatus.NETWORK_SELECTION_ENABLE, 0);
705
706        // Now set it to temporarily disabled. The threshold for association rejection is 5, so
707        // disable it 5 times to actually mark it temporarily disabled.
708        int assocRejectReason = NetworkSelectionStatus.DISABLED_ASSOCIATION_REJECTION;
709        int assocRejectThreshold =
710                WifiConfigManager.NETWORK_SELECTION_DISABLE_THRESHOLD[assocRejectReason];
711        for (int i = 1; i <= assocRejectThreshold; i++) {
712            verifyUpdateNetworkSelectionStatus(result.getNetworkId(), assocRejectReason, i);
713        }
714
715        // Now let's try enabling this network without changing the time, this should fail and the
716        // status remains temporarily disabled.
717        assertFalse(mWifiConfigManager.tryEnableNetwork(result.getNetworkId()));
718        NetworkSelectionStatus retrievedStatus =
719                mWifiConfigManager.getConfiguredNetwork(result.getNetworkId())
720                        .getNetworkSelectionStatus();
721        assertTrue(retrievedStatus.isNetworkTemporaryDisabled());
722
723        // Now advance time by the timeout for association rejection and ensure that the network
724        // is now enabled.
725        int assocRejectTimeout =
726                WifiConfigManager.NETWORK_SELECTION_DISABLE_TIMEOUT_MS[assocRejectReason];
727        when(mClock.getElapsedSinceBootMillis())
728                .thenReturn(TEST_ELAPSED_UPDATE_NETWORK_SELECTION_TIME_MILLIS + assocRejectTimeout);
729
730        assertTrue(mWifiConfigManager.tryEnableNetwork(result.getNetworkId()));
731        retrievedStatus =
732                mWifiConfigManager.getConfiguredNetwork(result.getNetworkId())
733                        .getNetworkSelectionStatus();
734        assertTrue(retrievedStatus.isNetworkEnabled());
735    }
736
737    /**
738     * Verifies the enabling of network using
739     * {@link WifiConfigManager#enableNetwork(int, boolean, int)} and
740     * {@link WifiConfigManager#disableNetwork(int, int)}.
741     */
742    @Test
743    public void testEnableDisableNetwork() throws Exception {
744        WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork();
745
746        NetworkUpdateResult result = verifyAddNetworkToWifiConfigManager(openNetwork);
747
748        assertTrue(mWifiConfigManager.enableNetwork(
749                result.getNetworkId(), false, TEST_CREATOR_UID));
750        WifiConfiguration retrievedNetwork =
751                mWifiConfigManager.getConfiguredNetwork(result.getNetworkId());
752        NetworkSelectionStatus retrievedStatus = retrievedNetwork.getNetworkSelectionStatus();
753        assertTrue(retrievedStatus.isNetworkEnabled());
754        verifyUpdateNetworkStatus(retrievedNetwork, WifiConfiguration.Status.ENABLED);
755        mContextConfigStoreMockOrder.verify(mWifiConfigStore).write(eq(true));
756
757        // Now set it disabled.
758        assertTrue(mWifiConfigManager.disableNetwork(result.getNetworkId(), TEST_CREATOR_UID));
759        retrievedNetwork = mWifiConfigManager.getConfiguredNetwork(result.getNetworkId());
760        retrievedStatus = retrievedNetwork.getNetworkSelectionStatus();
761        assertTrue(retrievedStatus.isNetworkPermanentlyDisabled());
762        verifyUpdateNetworkStatus(retrievedNetwork, WifiConfiguration.Status.DISABLED);
763        mContextConfigStoreMockOrder.verify(mWifiConfigStore).write(eq(true));
764    }
765
766    /**
767     * Verifies the enabling of network using
768     * {@link WifiConfigManager#enableNetwork(int, boolean, int)} with a UID which
769     * has no permission to modify the network fails..
770     */
771    @Test
772    public void testEnableDisableNetworkFailedDueToPermissionDenied() throws Exception {
773        WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork();
774
775        NetworkUpdateResult result = verifyAddNetworkToWifiConfigManager(openNetwork);
776
777        assertTrue(mWifiConfigManager.enableNetwork(
778                result.getNetworkId(), false, TEST_CREATOR_UID));
779        WifiConfiguration retrievedNetwork =
780                mWifiConfigManager.getConfiguredNetwork(result.getNetworkId());
781        NetworkSelectionStatus retrievedStatus = retrievedNetwork.getNetworkSelectionStatus();
782        assertTrue(retrievedStatus.isNetworkEnabled());
783        verifyUpdateNetworkStatus(retrievedNetwork, WifiConfiguration.Status.ENABLED);
784
785        when(mWifiPermissionsUtil.checkConfigOverridePermission(anyInt())).thenReturn(false);
786
787        // Now try to set it disabled with |TEST_UPDATE_UID|, it should fail and the network
788        // should remain enabled.
789        assertFalse(mWifiConfigManager.disableNetwork(result.getNetworkId(), TEST_UPDATE_UID));
790        retrievedStatus =
791                mWifiConfigManager.getConfiguredNetwork(result.getNetworkId())
792                        .getNetworkSelectionStatus();
793        assertTrue(retrievedStatus.isNetworkEnabled());
794        assertEquals(WifiConfiguration.Status.ENABLED, retrievedNetwork.status);
795    }
796
797    /**
798     * Verifies the updation of network's connectUid using
799     * {@link WifiConfigManager#checkAndUpdateLastConnectUid(int, int)}.
800     */
801    @Test
802    public void testUpdateLastConnectUid() throws Exception {
803        WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork();
804
805        NetworkUpdateResult result = verifyAddNetworkToWifiConfigManager(openNetwork);
806
807        assertTrue(
808                mWifiConfigManager.checkAndUpdateLastConnectUid(
809                        result.getNetworkId(), TEST_CREATOR_UID));
810        WifiConfiguration retrievedNetwork =
811                mWifiConfigManager.getConfiguredNetwork(result.getNetworkId());
812        assertEquals(TEST_CREATOR_UID, retrievedNetwork.lastConnectUid);
813
814        when(mWifiPermissionsUtil.checkConfigOverridePermission(anyInt())).thenReturn(false);
815
816        // Now try to update the last connect UID with |TEST_UPDATE_UID|, it should fail and
817        // the lastConnectUid should remain the same.
818        assertFalse(
819                mWifiConfigManager.checkAndUpdateLastConnectUid(
820                        result.getNetworkId(), TEST_UPDATE_UID));
821        retrievedNetwork = mWifiConfigManager.getConfiguredNetwork(result.getNetworkId());
822        assertEquals(TEST_CREATOR_UID, retrievedNetwork.lastConnectUid);
823    }
824
825    /**
826     * Verifies that any configuration update attempt with an null config is gracefully
827     * handled.
828     * This invokes {@link WifiConfigManager#addOrUpdateNetwork(WifiConfiguration, int)}.
829     */
830    @Test
831    public void testAddOrUpdateNetworkWithNullConfig() {
832        NetworkUpdateResult result = mWifiConfigManager.addOrUpdateNetwork(null, TEST_CREATOR_UID);
833        assertFalse(result.isSuccess());
834    }
835
836    /**
837     * Verifies that attempting to remove a network without any configs stored will return false.
838     * This tests the case where we have not loaded any configs, potentially due to a pending store
839     * read.
840     * This invokes {@link WifiConfigManager#removeNetwork(int)}.
841     */
842    @Test
843    public void testRemoveNetworkWithEmptyConfigStore() {
844        int networkId = new Random().nextInt();
845        assertFalse(mWifiConfigManager.removeNetwork(networkId, TEST_CREATOR_UID));
846    }
847
848    /**
849     * Verifies that any configuration removal attempt with an invalid networkID is gracefully
850     * handled.
851     * This invokes {@link WifiConfigManager#removeNetwork(int)}.
852     */
853    @Test
854    public void testRemoveNetworkWithInvalidNetworkId() {
855        WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork();
856
857        verifyAddNetworkToWifiConfigManager(openNetwork);
858
859        // Change the networkID to an invalid one.
860        openNetwork.networkId++;
861        assertFalse(mWifiConfigManager.removeNetwork(openNetwork.networkId, TEST_CREATOR_UID));
862    }
863
864    /**
865     * Verifies that any configuration update attempt with an invalid networkID is gracefully
866     * handled.
867     * This invokes {@link WifiConfigManager#enableNetwork(int, boolean, int)},
868     * {@link WifiConfigManager#disableNetwork(int, int)},
869     * {@link WifiConfigManager#updateNetworkSelectionStatus(int, int)} and
870     * {@link WifiConfigManager#checkAndUpdateLastConnectUid(int, int)}.
871     */
872    @Test
873    public void testChangeConfigurationWithInvalidNetworkId() {
874        WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork();
875
876        NetworkUpdateResult result = verifyAddNetworkToWifiConfigManager(openNetwork);
877
878        assertFalse(mWifiConfigManager.enableNetwork(
879                result.getNetworkId() + 1, false, TEST_CREATOR_UID));
880        assertFalse(mWifiConfigManager.disableNetwork(result.getNetworkId() + 1, TEST_CREATOR_UID));
881        assertFalse(mWifiConfigManager.updateNetworkSelectionStatus(
882                result.getNetworkId() + 1, NetworkSelectionStatus.DISABLED_BY_WIFI_MANAGER));
883        assertFalse(mWifiConfigManager.checkAndUpdateLastConnectUid(
884                result.getNetworkId() + 1, TEST_CREATOR_UID));
885    }
886
887    /**
888     * Verifies multiple modification of a single network using
889     * {@link WifiConfigManager#addOrUpdateNetwork(WifiConfiguration, int)}.
890     * This test is basically checking if the apps can reset some of the fields of the config after
891     * addition. The fields being reset in this test are the |preSharedKey| and |wepKeys|.
892     * 1. Create an open network initially.
893     * 2. Modify the added network config to a WEP network config with all the 4 keys set.
894     * 3. Modify the added network config to a WEP network config with only 1 key set.
895     * 4. Modify the added network config to a PSK network config.
896     */
897    @Test
898    public void testMultipleUpdatesSingleNetwork() {
899        WifiConfiguration network = WifiConfigurationTestUtil.createOpenNetwork();
900        verifyAddNetworkToWifiConfigManager(network);
901
902        // Now add |wepKeys| to the network. We don't need to update the |allowedKeyManagement|
903        // fields for open to WEP conversion.
904        String[] wepKeys =
905                Arrays.copyOf(WifiConfigurationTestUtil.TEST_WEP_KEYS,
906                        WifiConfigurationTestUtil.TEST_WEP_KEYS.length);
907        int wepTxKeyIdx = WifiConfigurationTestUtil.TEST_WEP_TX_KEY_INDEX;
908        assertAndSetNetworkWepKeysAndTxIndex(network, wepKeys, wepTxKeyIdx);
909
910        verifyUpdateNetworkToWifiConfigManagerWithoutIpChange(network);
911        WifiConfigurationTestUtil.assertConfigurationEqualForConfigManagerAddOrUpdate(
912                network, mWifiConfigManager.getConfiguredNetworkWithPassword(network.networkId));
913
914        // Now empty out 3 of the |wepKeys[]| and ensure that those keys have been reset correctly.
915        for (int i = 1; i < network.wepKeys.length; i++) {
916            wepKeys[i] = "";
917        }
918        wepTxKeyIdx = 0;
919        assertAndSetNetworkWepKeysAndTxIndex(network, wepKeys, wepTxKeyIdx);
920
921        verifyUpdateNetworkToWifiConfigManagerWithoutIpChange(network);
922        WifiConfigurationTestUtil.assertConfigurationEqualForConfigManagerAddOrUpdate(
923                network, mWifiConfigManager.getConfiguredNetworkWithPassword(network.networkId));
924
925        // Now change the config to a PSK network config by resetting the remaining |wepKey[0]|
926        // field and setting the |preSharedKey| and |allowedKeyManagement| fields.
927        wepKeys[0] = "";
928        wepTxKeyIdx = -1;
929        assertAndSetNetworkWepKeysAndTxIndex(network, wepKeys, wepTxKeyIdx);
930        network.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.WPA_PSK);
931        assertAndSetNetworkPreSharedKey(network, WifiConfigurationTestUtil.TEST_PSK);
932
933        verifyUpdateNetworkToWifiConfigManagerWithoutIpChange(network);
934        WifiConfigurationTestUtil.assertConfigurationEqualForConfigManagerAddOrUpdate(
935                network, mWifiConfigManager.getConfiguredNetworkWithPassword(network.networkId));
936    }
937
938    /**
939     * Verifies the modification of a WifiEnteriseConfig using
940     * {@link WifiConfigManager#addOrUpdateNetwork(WifiConfiguration, int)}.
941     */
942    @Test
943    public void testUpdateWifiEnterpriseConfig() {
944        WifiConfiguration network = WifiConfigurationTestUtil.createEapNetwork();
945        verifyAddNetworkToWifiConfigManager(network);
946
947        // Set the |password| field in WifiEnterpriseConfig and modify the config to PEAP/GTC.
948        network.enterpriseConfig =
949                WifiConfigurationTestUtil.createPEAPWifiEnterpriseConfigWithGTCPhase2();
950        assertAndSetNetworkEnterprisePassword(network, "test");
951
952        verifyUpdateNetworkToWifiConfigManagerWithoutIpChange(network);
953        WifiConfigurationTestUtil.assertConfigurationEqualForConfigManagerAddOrUpdate(
954                network, mWifiConfigManager.getConfiguredNetworkWithPassword(network.networkId));
955
956        // Reset the |password| field in WifiEnterpriseConfig and modify the config to TLS/None.
957        network.enterpriseConfig.setEapMethod(WifiEnterpriseConfig.Eap.TLS);
958        network.enterpriseConfig.setPhase2Method(WifiEnterpriseConfig.Phase2.NONE);
959        assertAndSetNetworkEnterprisePassword(network, "");
960
961        verifyUpdateNetworkToWifiConfigManagerWithoutIpChange(network);
962        WifiConfigurationTestUtil.assertConfigurationEqualForConfigManagerAddOrUpdate(
963                network, mWifiConfigManager.getConfiguredNetworkWithPassword(network.networkId));
964    }
965
966    /**
967     * Verifies the modification of a single network using
968     * {@link WifiConfigManager#addOrUpdateNetwork(WifiConfiguration, int)} by passing in nulls
969     * in all the publicly exposed fields.
970     */
971    @Test
972    public void testUpdateSingleNetworkWithNullValues() {
973        WifiConfiguration network = WifiConfigurationTestUtil.createEapNetwork();
974        verifyAddNetworkToWifiConfigManager(network);
975
976        // Save a copy of the original network for comparison.
977        WifiConfiguration originalNetwork = new WifiConfiguration(network);
978
979        // Now set all the public fields to null and try updating the network.
980        network.allowedAuthAlgorithms.clear();
981        network.allowedProtocols.clear();
982        network.allowedKeyManagement.clear();
983        network.allowedPairwiseCiphers.clear();
984        network.allowedGroupCiphers.clear();
985        network.setIpConfiguration(null);
986        network.enterpriseConfig = null;
987
988        // Update the network.
989        NetworkUpdateResult result = updateNetworkToWifiConfigManager(network);
990        assertTrue(result.getNetworkId() != WifiConfiguration.INVALID_NETWORK_ID);
991        assertFalse(result.isNewNetwork());
992
993        // Verify no changes to the original network configuration.
994        verifyNetworkUpdateBroadcast(originalNetwork);
995        verifyNetworkInConfigStoreData(originalNetwork);
996        assertFalse(result.hasIpChanged());
997        assertFalse(result.hasProxyChanged());
998
999        // Copy over the updated debug params to the original network config before comparison.
1000        originalNetwork.lastUpdateUid = network.lastUpdateUid;
1001        originalNetwork.lastUpdateName = network.lastUpdateName;
1002        originalNetwork.updateTime = network.updateTime;
1003
1004        // Now verify that there was no change to the network configurations.
1005        WifiConfigurationTestUtil.assertConfigurationEqualForConfigManagerAddOrUpdate(
1006                originalNetwork,
1007                mWifiConfigManager.getConfiguredNetworkWithPassword(originalNetwork.networkId));
1008    }
1009
1010    /**
1011     * Verifies that the modification of a single network using
1012     * {@link WifiConfigManager#addOrUpdateNetwork(WifiConfiguration, int)} does not modify
1013     * existing configuration if there is a failure.
1014     */
1015    @Test
1016    public void testUpdateSingleNetworkFailureDoesNotModifyOriginal() {
1017        WifiConfiguration network = WifiConfigurationTestUtil.createEapNetwork();
1018        network.enterpriseConfig =
1019                WifiConfigurationTestUtil.createPEAPWifiEnterpriseConfigWithGTCPhase2();
1020        verifyAddNetworkToWifiConfigManager(network);
1021
1022        // Save a copy of the original network for comparison.
1023        WifiConfiguration originalNetwork = new WifiConfiguration(network);
1024
1025        // Now modify the network's EAP method.
1026        network.enterpriseConfig =
1027                WifiConfigurationTestUtil.createTLSWifiEnterpriseConfigWithNonePhase2();
1028
1029        // Fail this update because of cert installation failure.
1030        when(mWifiKeyStore
1031                .updateNetworkKeys(any(WifiConfiguration.class), any(WifiConfiguration.class)))
1032                .thenReturn(false);
1033        NetworkUpdateResult result =
1034                mWifiConfigManager.addOrUpdateNetwork(network, TEST_UPDATE_UID);
1035        assertTrue(result.getNetworkId() == WifiConfiguration.INVALID_NETWORK_ID);
1036
1037        // Now verify that there was no change to the network configurations.
1038        WifiConfigurationTestUtil.assertConfigurationEqualForConfigManagerAddOrUpdate(
1039                originalNetwork,
1040                mWifiConfigManager.getConfiguredNetworkWithPassword(originalNetwork.networkId));
1041    }
1042
1043    /**
1044     * Verifies the matching of networks with different encryption types with the
1045     * corresponding scan detail using
1046     * {@link WifiConfigManager#getSavedNetworkForScanDetailAndCache(ScanDetail)}.
1047     * The test also verifies that the provided scan detail was cached,
1048     */
1049    @Test
1050    public void testMatchScanDetailToNetworksAndCache() {
1051        // Create networks of different types and ensure that they're all matched using
1052        // the corresponding ScanDetail correctly.
1053        verifyAddSingleNetworkAndMatchScanDetailToNetworkAndCache(
1054                WifiConfigurationTestUtil.createOpenNetwork());
1055        verifyAddSingleNetworkAndMatchScanDetailToNetworkAndCache(
1056                WifiConfigurationTestUtil.createWepNetwork());
1057        verifyAddSingleNetworkAndMatchScanDetailToNetworkAndCache(
1058                WifiConfigurationTestUtil.createPskNetwork());
1059        verifyAddSingleNetworkAndMatchScanDetailToNetworkAndCache(
1060                WifiConfigurationTestUtil.createEapNetwork());
1061    }
1062
1063    /**
1064     * Verifies that scan details with wrong SSID/authentication types are not matched using
1065     * {@link WifiConfigManager#getSavedNetworkForScanDetailAndCache(ScanDetail)}
1066     * to the added networks.
1067     */
1068    @Test
1069    public void testNoMatchScanDetailToNetwork() {
1070        // First create networks of different types.
1071        WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork();
1072        WifiConfiguration wepNetwork = WifiConfigurationTestUtil.createWepNetwork();
1073        WifiConfiguration pskNetwork = WifiConfigurationTestUtil.createPskNetwork();
1074        WifiConfiguration eapNetwork = WifiConfigurationTestUtil.createEapNetwork();
1075
1076        // Now add them to WifiConfigManager.
1077        verifyAddNetworkToWifiConfigManager(openNetwork);
1078        verifyAddNetworkToWifiConfigManager(wepNetwork);
1079        verifyAddNetworkToWifiConfigManager(pskNetwork);
1080        verifyAddNetworkToWifiConfigManager(eapNetwork);
1081
1082        // Now create dummy scan detail corresponding to the networks.
1083        ScanDetail openNetworkScanDetail = createScanDetailForNetwork(openNetwork);
1084        ScanDetail wepNetworkScanDetail = createScanDetailForNetwork(wepNetwork);
1085        ScanDetail pskNetworkScanDetail = createScanDetailForNetwork(pskNetwork);
1086        ScanDetail eapNetworkScanDetail = createScanDetailForNetwork(eapNetwork);
1087
1088        // Now mix and match parameters from different scan details.
1089        openNetworkScanDetail.getScanResult().SSID =
1090                wepNetworkScanDetail.getScanResult().SSID;
1091        wepNetworkScanDetail.getScanResult().capabilities =
1092                pskNetworkScanDetail.getScanResult().capabilities;
1093        pskNetworkScanDetail.getScanResult().capabilities =
1094                eapNetworkScanDetail.getScanResult().capabilities;
1095        eapNetworkScanDetail.getScanResult().capabilities =
1096                openNetworkScanDetail.getScanResult().capabilities;
1097
1098        // Try to lookup a saved network using the modified scan details. All of these should fail.
1099        assertNull(mWifiConfigManager.getSavedNetworkForScanDetailAndCache(openNetworkScanDetail));
1100        assertNull(mWifiConfigManager.getSavedNetworkForScanDetailAndCache(wepNetworkScanDetail));
1101        assertNull(mWifiConfigManager.getSavedNetworkForScanDetailAndCache(pskNetworkScanDetail));
1102        assertNull(mWifiConfigManager.getSavedNetworkForScanDetailAndCache(eapNetworkScanDetail));
1103
1104        // All the cache's should be empty as well.
1105        assertNull(mWifiConfigManager.getScanDetailCacheForNetwork(openNetwork.networkId));
1106        assertNull(mWifiConfigManager.getScanDetailCacheForNetwork(wepNetwork.networkId));
1107        assertNull(mWifiConfigManager.getScanDetailCacheForNetwork(pskNetwork.networkId));
1108        assertNull(mWifiConfigManager.getScanDetailCacheForNetwork(eapNetwork.networkId));
1109    }
1110
1111    /**
1112     * Verifies that ScanDetail added for a network is cached correctly.
1113     */
1114    @Test
1115    public void testUpdateScanDetailForNetwork() {
1116        // First add the provided network.
1117        WifiConfiguration testNetwork = WifiConfigurationTestUtil.createOpenNetwork();
1118        NetworkUpdateResult result = verifyAddNetworkToWifiConfigManager(testNetwork);
1119
1120        // Now create a dummy scan detail corresponding to the network.
1121        ScanDetail scanDetail = createScanDetailForNetwork(testNetwork);
1122        ScanResult scanResult = scanDetail.getScanResult();
1123
1124        mWifiConfigManager.updateScanDetailForNetwork(result.getNetworkId(), scanDetail);
1125
1126        // Now retrieve the scan detail cache and ensure that the new scan detail is in cache.
1127        ScanDetailCache retrievedScanDetailCache =
1128                mWifiConfigManager.getScanDetailCacheForNetwork(result.getNetworkId());
1129        assertEquals(1, retrievedScanDetailCache.size());
1130        ScanResult retrievedScanResult = retrievedScanDetailCache.get(scanResult.BSSID);
1131
1132        ScanTestUtil.assertScanResultEquals(scanResult, retrievedScanResult);
1133    }
1134
1135    /**
1136     * Verifies that scan detail cache is trimmed down when the size of the cache for a network
1137     * exceeds {@link WifiConfigManager#SCAN_CACHE_ENTRIES_MAX_SIZE}.
1138     */
1139    @Test
1140    public void testScanDetailCacheTrimForNetwork() {
1141        // Add a single network.
1142        WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork();
1143        verifyAddNetworkToWifiConfigManager(openNetwork);
1144
1145        ScanDetailCache scanDetailCache;
1146        String testBssidPrefix = "00:a5:b8:c9:45:";
1147
1148        // Modify |BSSID| field in the scan result and add copies of scan detail
1149        // |SCAN_CACHE_ENTRIES_MAX_SIZE| times.
1150        int scanDetailNum = 1;
1151        for (; scanDetailNum <= WifiConfigManager.SCAN_CACHE_ENTRIES_MAX_SIZE; scanDetailNum++) {
1152            // Create dummy scan detail caches with different BSSID for the network.
1153            ScanDetail scanDetail =
1154                    createScanDetailForNetwork(
1155                            openNetwork, String.format("%s%02x", testBssidPrefix, scanDetailNum));
1156            assertNotNull(
1157                    mWifiConfigManager.getSavedNetworkForScanDetailAndCache(scanDetail));
1158
1159            // The size of scan detail cache should keep growing until it hits
1160            // |SCAN_CACHE_ENTRIES_MAX_SIZE|.
1161            scanDetailCache =
1162                    mWifiConfigManager.getScanDetailCacheForNetwork(openNetwork.networkId);
1163            assertEquals(scanDetailNum, scanDetailCache.size());
1164        }
1165
1166        // Now add the |SCAN_CACHE_ENTRIES_MAX_SIZE + 1| entry. This should trigger the trim.
1167        ScanDetail scanDetail =
1168                createScanDetailForNetwork(
1169                        openNetwork, String.format("%s%02x", testBssidPrefix, scanDetailNum));
1170        assertNotNull(mWifiConfigManager.getSavedNetworkForScanDetailAndCache(scanDetail));
1171
1172        // Retrieve the scan detail cache and ensure that the size was trimmed down to
1173        // |SCAN_CACHE_ENTRIES_TRIM_SIZE + 1|. The "+1" is to account for the new entry that
1174        // was added after the trim.
1175        scanDetailCache = mWifiConfigManager.getScanDetailCacheForNetwork(openNetwork.networkId);
1176        assertEquals(WifiConfigManager.SCAN_CACHE_ENTRIES_TRIM_SIZE + 1, scanDetailCache.size());
1177    }
1178
1179    /**
1180     * Verifies that hasEverConnected is false for a newly added network.
1181     */
1182    @Test
1183    public void testAddNetworkHasEverConnectedFalse() {
1184        verifyAddNetworkHasEverConnectedFalse(WifiConfigurationTestUtil.createOpenNetwork());
1185    }
1186
1187    /**
1188     * Verifies that hasEverConnected is false for a newly added network even when new config has
1189     * mistakenly set HasEverConnected to true.
1190     */
1191    @Test
1192    public void testAddNetworkOverridesHasEverConnectedWhenTrueInNewConfig() {
1193        WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork();
1194        openNetwork.getNetworkSelectionStatus().setHasEverConnected(true);
1195        verifyAddNetworkHasEverConnectedFalse(openNetwork);
1196    }
1197
1198    /**
1199     * Verify that the |HasEverConnected| is set when
1200     * {@link WifiConfigManager#updateNetworkAfterConnect(int)} is invoked.
1201     */
1202    @Test
1203    public void testUpdateConfigAfterConnectHasEverConnectedTrue() {
1204        WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork();
1205        verifyAddNetworkHasEverConnectedFalse(openNetwork);
1206        verifyUpdateNetworkAfterConnectHasEverConnectedTrue(openNetwork.networkId);
1207    }
1208
1209    /**
1210     * Verifies that hasEverConnected is cleared when a network config |preSharedKey| is updated.
1211     */
1212    @Test
1213    public void testUpdatePreSharedKeyClearsHasEverConnected() {
1214        WifiConfiguration pskNetwork = WifiConfigurationTestUtil.createPskNetwork();
1215        verifyAddNetworkHasEverConnectedFalse(pskNetwork);
1216        verifyUpdateNetworkAfterConnectHasEverConnectedTrue(pskNetwork.networkId);
1217
1218        // Now update the same network with a different psk.
1219        assertFalse(pskNetwork.preSharedKey.equals("newpassword"));
1220        pskNetwork.preSharedKey = "newpassword";
1221        verifyUpdateNetworkWithCredentialChangeHasEverConnectedFalse(pskNetwork);
1222    }
1223
1224    /**
1225     * Verifies that hasEverConnected is cleared when a network config |wepKeys| is updated.
1226     */
1227    @Test
1228    public void testUpdateWepKeysClearsHasEverConnected() {
1229        WifiConfiguration wepNetwork = WifiConfigurationTestUtil.createWepNetwork();
1230        verifyAddNetworkHasEverConnectedFalse(wepNetwork);
1231        verifyUpdateNetworkAfterConnectHasEverConnectedTrue(wepNetwork.networkId);
1232
1233        // Now update the same network with a different wep.
1234        assertFalse(wepNetwork.wepKeys[0].equals("newpassword"));
1235        wepNetwork.wepKeys[0] = "newpassword";
1236        verifyUpdateNetworkWithCredentialChangeHasEverConnectedFalse(wepNetwork);
1237    }
1238
1239    /**
1240     * Verifies that hasEverConnected is cleared when a network config |wepTxKeyIndex| is updated.
1241     */
1242    @Test
1243    public void testUpdateWepTxKeyClearsHasEverConnected() {
1244        WifiConfiguration wepNetwork = WifiConfigurationTestUtil.createWepNetwork();
1245        verifyAddNetworkHasEverConnectedFalse(wepNetwork);
1246        verifyUpdateNetworkAfterConnectHasEverConnectedTrue(wepNetwork.networkId);
1247
1248        // Now update the same network with a different wep.
1249        assertFalse(wepNetwork.wepTxKeyIndex == 3);
1250        wepNetwork.wepTxKeyIndex = 3;
1251        verifyUpdateNetworkWithCredentialChangeHasEverConnectedFalse(wepNetwork);
1252    }
1253
1254    /**
1255     * Verifies that hasEverConnected is cleared when a network config |allowedKeyManagement| is
1256     * updated.
1257     */
1258    @Test
1259    public void testUpdateAllowedKeyManagementClearsHasEverConnected() {
1260        WifiConfiguration pskNetwork = WifiConfigurationTestUtil.createPskNetwork();
1261        verifyAddNetworkHasEverConnectedFalse(pskNetwork);
1262        verifyUpdateNetworkAfterConnectHasEverConnectedTrue(pskNetwork.networkId);
1263
1264        assertFalse(pskNetwork.allowedKeyManagement.get(WifiConfiguration.KeyMgmt.IEEE8021X));
1265        pskNetwork.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.IEEE8021X);
1266        verifyUpdateNetworkWithCredentialChangeHasEverConnectedFalse(pskNetwork);
1267    }
1268
1269    /**
1270     * Verifies that hasEverConnected is cleared when a network config |allowedProtocol| is
1271     * updated.
1272     */
1273    @Test
1274    public void testUpdateProtocolsClearsHasEverConnected() {
1275        WifiConfiguration pskNetwork = WifiConfigurationTestUtil.createPskNetwork();
1276        verifyAddNetworkHasEverConnectedFalse(pskNetwork);
1277        verifyUpdateNetworkAfterConnectHasEverConnectedTrue(pskNetwork.networkId);
1278
1279        assertFalse(pskNetwork.allowedProtocols.get(WifiConfiguration.Protocol.OSEN));
1280        pskNetwork.allowedProtocols.set(WifiConfiguration.Protocol.OSEN);
1281        verifyUpdateNetworkWithCredentialChangeHasEverConnectedFalse(pskNetwork);
1282    }
1283
1284    /**
1285     * Verifies that hasEverConnected is cleared when a network config |allowedAuthAlgorithms| is
1286     * updated.
1287     */
1288    @Test
1289    public void testUpdateAllowedAuthAlgorithmsClearsHasEverConnected() {
1290        WifiConfiguration pskNetwork = WifiConfigurationTestUtil.createPskNetwork();
1291        verifyAddNetworkHasEverConnectedFalse(pskNetwork);
1292        verifyUpdateNetworkAfterConnectHasEverConnectedTrue(pskNetwork.networkId);
1293
1294        assertFalse(pskNetwork.allowedAuthAlgorithms.get(WifiConfiguration.AuthAlgorithm.LEAP));
1295        pskNetwork.allowedAuthAlgorithms.set(WifiConfiguration.AuthAlgorithm.LEAP);
1296        verifyUpdateNetworkWithCredentialChangeHasEverConnectedFalse(pskNetwork);
1297    }
1298
1299    /**
1300     * Verifies that hasEverConnected is cleared when a network config |allowedPairwiseCiphers| is
1301     * updated.
1302     */
1303    @Test
1304    public void testUpdateAllowedPairwiseCiphersClearsHasEverConnected() {
1305        WifiConfiguration pskNetwork = WifiConfigurationTestUtil.createPskNetwork();
1306        verifyAddNetworkHasEverConnectedFalse(pskNetwork);
1307        verifyUpdateNetworkAfterConnectHasEverConnectedTrue(pskNetwork.networkId);
1308
1309        assertFalse(pskNetwork.allowedPairwiseCiphers.get(WifiConfiguration.PairwiseCipher.NONE));
1310        pskNetwork.allowedPairwiseCiphers.set(WifiConfiguration.PairwiseCipher.NONE);
1311        verifyUpdateNetworkWithCredentialChangeHasEverConnectedFalse(pskNetwork);
1312    }
1313
1314    /**
1315     * Verifies that hasEverConnected is cleared when a network config |allowedGroup| is
1316     * updated.
1317     */
1318    @Test
1319    public void testUpdateAllowedGroupCiphersClearsHasEverConnected() {
1320        WifiConfiguration pskNetwork = WifiConfigurationTestUtil.createPskNetwork();
1321        verifyAddNetworkHasEverConnectedFalse(pskNetwork);
1322        verifyUpdateNetworkAfterConnectHasEverConnectedTrue(pskNetwork.networkId);
1323
1324        assertTrue(pskNetwork.allowedGroupCiphers.get(WifiConfiguration.GroupCipher.WEP104));
1325        pskNetwork.allowedGroupCiphers.clear(WifiConfiguration.GroupCipher.WEP104);
1326        verifyUpdateNetworkWithCredentialChangeHasEverConnectedFalse(pskNetwork);
1327    }
1328
1329    /**
1330     * Verifies that hasEverConnected is cleared when a network config |hiddenSSID| is
1331     * updated.
1332     */
1333    @Test
1334    public void testUpdateHiddenSSIDClearsHasEverConnected() {
1335        WifiConfiguration pskNetwork = WifiConfigurationTestUtil.createPskNetwork();
1336        verifyAddNetworkHasEverConnectedFalse(pskNetwork);
1337        verifyUpdateNetworkAfterConnectHasEverConnectedTrue(pskNetwork.networkId);
1338
1339        assertFalse(pskNetwork.hiddenSSID);
1340        pskNetwork.hiddenSSID = true;
1341        verifyUpdateNetworkWithCredentialChangeHasEverConnectedFalse(pskNetwork);
1342    }
1343
1344    /**
1345     * Verifies that hasEverConnected is not cleared when a network config |requirePMF| is
1346     * updated.
1347     */
1348    @Test
1349    public void testUpdateRequirePMFDoesNotClearHasEverConnected() {
1350        WifiConfiguration pskNetwork = WifiConfigurationTestUtil.createPskNetwork();
1351        verifyAddNetworkHasEverConnectedFalse(pskNetwork);
1352        verifyUpdateNetworkAfterConnectHasEverConnectedTrue(pskNetwork.networkId);
1353
1354        assertFalse(pskNetwork.requirePMF);
1355        pskNetwork.requirePMF = true;
1356
1357        NetworkUpdateResult result =
1358                verifyUpdateNetworkToWifiConfigManagerWithoutIpChange(pskNetwork);
1359        WifiConfiguration retrievedNetwork =
1360                mWifiConfigManager.getConfiguredNetwork(result.getNetworkId());
1361        assertTrue("Updating network non-credentials config should not clear hasEverConnected.",
1362                retrievedNetwork.getNetworkSelectionStatus().getHasEverConnected());
1363        assertFalse(result.hasCredentialChanged());
1364    }
1365
1366    /**
1367     * Verifies that hasEverConnected is cleared when a network config |enterpriseConfig| is
1368     * updated.
1369     */
1370    @Test
1371    public void testUpdateEnterpriseConfigClearsHasEverConnected() {
1372        WifiConfiguration eapNetwork = WifiConfigurationTestUtil.createEapNetwork();
1373        eapNetwork.enterpriseConfig =
1374                WifiConfigurationTestUtil.createPEAPWifiEnterpriseConfigWithGTCPhase2();
1375        verifyAddNetworkHasEverConnectedFalse(eapNetwork);
1376        verifyUpdateNetworkAfterConnectHasEverConnectedTrue(eapNetwork.networkId);
1377
1378        assertFalse(eapNetwork.enterpriseConfig.getEapMethod() == WifiEnterpriseConfig.Eap.TLS);
1379        eapNetwork.enterpriseConfig.setEapMethod(WifiEnterpriseConfig.Eap.TLS);
1380        verifyUpdateNetworkWithCredentialChangeHasEverConnectedFalse(eapNetwork);
1381    }
1382
1383    /**
1384     * Verifies that if the app sends back the masked passwords in an update, we ignore it.
1385     */
1386    @Test
1387    public void testUpdateIgnoresMaskedPasswords() {
1388        WifiConfiguration someRandomNetworkWithAllMaskedFields =
1389                WifiConfigurationTestUtil.createEapNetwork();
1390        someRandomNetworkWithAllMaskedFields.wepKeys = WifiConfigurationTestUtil.TEST_WEP_KEYS;
1391        someRandomNetworkWithAllMaskedFields.preSharedKey = WifiConfigurationTestUtil.TEST_PSK;
1392        someRandomNetworkWithAllMaskedFields.enterpriseConfig.setPassword(
1393                WifiConfigurationTestUtil.TEST_EAP_PASSWORD);
1394
1395        NetworkUpdateResult result =
1396                verifyAddNetworkToWifiConfigManager(someRandomNetworkWithAllMaskedFields);
1397
1398        // All of these passwords must be masked in this retrieved network config.
1399        WifiConfiguration retrievedNetworkWithMaskedPassword =
1400                mWifiConfigManager.getConfiguredNetwork(result.getNetworkId());
1401        assertPasswordsMaskedInWifiConfiguration(retrievedNetworkWithMaskedPassword);
1402        // Ensure that the passwords are present internally.
1403        WifiConfiguration retrievedNetworkWithPassword =
1404                mWifiConfigManager.getConfiguredNetworkWithPassword(result.getNetworkId());
1405        assertEquals(someRandomNetworkWithAllMaskedFields.preSharedKey,
1406                retrievedNetworkWithPassword.preSharedKey);
1407        assertEquals(someRandomNetworkWithAllMaskedFields.wepKeys,
1408                retrievedNetworkWithPassword.wepKeys);
1409        assertEquals(someRandomNetworkWithAllMaskedFields.enterpriseConfig.getPassword(),
1410                retrievedNetworkWithPassword.enterpriseConfig.getPassword());
1411
1412        // Now update the same network config using the masked config.
1413        verifyUpdateNetworkToWifiConfigManager(retrievedNetworkWithMaskedPassword);
1414
1415        // Retrieve the network config with password and ensure that they have not been overwritten
1416        // with *.
1417        retrievedNetworkWithPassword =
1418                mWifiConfigManager.getConfiguredNetworkWithPassword(result.getNetworkId());
1419        assertEquals(someRandomNetworkWithAllMaskedFields.preSharedKey,
1420                retrievedNetworkWithPassword.preSharedKey);
1421        assertEquals(someRandomNetworkWithAllMaskedFields.wepKeys,
1422                retrievedNetworkWithPassword.wepKeys);
1423        assertEquals(someRandomNetworkWithAllMaskedFields.enterpriseConfig.getPassword(),
1424                retrievedNetworkWithPassword.enterpriseConfig.getPassword());
1425    }
1426
1427    /**
1428     * Verifies the ordering of network list generated using
1429     * {@link WifiConfigManager#retrievePnoNetworkList()}.
1430     */
1431    @Test
1432    public void testRetrievePnoList() {
1433        // Create and add 3 networks.
1434        WifiConfiguration network1 = WifiConfigurationTestUtil.createEapNetwork();
1435        WifiConfiguration network2 = WifiConfigurationTestUtil.createPskNetwork();
1436        WifiConfiguration network3 = WifiConfigurationTestUtil.createOpenHiddenNetwork();
1437        verifyAddNetworkToWifiConfigManager(network1);
1438        verifyAddNetworkToWifiConfigManager(network2);
1439        verifyAddNetworkToWifiConfigManager(network3);
1440
1441        // Enable all of them.
1442        assertTrue(mWifiConfigManager.enableNetwork(network1.networkId, false, TEST_CREATOR_UID));
1443        assertTrue(mWifiConfigManager.enableNetwork(network2.networkId, false, TEST_CREATOR_UID));
1444        assertTrue(mWifiConfigManager.enableNetwork(network3.networkId, false, TEST_CREATOR_UID));
1445
1446        // Now set scan results in 2 of them to set the corresponding
1447        // {@link NetworkSelectionStatus#mSeenInLastQualifiedNetworkSelection} field.
1448        assertTrue(mWifiConfigManager.setNetworkCandidateScanResult(
1449                network1.networkId, createScanDetailForNetwork(network1).getScanResult(), 54));
1450        assertTrue(mWifiConfigManager.setNetworkCandidateScanResult(
1451                network3.networkId, createScanDetailForNetwork(network3).getScanResult(), 54));
1452
1453        // Now increment |network3|'s association count. This should ensure that this network
1454        // is preferred over |network1|.
1455        assertTrue(mWifiConfigManager.updateNetworkAfterConnect(network3.networkId));
1456
1457        // Retrieve the Pno network list & verify the order of the networks returned.
1458        List<WifiScanner.PnoSettings.PnoNetwork> pnoNetworks =
1459                mWifiConfigManager.retrievePnoNetworkList();
1460        assertEquals(3, pnoNetworks.size());
1461        assertEquals(network3.SSID, pnoNetworks.get(0).ssid);
1462        assertEquals(network1.SSID, pnoNetworks.get(1).ssid);
1463        assertEquals(network2.SSID, pnoNetworks.get(2).ssid);
1464
1465        // Now permanently disable |network3|. This should remove network 3 from the list.
1466        assertTrue(mWifiConfigManager.disableNetwork(network3.networkId, TEST_CREATOR_UID));
1467
1468        // Retrieve the Pno network list again & verify the order of the networks returned.
1469        pnoNetworks = mWifiConfigManager.retrievePnoNetworkList();
1470        assertEquals(2, pnoNetworks.size());
1471        assertEquals(network1.SSID, pnoNetworks.get(0).ssid);
1472        assertEquals(network2.SSID, pnoNetworks.get(1).ssid);
1473    }
1474
1475    /**
1476     * Verifies the linking of networks when they have the same default GW Mac address in
1477     * {@link WifiConfigManager#getOrCreateScanDetailCacheForNetwork(WifiConfiguration)}.
1478     */
1479    @Test
1480    public void testNetworkLinkUsingGwMacAddress() {
1481        WifiConfiguration network1 = WifiConfigurationTestUtil.createPskNetwork();
1482        WifiConfiguration network2 = WifiConfigurationTestUtil.createPskNetwork();
1483        WifiConfiguration network3 = WifiConfigurationTestUtil.createPskNetwork();
1484        verifyAddNetworkToWifiConfigManager(network1);
1485        verifyAddNetworkToWifiConfigManager(network2);
1486        verifyAddNetworkToWifiConfigManager(network3);
1487
1488        // Set the same default GW mac address for all of the networks.
1489        assertTrue(mWifiConfigManager.setNetworkDefaultGwMacAddress(
1490                network1.networkId, TEST_DEFAULT_GW_MAC_ADDRESS));
1491        assertTrue(mWifiConfigManager.setNetworkDefaultGwMacAddress(
1492                network2.networkId, TEST_DEFAULT_GW_MAC_ADDRESS));
1493        assertTrue(mWifiConfigManager.setNetworkDefaultGwMacAddress(
1494                network3.networkId, TEST_DEFAULT_GW_MAC_ADDRESS));
1495
1496        // Now create dummy scan detail corresponding to the networks.
1497        ScanDetail networkScanDetail1 = createScanDetailForNetwork(network1);
1498        ScanDetail networkScanDetail2 = createScanDetailForNetwork(network2);
1499        ScanDetail networkScanDetail3 = createScanDetailForNetwork(network3);
1500
1501        // Now save all these scan details corresponding to each of this network and expect
1502        // all of these networks to be linked with each other.
1503        assertNotNull(mWifiConfigManager.getSavedNetworkForScanDetailAndCache(networkScanDetail1));
1504        assertNotNull(mWifiConfigManager.getSavedNetworkForScanDetailAndCache(networkScanDetail2));
1505        assertNotNull(mWifiConfigManager.getSavedNetworkForScanDetailAndCache(networkScanDetail3));
1506
1507        List<WifiConfiguration> retrievedNetworks =
1508                mWifiConfigManager.getConfiguredNetworks();
1509        for (WifiConfiguration network : retrievedNetworks) {
1510            assertEquals(2, network.linkedConfigurations.size());
1511            for (WifiConfiguration otherNetwork : retrievedNetworks) {
1512                if (otherNetwork == network) {
1513                    continue;
1514                }
1515                assertNotNull(network.linkedConfigurations.get(otherNetwork.configKey()));
1516            }
1517        }
1518    }
1519
1520    /**
1521     * Verifies the linking of networks when they have scan results with same first 16 ASCII of
1522     * bssid in
1523     * {@link WifiConfigManager#getOrCreateScanDetailCacheForNetwork(WifiConfiguration)}.
1524     */
1525    @Test
1526    public void testNetworkLinkUsingBSSIDMatch() {
1527        WifiConfiguration network1 = WifiConfigurationTestUtil.createPskNetwork();
1528        WifiConfiguration network2 = WifiConfigurationTestUtil.createPskNetwork();
1529        WifiConfiguration network3 = WifiConfigurationTestUtil.createPskNetwork();
1530        verifyAddNetworkToWifiConfigManager(network1);
1531        verifyAddNetworkToWifiConfigManager(network2);
1532        verifyAddNetworkToWifiConfigManager(network3);
1533
1534        // Create scan results with bssid which is different in only the last char.
1535        ScanDetail networkScanDetail1 = createScanDetailForNetwork(network1, "af:89:56:34:56:67");
1536        ScanDetail networkScanDetail2 = createScanDetailForNetwork(network2, "af:89:56:34:56:68");
1537        ScanDetail networkScanDetail3 = createScanDetailForNetwork(network3, "af:89:56:34:56:69");
1538
1539        // Now save all these scan details corresponding to each of this network and expect
1540        // all of these networks to be linked with each other.
1541        assertNotNull(mWifiConfigManager.getSavedNetworkForScanDetailAndCache(networkScanDetail1));
1542        assertNotNull(mWifiConfigManager.getSavedNetworkForScanDetailAndCache(networkScanDetail2));
1543        assertNotNull(mWifiConfigManager.getSavedNetworkForScanDetailAndCache(networkScanDetail3));
1544
1545        List<WifiConfiguration> retrievedNetworks =
1546                mWifiConfigManager.getConfiguredNetworks();
1547        for (WifiConfiguration network : retrievedNetworks) {
1548            assertEquals(2, network.linkedConfigurations.size());
1549            for (WifiConfiguration otherNetwork : retrievedNetworks) {
1550                if (otherNetwork == network) {
1551                    continue;
1552                }
1553                assertNotNull(network.linkedConfigurations.get(otherNetwork.configKey()));
1554            }
1555        }
1556    }
1557
1558    /**
1559     * Verifies the linking of networks does not happen for non WPA networks when they have scan
1560     * results with same first 16 ASCII of bssid in
1561     * {@link WifiConfigManager#getOrCreateScanDetailCacheForNetwork(WifiConfiguration)}.
1562     */
1563    @Test
1564    public void testNoNetworkLinkUsingBSSIDMatchForNonWpaNetworks() {
1565        WifiConfiguration network1 = WifiConfigurationTestUtil.createOpenNetwork();
1566        WifiConfiguration network2 = WifiConfigurationTestUtil.createPskNetwork();
1567        verifyAddNetworkToWifiConfigManager(network1);
1568        verifyAddNetworkToWifiConfigManager(network2);
1569
1570        // Create scan results with bssid which is different in only the last char.
1571        ScanDetail networkScanDetail1 = createScanDetailForNetwork(network1, "af:89:56:34:56:67");
1572        ScanDetail networkScanDetail2 = createScanDetailForNetwork(network2, "af:89:56:34:56:68");
1573
1574        assertNotNull(mWifiConfigManager.getSavedNetworkForScanDetailAndCache(networkScanDetail1));
1575        assertNotNull(mWifiConfigManager.getSavedNetworkForScanDetailAndCache(networkScanDetail2));
1576
1577        List<WifiConfiguration> retrievedNetworks =
1578                mWifiConfigManager.getConfiguredNetworks();
1579        for (WifiConfiguration network : retrievedNetworks) {
1580            assertNull(network.linkedConfigurations);
1581        }
1582    }
1583
1584    /**
1585     * Verifies the linking of networks does not happen for networks with more than
1586     * {@link WifiConfigManager#LINK_CONFIGURATION_MAX_SCAN_CACHE_ENTRIES} scan
1587     * results with same first 16 ASCII of bssid in
1588     * {@link WifiConfigManager#getOrCreateScanDetailCacheForNetwork(WifiConfiguration)}.
1589     */
1590    @Test
1591    public void testNoNetworkLinkUsingBSSIDMatchForNetworksWithHighScanDetailCacheSize() {
1592        WifiConfiguration network1 = WifiConfigurationTestUtil.createPskNetwork();
1593        WifiConfiguration network2 = WifiConfigurationTestUtil.createPskNetwork();
1594        verifyAddNetworkToWifiConfigManager(network1);
1595        verifyAddNetworkToWifiConfigManager(network2);
1596
1597        // Create 7 scan results with bssid which is different in only the last char.
1598        String test_bssid_base = "af:89:56:34:56:6";
1599        int scan_result_num = 0;
1600        for (; scan_result_num < WifiConfigManager.LINK_CONFIGURATION_MAX_SCAN_CACHE_ENTRIES + 1;
1601             scan_result_num++) {
1602            ScanDetail networkScanDetail =
1603                    createScanDetailForNetwork(
1604                            network1, test_bssid_base + Integer.toString(scan_result_num));
1605            assertNotNull(
1606                    mWifiConfigManager.getSavedNetworkForScanDetailAndCache(networkScanDetail));
1607        }
1608
1609        // Now add 1 scan result to the other network with bssid which is different in only the
1610        // last char.
1611        ScanDetail networkScanDetail2 =
1612                createScanDetailForNetwork(
1613                        network2, test_bssid_base + Integer.toString(scan_result_num++));
1614        assertNotNull(mWifiConfigManager.getSavedNetworkForScanDetailAndCache(networkScanDetail2));
1615
1616        List<WifiConfiguration> retrievedNetworks =
1617                mWifiConfigManager.getConfiguredNetworks();
1618        for (WifiConfiguration network : retrievedNetworks) {
1619            assertNull(network.linkedConfigurations);
1620        }
1621    }
1622
1623    /**
1624     * Verifies the linking of networks when they have scan results with same first 16 ASCII of
1625     * bssid in {@link WifiConfigManager#getOrCreateScanDetailCacheForNetwork(WifiConfiguration)}
1626     * and then subsequently delinked when the networks have default gateway set which do not match.
1627     */
1628    @Test
1629    public void testNetworkLinkUsingBSSIDMatchAndThenUnlinkDueToGwMacAddress() {
1630        WifiConfiguration network1 = WifiConfigurationTestUtil.createPskNetwork();
1631        WifiConfiguration network2 = WifiConfigurationTestUtil.createPskNetwork();
1632        verifyAddNetworkToWifiConfigManager(network1);
1633        verifyAddNetworkToWifiConfigManager(network2);
1634
1635        // Create scan results with bssid which is different in only the last char.
1636        ScanDetail networkScanDetail1 = createScanDetailForNetwork(network1, "af:89:56:34:56:67");
1637        ScanDetail networkScanDetail2 = createScanDetailForNetwork(network2, "af:89:56:34:56:68");
1638
1639        // Now save all these scan details corresponding to each of this network and expect
1640        // all of these networks to be linked with each other.
1641        assertNotNull(mWifiConfigManager.getSavedNetworkForScanDetailAndCache(networkScanDetail1));
1642        assertNotNull(mWifiConfigManager.getSavedNetworkForScanDetailAndCache(networkScanDetail2));
1643
1644        List<WifiConfiguration> retrievedNetworks =
1645                mWifiConfigManager.getConfiguredNetworks();
1646        for (WifiConfiguration network : retrievedNetworks) {
1647            assertEquals(1, network.linkedConfigurations.size());
1648            for (WifiConfiguration otherNetwork : retrievedNetworks) {
1649                if (otherNetwork == network) {
1650                    continue;
1651                }
1652                assertNotNull(network.linkedConfigurations.get(otherNetwork.configKey()));
1653            }
1654        }
1655
1656        // Now Set different GW mac address for both the networks and ensure they're unlinked.
1657        assertTrue(mWifiConfigManager.setNetworkDefaultGwMacAddress(
1658                network1.networkId, "de:ad:fe:45:23:34"));
1659        assertTrue(mWifiConfigManager.setNetworkDefaultGwMacAddress(
1660                network2.networkId, "ad:de:fe:45:23:34"));
1661
1662        // Add some dummy scan results again to re-evaluate the linking of networks.
1663        assertNotNull(mWifiConfigManager.getSavedNetworkForScanDetailAndCache(
1664                createScanDetailForNetwork(network1, "af:89:56:34:45:67")));
1665        assertNotNull(mWifiConfigManager.getSavedNetworkForScanDetailAndCache(
1666                createScanDetailForNetwork(network1, "af:89:56:34:45:68")));
1667
1668        retrievedNetworks = mWifiConfigManager.getConfiguredNetworks();
1669        for (WifiConfiguration network : retrievedNetworks) {
1670            assertNull(network.linkedConfigurations);
1671        }
1672    }
1673
1674    /**
1675     * Verifies the creation of channel list using
1676     * {@link WifiConfigManager#fetchChannelSetForNetworkForPartialScan(int, long, int)}.
1677     */
1678    @Test
1679    public void testFetchChannelSetForNetwork() {
1680        WifiConfiguration network = WifiConfigurationTestUtil.createPskNetwork();
1681        verifyAddNetworkToWifiConfigManager(network);
1682
1683        // Create 5 scan results with different bssid's & frequencies.
1684        String test_bssid_base = "af:89:56:34:56:6";
1685        for (int i = 0; i < TEST_FREQ_LIST.length; i++) {
1686            ScanDetail networkScanDetail =
1687                    createScanDetailForNetwork(
1688                            network, test_bssid_base + Integer.toString(i), 0, TEST_FREQ_LIST[i]);
1689            assertNotNull(
1690                    mWifiConfigManager.getSavedNetworkForScanDetailAndCache(networkScanDetail));
1691
1692        }
1693        assertEquals(new HashSet<Integer>(Arrays.asList(TEST_FREQ_LIST)),
1694                mWifiConfigManager.fetchChannelSetForNetworkForPartialScan(network.networkId, 1,
1695                        TEST_FREQ_LIST[4]));
1696    }
1697
1698    /**
1699     * Verifies the creation of channel list using
1700     * {@link WifiConfigManager#fetchChannelSetForNetworkForPartialScan(int, long, int)} and
1701     * ensures that the frequenecy of the currently connected network is in the returned
1702     * channel set.
1703     */
1704    @Test
1705    public void testFetchChannelSetForNetworkIncludeCurrentNetwork() {
1706        WifiConfiguration network = WifiConfigurationTestUtil.createPskNetwork();
1707        verifyAddNetworkToWifiConfigManager(network);
1708
1709        // Create 5 scan results with different bssid's & frequencies.
1710        String test_bssid_base = "af:89:56:34:56:6";
1711        for (int i = 0; i < TEST_FREQ_LIST.length; i++) {
1712            ScanDetail networkScanDetail =
1713                    createScanDetailForNetwork(
1714                            network, test_bssid_base + Integer.toString(i), 0, TEST_FREQ_LIST[i]);
1715            assertNotNull(
1716                    mWifiConfigManager.getSavedNetworkForScanDetailAndCache(networkScanDetail));
1717
1718        }
1719
1720        // Currently connected network frequency 2427 is not in the TEST_FREQ_LIST
1721        Set<Integer> freqs = mWifiConfigManager.fetchChannelSetForNetworkForPartialScan(
1722                network.networkId, 1, 2427);
1723
1724        assertEquals(true, freqs.contains(2427));
1725    }
1726
1727    /**
1728     * Verifies the creation of channel list using
1729     * {@link WifiConfigManager#fetchChannelSetForNetworkForPartialScan(int, long, int)} and
1730     * ensures that scan results which have a timestamp  beyond the provided age are not used
1731     * in the channel list.
1732     */
1733    @Test
1734    public void testFetchChannelSetForNetworkIgnoresStaleScanResults() {
1735        WifiConfiguration network = WifiConfigurationTestUtil.createPskNetwork();
1736        verifyAddNetworkToWifiConfigManager(network);
1737
1738        long wallClockBase = 0;
1739        // Create 5 scan results with different bssid's & frequencies.
1740        String test_bssid_base = "af:89:56:34:56:6";
1741        for (int i = 0; i < TEST_FREQ_LIST.length; i++) {
1742            // Increment the seen value in the scan results for each of them.
1743            when(mClock.getWallClockMillis()).thenReturn(wallClockBase + i);
1744            ScanDetail networkScanDetail =
1745                    createScanDetailForNetwork(
1746                            network, test_bssid_base + Integer.toString(i), 0, TEST_FREQ_LIST[i]);
1747            assertNotNull(
1748                    mWifiConfigManager.getSavedNetworkForScanDetailAndCache(networkScanDetail));
1749
1750        }
1751        int ageInMillis = 4;
1752        // Now fetch only scan results which are 4 millis stale. This should ignore the first
1753        // scan result.
1754        assertEquals(
1755                new HashSet<>(Arrays.asList(
1756                        Arrays.copyOfRange(
1757                                TEST_FREQ_LIST,
1758                                TEST_FREQ_LIST.length - ageInMillis, TEST_FREQ_LIST.length))),
1759                mWifiConfigManager.fetchChannelSetForNetworkForPartialScan(
1760                        network.networkId, ageInMillis, TEST_FREQ_LIST[4]));
1761    }
1762
1763    /**
1764     * Verifies the creation of channel list using
1765     * {@link WifiConfigManager#fetchChannelSetForNetworkForPartialScan(int, long, int)} and
1766     * ensures that the list size does not exceed the max configured for the device.
1767     */
1768    @Test
1769    public void testFetchChannelSetForNetworkIsLimitedToConfiguredSize() {
1770        // Need to recreate the WifiConfigManager instance for this test to modify the config
1771        // value which is read only in the constructor.
1772        int maxListSize = 3;
1773        mResources.setInteger(
1774                R.integer.config_wifi_framework_associated_partial_scan_max_num_active_channels,
1775                maxListSize);
1776        createWifiConfigManager();
1777
1778        WifiConfiguration network = WifiConfigurationTestUtil.createPskNetwork();
1779        verifyAddNetworkToWifiConfigManager(network);
1780
1781        // Create 5 scan results with different bssid's & frequencies.
1782        String test_bssid_base = "af:89:56:34:56:6";
1783        for (int i = 0; i < TEST_FREQ_LIST.length; i++) {
1784            ScanDetail networkScanDetail =
1785                    createScanDetailForNetwork(
1786                            network, test_bssid_base + Integer.toString(i), 0, TEST_FREQ_LIST[i]);
1787            assertNotNull(
1788                    mWifiConfigManager.getSavedNetworkForScanDetailAndCache(networkScanDetail));
1789
1790        }
1791        // Ensure that the fetched list size is limited.
1792        assertEquals(maxListSize,
1793                mWifiConfigManager.fetchChannelSetForNetworkForPartialScan(
1794                        network.networkId, 1, TEST_FREQ_LIST[4]).size());
1795    }
1796
1797    /**
1798     * Verifies the creation of channel list using
1799     * {@link WifiConfigManager#fetchChannelSetForNetworkForPartialScan(int, long, int)} and
1800     * ensures that scan results from linked networks are used in the channel list.
1801     */
1802    @Test
1803    public void testFetchChannelSetForNetworkIncludesLinkedNetworks() {
1804        WifiConfiguration network1 = WifiConfigurationTestUtil.createPskNetwork();
1805        WifiConfiguration network2 = WifiConfigurationTestUtil.createPskNetwork();
1806        verifyAddNetworkToWifiConfigManager(network1);
1807        verifyAddNetworkToWifiConfigManager(network2);
1808
1809        String test_bssid_base = "af:89:56:34:56:6";
1810        int TEST_FREQ_LISTIdx = 0;
1811        // Create 3 scan results with different bssid's & frequencies for network 1.
1812        for (; TEST_FREQ_LISTIdx < TEST_FREQ_LIST.length / 2; TEST_FREQ_LISTIdx++) {
1813            ScanDetail networkScanDetail =
1814                    createScanDetailForNetwork(
1815                            network1, test_bssid_base + Integer.toString(TEST_FREQ_LISTIdx), 0,
1816                            TEST_FREQ_LIST[TEST_FREQ_LISTIdx]);
1817            assertNotNull(
1818                    mWifiConfigManager.getSavedNetworkForScanDetailAndCache(networkScanDetail));
1819
1820        }
1821        // Create 3 scan results with different bssid's & frequencies for network 2.
1822        for (; TEST_FREQ_LISTIdx < TEST_FREQ_LIST.length; TEST_FREQ_LISTIdx++) {
1823            ScanDetail networkScanDetail =
1824                    createScanDetailForNetwork(
1825                            network2, test_bssid_base + Integer.toString(TEST_FREQ_LISTIdx), 0,
1826                            TEST_FREQ_LIST[TEST_FREQ_LISTIdx]);
1827            assertNotNull(
1828                    mWifiConfigManager.getSavedNetworkForScanDetailAndCache(networkScanDetail));
1829        }
1830
1831        // Link the 2 configurations together using the GwMacAddress.
1832        assertTrue(mWifiConfigManager.setNetworkDefaultGwMacAddress(
1833                network1.networkId, TEST_DEFAULT_GW_MAC_ADDRESS));
1834        assertTrue(mWifiConfigManager.setNetworkDefaultGwMacAddress(
1835                network2.networkId, TEST_DEFAULT_GW_MAC_ADDRESS));
1836
1837        // The channel list fetched should include scan results from both the linked networks.
1838        assertEquals(new HashSet<Integer>(Arrays.asList(TEST_FREQ_LIST)),
1839                mWifiConfigManager.fetchChannelSetForNetworkForPartialScan(network1.networkId, 1,
1840                        TEST_FREQ_LIST[0]));
1841        assertEquals(new HashSet<Integer>(Arrays.asList(TEST_FREQ_LIST)),
1842                mWifiConfigManager.fetchChannelSetForNetworkForPartialScan(network2.networkId, 1,
1843                        TEST_FREQ_LIST[0]));
1844    }
1845
1846    /**
1847     * Verifies the creation of channel list using
1848     * {@link WifiConfigManager#fetchChannelSetForNetworkForPartialScan(int, long, int)} and
1849     * ensures that scan results from linked networks are used in the channel list and that the
1850     * list size does not exceed the max configured for the device.
1851     */
1852    @Test
1853    public void testFetchChannelSetForNetworkIncludesLinkedNetworksIsLimitedToConfiguredSize() {
1854        // Need to recreate the WifiConfigManager instance for this test to modify the config
1855        // value which is read only in the constructor.
1856        int maxListSize = 3;
1857        mResources.setInteger(
1858                R.integer.config_wifi_framework_associated_partial_scan_max_num_active_channels,
1859                maxListSize);
1860
1861        createWifiConfigManager();
1862        WifiConfiguration network1 = WifiConfigurationTestUtil.createPskNetwork();
1863        WifiConfiguration network2 = WifiConfigurationTestUtil.createPskNetwork();
1864        verifyAddNetworkToWifiConfigManager(network1);
1865        verifyAddNetworkToWifiConfigManager(network2);
1866
1867        String test_bssid_base = "af:89:56:34:56:6";
1868        int TEST_FREQ_LISTIdx = 0;
1869        // Create 3 scan results with different bssid's & frequencies for network 1.
1870        for (; TEST_FREQ_LISTIdx < TEST_FREQ_LIST.length / 2; TEST_FREQ_LISTIdx++) {
1871            ScanDetail networkScanDetail =
1872                    createScanDetailForNetwork(
1873                            network1, test_bssid_base + Integer.toString(TEST_FREQ_LISTIdx), 0,
1874                            TEST_FREQ_LIST[TEST_FREQ_LISTIdx]);
1875            assertNotNull(
1876                    mWifiConfigManager.getSavedNetworkForScanDetailAndCache(networkScanDetail));
1877
1878        }
1879        // Create 3 scan results with different bssid's & frequencies for network 2.
1880        for (; TEST_FREQ_LISTIdx < TEST_FREQ_LIST.length; TEST_FREQ_LISTIdx++) {
1881            ScanDetail networkScanDetail =
1882                    createScanDetailForNetwork(
1883                            network2, test_bssid_base + Integer.toString(TEST_FREQ_LISTIdx), 0,
1884                            TEST_FREQ_LIST[TEST_FREQ_LISTIdx]);
1885            assertNotNull(
1886                    mWifiConfigManager.getSavedNetworkForScanDetailAndCache(networkScanDetail));
1887        }
1888
1889        // Link the 2 configurations together using the GwMacAddress.
1890        assertTrue(mWifiConfigManager.setNetworkDefaultGwMacAddress(
1891                network1.networkId, TEST_DEFAULT_GW_MAC_ADDRESS));
1892        assertTrue(mWifiConfigManager.setNetworkDefaultGwMacAddress(
1893                network2.networkId, TEST_DEFAULT_GW_MAC_ADDRESS));
1894
1895        // Ensure that the fetched list size is limited.
1896        assertEquals(maxListSize,
1897                mWifiConfigManager.fetchChannelSetForNetworkForPartialScan(
1898                        network1.networkId, 1, TEST_FREQ_LIST[0]).size());
1899        assertEquals(maxListSize,
1900                mWifiConfigManager.fetchChannelSetForNetworkForPartialScan(
1901                        network2.networkId, 1, TEST_FREQ_LIST[0]).size());
1902    }
1903
1904    /**
1905     * Verifies the foreground user switch using {@link WifiConfigManager#handleUserSwitch(int)}
1906     * and ensures that any shared private networks networkId is not changed.
1907     * Test scenario:
1908     * 1. Load the shared networks from shared store and user 1 store.
1909     * 2. Switch to user 2 and ensure that the shared network's Id is not changed.
1910     */
1911    @Test
1912    public void testHandleUserSwitchDoesNotChangeSharedNetworksId() throws Exception {
1913        int user1 = TEST_DEFAULT_USER;
1914        int user2 = TEST_DEFAULT_USER + 1;
1915        setupUserProfiles(user2);
1916
1917        int appId = 674;
1918
1919        // Create 3 networks. 1 for user1, 1 for user2 and 1 shared.
1920        final WifiConfiguration user1Network = WifiConfigurationTestUtil.createPskNetwork();
1921        user1Network.shared = false;
1922        user1Network.creatorUid = UserHandle.getUid(user1, appId);
1923        final WifiConfiguration user2Network = WifiConfigurationTestUtil.createPskNetwork();
1924        user2Network.shared = false;
1925        user2Network.creatorUid = UserHandle.getUid(user2, appId);
1926        final WifiConfiguration sharedNetwork1 = WifiConfigurationTestUtil.createPskNetwork();
1927        final WifiConfiguration sharedNetwork2 = WifiConfigurationTestUtil.createPskNetwork();
1928
1929        // Set up the store data that is loaded initially.
1930        List<WifiConfiguration> sharedNetworks = new ArrayList<WifiConfiguration>() {
1931            {
1932                add(sharedNetwork1);
1933                add(sharedNetwork2);
1934            }
1935        };
1936        List<WifiConfiguration> user1Networks = new ArrayList<WifiConfiguration>() {
1937            {
1938                add(user1Network);
1939            }
1940        };
1941        setupStoreDataForRead(sharedNetworks, user1Networks, new HashSet<String>());
1942        assertTrue(mWifiConfigManager.loadFromStore());
1943        verify(mWifiConfigStore).read();
1944
1945        // Fetch the network ID's assigned to the shared networks initially.
1946        int sharedNetwork1Id = WifiConfiguration.INVALID_NETWORK_ID;
1947        int sharedNetwork2Id = WifiConfiguration.INVALID_NETWORK_ID;
1948        List<WifiConfiguration> retrievedNetworks =
1949                mWifiConfigManager.getConfiguredNetworksWithPasswords();
1950        for (WifiConfiguration network : retrievedNetworks) {
1951            if (network.configKey().equals(sharedNetwork1.configKey())) {
1952                sharedNetwork1Id = network.networkId;
1953            } else if (network.configKey().equals(sharedNetwork2.configKey())) {
1954                sharedNetwork2Id = network.networkId;
1955            }
1956        }
1957        assertTrue(sharedNetwork1Id != WifiConfiguration.INVALID_NETWORK_ID);
1958        assertTrue(sharedNetwork2Id != WifiConfiguration.INVALID_NETWORK_ID);
1959
1960        // Set up the user 2 store data that is loaded at user switch.
1961        List<WifiConfiguration> user2Networks = new ArrayList<WifiConfiguration>() {
1962            {
1963                add(user2Network);
1964            }
1965        };
1966        setupStoreDataForUserRead(user2Networks, new HashSet<String>());
1967        // Now switch the user to user 2 and ensure that shared network's IDs have not changed.
1968        when(mUserManager.isUserUnlockingOrUnlocked(user2)).thenReturn(true);
1969        mWifiConfigManager.handleUserSwitch(user2);
1970        verify(mWifiConfigStore).switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class));
1971
1972        // Again fetch the network ID's assigned to the shared networks and ensure they have not
1973        // changed.
1974        int updatedSharedNetwork1Id = WifiConfiguration.INVALID_NETWORK_ID;
1975        int updatedSharedNetwork2Id = WifiConfiguration.INVALID_NETWORK_ID;
1976        retrievedNetworks = mWifiConfigManager.getConfiguredNetworksWithPasswords();
1977        for (WifiConfiguration network : retrievedNetworks) {
1978            if (network.configKey().equals(sharedNetwork1.configKey())) {
1979                updatedSharedNetwork1Id = network.networkId;
1980            } else if (network.configKey().equals(sharedNetwork2.configKey())) {
1981                updatedSharedNetwork2Id = network.networkId;
1982            }
1983        }
1984        assertEquals(sharedNetwork1Id, updatedSharedNetwork1Id);
1985        assertEquals(sharedNetwork2Id, updatedSharedNetwork2Id);
1986    }
1987
1988    /**
1989     * Verifies the foreground user switch using {@link WifiConfigManager#handleUserSwitch(int)}
1990     * and ensures that any old user private networks are not visible anymore.
1991     * Test scenario:
1992     * 1. Load the shared networks from shared store and user 1 store.
1993     * 2. Switch to user 2 and ensure that the user 1's private network has been removed.
1994     */
1995    @Test
1996    public void testHandleUserSwitchRemovesOldUserPrivateNetworks() throws Exception {
1997        int user1 = TEST_DEFAULT_USER;
1998        int user2 = TEST_DEFAULT_USER + 1;
1999        setupUserProfiles(user2);
2000
2001        int appId = 674;
2002
2003        // Create 3 networks. 1 for user1, 1 for user2 and 1 shared.
2004        final WifiConfiguration user1Network = WifiConfigurationTestUtil.createPskNetwork();
2005        user1Network.shared = false;
2006        user1Network.creatorUid = UserHandle.getUid(user1, appId);
2007        final WifiConfiguration user2Network = WifiConfigurationTestUtil.createPskNetwork();
2008        user2Network.shared = false;
2009        user2Network.creatorUid = UserHandle.getUid(user2, appId);
2010        final WifiConfiguration sharedNetwork = WifiConfigurationTestUtil.createPskNetwork();
2011
2012        // Set up the store data that is loaded initially.
2013        List<WifiConfiguration> sharedNetworks = new ArrayList<WifiConfiguration>() {
2014            {
2015                add(sharedNetwork);
2016            }
2017        };
2018        List<WifiConfiguration> user1Networks = new ArrayList<WifiConfiguration>() {
2019            {
2020                add(user1Network);
2021            }
2022        };
2023        setupStoreDataForRead(sharedNetworks, user1Networks, new HashSet<String>());
2024        assertTrue(mWifiConfigManager.loadFromStore());
2025        verify(mWifiConfigStore).read();
2026
2027        // Fetch the network ID assigned to the user 1 network initially.
2028        int user1NetworkId = WifiConfiguration.INVALID_NETWORK_ID;
2029        List<WifiConfiguration> retrievedNetworks =
2030                mWifiConfigManager.getConfiguredNetworksWithPasswords();
2031        for (WifiConfiguration network : retrievedNetworks) {
2032            if (network.configKey().equals(user1Network.configKey())) {
2033                user1NetworkId = network.networkId;
2034            }
2035        }
2036
2037        // Set up the user 2 store data that is loaded at user switch.
2038        List<WifiConfiguration> user2Networks = new ArrayList<WifiConfiguration>() {
2039            {
2040                add(user2Network);
2041            }
2042        };
2043        setupStoreDataForUserRead(user2Networks, new HashSet<String>());
2044        // Now switch the user to user 2 and ensure that user 1's private network has been removed.
2045        when(mUserManager.isUserUnlockingOrUnlocked(user2)).thenReturn(true);
2046        Set<Integer> removedNetworks = mWifiConfigManager.handleUserSwitch(user2);
2047        verify(mWifiConfigStore).switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class));
2048        assertTrue((removedNetworks.size() == 1) && (removedNetworks.contains(user1NetworkId)));
2049
2050        // Set the expected networks to be |sharedNetwork| and |user2Network|.
2051        List<WifiConfiguration> expectedNetworks = new ArrayList<WifiConfiguration>() {
2052            {
2053                add(sharedNetwork);
2054                add(user2Network);
2055            }
2056        };
2057        WifiConfigurationTestUtil.assertConfigurationsEqualForConfigManagerAddOrUpdate(
2058                expectedNetworks, mWifiConfigManager.getConfiguredNetworksWithPasswords());
2059
2060        // Send another user switch  indication with the same user 2. This should be ignored and
2061        // hence should not remove any new networks.
2062        when(mUserManager.isUserUnlockingOrUnlocked(user2)).thenReturn(true);
2063        removedNetworks = mWifiConfigManager.handleUserSwitch(user2);
2064        assertTrue(removedNetworks.isEmpty());
2065    }
2066
2067    /**
2068     * Verifies the foreground user switch using {@link WifiConfigManager#handleUserSwitch(int)}
2069     * and ensures that user switch from a user with no private networks is handled.
2070     * Test scenario:
2071     * 1. Load the shared networks from shared store and emptu user 1 store.
2072     * 2. Switch to user 2 and ensure that no private networks were removed.
2073     */
2074    @Test
2075    public void testHandleUserSwitchWithNoOldUserPrivateNetworks() throws Exception {
2076        int user1 = TEST_DEFAULT_USER;
2077        int user2 = TEST_DEFAULT_USER + 1;
2078        setupUserProfiles(user2);
2079
2080        int appId = 674;
2081
2082        // Create 2 networks. 1 for user2 and 1 shared.
2083        final WifiConfiguration user2Network = WifiConfigurationTestUtil.createPskNetwork();
2084        user2Network.shared = false;
2085        user2Network.creatorUid = UserHandle.getUid(user2, appId);
2086        final WifiConfiguration sharedNetwork = WifiConfigurationTestUtil.createPskNetwork();
2087
2088        // Set up the store data that is loaded initially.
2089        List<WifiConfiguration> sharedNetworks = new ArrayList<WifiConfiguration>() {
2090            {
2091                add(sharedNetwork);
2092            }
2093        };
2094        setupStoreDataForRead(sharedNetworks, new ArrayList<WifiConfiguration>(),
2095                new HashSet<String>());
2096        assertTrue(mWifiConfigManager.loadFromStore());
2097        verify(mWifiConfigStore).read();
2098
2099        // Set up the user 2 store data that is loaded at user switch.
2100        List<WifiConfiguration> user2Networks = new ArrayList<WifiConfiguration>() {
2101            {
2102                add(user2Network);
2103            }
2104        };
2105        setupStoreDataForUserRead(user2Networks, new HashSet<String>());
2106        // Now switch the user to user 2 and ensure that no private network has been removed.
2107        when(mUserManager.isUserUnlockingOrUnlocked(user2)).thenReturn(true);
2108        Set<Integer> removedNetworks = mWifiConfigManager.handleUserSwitch(user2);
2109        verify(mWifiConfigStore).switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class));
2110        assertTrue(removedNetworks.isEmpty());
2111    }
2112
2113    /**
2114     * Verifies the foreground user switch using {@link WifiConfigManager#handleUserSwitch(int)}
2115     * and ensures that any non current user private networks are moved to shared store file.
2116     * This test simulates the following test case:
2117     * 1. Loads the shared networks from shared store at bootup.
2118     * 2. Load the private networks from user store on user 1 unlock.
2119     * 3. Switch to user 2 and ensure that the user 2's private network has been moved to user 2's
2120     * private store file.
2121     */
2122    @Test
2123    public void testHandleUserSwitchPushesOtherPrivateNetworksToSharedStore() throws Exception {
2124        int user1 = TEST_DEFAULT_USER;
2125        int user2 = TEST_DEFAULT_USER + 1;
2126        setupUserProfiles(user2);
2127
2128        int appId = 674;
2129
2130        // Create 3 networks. 1 for user1, 1 for user2 and 1 shared.
2131        final WifiConfiguration user1Network = WifiConfigurationTestUtil.createPskNetwork();
2132        user1Network.shared = false;
2133        user1Network.creatorUid = UserHandle.getUid(user1, appId);
2134        final WifiConfiguration user2Network = WifiConfigurationTestUtil.createPskNetwork();
2135        user2Network.shared = false;
2136        user2Network.creatorUid = UserHandle.getUid(user2, appId);
2137        final WifiConfiguration sharedNetwork = WifiConfigurationTestUtil.createPskNetwork();
2138
2139        // Set up the shared store data that is loaded at bootup. User 2's private network
2140        // is still in shared store because they have not yet logged-in after upgrade.
2141        List<WifiConfiguration> sharedNetworks = new ArrayList<WifiConfiguration>() {
2142            {
2143                add(sharedNetwork);
2144                add(user2Network);
2145            }
2146        };
2147        setupStoreDataForRead(sharedNetworks, new ArrayList<WifiConfiguration>(),
2148                new HashSet<String>());
2149        assertTrue(mWifiConfigManager.loadFromStore());
2150        verify(mWifiConfigStore).read();
2151
2152        // Set up the user store data that is loaded at user unlock.
2153        List<WifiConfiguration> userNetworks = new ArrayList<WifiConfiguration>() {
2154            {
2155                add(user1Network);
2156            }
2157        };
2158        setupStoreDataForUserRead(userNetworks, new HashSet<String>());
2159        mWifiConfigManager.handleUserUnlock(user1);
2160        verify(mWifiConfigStore).switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class));
2161        // Capture the written data for the user 1 and ensure that it corresponds to what was
2162        // setup.
2163        Pair<List<WifiConfiguration>, List<WifiConfiguration>> writtenNetworkList =
2164                captureWriteNetworksListStoreData();
2165        WifiConfigurationTestUtil.assertConfigurationsEqualForConfigManagerAddOrUpdate(
2166                sharedNetworks, writtenNetworkList.first);
2167        WifiConfigurationTestUtil.assertConfigurationsEqualForConfigManagerAddOrUpdate(
2168                userNetworks, writtenNetworkList.second);
2169
2170        // Now switch the user to user2 and ensure that user 2's private network has been moved to
2171        // the user store.
2172        when(mUserManager.isUserUnlockingOrUnlocked(user2)).thenReturn(true);
2173        mWifiConfigManager.handleUserSwitch(user2);
2174        // Set the expected network list before comparing. user1Network should be in shared data.
2175        // Note: In the real world, user1Network will no longer be visible now because it should
2176        // already be in user1's private store file. But, we're purposefully exposing it
2177        // via |loadStoreData| to test if other user's private networks are pushed to shared store.
2178        List<WifiConfiguration> expectedSharedNetworks = new ArrayList<WifiConfiguration>() {
2179            {
2180                add(sharedNetwork);
2181                add(user1Network);
2182            }
2183        };
2184        List<WifiConfiguration> expectedUserNetworks = new ArrayList<WifiConfiguration>() {
2185            {
2186                add(user2Network);
2187            }
2188        };
2189        // Capture the first written data triggered for saving the old user's network
2190        // configurations.
2191        writtenNetworkList = captureWriteNetworksListStoreData();
2192        WifiConfigurationTestUtil.assertConfigurationsEqualForConfigManagerAddOrUpdate(
2193                sharedNetworks, writtenNetworkList.first);
2194        WifiConfigurationTestUtil.assertConfigurationsEqualForConfigManagerAddOrUpdate(
2195                userNetworks, writtenNetworkList.second);
2196
2197        // Now capture the next written data triggered after the switch and ensure that user 2's
2198        // network is now in user store data.
2199        writtenNetworkList = captureWriteNetworksListStoreData();
2200        WifiConfigurationTestUtil.assertConfigurationsEqualForConfigManagerAddOrUpdate(
2201                expectedSharedNetworks, writtenNetworkList.first);
2202        WifiConfigurationTestUtil.assertConfigurationsEqualForConfigManagerAddOrUpdate(
2203                expectedUserNetworks, writtenNetworkList.second);
2204    }
2205
2206    /**
2207     * Verify that unlocking an user that owns a legacy Passpoint configuration (which is stored
2208     * temporarily in the share store) will migrate it to PasspointManager and removed from
2209     * the list of configured networks.
2210     *
2211     * @throws Exception
2212     */
2213    @Test
2214    public void testHandleUserUnlockRemovePasspointConfigFromSharedConfig() throws Exception {
2215        int user1 = TEST_DEFAULT_USER;
2216        int appId = 674;
2217
2218        final WifiConfiguration passpointConfig =
2219                WifiConfigurationTestUtil.createPasspointNetwork();
2220        passpointConfig.creatorUid = UserHandle.getUid(user1, appId);
2221        passpointConfig.isLegacyPasspointConfig = true;
2222
2223        // Set up the shared store data to contain one legacy Passpoint configuration.
2224        List<WifiConfiguration> sharedNetworks = new ArrayList<WifiConfiguration>() {
2225            {
2226                add(passpointConfig);
2227            }
2228        };
2229        setupStoreDataForRead(sharedNetworks, new ArrayList<WifiConfiguration>(),
2230                new HashSet<String>());
2231        assertTrue(mWifiConfigManager.loadFromStore());
2232        verify(mWifiConfigStore).read();
2233        assertEquals(1, mWifiConfigManager.getConfiguredNetworks().size());
2234
2235        // Unlock the owner of the legacy Passpoint configuration, verify it is removed from
2236        // the configured networks (migrated to PasspointManager).
2237        setupStoreDataForUserRead(new ArrayList<WifiConfiguration>(), new HashSet<String>());
2238        mWifiConfigManager.handleUserUnlock(user1);
2239        verify(mWifiConfigStore).switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class));
2240        Pair<List<WifiConfiguration>, List<WifiConfiguration>> writtenNetworkList =
2241                captureWriteNetworksListStoreData();
2242        assertTrue(writtenNetworkList.first.isEmpty());
2243        assertTrue(writtenNetworkList.second.isEmpty());
2244        assertTrue(mWifiConfigManager.getConfiguredNetworks().isEmpty());
2245    }
2246
2247    /**
2248     * Verifies the foreground user switch using {@link WifiConfigManager#handleUserSwitch(int)}
2249     * and {@link WifiConfigManager#handleUserUnlock(int)} and ensures that the new store is
2250     * read immediately if the user is unlocked during the switch.
2251     */
2252    @Test
2253    public void testHandleUserSwitchWhenUnlocked() throws Exception {
2254        int user1 = TEST_DEFAULT_USER;
2255        int user2 = TEST_DEFAULT_USER + 1;
2256        setupUserProfiles(user2);
2257
2258        // Set up the internal data first.
2259        assertTrue(mWifiConfigManager.loadFromStore());
2260
2261        setupStoreDataForUserRead(new ArrayList<WifiConfiguration>(), new HashSet<String>());
2262        // user2 is unlocked and switched to foreground.
2263        when(mUserManager.isUserUnlockingOrUnlocked(user2)).thenReturn(true);
2264        mWifiConfigManager.handleUserSwitch(user2);
2265        // Ensure that the read was invoked.
2266        mContextConfigStoreMockOrder.verify(mWifiConfigStore)
2267                .switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class));
2268    }
2269
2270    /**
2271     * Verifies the foreground user switch using {@link WifiConfigManager#handleUserSwitch(int)}
2272     * and {@link WifiConfigManager#handleUserUnlock(int)} and ensures that the new store is not
2273     * read until the user is unlocked.
2274     */
2275    public void testHandleUserSwitchWhenLocked() throws Exception {
2276        int user1 = TEST_DEFAULT_USER;
2277        int user2 = TEST_DEFAULT_USER + 1;
2278        setupUserProfiles(user2);
2279
2280        // Set up the internal data first.
2281        assertTrue(mWifiConfigManager.loadFromStore());
2282
2283        // user2 is locked and switched to foreground.
2284        when(mUserManager.isUserUnlockingOrUnlocked(user2)).thenReturn(false);
2285        mWifiConfigManager.handleUserSwitch(user2);
2286
2287        // Ensure that the read was not invoked.
2288        mContextConfigStoreMockOrder.verify(mWifiConfigStore, never())
2289                .switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class));
2290
2291        // Now try unlocking some other user (user1), this should be ignored.
2292        mWifiConfigManager.handleUserUnlock(user1);
2293        mContextConfigStoreMockOrder.verify(mWifiConfigStore, never())
2294                .switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class));
2295
2296        setupStoreDataForUserRead(new ArrayList<WifiConfiguration>(), new HashSet<String>());
2297        // Unlock the user2 and ensure that we read the data now.
2298        mWifiConfigManager.handleUserUnlock(user2);
2299        mContextConfigStoreMockOrder.verify(mWifiConfigStore)
2300                .switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class));
2301    }
2302
2303    /**
2304     * Verifies that the foreground user stop using {@link WifiConfigManager#handleUserStop(int)}
2305     * and ensures that the store is written only when the foreground user is stopped.
2306     */
2307    @Test
2308    public void testHandleUserStop() throws Exception {
2309        int user1 = TEST_DEFAULT_USER;
2310        int user2 = TEST_DEFAULT_USER + 1;
2311        setupUserProfiles(user2);
2312
2313        // Try stopping background user2 first, this should not do anything.
2314        when(mUserManager.isUserUnlockingOrUnlocked(user2)).thenReturn(false);
2315        mWifiConfigManager.handleUserStop(user2);
2316        mContextConfigStoreMockOrder.verify(mWifiConfigStore, never())
2317                .switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class));
2318
2319        // Now try stopping the foreground user1, this should trigger a write to store.
2320        mWifiConfigManager.handleUserStop(user1);
2321        mContextConfigStoreMockOrder.verify(mWifiConfigStore, never())
2322                .switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class));
2323        mContextConfigStoreMockOrder.verify(mWifiConfigStore).write(anyBoolean());
2324    }
2325
2326    /**
2327     * Verifies the foreground user unlock via {@link WifiConfigManager#handleUserUnlock(int)}
2328     * results in a store read after bootup.
2329     */
2330    @Test
2331    public void testHandleUserUnlockAfterBootup() throws Exception {
2332        int user1 = TEST_DEFAULT_USER;
2333
2334        // Set up the internal data first.
2335        assertTrue(mWifiConfigManager.loadFromStore());
2336        mContextConfigStoreMockOrder.verify(mWifiConfigStore).read();
2337        mContextConfigStoreMockOrder.verify(mWifiConfigStore, never()).write(anyBoolean());
2338        mContextConfigStoreMockOrder.verify(mWifiConfigStore, never())
2339                .switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class));
2340
2341        setupStoreDataForUserRead(new ArrayList<WifiConfiguration>(), new HashSet<String>());
2342        // Unlock the user1 (default user) for the first time and ensure that we read the data.
2343        mWifiConfigManager.handleUserUnlock(user1);
2344        mContextConfigStoreMockOrder.verify(mWifiConfigStore, never()).read();
2345        mContextConfigStoreMockOrder.verify(mWifiConfigStore)
2346                .switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class));
2347        mContextConfigStoreMockOrder.verify(mWifiConfigStore).write(anyBoolean());
2348    }
2349
2350    /**
2351     * Verifies that the store read after bootup received after
2352     * foreground user unlock via {@link WifiConfigManager#handleUserUnlock(int)}
2353     * results in a user store read.
2354     */
2355    @Test
2356    public void testHandleBootupAfterUserUnlock() throws Exception {
2357        int user1 = TEST_DEFAULT_USER;
2358
2359        // Unlock the user1 (default user) for the first time and ensure that we don't read the
2360        // data.
2361        mWifiConfigManager.handleUserUnlock(user1);
2362        mContextConfigStoreMockOrder.verify(mWifiConfigStore, never()).read();
2363        mContextConfigStoreMockOrder.verify(mWifiConfigStore, never()).write(anyBoolean());
2364        mContextConfigStoreMockOrder.verify(mWifiConfigStore, never())
2365                .switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class));
2366
2367        setupStoreDataForUserRead(new ArrayList<WifiConfiguration>(), new HashSet<String>());
2368        // Read from store now.
2369        assertTrue(mWifiConfigManager.loadFromStore());
2370        mContextConfigStoreMockOrder.verify(mWifiConfigStore)
2371                .setUserStore(any(WifiConfigStore.StoreFile.class));
2372        mContextConfigStoreMockOrder.verify(mWifiConfigStore).read();
2373    }
2374
2375    /**
2376     * Verifies the foreground user unlock via {@link WifiConfigManager#handleUserUnlock(int)} does
2377     * not always result in a store read unless the user had switched or just booted up.
2378     */
2379    @Test
2380    public void testHandleUserUnlockWithoutSwitchOrBootup() throws Exception {
2381        int user1 = TEST_DEFAULT_USER;
2382        int user2 = TEST_DEFAULT_USER + 1;
2383        setupUserProfiles(user2);
2384
2385        // Set up the internal data first.
2386        assertTrue(mWifiConfigManager.loadFromStore());
2387
2388        setupStoreDataForUserRead(new ArrayList<WifiConfiguration>(), new HashSet<String>());
2389        // user2 is unlocked and switched to foreground.
2390        when(mUserManager.isUserUnlockingOrUnlocked(user2)).thenReturn(true);
2391        mWifiConfigManager.handleUserSwitch(user2);
2392        // Ensure that the read was invoked.
2393        mContextConfigStoreMockOrder.verify(mWifiConfigStore)
2394                .switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class));
2395
2396        // Unlock the user2 again and ensure that we don't read the data now.
2397        mWifiConfigManager.handleUserUnlock(user2);
2398        mContextConfigStoreMockOrder.verify(mWifiConfigStore, never())
2399                .switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class));
2400    }
2401
2402    /**
2403     * Verifies the foreground user unlock via {@link WifiConfigManager#handleUserSwitch(int)}
2404     * is ignored if the legacy store migration is not complete.
2405     */
2406    @Test
2407    public void testHandleUserSwitchAfterBootupBeforeLegacyStoreMigration() throws Exception {
2408        int user2 = TEST_DEFAULT_USER + 1;
2409
2410        // Switch to user2 for the first time and ensure that we don't read or
2411        // write the store files.
2412        when(mUserManager.isUserUnlockingOrUnlocked(user2)).thenReturn(false);
2413        mWifiConfigManager.handleUserSwitch(user2);
2414        mContextConfigStoreMockOrder.verify(mWifiConfigStore, never())
2415                .switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class));
2416        mContextConfigStoreMockOrder.verify(mWifiConfigStore, never()).write(anyBoolean());
2417    }
2418
2419    /**
2420     * Verifies the foreground user unlock via {@link WifiConfigManager#handleUserUnlock(int)}
2421     * is ignored if the legacy store migration is not complete.
2422     */
2423    @Test
2424    public void testHandleUserUnlockAfterBootupBeforeLegacyStoreMigration() throws Exception {
2425        int user1 = TEST_DEFAULT_USER;
2426
2427        // Unlock the user1 (default user) for the first time and ensure that we don't read or
2428        // write the store files.
2429        mWifiConfigManager.handleUserUnlock(user1);
2430        mContextConfigStoreMockOrder.verify(mWifiConfigStore, never())
2431                .switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class));
2432        mContextConfigStoreMockOrder.verify(mWifiConfigStore, never()).write(anyBoolean());
2433    }
2434
2435    /**
2436     * Verifies the private network addition using
2437     * {@link WifiConfigManager#addOrUpdateNetwork(WifiConfiguration, int)}
2438     * by a non foreground user is rejected.
2439     */
2440    @Test
2441    public void testAddNetworkUsingBackgroundUserUId() throws Exception {
2442        int user2 = TEST_DEFAULT_USER + 1;
2443        setupUserProfiles(user2);
2444
2445        int creatorUid = UserHandle.getUid(user2, 674);
2446
2447        // Create a network for user2 try adding it. This should be rejected.
2448        final WifiConfiguration user2Network = WifiConfigurationTestUtil.createPskNetwork();
2449        NetworkUpdateResult result = addNetworkToWifiConfigManager(user2Network, creatorUid);
2450        assertFalse(result.isSuccess());
2451    }
2452
2453    /**
2454     * Verifies the private network addition using
2455     * {@link WifiConfigManager#addOrUpdateNetwork(WifiConfiguration, int)}
2456     * by SysUI is always accepted.
2457     */
2458    @Test
2459    public void testAddNetworkUsingSysUiUid() throws Exception {
2460        // Set up the user profiles stuff. Needed for |WifiConfigurationUtil.isVisibleToAnyProfile|
2461        int user2 = TEST_DEFAULT_USER + 1;
2462        setupUserProfiles(user2);
2463
2464        when(mUserManager.isUserUnlockingOrUnlocked(user2)).thenReturn(false);
2465        mWifiConfigManager.handleUserSwitch(user2);
2466
2467        // Create a network for user2 try adding it. This should be rejected.
2468        final WifiConfiguration user2Network = WifiConfigurationTestUtil.createPskNetwork();
2469        NetworkUpdateResult result = addNetworkToWifiConfigManager(user2Network, TEST_SYSUI_UID);
2470        assertTrue(result.isSuccess());
2471    }
2472
2473    /**
2474     * Verifies the loading of networks using {@link WifiConfigManager#migrateFromLegacyStore()} ()}
2475     * attempts to migrate data from legacy stores when the legacy store files are present.
2476     */
2477    @Test
2478    public void testMigrationFromLegacyStore() throws Exception {
2479        // Create the store data to be returned from legacy stores.
2480        List<WifiConfiguration> networks = new ArrayList<>();
2481        networks.add(WifiConfigurationTestUtil.createPskNetwork());
2482        networks.add(WifiConfigurationTestUtil.createEapNetwork());
2483        networks.add(WifiConfigurationTestUtil.createWepNetwork());
2484        String deletedEphemeralSSID = "EphemeralSSID";
2485        Set<String> deletedEphermalSSIDs = new HashSet<>(Arrays.asList(deletedEphemeralSSID));
2486        WifiConfigStoreDataLegacy storeData =
2487                new WifiConfigStoreDataLegacy(networks, deletedEphermalSSIDs);
2488
2489        when(mWifiConfigStoreLegacy.areStoresPresent()).thenReturn(true);
2490        when(mWifiConfigStoreLegacy.read()).thenReturn(storeData);
2491
2492        // Now trigger the migration from legacy store. This should populate the in memory list with
2493        // all the networks above from the legacy store.
2494        assertTrue(mWifiConfigManager.migrateFromLegacyStore());
2495
2496        verify(mWifiConfigStoreLegacy).read();
2497        verify(mWifiConfigStoreLegacy).removeStores();
2498
2499        List<WifiConfiguration> retrievedNetworks =
2500                mWifiConfigManager.getConfiguredNetworksWithPasswords();
2501        WifiConfigurationTestUtil.assertConfigurationsEqualForConfigManagerAddOrUpdate(
2502                networks, retrievedNetworks);
2503        assertTrue(mWifiConfigManager.wasEphemeralNetworkDeleted(deletedEphemeralSSID));
2504    }
2505
2506    /**
2507     * Verifies the loading of networks using {@link WifiConfigManager#migrateFromLegacyStore()} ()}
2508     * does not attempt to migrate data from legacy stores when the legacy store files are absent
2509     * (i.e migration was already done once).
2510     */
2511    @Test
2512    public void testNoDuplicateMigrationFromLegacyStore() throws Exception {
2513        when(mWifiConfigStoreLegacy.areStoresPresent()).thenReturn(false);
2514
2515        // Now trigger a migration from legacy store.
2516        assertTrue(mWifiConfigManager.migrateFromLegacyStore());
2517
2518        verify(mWifiConfigStoreLegacy, never()).read();
2519        verify(mWifiConfigStoreLegacy, never()).removeStores();
2520    }
2521
2522    /**
2523     * Verifies the loading of networks using {@link WifiConfigManager#loadFromStore()} does
2524     * not attempt to read from any of the stores (new or legacy) when the store files are
2525     * not present.
2526     */
2527    @Test
2528    public void testFreshInstallDoesNotLoadFromStore() throws Exception {
2529        when(mWifiConfigStore.areStoresPresent()).thenReturn(false);
2530        when(mWifiConfigStoreLegacy.areStoresPresent()).thenReturn(false);
2531
2532        assertTrue(mWifiConfigManager.loadFromStore());
2533
2534        verify(mWifiConfigStore, never()).read();
2535        verify(mWifiConfigStoreLegacy, never()).read();
2536
2537        assertTrue(mWifiConfigManager.getConfiguredNetworksWithPasswords().isEmpty());
2538    }
2539
2540    /**
2541     * Verifies the user switch using {@link WifiConfigManager#handleUserSwitch(int)} is handled
2542     * when the store files (new or legacy) are not present.
2543     */
2544    @Test
2545    public void testHandleUserSwitchAfterFreshInstall() throws Exception {
2546        int user2 = TEST_DEFAULT_USER + 1;
2547        when(mWifiConfigStore.areStoresPresent()).thenReturn(false);
2548        when(mWifiConfigStoreLegacy.areStoresPresent()).thenReturn(false);
2549
2550        assertTrue(mWifiConfigManager.loadFromStore());
2551        verify(mWifiConfigStore, never()).read();
2552        verify(mWifiConfigStoreLegacy, never()).read();
2553
2554        setupStoreDataForUserRead(new ArrayList<WifiConfiguration>(), new HashSet<String>());
2555        // Now switch the user to user 2.
2556        when(mUserManager.isUserUnlockingOrUnlocked(user2)).thenReturn(true);
2557        mWifiConfigManager.handleUserSwitch(user2);
2558        // Ensure that the read was invoked.
2559        mContextConfigStoreMockOrder.verify(mWifiConfigStore)
2560                .switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class));
2561    }
2562
2563    /**
2564     * Verifies that the last user selected network parameter is set when
2565     * {@link WifiConfigManager#enableNetwork(int, boolean, int)} with disableOthers flag is set
2566     * to true and cleared when either {@link WifiConfigManager#disableNetwork(int, int)} or
2567     * {@link WifiConfigManager#removeNetwork(int, int)} is invoked using the same network ID.
2568     */
2569    @Test
2570    public void testLastSelectedNetwork() throws Exception {
2571        WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork();
2572        NetworkUpdateResult result = verifyAddNetworkToWifiConfigManager(openNetwork);
2573
2574        when(mClock.getElapsedSinceBootMillis()).thenReturn(67L);
2575        assertTrue(mWifiConfigManager.enableNetwork(
2576                result.getNetworkId(), true, TEST_CREATOR_UID));
2577        assertEquals(result.getNetworkId(), mWifiConfigManager.getLastSelectedNetwork());
2578        assertEquals(67, mWifiConfigManager.getLastSelectedTimeStamp());
2579
2580        // Now disable the network and ensure that the last selected flag is cleared.
2581        assertTrue(mWifiConfigManager.disableNetwork(result.getNetworkId(), TEST_CREATOR_UID));
2582        assertEquals(
2583                WifiConfiguration.INVALID_NETWORK_ID, mWifiConfigManager.getLastSelectedNetwork());
2584
2585        // Enable it again and remove the network to ensure that the last selected flag was cleared.
2586        assertTrue(mWifiConfigManager.enableNetwork(
2587                result.getNetworkId(), true, TEST_CREATOR_UID));
2588        assertEquals(result.getNetworkId(), mWifiConfigManager.getLastSelectedNetwork());
2589        assertEquals(openNetwork.configKey(), mWifiConfigManager.getLastSelectedNetworkConfigKey());
2590
2591        assertTrue(mWifiConfigManager.removeNetwork(result.getNetworkId(), TEST_CREATOR_UID));
2592        assertEquals(
2593                WifiConfiguration.INVALID_NETWORK_ID, mWifiConfigManager.getLastSelectedNetwork());
2594    }
2595
2596    /**
2597     * Verifies that all the networks for the provided app is removed when
2598     * {@link WifiConfigManager#removeNetworksForApp(ApplicationInfo)} is invoked.
2599     */
2600    @Test
2601    public void testRemoveNetworksForApp() throws Exception {
2602        verifyAddNetworkToWifiConfigManager(WifiConfigurationTestUtil.createOpenNetwork());
2603        verifyAddNetworkToWifiConfigManager(WifiConfigurationTestUtil.createPskNetwork());
2604        verifyAddNetworkToWifiConfigManager(WifiConfigurationTestUtil.createWepNetwork());
2605
2606        assertFalse(mWifiConfigManager.getConfiguredNetworks().isEmpty());
2607
2608        ApplicationInfo app = new ApplicationInfo();
2609        app.uid = TEST_CREATOR_UID;
2610        app.packageName = TEST_CREATOR_NAME;
2611        assertEquals(3, mWifiConfigManager.removeNetworksForApp(app).size());
2612
2613        // Ensure all the networks are removed now.
2614        assertTrue(mWifiConfigManager.getConfiguredNetworks().isEmpty());
2615    }
2616
2617    /**
2618     * Verifies that all the networks for the provided user is removed when
2619     * {@link WifiConfigManager#removeNetworksForUser(int)} is invoked.
2620     */
2621    @Test
2622    public void testRemoveNetworksForUser() throws Exception {
2623        verifyAddNetworkToWifiConfigManager(WifiConfigurationTestUtil.createOpenNetwork());
2624        verifyAddNetworkToWifiConfigManager(WifiConfigurationTestUtil.createPskNetwork());
2625        verifyAddNetworkToWifiConfigManager(WifiConfigurationTestUtil.createWepNetwork());
2626
2627        assertFalse(mWifiConfigManager.getConfiguredNetworks().isEmpty());
2628
2629        assertEquals(3, mWifiConfigManager.removeNetworksForUser(TEST_DEFAULT_USER).size());
2630
2631        // Ensure all the networks are removed now.
2632        assertTrue(mWifiConfigManager.getConfiguredNetworks().isEmpty());
2633    }
2634
2635    /**
2636     * Verifies that the connect choice is removed from all networks when
2637     * {@link WifiConfigManager#removeNetwork(int, int)} is invoked.
2638     */
2639    @Test
2640    public void testRemoveNetworkRemovesConnectChoice() throws Exception {
2641        WifiConfiguration network1 = WifiConfigurationTestUtil.createOpenNetwork();
2642        WifiConfiguration network2 = WifiConfigurationTestUtil.createPskNetwork();
2643        WifiConfiguration network3 = WifiConfigurationTestUtil.createPskNetwork();
2644        verifyAddNetworkToWifiConfigManager(network1);
2645        verifyAddNetworkToWifiConfigManager(network2);
2646        verifyAddNetworkToWifiConfigManager(network3);
2647
2648        // Set connect choice of network 2 over network 1.
2649        assertTrue(
2650                mWifiConfigManager.setNetworkConnectChoice(
2651                        network1.networkId, network2.configKey(), 78L));
2652
2653        WifiConfiguration retrievedNetwork =
2654                mWifiConfigManager.getConfiguredNetwork(network1.networkId);
2655        assertEquals(
2656                network2.configKey(),
2657                retrievedNetwork.getNetworkSelectionStatus().getConnectChoice());
2658
2659        // Remove network 3 and ensure that the connect choice on network 1 is not removed.
2660        assertTrue(mWifiConfigManager.removeNetwork(network3.networkId, TEST_CREATOR_UID));
2661        retrievedNetwork = mWifiConfigManager.getConfiguredNetwork(network1.networkId);
2662        assertEquals(
2663                network2.configKey(),
2664                retrievedNetwork.getNetworkSelectionStatus().getConnectChoice());
2665
2666        // Now remove network 2 and ensure that the connect choice on network 1 is removed..
2667        assertTrue(mWifiConfigManager.removeNetwork(network2.networkId, TEST_CREATOR_UID));
2668        retrievedNetwork = mWifiConfigManager.getConfiguredNetwork(network1.networkId);
2669        assertNotEquals(
2670                network2.configKey(),
2671                retrievedNetwork.getNetworkSelectionStatus().getConnectChoice());
2672
2673        // This should have triggered 2 buffered writes. 1 for setting the connect choice, 1 for
2674        // clearing it after network removal.
2675        mContextConfigStoreMockOrder.verify(mWifiConfigStore, times(2)).write(eq(false));
2676    }
2677
2678    /**
2679     * Verifies that the modification of a single network using
2680     * {@link WifiConfigManager#addOrUpdateNetwork(WifiConfiguration, int)} and ensures that any
2681     * updates to the network config in
2682     * {@link WifiKeyStore#updateNetworkKeys(WifiConfiguration, WifiConfiguration)} is reflected
2683     * in the internal database.
2684     */
2685    @Test
2686    public void testUpdateSingleNetworkWithKeysUpdate() {
2687        WifiConfiguration network = WifiConfigurationTestUtil.createEapNetwork();
2688        network.enterpriseConfig =
2689                WifiConfigurationTestUtil.createPEAPWifiEnterpriseConfigWithGTCPhase2();
2690        verifyAddNetworkToWifiConfigManager(network);
2691
2692        // Now verify that network configurations match before we make any change.
2693        WifiConfigurationTestUtil.assertConfigurationEqualForConfigManagerAddOrUpdate(
2694                network,
2695                mWifiConfigManager.getConfiguredNetworkWithPassword(network.networkId));
2696
2697        // Modify the network ca_cert field in updateNetworkKeys method during a network
2698        // config update.
2699        final String newCaCertAlias = "test";
2700        assertNotEquals(newCaCertAlias, network.enterpriseConfig.getCaCertificateAlias());
2701
2702        doAnswer(new AnswerWithArguments() {
2703            public boolean answer(WifiConfiguration newConfig, WifiConfiguration existingConfig) {
2704                newConfig.enterpriseConfig.setCaCertificateAlias(newCaCertAlias);
2705                return true;
2706            }
2707        }).when(mWifiKeyStore).updateNetworkKeys(
2708                any(WifiConfiguration.class), any(WifiConfiguration.class));
2709
2710        verifyUpdateNetworkToWifiConfigManagerWithoutIpChange(network);
2711
2712        // Now verify that the keys update is reflected in the configuration fetched from internal
2713        // db.
2714        network.enterpriseConfig.setCaCertificateAlias(newCaCertAlias);
2715        WifiConfigurationTestUtil.assertConfigurationEqualForConfigManagerAddOrUpdate(
2716                network,
2717                mWifiConfigManager.getConfiguredNetworkWithPassword(network.networkId));
2718    }
2719
2720    /**
2721     * Verifies that the dump method prints out all the saved network details with passwords masked.
2722     * {@link WifiConfigManager#dump(FileDescriptor, PrintWriter, String[])}.
2723     */
2724    @Test
2725    public void testDump() {
2726        WifiConfiguration pskNetwork = WifiConfigurationTestUtil.createPskNetwork();
2727        WifiConfiguration eapNetwork = WifiConfigurationTestUtil.createEapNetwork();
2728        eapNetwork.enterpriseConfig.setPassword("blah");
2729
2730        verifyAddNetworkToWifiConfigManager(pskNetwork);
2731        verifyAddNetworkToWifiConfigManager(eapNetwork);
2732
2733        StringWriter stringWriter = new StringWriter();
2734        mWifiConfigManager.dump(
2735                new FileDescriptor(), new PrintWriter(stringWriter), new String[0]);
2736        String dumpString = stringWriter.toString();
2737
2738        // Ensure that the network SSIDs were dumped out.
2739        assertTrue(dumpString.contains(pskNetwork.SSID));
2740        assertTrue(dumpString.contains(eapNetwork.SSID));
2741
2742        // Ensure that the network passwords were not dumped out.
2743        assertFalse(dumpString.contains(pskNetwork.preSharedKey));
2744        assertFalse(dumpString.contains(eapNetwork.enterpriseConfig.getPassword()));
2745    }
2746
2747    /**
2748     * Verifies the ordering of network list generated using
2749     * {@link WifiConfigManager#retrieveHiddenNetworkList()}.
2750     */
2751    @Test
2752    public void testRetrieveHiddenList() {
2753        // Create and add 3 networks.
2754        WifiConfiguration network1 = WifiConfigurationTestUtil.createWepHiddenNetwork();
2755        WifiConfiguration network2 = WifiConfigurationTestUtil.createPskHiddenNetwork();
2756        WifiConfiguration network3 = WifiConfigurationTestUtil.createOpenHiddenNetwork();
2757        verifyAddNetworkToWifiConfigManager(network1);
2758        verifyAddNetworkToWifiConfigManager(network2);
2759        verifyAddNetworkToWifiConfigManager(network3);
2760
2761        // Enable all of them.
2762        assertTrue(mWifiConfigManager.enableNetwork(network1.networkId, false, TEST_CREATOR_UID));
2763        assertTrue(mWifiConfigManager.enableNetwork(network2.networkId, false, TEST_CREATOR_UID));
2764        assertTrue(mWifiConfigManager.enableNetwork(network3.networkId, false, TEST_CREATOR_UID));
2765
2766        // Now set scan results in 2 of them to set the corresponding
2767        // {@link NetworkSelectionStatus#mSeenInLastQualifiedNetworkSelection} field.
2768        assertTrue(mWifiConfigManager.setNetworkCandidateScanResult(
2769                network1.networkId, createScanDetailForNetwork(network1).getScanResult(), 54));
2770        assertTrue(mWifiConfigManager.setNetworkCandidateScanResult(
2771                network3.networkId, createScanDetailForNetwork(network3).getScanResult(), 54));
2772
2773        // Now increment |network3|'s association count. This should ensure that this network
2774        // is preferred over |network1|.
2775        assertTrue(mWifiConfigManager.updateNetworkAfterConnect(network3.networkId));
2776
2777        // Retrieve the hidden network list & verify the order of the networks returned.
2778        List<WifiScanner.ScanSettings.HiddenNetwork> hiddenNetworks =
2779                mWifiConfigManager.retrieveHiddenNetworkList();
2780        assertEquals(3, hiddenNetworks.size());
2781        assertEquals(network3.SSID, hiddenNetworks.get(0).ssid);
2782        assertEquals(network1.SSID, hiddenNetworks.get(1).ssid);
2783        assertEquals(network2.SSID, hiddenNetworks.get(2).ssid);
2784
2785        // Now permanently disable |network3|. This should remove network 3 from the list.
2786        assertTrue(mWifiConfigManager.disableNetwork(network3.networkId, TEST_CREATOR_UID));
2787
2788        // Retrieve the hidden network list again & verify the order of the networks returned.
2789        hiddenNetworks = mWifiConfigManager.retrieveHiddenNetworkList();
2790        assertEquals(2, hiddenNetworks.size());
2791        assertEquals(network1.SSID, hiddenNetworks.get(0).ssid);
2792        assertEquals(network2.SSID, hiddenNetworks.get(1).ssid);
2793    }
2794
2795    /**
2796     * Verifies the addition of network configurations using
2797     * {@link WifiConfigManager#addOrUpdateNetwork(WifiConfiguration, int)} with same SSID and
2798     * default key mgmt does not add duplicate network configs.
2799     */
2800    @Test
2801    public void testAddMultipleNetworksWithSameSSIDAndDefaultKeyMgmt() {
2802        final String ssid = "test_blah";
2803        // Add a network with the above SSID and default key mgmt and ensure it was added
2804        // successfully.
2805        WifiConfiguration network1 = new WifiConfiguration();
2806        network1.SSID = ssid;
2807        NetworkUpdateResult result = addNetworkToWifiConfigManager(network1);
2808        assertTrue(result.getNetworkId() != WifiConfiguration.INVALID_NETWORK_ID);
2809        assertTrue(result.isNewNetwork());
2810
2811        List<WifiConfiguration> retrievedNetworks =
2812                mWifiConfigManager.getConfiguredNetworksWithPasswords();
2813        assertEquals(1, retrievedNetworks.size());
2814        WifiConfigurationTestUtil.assertConfigurationEqualForConfigManagerAddOrUpdate(
2815                network1, retrievedNetworks.get(0));
2816
2817        // Now add a second network with the same SSID and default key mgmt and ensure that it
2818        // didn't add a new duplicate network.
2819        WifiConfiguration network2 = new WifiConfiguration();
2820        network2.SSID = ssid;
2821        result = addNetworkToWifiConfigManager(network2);
2822        assertTrue(result.getNetworkId() != WifiConfiguration.INVALID_NETWORK_ID);
2823        assertFalse(result.isNewNetwork());
2824
2825        retrievedNetworks = mWifiConfigManager.getConfiguredNetworksWithPasswords();
2826        assertEquals(1, retrievedNetworks.size());
2827        WifiConfigurationTestUtil.assertConfigurationEqualForConfigManagerAddOrUpdate(
2828                network2, retrievedNetworks.get(0));
2829    }
2830
2831    /**
2832     * Verifies the addition of network configurations using
2833     * {@link WifiConfigManager#addOrUpdateNetwork(WifiConfiguration, int)} with same SSID and
2834     * different key mgmt should add different network configs.
2835     */
2836    @Test
2837    public void testAddMultipleNetworksWithSameSSIDAndDifferentKeyMgmt() {
2838        final String ssid = "test_blah";
2839        // Add a network with the above SSID and WPA_PSK key mgmt and ensure it was added
2840        // successfully.
2841        WifiConfiguration network1 = new WifiConfiguration();
2842        network1.SSID = ssid;
2843        network1.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.WPA_PSK);
2844        NetworkUpdateResult result = addNetworkToWifiConfigManager(network1);
2845        assertTrue(result.getNetworkId() != WifiConfiguration.INVALID_NETWORK_ID);
2846        assertTrue(result.isNewNetwork());
2847
2848        List<WifiConfiguration> retrievedNetworks =
2849                mWifiConfigManager.getConfiguredNetworksWithPasswords();
2850        assertEquals(1, retrievedNetworks.size());
2851        WifiConfigurationTestUtil.assertConfigurationEqualForConfigManagerAddOrUpdate(
2852                network1, retrievedNetworks.get(0));
2853
2854        // Now add a second network with the same SSID and NONE key mgmt and ensure that it
2855        // does add a new network.
2856        WifiConfiguration network2 = new WifiConfiguration();
2857        network2.SSID = ssid;
2858        network2.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.NONE);
2859        result = addNetworkToWifiConfigManager(network2);
2860        assertTrue(result.getNetworkId() != WifiConfiguration.INVALID_NETWORK_ID);
2861        assertTrue(result.isNewNetwork());
2862
2863        retrievedNetworks = mWifiConfigManager.getConfiguredNetworksWithPasswords();
2864        assertEquals(2, retrievedNetworks.size());
2865        List<WifiConfiguration> networks = Arrays.asList(network1, network2);
2866        WifiConfigurationTestUtil.assertConfigurationsEqualForConfigManagerAddOrUpdate(
2867                networks, retrievedNetworks);
2868    }
2869
2870    /**
2871     * Verifies that adding a network with a proxy, without having permission OVERRIDE_WIFI_CONFIG,
2872     * holding device policy, or profile owner policy fails.
2873     */
2874    @Test
2875    public void testAddNetworkWithProxyFails() {
2876        verifyAddOrUpdateNetworkWithProxySettingsAndPermissions(
2877                false, // withConfOverride
2878                false, // withProfileOwnerPolicy
2879                false, // withDeviceOwnerPolicy
2880                WifiConfigurationTestUtil.createDHCPIpConfigurationWithPacProxy(),
2881                false, // assertSuccess
2882                WifiConfiguration.INVALID_NETWORK_ID); // Update networkID
2883        verifyAddOrUpdateNetworkWithProxySettingsAndPermissions(
2884                false, // withConfOverride
2885                false, // withProfileOwnerPolicy
2886                false, // withDeviceOwnerPolicy
2887                WifiConfigurationTestUtil.createDHCPIpConfigurationWithStaticProxy(),
2888                false, // assertSuccess
2889                WifiConfiguration.INVALID_NETWORK_ID); // Update networkID
2890    }
2891
2892    /**
2893     * Verifies that adding a network with a PAC or STATIC proxy with permission
2894     * OVERRIDE_WIFI_CONFIG is successful
2895     */
2896    @Test
2897    public void testAddNetworkWithProxyWithConfOverride() {
2898        verifyAddOrUpdateNetworkWithProxySettingsAndPermissions(
2899                true,  // withConfOverride
2900                false, // withProfileOwnerPolicy
2901                false, // withDeviceOwnerPolicy
2902                WifiConfigurationTestUtil.createDHCPIpConfigurationWithPacProxy(),
2903                true, // assertSuccess
2904                WifiConfiguration.INVALID_NETWORK_ID); // Update networkID
2905        verifyAddOrUpdateNetworkWithProxySettingsAndPermissions(
2906                true,  // withConfOverride
2907                false, // withProfileOwnerPolicy
2908                false, // withDeviceOwnerPolicy
2909                WifiConfigurationTestUtil.createDHCPIpConfigurationWithStaticProxy(),
2910                true, // assertSuccess
2911                WifiConfiguration.INVALID_NETWORK_ID); // Update networkID
2912    }
2913
2914    /**
2915     * Verifies that adding a network with a PAC or STATIC proxy, while holding policy
2916     * {@link DeviceAdminInfo.USES_POLICY_PROFILE_OWNER} is successful
2917     */
2918    @Test
2919    public void testAddNetworkWithProxyAsProfileOwner() {
2920        verifyAddOrUpdateNetworkWithProxySettingsAndPermissions(
2921                false,  // withConfOverride
2922                true, // withProfileOwnerPolicy
2923                false, // withDeviceOwnerPolicy
2924                WifiConfigurationTestUtil.createDHCPIpConfigurationWithPacProxy(),
2925                true, // assertSuccess
2926                WifiConfiguration.INVALID_NETWORK_ID); // Update networkID
2927        verifyAddOrUpdateNetworkWithProxySettingsAndPermissions(
2928                false,  // withConfOverride
2929                true, // withProfileOwnerPolicy
2930                false, // withDeviceOwnerPolicy
2931                WifiConfigurationTestUtil.createDHCPIpConfigurationWithStaticProxy(),
2932                true, // assertSuccess
2933                WifiConfiguration.INVALID_NETWORK_ID); // Update networkID
2934    }
2935    /**
2936     * Verifies that adding a network with a PAC or STATIC proxy, while holding policy
2937     * {@link DeviceAdminInfo.USES_POLICY_DEVICE_OWNER} is successful
2938     */
2939    @Test
2940    public void testAddNetworkWithProxyAsDeviceOwner() {
2941        verifyAddOrUpdateNetworkWithProxySettingsAndPermissions(
2942                false,  // withConfOverride
2943                false, // withProfileOwnerPolicy
2944                true, // withDeviceOwnerPolicy
2945                WifiConfigurationTestUtil.createDHCPIpConfigurationWithPacProxy(),
2946                true, // assertSuccess
2947                WifiConfiguration.INVALID_NETWORK_ID); // Update networkID
2948        verifyAddOrUpdateNetworkWithProxySettingsAndPermissions(
2949                false,  // withConfOverride
2950                false, // withProfileOwnerPolicy
2951                true, // withDeviceOwnerPolicy
2952                WifiConfigurationTestUtil.createDHCPIpConfigurationWithStaticProxy(),
2953                true, // assertSuccess
2954                WifiConfiguration.INVALID_NETWORK_ID); // Update networkID
2955    }
2956    /**
2957     * Verifies that updating a network (that has no proxy) and adding a PAC or STATIC proxy fails
2958     * without being able to override configs, or holding Device or Profile owner policies.
2959     */
2960    @Test
2961    public void testUpdateNetworkAddProxyFails() {
2962        WifiConfiguration network = WifiConfigurationTestUtil.createOpenHiddenNetwork();
2963        NetworkUpdateResult result = verifyAddNetworkToWifiConfigManager(network);
2964        verifyAddOrUpdateNetworkWithProxySettingsAndPermissions(
2965                false, // withConfOverride
2966                false, // withProfileOwnerPolicy
2967                false, // withDeviceOwnerPolicy
2968                WifiConfigurationTestUtil.createDHCPIpConfigurationWithPacProxy(),
2969                false, // assertSuccess
2970                result.getNetworkId()); // Update networkID
2971        verifyAddOrUpdateNetworkWithProxySettingsAndPermissions(
2972                false, // withConfOverride
2973                false, // withProfileOwnerPolicy
2974                false, // withDeviceOwnerPolicy
2975                WifiConfigurationTestUtil.createDHCPIpConfigurationWithStaticProxy(),
2976                false, // assertSuccess
2977                result.getNetworkId()); // Update networkID
2978    }
2979    /**
2980     * Verifies that updating a network and adding a proxy is successful in the cases where app can
2981     * override configs, holds policy {@link DeviceAdminInfo.USES_POLICY_PROFILE_OWNER},
2982     * and holds policy {@link DeviceAdminInfo.USES_POLICY_DEVICE_OWNER}, and that it fails
2983     * otherwise.
2984     */
2985    @Test
2986    public void testUpdateNetworkAddProxyWithPermissionAndSystem() {
2987        // Testing updating network with uid permission OVERRIDE_WIFI_CONFIG
2988        WifiConfiguration network = WifiConfigurationTestUtil.createOpenHiddenNetwork();
2989        NetworkUpdateResult result = addNetworkToWifiConfigManager(network, TEST_CREATOR_UID);
2990        assertTrue(result.getNetworkId() != WifiConfiguration.INVALID_NETWORK_ID);
2991        verifyAddOrUpdateNetworkWithProxySettingsAndPermissions(
2992                true, // withConfOverride
2993                false, // withProfileOwnerPolicy
2994                false, // withDeviceOwnerPolicy
2995                WifiConfigurationTestUtil.createDHCPIpConfigurationWithPacProxy(),
2996                true, // assertSuccess
2997                result.getNetworkId()); // Update networkID
2998
2999        // Testing updating network with proxy while holding Profile Owner policy
3000        network = WifiConfigurationTestUtil.createOpenHiddenNetwork();
3001        result = addNetworkToWifiConfigManager(network, TEST_NO_PERM_UID);
3002        assertTrue(result.getNetworkId() != WifiConfiguration.INVALID_NETWORK_ID);
3003        verifyAddOrUpdateNetworkWithProxySettingsAndPermissions(
3004                false, // withConfOverride
3005                true, // withProfileOwnerPolicy
3006                false, // withDeviceOwnerPolicy
3007                WifiConfigurationTestUtil.createDHCPIpConfigurationWithPacProxy(),
3008                true, // assertSuccess
3009                result.getNetworkId()); // Update networkID
3010
3011        // Testing updating network with proxy while holding Device Owner Policy
3012        network = WifiConfigurationTestUtil.createOpenHiddenNetwork();
3013        result = addNetworkToWifiConfigManager(network, TEST_NO_PERM_UID);
3014        assertTrue(result.getNetworkId() != WifiConfiguration.INVALID_NETWORK_ID);
3015        verifyAddOrUpdateNetworkWithProxySettingsAndPermissions(
3016                false, // withConfOverride
3017                false, // withProfileOwnerPolicy
3018                true, // withDeviceOwnerPolicy
3019                WifiConfigurationTestUtil.createDHCPIpConfigurationWithPacProxy(),
3020                true, // assertSuccess
3021                result.getNetworkId()); // Update networkID
3022    }
3023
3024    /**
3025     * Verifies that updating a network that has a proxy without changing the proxy, can succeed
3026     * without proxy specific permissions.
3027     */
3028    @Test
3029    public void testUpdateNetworkUnchangedProxy() {
3030        IpConfiguration ipConf = WifiConfigurationTestUtil.createDHCPIpConfigurationWithPacProxy();
3031        // First create a WifiConfiguration with proxy
3032        NetworkUpdateResult result = verifyAddOrUpdateNetworkWithProxySettingsAndPermissions(
3033                        false, // withConfOverride
3034                        true, // withProfileOwnerPolicy
3035                        false, // withDeviceOwnerPolicy
3036                        ipConf,
3037                        true, // assertSuccess
3038                        WifiConfiguration.INVALID_NETWORK_ID); // Update networkID
3039        // Update the network while using the same ipConf, and no proxy specific permissions
3040        verifyAddOrUpdateNetworkWithProxySettingsAndPermissions(
3041                        false, // withConfOverride
3042                        false, // withProfileOwnerPolicy
3043                        false, // withDeviceOwnerPolicy
3044                        ipConf,
3045                        true, // assertSuccess
3046                        result.getNetworkId()); // Update networkID
3047    }
3048
3049    /**
3050     * Verifies that updating a network with a different proxy succeeds in the cases where app can
3051     * override configs, holds policy {@link DeviceAdminInfo.USES_POLICY_PROFILE_OWNER},
3052     * and holds policy {@link DeviceAdminInfo.USES_POLICY_DEVICE_OWNER}, and that it fails
3053     * otherwise.
3054     */
3055    @Test
3056    public void testUpdateNetworkDifferentProxy() {
3057        // Create two proxy configurations of the same type, but different values
3058        IpConfiguration ipConf1 =
3059                WifiConfigurationTestUtil.createDHCPIpConfigurationWithSpecificProxy(
3060                        WifiConfigurationTestUtil.STATIC_PROXY_SETTING,
3061                        TEST_STATIC_PROXY_HOST_1,
3062                        TEST_STATIC_PROXY_PORT_1,
3063                        TEST_STATIC_PROXY_EXCLUSION_LIST_1,
3064                        TEST_PAC_PROXY_LOCATION_1);
3065        IpConfiguration ipConf2 =
3066                WifiConfigurationTestUtil.createDHCPIpConfigurationWithSpecificProxy(
3067                        WifiConfigurationTestUtil.STATIC_PROXY_SETTING,
3068                        TEST_STATIC_PROXY_HOST_2,
3069                        TEST_STATIC_PROXY_PORT_2,
3070                        TEST_STATIC_PROXY_EXCLUSION_LIST_2,
3071                        TEST_PAC_PROXY_LOCATION_2);
3072
3073        // Update with Conf Override
3074        NetworkUpdateResult result = verifyAddOrUpdateNetworkWithProxySettingsAndPermissions(
3075                true, // withConfOverride
3076                false, // withProfileOwnerPolicy
3077                false, // withDeviceOwnerPolicy
3078                ipConf1,
3079                true, // assertSuccess
3080                WifiConfiguration.INVALID_NETWORK_ID); // Update networkID
3081        verifyAddOrUpdateNetworkWithProxySettingsAndPermissions(
3082                true, // withConfOverride
3083                false, // withProfileOwnerPolicy
3084                false, // withDeviceOwnerPolicy
3085                ipConf2,
3086                true, // assertSuccess
3087                result.getNetworkId()); // Update networkID
3088
3089        // Update as Device Owner
3090        result = verifyAddOrUpdateNetworkWithProxySettingsAndPermissions(
3091                false, // withConfOverride
3092                false, // withProfileOwnerPolicy
3093                true, // withDeviceOwnerPolicy
3094                ipConf1,
3095                true, // assertSuccess
3096                WifiConfiguration.INVALID_NETWORK_ID); // Update networkID
3097        verifyAddOrUpdateNetworkWithProxySettingsAndPermissions(
3098                false, // withConfOverride
3099                false, // withProfileOwnerPolicy
3100                true, // withDeviceOwnerPolicy
3101                ipConf2,
3102                true, // assertSuccess
3103                result.getNetworkId()); // Update networkID
3104
3105        // Update as Profile Owner
3106        result = verifyAddOrUpdateNetworkWithProxySettingsAndPermissions(
3107                false, // withConfOverride
3108                true, // withProfileOwnerPolicy
3109                false, // withDeviceOwnerPolicy
3110                ipConf1,
3111                true, // assertSuccess
3112                WifiConfiguration.INVALID_NETWORK_ID); // Update networkID
3113        verifyAddOrUpdateNetworkWithProxySettingsAndPermissions(
3114                false, // withConfOverride
3115                true, // withProfileOwnerPolicy
3116                false, // withDeviceOwnerPolicy
3117                ipConf2,
3118                true, // assertSuccess
3119                result.getNetworkId()); // Update networkID
3120
3121        // Update with no permissions (should fail)
3122        result = verifyAddOrUpdateNetworkWithProxySettingsAndPermissions(
3123                false, // withConfOverride
3124                true, // withProfileOwnerPolicy
3125                false, // withDeviceOwnerPolicy
3126                ipConf1,
3127                true, // assertSuccess
3128                WifiConfiguration.INVALID_NETWORK_ID); // Update networkID
3129        verifyAddOrUpdateNetworkWithProxySettingsAndPermissions(
3130                false, // withConfOverride
3131                false, // withProfileOwnerPolicy
3132                false, // withDeviceOwnerPolicy
3133                ipConf2,
3134                false, // assertSuccess
3135                result.getNetworkId()); // Update networkID
3136    }
3137    /**
3138     * Verifies that updating a network removing its proxy succeeds in the cases where app can
3139     * override configs, holds policy {@link DeviceAdminInfo.USES_POLICY_PROFILE_OWNER},
3140     * and holds policy {@link DeviceAdminInfo.USES_POLICY_DEVICE_OWNER}, and that it fails
3141     * otherwise.
3142     */
3143    @Test
3144    public void testUpdateNetworkRemoveProxy() {
3145        // Create two different IP configurations, one with a proxy and another without.
3146        IpConfiguration ipConf1 =
3147                WifiConfigurationTestUtil.createDHCPIpConfigurationWithSpecificProxy(
3148                        WifiConfigurationTestUtil.STATIC_PROXY_SETTING,
3149                        TEST_STATIC_PROXY_HOST_1,
3150                        TEST_STATIC_PROXY_PORT_1,
3151                        TEST_STATIC_PROXY_EXCLUSION_LIST_1,
3152                        TEST_PAC_PROXY_LOCATION_1);
3153        IpConfiguration ipConf2 =
3154                WifiConfigurationTestUtil.createDHCPIpConfigurationWithSpecificProxy(
3155                        WifiConfigurationTestUtil.NONE_PROXY_SETTING,
3156                        TEST_STATIC_PROXY_HOST_2,
3157                        TEST_STATIC_PROXY_PORT_2,
3158                        TEST_STATIC_PROXY_EXCLUSION_LIST_2,
3159                        TEST_PAC_PROXY_LOCATION_2);
3160
3161        // Update with Conf Override
3162        NetworkUpdateResult result = verifyAddOrUpdateNetworkWithProxySettingsAndPermissions(
3163                true, // withConfOverride
3164                false, // withProfileOwnerPolicy
3165                false, // withDeviceOwnerPolicy
3166                ipConf1,
3167                true, // assertSuccess
3168                WifiConfiguration.INVALID_NETWORK_ID); // Update networkID
3169        verifyAddOrUpdateNetworkWithProxySettingsAndPermissions(
3170                true, // withConfOverride
3171                false, // withProfileOwnerPolicy
3172                false, // withDeviceOwnerPolicy
3173                ipConf2,
3174                true, // assertSuccess
3175                result.getNetworkId()); // Update networkID
3176
3177        // Update as Device Owner
3178        result = verifyAddOrUpdateNetworkWithProxySettingsAndPermissions(
3179                false, // withConfOverride
3180                false, // withProfileOwnerPolicy
3181                true, // withDeviceOwnerPolicy
3182                ipConf1,
3183                true, // assertSuccess
3184                WifiConfiguration.INVALID_NETWORK_ID); // Update networkID
3185        verifyAddOrUpdateNetworkWithProxySettingsAndPermissions(
3186                false, // withConfOverride
3187                false, // withProfileOwnerPolicy
3188                true, // withDeviceOwnerPolicy
3189                ipConf2,
3190                true, // assertSuccess
3191                result.getNetworkId()); // Update networkID
3192
3193        // Update as Profile Owner
3194        result = verifyAddOrUpdateNetworkWithProxySettingsAndPermissions(
3195                false, // withConfOverride
3196                true, // withProfileOwnerPolicy
3197                false, // withDeviceOwnerPolicy
3198                ipConf1,
3199                true, // assertSuccess
3200                WifiConfiguration.INVALID_NETWORK_ID); // Update networkID
3201        verifyAddOrUpdateNetworkWithProxySettingsAndPermissions(
3202                false, // withConfOverride
3203                true, // withProfileOwnerPolicy
3204                false, // withDeviceOwnerPolicy
3205                ipConf2,
3206                true, // assertSuccess
3207                result.getNetworkId()); // Update networkID
3208
3209        // Update with no permissions (should fail)
3210        result = verifyAddOrUpdateNetworkWithProxySettingsAndPermissions(
3211                false, // withConfOverride
3212                true, // withProfileOwnerPolicy
3213                false, // withDeviceOwnerPolicy
3214                ipConf1,
3215                true, // assertSuccess
3216                WifiConfiguration.INVALID_NETWORK_ID); // Update networkID
3217        verifyAddOrUpdateNetworkWithProxySettingsAndPermissions(
3218                false, // withConfOverride
3219                false, // withProfileOwnerPolicy
3220                false, // withDeviceOwnerPolicy
3221                ipConf2,
3222                false, // assertSuccess
3223                result.getNetworkId()); // Update networkID
3224    }
3225
3226    /**
3227     * Verifies that the app specified BSSID is converted and saved in lower case.
3228     */
3229    @Test
3230    public void testAppSpecifiedBssidIsSavedInLowerCase() {
3231        final String bssid = "0A:08:5C:BB:89:6D"; // upper case
3232        WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork();
3233        openNetwork.BSSID = bssid;
3234
3235        NetworkUpdateResult result = verifyAddNetworkToWifiConfigManager(openNetwork);
3236
3237        WifiConfiguration retrievedNetwork = mWifiConfigManager.getConfiguredNetwork(
3238                result.getNetworkId());
3239
3240        assertNotEquals(retrievedNetwork.BSSID, bssid);
3241        assertEquals(retrievedNetwork.BSSID, bssid.toLowerCase());
3242    }
3243
3244    private NetworkUpdateResult verifyAddOrUpdateNetworkWithProxySettingsAndPermissions(
3245            boolean withConfOverride,
3246            boolean withProfileOwnerPolicy,
3247            boolean withDeviceOwnerPolicy,
3248            IpConfiguration ipConfiguration,
3249            boolean assertSuccess,
3250            int networkId) {
3251        WifiConfiguration network;
3252        if (networkId == WifiConfiguration.INVALID_NETWORK_ID) {
3253            network = WifiConfigurationTestUtil.createOpenHiddenNetwork();
3254        } else {
3255            network = mWifiConfigManager.getConfiguredNetwork(networkId);
3256        }
3257        network.setIpConfiguration(ipConfiguration);
3258        when(mDevicePolicyManagerInternal.isActiveAdminWithPolicy(anyInt(),
3259                eq(DeviceAdminInfo.USES_POLICY_PROFILE_OWNER)))
3260                .thenReturn(withProfileOwnerPolicy);
3261        when(mDevicePolicyManagerInternal.isActiveAdminWithPolicy(anyInt(),
3262                eq(DeviceAdminInfo.USES_POLICY_DEVICE_OWNER)))
3263                .thenReturn(withDeviceOwnerPolicy);
3264        when(mWifiPermissionsUtil.checkConfigOverridePermission(anyInt()))
3265                .thenReturn(withConfOverride);
3266        int uid = withConfOverride ? TEST_CREATOR_UID : TEST_NO_PERM_UID;
3267        NetworkUpdateResult result = addNetworkToWifiConfigManager(network, uid);
3268        assertEquals(assertSuccess, result.getNetworkId() != WifiConfiguration.INVALID_NETWORK_ID);
3269        return result;
3270    }
3271
3272    private void createWifiConfigManager() {
3273        mWifiConfigManager =
3274                new WifiConfigManager(
3275                        mContext, mClock, mUserManager, mTelephonyManager,
3276                        mWifiKeyStore, mWifiConfigStore, mWifiConfigStoreLegacy,
3277                        mWifiPermissionsUtil, mWifiPermissionsWrapper, mNetworkListStoreData,
3278                        mDeletedEphemeralSsidsStoreData);
3279        mWifiConfigManager.enableVerboseLogging(1);
3280    }
3281
3282    /**
3283     * This method sets defaults in the provided WifiConfiguration object if not set
3284     * so that it can be used for comparison with the configuration retrieved from
3285     * WifiConfigManager.
3286     */
3287    private void setDefaults(WifiConfiguration configuration) {
3288        if (configuration.allowedAuthAlgorithms.isEmpty()) {
3289            configuration.allowedAuthAlgorithms.set(WifiConfiguration.AuthAlgorithm.OPEN);
3290        }
3291        if (configuration.allowedProtocols.isEmpty()) {
3292            configuration.allowedProtocols.set(WifiConfiguration.Protocol.RSN);
3293            configuration.allowedProtocols.set(WifiConfiguration.Protocol.WPA);
3294        }
3295        if (configuration.allowedKeyManagement.isEmpty()) {
3296            configuration.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.WPA_PSK);
3297            configuration.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.WPA_EAP);
3298        }
3299        if (configuration.allowedPairwiseCiphers.isEmpty()) {
3300            configuration.allowedPairwiseCiphers.set(WifiConfiguration.PairwiseCipher.CCMP);
3301            configuration.allowedPairwiseCiphers.set(WifiConfiguration.PairwiseCipher.TKIP);
3302        }
3303        if (configuration.allowedGroupCiphers.isEmpty()) {
3304            configuration.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.CCMP);
3305            configuration.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.TKIP);
3306            configuration.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.WEP40);
3307            configuration.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.WEP104);
3308        }
3309        if (configuration.getIpAssignment() == IpConfiguration.IpAssignment.UNASSIGNED) {
3310            configuration.setIpAssignment(IpConfiguration.IpAssignment.DHCP);
3311        }
3312        if (configuration.getProxySettings() == IpConfiguration.ProxySettings.UNASSIGNED) {
3313            configuration.setProxySettings(IpConfiguration.ProxySettings.NONE);
3314        }
3315        configuration.status = WifiConfiguration.Status.DISABLED;
3316        configuration.getNetworkSelectionStatus().setNetworkSelectionStatus(
3317                NetworkSelectionStatus.NETWORK_SELECTION_PERMANENTLY_DISABLED);
3318    }
3319
3320    /**
3321     * Modifies the provided configuration with creator uid, package name
3322     * and time.
3323     */
3324    private void setCreationDebugParams(WifiConfiguration configuration) {
3325        configuration.creatorUid = configuration.lastUpdateUid = TEST_CREATOR_UID;
3326        configuration.creatorName = configuration.lastUpdateName = TEST_CREATOR_NAME;
3327        configuration.creationTime = configuration.updateTime =
3328                WifiConfigManager.createDebugTimeStampString(
3329                        TEST_WALLCLOCK_CREATION_TIME_MILLIS);
3330    }
3331
3332    /**
3333     * Modifies the provided configuration with update uid, package name
3334     * and time.
3335     */
3336    private void setUpdateDebugParams(WifiConfiguration configuration) {
3337        configuration.lastUpdateUid = TEST_UPDATE_UID;
3338        configuration.lastUpdateName = TEST_UPDATE_NAME;
3339        configuration.updateTime =
3340                WifiConfigManager.createDebugTimeStampString(TEST_WALLCLOCK_UPDATE_TIME_MILLIS);
3341    }
3342
3343    private void assertNotEquals(Object expected, Object actual) {
3344        if (actual != null) {
3345            assertFalse(actual.equals(expected));
3346        } else {
3347            assertNotNull(expected);
3348        }
3349    }
3350
3351    /**
3352     * Modifies the provided WifiConfiguration with the specified bssid value. Also, asserts that
3353     * the existing |BSSID| field is not the same value as the one being set
3354     */
3355    private void assertAndSetNetworkBSSID(WifiConfiguration configuration, String bssid) {
3356        assertNotEquals(bssid, configuration.BSSID);
3357        configuration.BSSID = bssid;
3358    }
3359
3360    /**
3361     * Modifies the provided WifiConfiguration with the specified |IpConfiguration| object. Also,
3362     * asserts that the existing |mIpConfiguration| field is not the same value as the one being set
3363     */
3364    private void assertAndSetNetworkIpConfiguration(
3365            WifiConfiguration configuration, IpConfiguration ipConfiguration) {
3366        assertNotEquals(ipConfiguration, configuration.getIpConfiguration());
3367        configuration.setIpConfiguration(ipConfiguration);
3368    }
3369
3370    /**
3371     * Modifies the provided WifiConfiguration with the specified |wepKeys| value and
3372     * |wepTxKeyIndex|.
3373     */
3374    private void assertAndSetNetworkWepKeysAndTxIndex(
3375            WifiConfiguration configuration, String[] wepKeys, int wepTxKeyIdx) {
3376        assertNotEquals(wepKeys, configuration.wepKeys);
3377        assertNotEquals(wepTxKeyIdx, configuration.wepTxKeyIndex);
3378        configuration.wepKeys = Arrays.copyOf(wepKeys, wepKeys.length);
3379        configuration.wepTxKeyIndex = wepTxKeyIdx;
3380    }
3381
3382    /**
3383     * Modifies the provided WifiConfiguration with the specified |preSharedKey| value.
3384     */
3385    private void assertAndSetNetworkPreSharedKey(
3386            WifiConfiguration configuration, String preSharedKey) {
3387        assertNotEquals(preSharedKey, configuration.preSharedKey);
3388        configuration.preSharedKey = preSharedKey;
3389    }
3390
3391    /**
3392     * Modifies the provided WifiConfiguration with the specified enteprise |password| value.
3393     */
3394    private void assertAndSetNetworkEnterprisePassword(
3395            WifiConfiguration configuration, String password) {
3396        assertNotEquals(password, configuration.enterpriseConfig.getPassword());
3397        configuration.enterpriseConfig.setPassword(password);
3398    }
3399
3400    /**
3401     * Helper method to capture the networks list store data that will be written by
3402     * WifiConfigStore.write() method.
3403     */
3404    private Pair<List<WifiConfiguration>, List<WifiConfiguration>>
3405            captureWriteNetworksListStoreData() {
3406        try {
3407            ArgumentCaptor<ArrayList> sharedConfigsCaptor =
3408                    ArgumentCaptor.forClass(ArrayList.class);
3409            ArgumentCaptor<ArrayList> userConfigsCaptor =
3410                    ArgumentCaptor.forClass(ArrayList.class);
3411            mNetworkListStoreDataMockOrder.verify(mNetworkListStoreData)
3412                    .setSharedConfigurations(sharedConfigsCaptor.capture());
3413            mNetworkListStoreDataMockOrder.verify(mNetworkListStoreData)
3414                    .setUserConfigurations(userConfigsCaptor.capture());
3415            mContextConfigStoreMockOrder.verify(mWifiConfigStore).write(anyBoolean());
3416            return Pair.create(sharedConfigsCaptor.getValue(), userConfigsCaptor.getValue());
3417        } catch (Exception e) {
3418            fail("Exception encountered during write " + e);
3419        }
3420        return null;
3421    }
3422
3423    /**
3424     * Returns whether the provided network was in the store data or not.
3425     */
3426    private boolean isNetworkInConfigStoreData(WifiConfiguration configuration) {
3427        Pair<List<WifiConfiguration>, List<WifiConfiguration>> networkListStoreData =
3428                captureWriteNetworksListStoreData();
3429        if (networkListStoreData == null) {
3430            return false;
3431        }
3432        List<WifiConfiguration> networkList = new ArrayList<>();
3433        networkList.addAll(networkListStoreData.first);
3434        networkList.addAll(networkListStoreData.second);
3435        return isNetworkInConfigStoreData(configuration, networkList);
3436    }
3437
3438    /**
3439     * Returns whether the provided network was in the store data or not.
3440     */
3441    private boolean isNetworkInConfigStoreData(
3442            WifiConfiguration configuration, List<WifiConfiguration> networkList) {
3443        boolean foundNetworkInStoreData = false;
3444        for (WifiConfiguration retrievedConfig : networkList) {
3445            if (retrievedConfig.configKey().equals(configuration.configKey())) {
3446                foundNetworkInStoreData = true;
3447                break;
3448            }
3449        }
3450        return foundNetworkInStoreData;
3451    }
3452
3453    /**
3454     * Setup expectations for WifiNetworksListStoreData and DeletedEphemeralSsidsStoreData
3455     * after WifiConfigStore#read.
3456     */
3457    private void setupStoreDataForRead(List<WifiConfiguration> sharedConfigurations,
3458            List<WifiConfiguration> userConfigurations, Set<String> deletedEphemeralSsids) {
3459        when(mNetworkListStoreData.getSharedConfigurations())
3460                .thenReturn(sharedConfigurations);
3461        when(mNetworkListStoreData.getUserConfigurations()).thenReturn(userConfigurations);
3462        when(mDeletedEphemeralSsidsStoreData.getSsidList()).thenReturn(deletedEphemeralSsids);
3463    }
3464
3465    /**
3466     * Setup expectations for WifiNetworksListStoreData and DeletedEphemeralSsidsStoreData
3467     * after WifiConfigStore#switchUserStoreAndRead.
3468     */
3469    private void setupStoreDataForUserRead(List<WifiConfiguration> userConfigurations,
3470            Set<String> deletedEphemeralSsids) {
3471        when(mNetworkListStoreData.getUserConfigurations()).thenReturn(userConfigurations);
3472        when(mDeletedEphemeralSsidsStoreData.getSsidList()).thenReturn(deletedEphemeralSsids);
3473    }
3474
3475    /**
3476     * Verifies that the provided network was not present in the last config store write.
3477     */
3478    private void verifyNetworkNotInConfigStoreData(WifiConfiguration configuration) {
3479        assertFalse(isNetworkInConfigStoreData(configuration));
3480    }
3481
3482    /**
3483     * Verifies that the provided network was present in the last config store write.
3484     */
3485    private void verifyNetworkInConfigStoreData(WifiConfiguration configuration) {
3486        assertTrue(isNetworkInConfigStoreData(configuration));
3487    }
3488
3489    private void assertPasswordsMaskedInWifiConfiguration(WifiConfiguration configuration) {
3490        if (!TextUtils.isEmpty(configuration.preSharedKey)) {
3491            assertEquals(WifiConfigManager.PASSWORD_MASK, configuration.preSharedKey);
3492        }
3493        if (configuration.wepKeys != null) {
3494            for (int i = 0; i < configuration.wepKeys.length; i++) {
3495                if (!TextUtils.isEmpty(configuration.wepKeys[i])) {
3496                    assertEquals(WifiConfigManager.PASSWORD_MASK, configuration.wepKeys[i]);
3497                }
3498            }
3499        }
3500        if (!TextUtils.isEmpty(configuration.enterpriseConfig.getPassword())) {
3501            assertEquals(
3502                    WifiConfigManager.PASSWORD_MASK,
3503                    configuration.enterpriseConfig.getPassword());
3504        }
3505    }
3506
3507    /**
3508     * Verifies that the network was present in the network change broadcast and returns the
3509     * change reason.
3510     */
3511    private int verifyNetworkInBroadcastAndReturnReason(WifiConfiguration configuration) {
3512        ArgumentCaptor<Intent> intentCaptor = ArgumentCaptor.forClass(Intent.class);
3513        ArgumentCaptor<UserHandle> userHandleCaptor = ArgumentCaptor.forClass(UserHandle.class);
3514        mContextConfigStoreMockOrder.verify(mContext)
3515                .sendBroadcastAsUser(intentCaptor.capture(), userHandleCaptor.capture());
3516
3517        assertEquals(userHandleCaptor.getValue(), UserHandle.ALL);
3518        Intent intent = intentCaptor.getValue();
3519
3520        int changeReason = intent.getIntExtra(WifiManager.EXTRA_CHANGE_REASON, -1);
3521        WifiConfiguration retrievedConfig =
3522                (WifiConfiguration) intent.getExtra(WifiManager.EXTRA_WIFI_CONFIGURATION);
3523        assertEquals(retrievedConfig.configKey(), configuration.configKey());
3524
3525        // Verify that all the passwords are masked in the broadcast configuration.
3526        assertPasswordsMaskedInWifiConfiguration(retrievedConfig);
3527
3528        return changeReason;
3529    }
3530
3531    /**
3532     * Verifies that we sent out an add broadcast with the provided network.
3533     */
3534    private void verifyNetworkAddBroadcast(WifiConfiguration configuration) {
3535        assertEquals(
3536                verifyNetworkInBroadcastAndReturnReason(configuration),
3537                WifiManager.CHANGE_REASON_ADDED);
3538    }
3539
3540    /**
3541     * Verifies that we sent out an update broadcast with the provided network.
3542     */
3543    private void verifyNetworkUpdateBroadcast(WifiConfiguration configuration) {
3544        assertEquals(
3545                verifyNetworkInBroadcastAndReturnReason(configuration),
3546                WifiManager.CHANGE_REASON_CONFIG_CHANGE);
3547    }
3548
3549    /**
3550     * Verifies that we sent out a remove broadcast with the provided network.
3551     */
3552    private void verifyNetworkRemoveBroadcast(WifiConfiguration configuration) {
3553        assertEquals(
3554                verifyNetworkInBroadcastAndReturnReason(configuration),
3555                WifiManager.CHANGE_REASON_REMOVED);
3556    }
3557
3558    private void verifyWifiConfigStoreRead() {
3559        assertTrue(mWifiConfigManager.loadFromStore());
3560        mContextConfigStoreMockOrder.verify(mContext)
3561                .sendBroadcastAsUser(any(Intent.class), any(UserHandle.class));
3562    }
3563
3564    private void triggerStoreReadIfNeeded() {
3565        // Trigger a store read if not already done.
3566        if (!mStoreReadTriggered) {
3567            verifyWifiConfigStoreRead();
3568            mStoreReadTriggered = true;
3569        }
3570    }
3571
3572    /**
3573     * Adds the provided configuration to WifiConfigManager with uid = TEST_CREATOR_UID.
3574     */
3575    private NetworkUpdateResult addNetworkToWifiConfigManager(WifiConfiguration configuration) {
3576        return addNetworkToWifiConfigManager(configuration, TEST_CREATOR_UID);
3577    }
3578
3579    /**
3580     * Adds the provided configuration to WifiConfigManager and modifies the provided configuration
3581     * with creator/update uid, package name and time. This also sets defaults for fields not
3582     * populated.
3583     * These fields are populated internally by WifiConfigManager and hence we need
3584     * to modify the configuration before we compare the added network with the retrieved network.
3585     * This method also triggers a store read if not already done.
3586     */
3587    private NetworkUpdateResult addNetworkToWifiConfigManager(WifiConfiguration configuration,
3588                                                              int uid) {
3589        triggerStoreReadIfNeeded();
3590        when(mClock.getWallClockMillis()).thenReturn(TEST_WALLCLOCK_CREATION_TIME_MILLIS);
3591        NetworkUpdateResult result =
3592                mWifiConfigManager.addOrUpdateNetwork(configuration, uid);
3593        setDefaults(configuration);
3594        setCreationDebugParams(configuration);
3595        configuration.networkId = result.getNetworkId();
3596        return result;
3597    }
3598
3599    /**
3600     * Add network to WifiConfigManager and ensure that it was successful.
3601     */
3602    private NetworkUpdateResult verifyAddNetworkToWifiConfigManager(
3603            WifiConfiguration configuration) {
3604        NetworkUpdateResult result = addNetworkToWifiConfigManager(configuration);
3605        assertTrue(result.getNetworkId() != WifiConfiguration.INVALID_NETWORK_ID);
3606        assertTrue(result.isNewNetwork());
3607        assertTrue(result.hasIpChanged());
3608        assertTrue(result.hasProxyChanged());
3609
3610        verifyNetworkAddBroadcast(configuration);
3611        // Verify that the config store write was triggered with this new configuration.
3612        verifyNetworkInConfigStoreData(configuration);
3613        return result;
3614    }
3615
3616    /**
3617     * Add ephemeral network to WifiConfigManager and ensure that it was successful.
3618     */
3619    private NetworkUpdateResult verifyAddEphemeralNetworkToWifiConfigManager(
3620            WifiConfiguration configuration) throws Exception {
3621        NetworkUpdateResult result = addNetworkToWifiConfigManager(configuration);
3622        assertTrue(result.getNetworkId() != WifiConfiguration.INVALID_NETWORK_ID);
3623        assertTrue(result.isNewNetwork());
3624        assertTrue(result.hasIpChanged());
3625        assertTrue(result.hasProxyChanged());
3626
3627        verifyNetworkAddBroadcast(configuration);
3628        // Ensure that the write was not invoked for ephemeral network addition.
3629        mContextConfigStoreMockOrder.verify(mWifiConfigStore, never()).write(anyBoolean());
3630        return result;
3631    }
3632
3633    /**
3634     * Add Passpoint network to WifiConfigManager and ensure that it was successful.
3635     */
3636    private NetworkUpdateResult verifyAddPasspointNetworkToWifiConfigManager(
3637            WifiConfiguration configuration) throws Exception {
3638        NetworkUpdateResult result = addNetworkToWifiConfigManager(configuration);
3639        assertTrue(result.getNetworkId() != WifiConfiguration.INVALID_NETWORK_ID);
3640        assertTrue(result.isNewNetwork());
3641        assertTrue(result.hasIpChanged());
3642        assertTrue(result.hasProxyChanged());
3643
3644        // Verify keys are not being installed.
3645        verify(mWifiKeyStore, never()).updateNetworkKeys(any(WifiConfiguration.class),
3646                any(WifiConfiguration.class));
3647        verifyNetworkAddBroadcast(configuration);
3648        // Ensure that the write was not invoked for Passpoint network addition.
3649        mContextConfigStoreMockOrder.verify(mWifiConfigStore, never()).write(anyBoolean());
3650        return result;
3651    }
3652
3653    /**
3654     * Updates the provided configuration to WifiConfigManager and modifies the provided
3655     * configuration with update uid, package name and time.
3656     * These fields are populated internally by WifiConfigManager and hence we need
3657     * to modify the configuration before we compare the added network with the retrieved network.
3658     */
3659    private NetworkUpdateResult updateNetworkToWifiConfigManager(WifiConfiguration configuration) {
3660        when(mClock.getWallClockMillis()).thenReturn(TEST_WALLCLOCK_UPDATE_TIME_MILLIS);
3661        NetworkUpdateResult result =
3662                mWifiConfigManager.addOrUpdateNetwork(configuration, TEST_UPDATE_UID);
3663        setUpdateDebugParams(configuration);
3664        return result;
3665    }
3666
3667    /**
3668     * Update network to WifiConfigManager config change and ensure that it was successful.
3669     */
3670    private NetworkUpdateResult verifyUpdateNetworkToWifiConfigManager(
3671            WifiConfiguration configuration) {
3672        NetworkUpdateResult result = updateNetworkToWifiConfigManager(configuration);
3673        assertTrue(result.getNetworkId() != WifiConfiguration.INVALID_NETWORK_ID);
3674        assertFalse(result.isNewNetwork());
3675
3676        verifyNetworkUpdateBroadcast(configuration);
3677        // Verify that the config store write was triggered with this new configuration.
3678        verifyNetworkInConfigStoreData(configuration);
3679        return result;
3680    }
3681
3682    /**
3683     * Update network to WifiConfigManager without IP config change and ensure that it was
3684     * successful.
3685     */
3686    private NetworkUpdateResult verifyUpdateNetworkToWifiConfigManagerWithoutIpChange(
3687            WifiConfiguration configuration) {
3688        NetworkUpdateResult result = verifyUpdateNetworkToWifiConfigManager(configuration);
3689        assertFalse(result.hasIpChanged());
3690        assertFalse(result.hasProxyChanged());
3691        return result;
3692    }
3693
3694    /**
3695     * Update network to WifiConfigManager with IP config change and ensure that it was
3696     * successful.
3697     */
3698    private NetworkUpdateResult verifyUpdateNetworkToWifiConfigManagerWithIpChange(
3699            WifiConfiguration configuration) {
3700        NetworkUpdateResult result = verifyUpdateNetworkToWifiConfigManager(configuration);
3701        assertTrue(result.hasIpChanged());
3702        assertTrue(result.hasProxyChanged());
3703        return result;
3704    }
3705
3706    /**
3707     * Removes network from WifiConfigManager and ensure that it was successful.
3708     */
3709    private void verifyRemoveNetworkFromWifiConfigManager(
3710            WifiConfiguration configuration) {
3711        assertTrue(mWifiConfigManager.removeNetwork(configuration.networkId, TEST_CREATOR_UID));
3712
3713        verifyNetworkRemoveBroadcast(configuration);
3714        // Verify if the config store write was triggered without this new configuration.
3715        verifyNetworkNotInConfigStoreData(configuration);
3716    }
3717
3718    /**
3719     * Removes ephemeral network from WifiConfigManager and ensure that it was successful.
3720     */
3721    private void verifyRemoveEphemeralNetworkFromWifiConfigManager(
3722            WifiConfiguration configuration) throws Exception {
3723        assertTrue(mWifiConfigManager.removeNetwork(configuration.networkId, TEST_CREATOR_UID));
3724
3725        verifyNetworkRemoveBroadcast(configuration);
3726        // Ensure that the write was not invoked for ephemeral network remove.
3727        mContextConfigStoreMockOrder.verify(mWifiConfigStore, never()).write(anyBoolean());
3728    }
3729
3730    /**
3731     * Removes Passpoint network from WifiConfigManager and ensure that it was successful.
3732     */
3733    private void verifyRemovePasspointNetworkFromWifiConfigManager(
3734            WifiConfiguration configuration) throws Exception {
3735        assertTrue(mWifiConfigManager.removeNetwork(configuration.networkId, TEST_CREATOR_UID));
3736
3737        // Verify keys are not being removed.
3738        verify(mWifiKeyStore, never()).removeKeys(any(WifiEnterpriseConfig.class));
3739        verifyNetworkRemoveBroadcast(configuration);
3740        // Ensure that the write was not invoked for Passpoint network remove.
3741        mContextConfigStoreMockOrder.verify(mWifiConfigStore, never()).write(anyBoolean());
3742    }
3743
3744    /**
3745     * Verifies the provided network's public status and ensures that the network change broadcast
3746     * has been sent out.
3747     */
3748    private void verifyUpdateNetworkStatus(WifiConfiguration configuration, int status) {
3749        assertEquals(status, configuration.status);
3750        verifyNetworkUpdateBroadcast(configuration);
3751    }
3752
3753    /**
3754     * Verifies the network's selection status update.
3755     *
3756     * For temporarily disabled reasons, the method ensures that the status has changed only if
3757     * disable reason counter has exceeded the threshold.
3758     *
3759     * For permanently disabled/enabled reasons, the method ensures that the public status has
3760     * changed and the network change broadcast has been sent out.
3761     */
3762    private void verifyUpdateNetworkSelectionStatus(
3763            int networkId, int reason, int temporaryDisableReasonCounter) {
3764        when(mClock.getElapsedSinceBootMillis())
3765                .thenReturn(TEST_ELAPSED_UPDATE_NETWORK_SELECTION_TIME_MILLIS);
3766
3767        // Fetch the current status of the network before we try to update the status.
3768        WifiConfiguration retrievedNetwork = mWifiConfigManager.getConfiguredNetwork(networkId);
3769        NetworkSelectionStatus currentStatus = retrievedNetwork.getNetworkSelectionStatus();
3770        int currentDisableReason = currentStatus.getNetworkSelectionDisableReason();
3771
3772        // First set the status to the provided reason.
3773        assertTrue(mWifiConfigManager.updateNetworkSelectionStatus(networkId, reason));
3774
3775        // Now fetch the network configuration and verify the new status of the network.
3776        retrievedNetwork = mWifiConfigManager.getConfiguredNetwork(networkId);
3777
3778        NetworkSelectionStatus retrievedStatus = retrievedNetwork.getNetworkSelectionStatus();
3779        int retrievedDisableReason = retrievedStatus.getNetworkSelectionDisableReason();
3780        long retrievedDisableTime = retrievedStatus.getDisableTime();
3781        int retrievedDisableReasonCounter = retrievedStatus.getDisableReasonCounter(reason);
3782        int disableReasonThreshold =
3783                WifiConfigManager.NETWORK_SELECTION_DISABLE_THRESHOLD[reason];
3784
3785        if (reason == NetworkSelectionStatus.NETWORK_SELECTION_ENABLE) {
3786            assertEquals(reason, retrievedDisableReason);
3787            assertTrue(retrievedStatus.isNetworkEnabled());
3788            assertEquals(
3789                    NetworkSelectionStatus.INVALID_NETWORK_SELECTION_DISABLE_TIMESTAMP,
3790                    retrievedDisableTime);
3791            verifyUpdateNetworkStatus(retrievedNetwork, WifiConfiguration.Status.ENABLED);
3792        } else if (reason < NetworkSelectionStatus.DISABLED_TLS_VERSION_MISMATCH) {
3793            // For temporarily disabled networks, we need to ensure that the current status remains
3794            // until the threshold is crossed.
3795            assertEquals(temporaryDisableReasonCounter, retrievedDisableReasonCounter);
3796            if (retrievedDisableReasonCounter < disableReasonThreshold) {
3797                assertEquals(currentDisableReason, retrievedDisableReason);
3798                assertEquals(
3799                        currentStatus.getNetworkSelectionStatus(),
3800                        retrievedStatus.getNetworkSelectionStatus());
3801            } else {
3802                assertEquals(reason, retrievedDisableReason);
3803                assertTrue(retrievedStatus.isNetworkTemporaryDisabled());
3804                assertEquals(
3805                        TEST_ELAPSED_UPDATE_NETWORK_SELECTION_TIME_MILLIS, retrievedDisableTime);
3806            }
3807        } else if (reason < NetworkSelectionStatus.NETWORK_SELECTION_DISABLED_MAX) {
3808            assertEquals(reason, retrievedDisableReason);
3809            assertTrue(retrievedStatus.isNetworkPermanentlyDisabled());
3810            assertEquals(
3811                    NetworkSelectionStatus.INVALID_NETWORK_SELECTION_DISABLE_TIMESTAMP,
3812                    retrievedDisableTime);
3813            verifyUpdateNetworkStatus(retrievedNetwork, WifiConfiguration.Status.DISABLED);
3814        }
3815    }
3816
3817    /**
3818     * Creates a scan detail corresponding to the provided network and given BSSID, level &frequency
3819     * values.
3820     */
3821    private ScanDetail createScanDetailForNetwork(
3822            WifiConfiguration configuration, String bssid, int level, int frequency) {
3823        String caps;
3824        if (configuration.allowedKeyManagement.get(WifiConfiguration.KeyMgmt.WPA_PSK)) {
3825            caps = "[WPA2-PSK-CCMP]";
3826        } else if (configuration.allowedKeyManagement.get(WifiConfiguration.KeyMgmt.WPA_EAP)
3827                || configuration.allowedKeyManagement.get(WifiConfiguration.KeyMgmt.IEEE8021X)) {
3828            caps = "[WPA2-EAP-CCMP]";
3829        } else if (configuration.allowedKeyManagement.get(WifiConfiguration.KeyMgmt.NONE)
3830                && WifiConfigurationUtil.hasAnyValidWepKey(configuration.wepKeys)) {
3831            caps = "[WEP]";
3832        } else {
3833            caps = "[]";
3834        }
3835        WifiSsid ssid = WifiSsid.createFromAsciiEncoded(configuration.getPrintableSsid());
3836        // Fill in 0's in the fields we don't care about.
3837        return new ScanDetail(
3838                ssid, bssid, caps, level, frequency, mClock.getUptimeSinceBootMillis(),
3839                mClock.getWallClockMillis());
3840    }
3841
3842    /**
3843     * Creates a scan detail corresponding to the provided network and BSSID value.
3844     */
3845    private ScanDetail createScanDetailForNetwork(WifiConfiguration configuration, String bssid) {
3846        return createScanDetailForNetwork(configuration, bssid, 0, 0);
3847    }
3848
3849    /**
3850     * Creates a scan detail corresponding to the provided network and fixed BSSID value.
3851     */
3852    private ScanDetail createScanDetailForNetwork(WifiConfiguration configuration) {
3853        return createScanDetailForNetwork(configuration, TEST_BSSID);
3854    }
3855
3856    /**
3857     * Adds the provided network and then creates a scan detail corresponding to the network. The
3858     * method then creates a ScanDetail corresponding to the network and ensures that the network
3859     * is properly matched using
3860     * {@link WifiConfigManager#getSavedNetworkForScanDetailAndCache(ScanDetail)} and also
3861     * verifies that the provided scan detail was cached,
3862     */
3863    private void verifyAddSingleNetworkAndMatchScanDetailToNetworkAndCache(
3864            WifiConfiguration network) {
3865        // First add the provided network.
3866        verifyAddNetworkToWifiConfigManager(network);
3867
3868        // Now create a dummy scan detail corresponding to the network.
3869        ScanDetail scanDetail = createScanDetailForNetwork(network);
3870        ScanResult scanResult = scanDetail.getScanResult();
3871
3872        WifiConfiguration retrievedNetwork =
3873                mWifiConfigManager.getSavedNetworkForScanDetailAndCache(scanDetail);
3874        // Retrieve the network with password data for comparison.
3875        retrievedNetwork =
3876                mWifiConfigManager.getConfiguredNetworkWithPassword(retrievedNetwork.networkId);
3877
3878        WifiConfigurationTestUtil.assertConfigurationEqualForConfigManagerAddOrUpdate(
3879                network, retrievedNetwork);
3880
3881        // Now retrieve the scan detail cache and ensure that the new scan detail is in cache.
3882        ScanDetailCache retrievedScanDetailCache =
3883                mWifiConfigManager.getScanDetailCacheForNetwork(network.networkId);
3884        assertEquals(1, retrievedScanDetailCache.size());
3885        ScanResult retrievedScanResult = retrievedScanDetailCache.get(scanResult.BSSID);
3886
3887        ScanTestUtil.assertScanResultEquals(scanResult, retrievedScanResult);
3888    }
3889
3890    /**
3891     * Adds a new network and verifies that the |HasEverConnected| flag is set to false.
3892     */
3893    private void verifyAddNetworkHasEverConnectedFalse(WifiConfiguration network) {
3894        NetworkUpdateResult result = verifyAddNetworkToWifiConfigManager(network);
3895        WifiConfiguration retrievedNetwork =
3896                mWifiConfigManager.getConfiguredNetwork(result.getNetworkId());
3897        assertFalse("Adding a new network should not have hasEverConnected set to true.",
3898                retrievedNetwork.getNetworkSelectionStatus().getHasEverConnected());
3899    }
3900
3901    /**
3902     * Updates an existing network with some credential change and verifies that the
3903     * |HasEverConnected| flag is set to false.
3904     */
3905    private void verifyUpdateNetworkWithCredentialChangeHasEverConnectedFalse(
3906            WifiConfiguration network) {
3907        NetworkUpdateResult result = verifyUpdateNetworkToWifiConfigManagerWithoutIpChange(network);
3908        WifiConfiguration retrievedNetwork =
3909                mWifiConfigManager.getConfiguredNetwork(result.getNetworkId());
3910        assertFalse("Updating network credentials config should clear hasEverConnected.",
3911                retrievedNetwork.getNetworkSelectionStatus().getHasEverConnected());
3912        assertTrue(result.hasCredentialChanged());
3913    }
3914
3915    /**
3916     * Updates an existing network after connection using
3917     * {@link WifiConfigManager#updateNetworkAfterConnect(int)} and asserts that the
3918     * |HasEverConnected| flag is set to true.
3919     */
3920    private void verifyUpdateNetworkAfterConnectHasEverConnectedTrue(int networkId) {
3921        assertTrue(mWifiConfigManager.updateNetworkAfterConnect(networkId));
3922        WifiConfiguration retrievedNetwork = mWifiConfigManager.getConfiguredNetwork(networkId);
3923        assertTrue("hasEverConnected expected to be true after connection.",
3924                retrievedNetwork.getNetworkSelectionStatus().getHasEverConnected());
3925    }
3926
3927    /**
3928     * Sets up a user profiles for WifiConfigManager testing.
3929     *
3930     * @param userId Id of the user.
3931     */
3932    private void setupUserProfiles(int userId) {
3933        final UserInfo userInfo =
3934                new UserInfo(userId, Integer.toString(userId), UserInfo.FLAG_PRIMARY);
3935        List<UserInfo> userProfiles = Arrays.asList(userInfo);
3936        when(mUserManager.getProfiles(userId)).thenReturn(userProfiles);
3937        when(mUserManager.isUserUnlockingOrUnlocked(userId)).thenReturn(true);
3938    }
3939
3940}
3941