WifiBackupRestoreTest.java revision 7f2a1e30dd5d14320ffc7b185ac25fdb79fe52b0
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.net.IpConfiguration;
23import android.net.wifi.WifiConfiguration;
24import android.os.Process;
25import android.support.test.filters.SmallTest;
26
27import com.android.server.net.IpConfigStore;
28import com.android.server.wifi.util.WifiPermissionsUtil;
29
30import org.junit.After;
31import org.junit.Before;
32import org.junit.Test;
33import org.mockito.Mock;
34import org.mockito.MockitoAnnotations;
35
36import java.io.ByteArrayOutputStream;
37import java.io.DataOutputStream;
38import java.io.FileDescriptor;
39import java.io.IOException;
40import java.io.OutputStreamWriter;
41import java.io.PrintWriter;
42import java.io.StringWriter;
43import java.util.ArrayList;
44import java.util.HashMap;
45import java.util.List;
46import java.util.Map;
47import java.util.Random;
48
49/**
50 * Unit tests for {@link com.android.server.wifi.WifiBackupRestore}.
51 */
52@SmallTest
53public class WifiBackupRestoreTest {
54
55    private static final String WIFI_BACKUP_DATA_WITH_UNSUPPORTED_TAG =
56            "<?xml version='1.0' encoding='utf-8' standalone='yes' ?>"
57            + "<WifiBackupData>"
58            + "<int name=\"Version\" value=\"1\" />"
59            + "<NetworkList>"
60            + "<Network>"
61            + "<WifiConfiguration>"
62            + "<string name=\"ConfigKey\">&quot;GoogleGuest-Legacy&quot;NONE</string>"
63            + "<string name=\"SSID\">&quot;GoogleGuest-Legacy&quot;</string>"
64            + "<null name=\"BSSID\" />"
65            + "<null name=\"PreSharedKey\" />"
66            + "<null name=\"WEPKeys\" />"
67            + "<int name=\"WEPTxKeyIndex\" value=\"0\" />"
68            + "<boolean name=\"HiddenSSID\" value=\"false\" />"
69            + "<boolean name=\"RequirePMF\" value=\"false\" />"
70            + "<byte-array name=\"AllowedKeyMgmt\" num=\"1\">01</byte-array>"
71            + "<byte-array name=\"AllowedProtocols\" num=\"1\">03</byte-array>"
72            + "<byte-array name=\"AllowedAuthAlgos\" num=\"1\">01</byte-array>"
73            + "<byte-array name=\"AllowedGroupCiphers\" num=\"1\">0f</byte-array>"
74            + "<byte-array name=\"AllowedPairwiseCiphers\" num=\"1\">06</byte-array>"
75            + "<boolean name=\"Shared\" value=\"true\" />"
76            + "<null name=\"SimSlot\" />"
77            + "</WifiConfiguration>"
78            + "<IpConfiguration>"
79            + "<string name=\"IpAssignment\">DHCP</string>"
80            + "<string name=\"ProxySettings\">NONE</string>"
81            + "</IpConfiguration>"
82            + "</Network>"
83            + "</NetworkList>"
84            + "</WifiBackupData>";
85
86    @Mock WifiPermissionsUtil mWifiPermissionsUtil;
87    private WifiBackupRestore mWifiBackupRestore;
88    private boolean mCheckDump = true;
89
90    @Before
91    public void setUp() throws Exception {
92        MockitoAnnotations.initMocks(this);
93        when(mWifiPermissionsUtil.checkConfigOverridePermission(anyInt())).thenReturn(true);
94        mWifiBackupRestore = new WifiBackupRestore(mWifiPermissionsUtil);
95        // Enable verbose logging before tests to check the backup data dumps.
96        mWifiBackupRestore.enableVerboseLogging(1);
97    }
98
99    @After
100    public void cleanUp() throws Exception {
101        if (mCheckDump) {
102            StringWriter stringWriter = new StringWriter();
103            mWifiBackupRestore.dump(
104                    new FileDescriptor(), new PrintWriter(stringWriter), new String[0]);
105            String dumpString = stringWriter.toString();
106            // Ensure that the SSID was dumped out.
107            assertTrue("Dump: " + dumpString,
108                    dumpString.contains(WifiConfigurationTestUtil.TEST_SSID));
109            // Ensure that the password wasn't dumped out.
110            assertFalse("Dump: " + dumpString,
111                    dumpString.contains(WifiConfigurationTestUtil.TEST_PSK));
112            assertFalse("Dump: " + dumpString,
113                    dumpString.contains(WifiConfigurationTestUtil.TEST_WEP_KEYS[0]));
114            assertFalse("Dump: " + dumpString,
115                    dumpString.contains(WifiConfigurationTestUtil.TEST_WEP_KEYS[1]));
116            assertFalse("Dump: " + dumpString,
117                    dumpString.contains(WifiConfigurationTestUtil.TEST_WEP_KEYS[2]));
118            assertFalse("Dump: " + dumpString,
119                    dumpString.contains(WifiConfigurationTestUtil.TEST_WEP_KEYS[3]));
120        }
121    }
122
123    /**
124     * Verify that a null network list is serialized correctly.
125     */
126    @Test
127    public void testNullNetworkListBackup() {
128        byte[] backupData = mWifiBackupRestore.retrieveBackupDataFromConfigurations(null);
129        assertTrue(backupData != null);
130        assertEquals(backupData.length, 0);
131        // No valid data to check in dump.
132        mCheckDump = false;
133    }
134
135    /**
136     * Verify that a single open network configuration is serialized & deserialized correctly.
137     */
138    @Test
139    public void testSingleOpenNetworkBackupRestore() {
140        List<WifiConfiguration> configurations = new ArrayList<>();
141        configurations.add(WifiConfigurationTestUtil.createOpenNetwork());
142
143        byte[] backupData = mWifiBackupRestore.retrieveBackupDataFromConfigurations(configurations);
144        List<WifiConfiguration> retrievedConfigurations =
145                mWifiBackupRestore.retrieveConfigurationsFromBackupData(backupData);
146        WifiConfigurationTestUtil.assertConfigurationsEqualForBackup(
147                configurations, retrievedConfigurations);
148    }
149
150    /**
151     * Verify that a single open hidden network configuration is serialized & deserialized
152     * correctly.
153     */
154    @Test
155    public void testSingleOpenHiddenNetworkBackupRestore() {
156        List<WifiConfiguration> configurations = new ArrayList<>();
157        configurations.add(WifiConfigurationTestUtil.createOpenHiddenNetwork());
158
159        byte[] backupData = mWifiBackupRestore.retrieveBackupDataFromConfigurations(configurations);
160        List<WifiConfiguration> retrievedConfigurations =
161                mWifiBackupRestore.retrieveConfigurationsFromBackupData(backupData);
162        WifiConfigurationTestUtil.assertConfigurationsEqualForBackup(
163                configurations, retrievedConfigurations);
164    }
165
166    /**
167     * Verify that a single PSK network configuration is serialized & deserialized correctly.
168     */
169    @Test
170    public void testSinglePskNetworkBackupRestore() {
171        List<WifiConfiguration> configurations = new ArrayList<>();
172        configurations.add(WifiConfigurationTestUtil.createPskNetwork());
173
174        byte[] backupData = mWifiBackupRestore.retrieveBackupDataFromConfigurations(configurations);
175        List<WifiConfiguration> retrievedConfigurations =
176                mWifiBackupRestore.retrieveConfigurationsFromBackupData(backupData);
177        WifiConfigurationTestUtil.assertConfigurationsEqualForBackup(
178                configurations, retrievedConfigurations);
179    }
180
181    /**
182     * Verify that a single PSK hidden network configuration is serialized & deserialized correctly.
183     */
184    @Test
185    public void testSinglePskHiddenNetworkBackupRestore() {
186        List<WifiConfiguration> configurations = new ArrayList<>();
187        configurations.add(WifiConfigurationTestUtil.createPskHiddenNetwork());
188
189        byte[] backupData = mWifiBackupRestore.retrieveBackupDataFromConfigurations(configurations);
190        List<WifiConfiguration> retrievedConfigurations =
191                mWifiBackupRestore.retrieveConfigurationsFromBackupData(backupData);
192        WifiConfigurationTestUtil.assertConfigurationsEqualForBackup(
193                configurations, retrievedConfigurations);
194    }
195
196    /**
197     * Verify that a single WEP network configuration is serialized & deserialized correctly.
198     */
199    @Test
200    public void testSingleWepNetworkBackupRestore() {
201        List<WifiConfiguration> configurations = new ArrayList<>();
202        configurations.add(WifiConfigurationTestUtil.createWepNetwork());
203
204        byte[] backupData = mWifiBackupRestore.retrieveBackupDataFromConfigurations(configurations);
205        List<WifiConfiguration> retrievedConfigurations =
206                mWifiBackupRestore.retrieveConfigurationsFromBackupData(backupData);
207        WifiConfigurationTestUtil.assertConfigurationsEqualForBackup(
208                configurations, retrievedConfigurations);
209    }
210
211    /**
212     * Verify that restoring of configuration that contains unsupported tags works correctly
213     * (unsupported tags are ignored).
214     */
215    @Test
216    public void testConfigurationWithUnsupportedTagsRestore() {
217        List<WifiConfiguration> configurations = new ArrayList<>();
218        configurations.add(createNetworkForConfigurationWithUnsupportedTag());
219
220        byte[] backupData = WIFI_BACKUP_DATA_WITH_UNSUPPORTED_TAG.getBytes();
221        List<WifiConfiguration> retrievedConfigurations =
222                mWifiBackupRestore.retrieveConfigurationsFromBackupData(backupData);
223        WifiConfigurationTestUtil.assertConfigurationsEqualForBackup(
224                configurations, retrievedConfigurations);
225
226        // No valid data to check in dump.
227        mCheckDump = false;
228    }
229
230    /**
231     * Creates correct WiFiConfiguration that should be parsed out of
232     * {@link #WIFI_BACKUP_DATA_WITH_UNSUPPORTED_TAG} configuration which contains unsupported tag.
233     */
234    private static WifiConfiguration createNetworkForConfigurationWithUnsupportedTag() {
235        final WifiConfiguration config = new WifiConfiguration();
236        config.SSID = "\"GoogleGuest-Legacy\"";
237        config.wepTxKeyIndex = 0;
238        config.hiddenSSID = false;
239        config.requirePMF = false;
240        config.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.NONE);
241        config.allowedProtocols.set(WifiConfiguration.Protocol.WPA);
242        config.allowedProtocols.set(WifiConfiguration.Protocol.RSN);
243        config.allowedAuthAlgorithms.set(WifiConfiguration.AuthAlgorithm.OPEN);
244        config.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.WEP40);
245        config.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.WEP104);
246        config.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.TKIP);
247        config.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.CCMP);
248        config.allowedPairwiseCiphers.set(WifiConfiguration.PairwiseCipher.TKIP);
249        config.allowedPairwiseCiphers.set(WifiConfiguration.PairwiseCipher.CCMP);
250        config.shared = true;
251
252        IpConfiguration ipConfiguration = new IpConfiguration();
253        ipConfiguration.setIpAssignment(IpConfiguration.IpAssignment.DHCP);
254        ipConfiguration.setProxySettings(IpConfiguration.ProxySettings.NONE);
255        config.setIpConfiguration(ipConfiguration);
256
257        return config;
258    }
259
260    /**
261     * Verify that a single WEP network configuration with only 1 key is serialized & deserialized
262     * correctly.
263     */
264    @Test
265    public void testSingleWepNetworkWithSingleKeyBackupRestore() {
266        List<WifiConfiguration> configurations = new ArrayList<>();
267        configurations.add(WifiConfigurationTestUtil.createWepNetworkWithSingleKey());
268
269        byte[] backupData = mWifiBackupRestore.retrieveBackupDataFromConfigurations(configurations);
270        List<WifiConfiguration> retrievedConfigurations =
271                mWifiBackupRestore.retrieveConfigurationsFromBackupData(backupData);
272        WifiConfigurationTestUtil.assertConfigurationsEqualForBackup(
273                configurations, retrievedConfigurations);
274    }
275
276    /**
277     * Verify that a single enterprise network configuration is not serialized.
278     */
279    @Test
280    public void testSingleEnterpriseNetworkNotBackupRestore() {
281        List<WifiConfiguration> configurations = new ArrayList<>();
282        configurations.add(WifiConfigurationTestUtil.createEapNetwork());
283
284        byte[] backupData = mWifiBackupRestore.retrieveBackupDataFromConfigurations(configurations);
285        List<WifiConfiguration> retrievedConfigurations =
286                mWifiBackupRestore.retrieveConfigurationsFromBackupData(backupData);
287        assertTrue(retrievedConfigurations.isEmpty());
288        // No valid data to check in dump.
289        mCheckDump = false;
290    }
291
292    /**
293     * Verify that a single PSK network configuration with static ip/proxy settings is serialized &
294     * deserialized correctly.
295     */
296    @Test
297    public void testSinglePskNetworkWithStaticIpAndStaticProxyBackupRestore() {
298        List<WifiConfiguration> configurations = new ArrayList<>();
299        WifiConfiguration pskNetwork = WifiConfigurationTestUtil.createPskNetwork();
300        pskNetwork.setIpConfiguration(
301                WifiConfigurationTestUtil.createStaticIpConfigurationWithStaticProxy());
302        configurations.add(pskNetwork);
303
304        byte[] backupData = mWifiBackupRestore.retrieveBackupDataFromConfigurations(configurations);
305        List<WifiConfiguration> retrievedConfigurations =
306                mWifiBackupRestore.retrieveConfigurationsFromBackupData(backupData);
307        WifiConfigurationTestUtil.assertConfigurationsEqualForBackup(
308                configurations, retrievedConfigurations);
309    }
310
311    /**
312     * Verify that a single PSK network configuration with static ip & PAC proxy settings is
313     * serialized & deserialized correctly.
314     */
315    @Test
316    public void testSinglePskNetworkWithStaticIpAndPACProxyBackupRestore() {
317        List<WifiConfiguration> configurations = new ArrayList<>();
318        WifiConfiguration pskNetwork = WifiConfigurationTestUtil.createPskNetwork();
319        pskNetwork.setIpConfiguration(
320                WifiConfigurationTestUtil.createStaticIpConfigurationWithPacProxy());
321        configurations.add(pskNetwork);
322
323        byte[] backupData = mWifiBackupRestore.retrieveBackupDataFromConfigurations(configurations);
324        List<WifiConfiguration> retrievedConfigurations =
325                mWifiBackupRestore.retrieveConfigurationsFromBackupData(backupData);
326        WifiConfigurationTestUtil.assertConfigurationsEqualForBackup(
327                configurations, retrievedConfigurations);
328    }
329
330    /**
331     * Verify that a single PSK network configuration with DHCP ip & PAC proxy settings is
332     * serialized & deserialized correctly.
333     */
334    @Test
335    public void testSinglePskNetworkWithDHCPIpAndPACProxyBackupRestore() {
336        List<WifiConfiguration> configurations = new ArrayList<>();
337        WifiConfiguration pskNetwork = WifiConfigurationTestUtil.createPskNetwork();
338        pskNetwork.setIpConfiguration(
339                WifiConfigurationTestUtil.createDHCPIpConfigurationWithPacProxy());
340        configurations.add(pskNetwork);
341
342        byte[] backupData = mWifiBackupRestore.retrieveBackupDataFromConfigurations(configurations);
343        List<WifiConfiguration> retrievedConfigurations =
344                mWifiBackupRestore.retrieveConfigurationsFromBackupData(backupData);
345        WifiConfigurationTestUtil.assertConfigurationsEqualForBackup(
346                configurations, retrievedConfigurations);
347    }
348
349    /**
350     * Verify that a single PSK network configuration with partial static ip settings is serialized
351     * & deserialized correctly.
352     */
353    @Test
354    public void testSinglePskNetworkWithPartialStaticIpBackupRestore() {
355        List<WifiConfiguration> configurations = new ArrayList<>();
356        WifiConfiguration pskNetwork = WifiConfigurationTestUtil.createPskNetwork();
357        pskNetwork.setIpConfiguration(
358                WifiConfigurationTestUtil.createPartialStaticIpConfigurationWithPacProxy());
359        configurations.add(pskNetwork);
360
361        byte[] backupData = mWifiBackupRestore.retrieveBackupDataFromConfigurations(configurations);
362        List<WifiConfiguration> retrievedConfigurations =
363                mWifiBackupRestore.retrieveConfigurationsFromBackupData(backupData);
364        WifiConfigurationTestUtil.assertConfigurationsEqualForBackup(
365                configurations, retrievedConfigurations);
366    }
367
368    /**
369     * Verify that multiple networks of different types are serialized and deserialized correctly.
370     */
371    @Test
372    public void testMultipleNetworksAllBackupRestore() {
373        List<WifiConfiguration> configurations = new ArrayList<>();
374        configurations.add(WifiConfigurationTestUtil.createWepNetwork());
375        configurations.add(WifiConfigurationTestUtil.createWepNetwork());
376        configurations.add(WifiConfigurationTestUtil.createPskNetwork());
377        configurations.add(WifiConfigurationTestUtil.createOpenNetwork());
378
379        byte[] backupData = mWifiBackupRestore.retrieveBackupDataFromConfigurations(configurations);
380        List<WifiConfiguration> retrievedConfigurations =
381                mWifiBackupRestore.retrieveConfigurationsFromBackupData(backupData);
382        WifiConfigurationTestUtil.assertConfigurationsEqualForBackup(
383                configurations, retrievedConfigurations);
384    }
385
386    /**
387     * Verify that multiple networks of different types except enterprise ones are serialized and
388     * deserialized correctly
389     */
390    @Test
391    public void testMultipleNetworksNonEnterpriseBackupRestore() {
392        List<WifiConfiguration> configurations = new ArrayList<>();
393        List<WifiConfiguration> expectedConfigurations = new ArrayList<>();
394
395        WifiConfiguration wepNetwork = WifiConfigurationTestUtil.createWepNetwork();
396        configurations.add(wepNetwork);
397        expectedConfigurations.add(wepNetwork);
398
399        configurations.add(WifiConfigurationTestUtil.createEapNetwork());
400
401        WifiConfiguration pskNetwork = WifiConfigurationTestUtil.createPskNetwork();
402        configurations.add(pskNetwork);
403        expectedConfigurations.add(pskNetwork);
404
405        WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork();
406        configurations.add(openNetwork);
407        expectedConfigurations.add(openNetwork);
408
409        byte[] backupData = mWifiBackupRestore.retrieveBackupDataFromConfigurations(configurations);
410        List<WifiConfiguration> retrievedConfigurations =
411                mWifiBackupRestore.retrieveConfigurationsFromBackupData(backupData);
412        WifiConfigurationTestUtil.assertConfigurationsEqualForBackup(
413                expectedConfigurations, retrievedConfigurations);
414    }
415
416    /**
417     * Verify that multiple networks with different credential types and IpConfiguration types are
418     * serialized and deserialized correctly.
419     */
420    @Test
421    public void testMultipleNetworksWithDifferentIpConfigurationsAllBackupRestore() {
422        List<WifiConfiguration> configurations = new ArrayList<>();
423
424        WifiConfiguration wepNetwork = WifiConfigurationTestUtil.createWepNetwork();
425        wepNetwork.setIpConfiguration(
426                WifiConfigurationTestUtil.createDHCPIpConfigurationWithPacProxy());
427        configurations.add(wepNetwork);
428
429        WifiConfiguration pskNetwork = WifiConfigurationTestUtil.createPskNetwork();
430        pskNetwork.setIpConfiguration(
431                WifiConfigurationTestUtil.createStaticIpConfigurationWithPacProxy());
432        configurations.add(pskNetwork);
433
434        WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork();
435        openNetwork.setIpConfiguration(
436                WifiConfigurationTestUtil.createStaticIpConfigurationWithStaticProxy());
437        configurations.add(openNetwork);
438
439        byte[] backupData = mWifiBackupRestore.retrieveBackupDataFromConfigurations(configurations);
440        List<WifiConfiguration> retrievedConfigurations =
441                mWifiBackupRestore.retrieveConfigurationsFromBackupData(backupData);
442        WifiConfigurationTestUtil.assertConfigurationsEqualForBackup(
443                configurations, retrievedConfigurations);
444    }
445
446    /**
447     * Verify that multiple networks of different types except the non system app created ones are
448     * serialized and deserialized correctly.
449     */
450    @Test
451    public void testMultipleNetworksSystemAppBackupRestore() {
452        int systemAppUid = Process.SYSTEM_UID;
453        int nonSystemAppUid = Process.FIRST_APPLICATION_UID + 556;
454        when(mWifiPermissionsUtil.checkConfigOverridePermission(eq(systemAppUid)))
455                .thenReturn(true);
456        when(mWifiPermissionsUtil.checkConfigOverridePermission(eq(nonSystemAppUid)))
457                .thenReturn(false);
458
459        List<WifiConfiguration> configurations = new ArrayList<>();
460        List<WifiConfiguration> expectedConfigurations = new ArrayList<>();
461
462        WifiConfiguration wepNetwork = WifiConfigurationTestUtil.createWepNetwork();
463        wepNetwork.creatorUid = systemAppUid;
464        configurations.add(wepNetwork);
465        expectedConfigurations.add(wepNetwork);
466
467        // These should not be in |expectedConfigurations|.
468        WifiConfiguration nonSystemAppWepNetwork = WifiConfigurationTestUtil.createWepNetwork();
469        nonSystemAppWepNetwork.creatorUid = nonSystemAppUid;
470        configurations.add(nonSystemAppWepNetwork);
471
472        WifiConfiguration pskNetwork = WifiConfigurationTestUtil.createPskNetwork();
473        pskNetwork.creatorUid = systemAppUid;
474        configurations.add(pskNetwork);
475        expectedConfigurations.add(pskNetwork);
476
477        // These should not be in |expectedConfigurations|.
478        WifiConfiguration nonSystemAppPskNetwork = WifiConfigurationTestUtil.createPskNetwork();
479        nonSystemAppPskNetwork.creatorUid = nonSystemAppUid;
480        configurations.add(nonSystemAppPskNetwork);
481
482        WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork();
483        configurations.add(openNetwork);
484        expectedConfigurations.add(openNetwork);
485
486        byte[] backupData = mWifiBackupRestore.retrieveBackupDataFromConfigurations(configurations);
487        List<WifiConfiguration> retrievedConfigurations =
488                mWifiBackupRestore.retrieveConfigurationsFromBackupData(backupData);
489        WifiConfigurationTestUtil.assertConfigurationsEqualForBackup(
490                expectedConfigurations, retrievedConfigurations);
491    }
492
493    /**
494     * Verify that a single open network configuration is serialized & deserialized correctly from
495     * old backups.
496     */
497    @Test
498    public void testSingleOpenNetworkSupplicantBackupRestore() {
499        List<WifiConfiguration> configurations = new ArrayList<>();
500        configurations.add(WifiConfigurationTestUtil.createOpenNetwork());
501
502        byte[] supplicantData = createWpaSupplicantConfBackupData(configurations);
503        byte[] ipConfigData = createIpConfBackupData(configurations);
504        List<WifiConfiguration> retrievedConfigurations =
505                mWifiBackupRestore.retrieveConfigurationsFromSupplicantBackupData(
506                        supplicantData, ipConfigData);
507        WifiConfigurationTestUtil.assertConfigurationsEqualForBackup(
508                configurations, retrievedConfigurations);
509    }
510
511    /**
512     * Verify that a single open hidden network configuration is serialized & deserialized
513     * correctly from old backups.
514     */
515    @Test
516    public void testSingleOpenHiddenNetworkSupplicantBackupRestore() {
517        List<WifiConfiguration> configurations = new ArrayList<>();
518        configurations.add(WifiConfigurationTestUtil.createOpenHiddenNetwork());
519
520        byte[] supplicantData = createWpaSupplicantConfBackupData(configurations);
521        byte[] ipConfigData = createIpConfBackupData(configurations);
522        List<WifiConfiguration> retrievedConfigurations =
523                mWifiBackupRestore.retrieveConfigurationsFromSupplicantBackupData(
524                        supplicantData, ipConfigData);
525        WifiConfigurationTestUtil.assertConfigurationsEqualForBackup(
526                configurations, retrievedConfigurations);
527    }
528
529    /**
530     * Verify that a single PSK network configuration is serialized & deserialized correctly from
531     * old backups.
532     */
533    @Test
534    public void testSinglePskNetworkSupplicantBackupRestore() {
535        List<WifiConfiguration> configurations = new ArrayList<>();
536        configurations.add(WifiConfigurationTestUtil.createPskNetwork());
537
538        byte[] supplicantData = createWpaSupplicantConfBackupData(configurations);
539        byte[] ipConfigData = createIpConfBackupData(configurations);
540        List<WifiConfiguration> retrievedConfigurations =
541                mWifiBackupRestore.retrieveConfigurationsFromSupplicantBackupData(
542                        supplicantData, ipConfigData);
543        WifiConfigurationTestUtil.assertConfigurationsEqualForBackup(
544                configurations, retrievedConfigurations);
545    }
546
547    /**
548     * Verify that a single PSK hidden network configuration is serialized & deserialized correctly
549     * from old backups.
550     */
551    @Test
552    public void testSinglePskHiddenNetworkSupplicantBackupRestore() {
553        List<WifiConfiguration> configurations = new ArrayList<>();
554        configurations.add(WifiConfigurationTestUtil.createPskHiddenNetwork());
555
556        byte[] supplicantData = createWpaSupplicantConfBackupData(configurations);
557        byte[] ipConfigData = createIpConfBackupData(configurations);
558        List<WifiConfiguration> retrievedConfigurations =
559                mWifiBackupRestore.retrieveConfigurationsFromSupplicantBackupData(
560                        supplicantData, ipConfigData);
561        WifiConfigurationTestUtil.assertConfigurationsEqualForBackup(
562                configurations, retrievedConfigurations);
563    }
564
565    /**
566     * Verify that a single WEP network configuration is serialized & deserialized correctly from
567     * old backups.
568     */
569    @Test
570    public void testSingleWepNetworkSupplicantBackupRestore() {
571        List<WifiConfiguration> configurations = new ArrayList<>();
572        configurations.add(WifiConfigurationTestUtil.createWepNetwork());
573
574        byte[] supplicantData = createWpaSupplicantConfBackupData(configurations);
575        byte[] ipConfigData = createIpConfBackupData(configurations);
576        List<WifiConfiguration> retrievedConfigurations =
577                mWifiBackupRestore.retrieveConfigurationsFromSupplicantBackupData(
578                        supplicantData, ipConfigData);
579        WifiConfigurationTestUtil.assertConfigurationsEqualForBackup(
580                configurations, retrievedConfigurations);
581    }
582
583    /**
584     * Verify that a single WEP network configuration with only 1 key is serialized & deserialized
585     * correctly from old backups.
586     */
587    @Test
588    public void testSingleWepNetworkWithSingleKeySupplicantBackupRestore() {
589        List<WifiConfiguration> configurations = new ArrayList<>();
590        configurations.add(WifiConfigurationTestUtil.createWepNetworkWithSingleKey());
591
592        byte[] supplicantData = createWpaSupplicantConfBackupData(configurations);
593        byte[] ipConfigData = createIpConfBackupData(configurations);
594        List<WifiConfiguration> retrievedConfigurations =
595                mWifiBackupRestore.retrieveConfigurationsFromSupplicantBackupData(
596                        supplicantData, ipConfigData);
597        WifiConfigurationTestUtil.assertConfigurationsEqualForBackup(
598                configurations, retrievedConfigurations);
599    }
600
601    /**
602     * Verify that a single enterprise network configuration is not serialized from old backups.
603     */
604    @Test
605    public void testSingleEnterpriseNetworkNotSupplicantBackupRestore() {
606        List<WifiConfiguration> configurations = new ArrayList<>();
607        configurations.add(WifiConfigurationTestUtil.createEapNetwork());
608
609        byte[] supplicantData = createWpaSupplicantConfBackupData(configurations);
610        byte[] ipConfigData = createIpConfBackupData(configurations);
611        List<WifiConfiguration> retrievedConfigurations =
612                mWifiBackupRestore.retrieveConfigurationsFromSupplicantBackupData(
613                        supplicantData, ipConfigData);
614        assertTrue(retrievedConfigurations.isEmpty());
615    }
616
617    /**
618     * Verify that multiple networks with different credential types and IpConfiguration types are
619     * serialized and deserialized correctly from old backups
620     */
621    @Test
622    public void testMultipleNetworksWithDifferentIpConfigurationsAllSupplicantBackupRestore() {
623        List<WifiConfiguration> configurations = new ArrayList<>();
624
625        WifiConfiguration wepNetwork = WifiConfigurationTestUtil.createWepNetwork();
626        wepNetwork.setIpConfiguration(
627                WifiConfigurationTestUtil.createDHCPIpConfigurationWithPacProxy());
628        configurations.add(wepNetwork);
629
630        WifiConfiguration pskNetwork = WifiConfigurationTestUtil.createPskNetwork();
631        pskNetwork.setIpConfiguration(
632                WifiConfigurationTestUtil.createStaticIpConfigurationWithPacProxy());
633        configurations.add(pskNetwork);
634
635        WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork();
636        openNetwork.setIpConfiguration(
637                WifiConfigurationTestUtil.createStaticIpConfigurationWithStaticProxy());
638        configurations.add(openNetwork);
639
640        byte[] supplicantData = createWpaSupplicantConfBackupData(configurations);
641        byte[] ipConfigData = createIpConfBackupData(configurations);
642        List<WifiConfiguration> retrievedConfigurations =
643                mWifiBackupRestore.retrieveConfigurationsFromSupplicantBackupData(
644                        supplicantData, ipConfigData);
645        WifiConfigurationTestUtil.assertConfigurationsEqualForBackup(
646                configurations, retrievedConfigurations);
647    }
648
649    /**
650     * Verify that a single open network configuration is serialized & deserialized correctly from
651     * old backups with no ipconfig data.
652     */
653    @Test
654    public void testSingleOpenNetworkSupplicantBackupRestoreWithNoIpConfigData() {
655        List<WifiConfiguration> configurations = new ArrayList<>();
656        configurations.add(WifiConfigurationTestUtil.createOpenNetwork());
657
658        byte[] supplicantData = createWpaSupplicantConfBackupData(configurations);
659        List<WifiConfiguration> retrievedConfigurations =
660                mWifiBackupRestore.retrieveConfigurationsFromSupplicantBackupData(
661                        supplicantData, null);
662        WifiConfigurationTestUtil.assertConfigurationsEqualForBackup(
663                configurations, retrievedConfigurations);
664    }
665
666    /**
667     * Verify that multiple networks with different credential types are serialized and
668     * deserialized correctly from old backups with no ipconfig data.
669     */
670    @Test
671    public void testMultipleNetworksAllSupplicantBackupRestoreWithNoIpConfigData() {
672        List<WifiConfiguration> configurations = new ArrayList<>();
673
674        WifiConfiguration wepNetwork = WifiConfigurationTestUtil.createWepNetwork();
675        configurations.add(wepNetwork);
676
677        WifiConfiguration pskNetwork = WifiConfigurationTestUtil.createPskNetwork();
678        configurations.add(pskNetwork);
679
680        WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork();
681        configurations.add(openNetwork);
682
683        byte[] supplicantData = createWpaSupplicantConfBackupData(configurations);
684        List<WifiConfiguration> retrievedConfigurations =
685                mWifiBackupRestore.retrieveConfigurationsFromSupplicantBackupData(
686                        supplicantData, null);
687        WifiConfigurationTestUtil.assertConfigurationsEqualForBackup(
688                configurations, retrievedConfigurations);
689    }
690
691    /**
692     * Verify that multiple networks of different types except the non system app created ones are
693     * serialized and deserialized correctly from old backups.
694     */
695    @Test
696    public void testMultipleNetworksSystemAppSupplicantBackupRestore() {
697        List<WifiConfiguration> configurations = new ArrayList<>();
698        List<WifiConfiguration> expectedConfigurations = new ArrayList<>();
699
700        WifiConfiguration wepNetwork = WifiConfigurationTestUtil.createWepNetwork();
701        configurations.add(wepNetwork);
702        expectedConfigurations.add(wepNetwork);
703
704        // These should not be in |expectedConfigurations|.
705        WifiConfiguration nonSystemAppWepNetwork = WifiConfigurationTestUtil.createWepNetwork();
706        nonSystemAppWepNetwork.creatorUid = Process.FIRST_APPLICATION_UID;
707        configurations.add(nonSystemAppWepNetwork);
708
709        WifiConfiguration pskNetwork = WifiConfigurationTestUtil.createPskNetwork();
710        configurations.add(pskNetwork);
711        expectedConfigurations.add(pskNetwork);
712
713        // These should not be in |expectedConfigurations|.
714        WifiConfiguration nonSystemAppPskNetwork = WifiConfigurationTestUtil.createPskNetwork();
715        nonSystemAppPskNetwork.creatorUid = Process.FIRST_APPLICATION_UID + 1;
716        configurations.add(nonSystemAppPskNetwork);
717
718        WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork();
719        configurations.add(openNetwork);
720        expectedConfigurations.add(openNetwork);
721
722        byte[] supplicantData = createWpaSupplicantConfBackupData(configurations);
723        byte[] ipConfigData = createIpConfBackupData(configurations);
724        List<WifiConfiguration> retrievedConfigurations =
725                mWifiBackupRestore.retrieveConfigurationsFromSupplicantBackupData(
726                        supplicantData, ipConfigData);
727        WifiConfigurationTestUtil.assertConfigurationsEqualForBackup(
728                expectedConfigurations, retrievedConfigurations);
729    }
730
731    /**
732     * Verifying that backup data containing some unknown keys is properly restored.
733     * The backup data used here is a PII masked version of a backup data seen in a reported bug.
734     */
735    @Test
736    public void testSingleNetworkSupplicantBackupRestoreWithUnknownEAPKey() {
737        String backupSupplicantConfNetworkBlock = "network={\n"
738                + "ssid=" + WifiConfigurationTestUtil.TEST_SSID + "\n"
739                + "psk=" + WifiConfigurationTestUtil.TEST_PSK + "\n"
740                + "key_mgmt=WPA-PSK WPA-PSK-SHA256\n"
741                + "priority=18\n"
742                + "id_str=\"%7B%22creatorUid%22%3A%221000%22%2C%22configKey"
743                + "%22%3A%22%5C%22BLAH%5C%22WPA_PSK%22%7D\"\n"
744                + "eapRetryCount=6\n";
745        byte[] supplicantData = backupSupplicantConfNetworkBlock.getBytes();
746        List<WifiConfiguration> retrievedConfigurations =
747                mWifiBackupRestore.retrieveConfigurationsFromSupplicantBackupData(
748                        supplicantData, null);
749
750        final WifiConfiguration expectedConfiguration = new WifiConfiguration();
751        expectedConfiguration.SSID = WifiConfigurationTestUtil.TEST_SSID;
752        expectedConfiguration.preSharedKey = WifiConfigurationTestUtil.TEST_PSK;
753        expectedConfiguration.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.WPA_PSK);
754
755        ArrayList<WifiConfiguration> expectedConfigurations = new ArrayList<WifiConfiguration>() {{
756                add(expectedConfiguration);
757            }};
758        WifiConfigurationTestUtil.assertConfigurationsEqualForBackup(
759                expectedConfigurations, retrievedConfigurations);
760    }
761
762    /**
763     * Verify that any corrupted data provided by Backup/Restore is ignored correctly.
764     */
765    @Test
766    public void testCorruptBackupRestore() {
767        Random random = new Random();
768        byte[] backupData = new byte[100];
769        random.nextBytes(backupData);
770
771        List<WifiConfiguration> retrievedConfigurations =
772                mWifiBackupRestore.retrieveConfigurationsFromBackupData(backupData);
773        assertNull(retrievedConfigurations);
774        // No valid data to check in dump.
775        mCheckDump = false;
776    }
777
778    /**
779     * Helper method to write a list of networks in wpa_supplicant.conf format to the output stream.
780     */
781    private byte[] createWpaSupplicantConfBackupData(List<WifiConfiguration> configurations) {
782        ByteArrayOutputStream bos = new ByteArrayOutputStream();
783        OutputStreamWriter out = new OutputStreamWriter(bos);
784        try {
785            for (WifiConfiguration configuration : configurations) {
786                writeConfigurationToWpaSupplicantConf(out, configuration);
787            }
788            out.flush();
789            return bos.toByteArray();
790        } catch (IOException e) {
791            return null;
792        }
793    }
794
795    /**
796     * Helper method to write a network in wpa_supplicant.conf format to the output stream.
797     * This was created using a sample wpa_supplicant.conf file. Using the raw key strings here
798     * (instead of consts in WifiBackupRestore).
799     */
800    private void writeConfigurationToWpaSupplicantConf(
801            OutputStreamWriter out, WifiConfiguration configuration)
802            throws IOException {
803        out.write("network={\n");
804        out.write("        " + "ssid=" + configuration.SSID + "\n");
805        String allowedKeyManagement = "";
806        if (configuration.hiddenSSID) {
807            out.write("        " + "scan_ssid=1" + "\n");
808        }
809        if (configuration.allowedKeyManagement.get(WifiConfiguration.KeyMgmt.NONE)) {
810            allowedKeyManagement += "NONE";
811        }
812        if (configuration.allowedKeyManagement.get(WifiConfiguration.KeyMgmt.WPA_PSK)) {
813            allowedKeyManagement += "WPA-PSK ";
814        }
815        if (configuration.allowedKeyManagement.get(WifiConfiguration.KeyMgmt.WPA_EAP)) {
816            allowedKeyManagement += "WPA-EAP ";
817        }
818        if (configuration.allowedKeyManagement.get(WifiConfiguration.KeyMgmt.IEEE8021X)) {
819            allowedKeyManagement += "IEEE8021X ";
820        }
821        out.write("        " + "key_mgmt=" + allowedKeyManagement + "\n");
822        if (configuration.preSharedKey != null) {
823            out.write("        " + "psk=" + configuration.preSharedKey + "\n");
824        }
825        if (configuration.wepKeys[0] != null) {
826            out.write("        " + "wep_key0=" + configuration.wepKeys[0] + "\n");
827        }
828        if (configuration.wepKeys[1] != null) {
829            out.write("        " + "wep_key1=" + configuration.wepKeys[1] + "\n");
830        }
831        if (configuration.wepKeys[2] != null) {
832            out.write("        " + "wep_key2=" + configuration.wepKeys[2] + "\n");
833        }
834        if (configuration.wepKeys[3] != null) {
835            out.write("        " + "wep_key3=" + configuration.wepKeys[3] + "\n");
836        }
837        if (configuration.wepKeys[0] != null || configuration.wepKeys[1] != null
838                || configuration.wepKeys[2] != null || configuration.wepKeys[3] != null) {
839            out.write("        " + "wep_tx_keyidx=" + configuration.wepTxKeyIndex + "\n");
840        }
841        Map<String, String> extras = new HashMap<>();
842        extras.put(SupplicantStaNetworkHal.ID_STRING_KEY_CONFIG_KEY, configuration.configKey());
843        extras.put(SupplicantStaNetworkHal.ID_STRING_KEY_CREATOR_UID,
844                Integer.toString(configuration.creatorUid));
845        String idString = "\"" + SupplicantStaNetworkHal.createNetworkExtra(extras) + "\"";
846        if (idString != null) {
847            out.write("        " + "id_str=" + idString + "\n");
848        }
849        out.write("}\n");
850        out.write("\n");
851    }
852
853    /**
854     * Helper method to write a list of networks in ipconfig.txt format to the output stream.
855     */
856    private byte[] createIpConfBackupData(List<WifiConfiguration> configurations) {
857        ByteArrayOutputStream bos = new ByteArrayOutputStream();
858        DataOutputStream out = new DataOutputStream(bos);
859        try {
860            // write version first.
861            out.writeInt(2);
862            for (WifiConfiguration configuration : configurations) {
863                IpConfigStore.writeConfig(out, configuration.configKey().hashCode(),
864                        configuration.getIpConfiguration());
865            }
866            out.flush();
867            return bos.toByteArray();
868        } catch (IOException e) {
869            return null;
870        }
871    }
872}
873