From 0a0b5035ce8013ed327a0802357a1b7df3061912 Mon Sep 17 00:00:00 2001 From: Peter Qiu Date: Tue, 7 Feb 2017 12:46:22 -0800 Subject: Wifi configuration store data refactor Currently, the unified config store files contained data for network list and deleted ephemeral SSID list. Since both of them are owned by WifiConfigManager, it is tightly integrated into WifiConfigManager, results in complexities when need to add new data that's not owned by WifiConfigManager (e.g. Passpoint configurations) to the store file. To reduce the complexity, an abstraction is provided for the store data to be persist to the store files. Any interested module can register its own store data to the store file. Then at read/ write time, WifiConfigStore will iterate through each registered store data to deserialize/serialize configuration data from/to a XML block, to be persist to the store file. So each StoreData is responsible for serialization/deserialization of a XML block denoted by its tag. For example, WifiNetworkListStoreData is responsible for the XML block under tag . Bug: 31065385 Test: frameworks/opt/net/wifi/tests/wifitests/runtests.sh Test: Manual test to verify saved networks are persisted over boots Test: Manual test to verify migration of legacy store file still works Test: Regression integration test Change-Id: I83c2eb7cd907188f392b5179405f19182ee13bb9 --- .../wifi/DeletedEphemeralSsidsStoreDataTest.java | 178 ++++++++ .../server/wifi/NetworkListStoreDataTest.java | 414 +++++++++++++++++++ .../android/server/wifi/WifiConfigManagerTest.java | 220 +++++----- .../server/wifi/WifiConfigStoreDataTest.java | 446 --------------------- .../android/server/wifi/WifiConfigStoreTest.java | 399 +++++++++++++++--- 5 files changed, 1051 insertions(+), 606 deletions(-) create mode 100644 tests/wifitests/src/com/android/server/wifi/DeletedEphemeralSsidsStoreDataTest.java create mode 100644 tests/wifitests/src/com/android/server/wifi/NetworkListStoreDataTest.java delete mode 100644 tests/wifitests/src/com/android/server/wifi/WifiConfigStoreDataTest.java (limited to 'tests') diff --git a/tests/wifitests/src/com/android/server/wifi/DeletedEphemeralSsidsStoreDataTest.java b/tests/wifitests/src/com/android/server/wifi/DeletedEphemeralSsidsStoreDataTest.java new file mode 100644 index 000000000..0db93f598 --- /dev/null +++ b/tests/wifitests/src/com/android/server/wifi/DeletedEphemeralSsidsStoreDataTest.java @@ -0,0 +1,178 @@ +/* + * Copyright (C) 2017 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.android.server.wifi; + +import static org.junit.Assert.*; +import static org.mockito.Mockito.*; + +import android.test.suitebuilder.annotation.SmallTest; +import android.util.Xml; + +import com.android.internal.util.FastXmlSerializer; + +import org.junit.Before; +import org.junit.Test; +import org.xmlpull.v1.XmlPullParser; +import org.xmlpull.v1.XmlPullParserException; +import org.xmlpull.v1.XmlSerializer; + +import java.io.ByteArrayInputStream; +import java.io.ByteArrayOutputStream; +import java.nio.charset.StandardCharsets; +import java.util.Arrays; +import java.util.HashSet; +import java.util.Set; + +/** + * Unit tests for {@link com.android.server.wifi.DeletedEphemeralSsidsStoreData}. + */ +@SmallTest +public class DeletedEphemeralSsidsStoreDataTest { + private static final String TEST_SSID1 = "SSID 1"; + private static final String TEST_SSID2 = "SSID 2"; + private static final String TEST_SSID_LIST_XML_STRING = + "\n" + + "" + TEST_SSID1 + "\n" + + "" + TEST_SSID2 + "\n" + + "\n"; + private static final byte[] TEST_SSID_LIST_XML_BYTES = + TEST_SSID_LIST_XML_STRING.getBytes(StandardCharsets.UTF_8); + private DeletedEphemeralSsidsStoreData mDeletedEphemeralSsidsStoreData; + + @Before + public void setUp() throws Exception { + mDeletedEphemeralSsidsStoreData = new DeletedEphemeralSsidsStoreData(); + } + + /** + * Helper function for serializing configuration data to a XML block. + * + * @param shared Flag indicating serializing shared or user configurations + * @return byte[] of the XML data + * @throws Exception + */ + private byte[] serializeData(boolean shared) throws Exception { + final XmlSerializer out = new FastXmlSerializer(); + final ByteArrayOutputStream outputStream = new ByteArrayOutputStream(); + out.setOutput(outputStream, StandardCharsets.UTF_8.name()); + mDeletedEphemeralSsidsStoreData.serializeData(out, shared); + out.flush(); + return outputStream.toByteArray(); + } + + /** + * Helper function for parsing configuration data from a XML block. + * + * @param data XML data to parse from + * @param shared Flag indicating parsing of shared or user configurations + * @return SSID list + * @throws Exception + */ + private Set deserializeData(byte[] data, boolean shared) throws Exception { + final XmlPullParser in = Xml.newPullParser(); + final ByteArrayInputStream inputStream = new ByteArrayInputStream(data); + in.setInput(inputStream, StandardCharsets.UTF_8.name()); + mDeletedEphemeralSsidsStoreData.deserializeData(in, in.getDepth(), shared); + return mDeletedEphemeralSsidsStoreData.getSsidList(); + } + + /** + * Verify that a XmlPullParserException will be thrown when attempting to serialize SSID list + * to the share store, since the deleted ephemeral SSID list should never be persist + * to the share store. + * + * @throws Exception + */ + @Test(expected = XmlPullParserException.class) + public void serializeShareData() throws Exception { + serializeData(true /* shared */); + } + + /** + * Verify that a XmlPullParserException will be thrown when attempting to parse SSID list + * from the share store, since the deleted ephemeral SSID list should never be persist + * to the share store. + * + * @throws Exception + */ + @Test(expected = XmlPullParserException.class) + public void deserializeShareData() throws Exception { + deserializeData(new byte[0], true /* shared */); + } + + /** + * Verify that serializing the user store data without any configuration doesn't cause any + * crash and no data should be serialized. + * + * @throws Exception + */ + @Test + public void serializeEmptyConfigs() throws Exception { + assertEquals(0, serializeData(false /* shared */).length); + } + + /** + * Verify that parsing an empty data doesn't cause any crash and no configuration should + * be deserialized. + * + * @throws Exception + */ + @Test + public void deserializeEmptyData() throws Exception { + assertTrue(deserializeData(new byte[0], false /* shared */).isEmpty()); + } + + /** + * Verify that DeletedEphemeralSsidsStoreData does not support share data. + * + * @throws Exception + */ + @Test + public void supportShareData() throws Exception { + assertFalse(mDeletedEphemeralSsidsStoreData.supportShareData()); + } + + /** + * Verify that user store SSID list is serialized correctly, matches the predefined test + * XML data. + * + * @throws Exception + */ + @Test + public void serializeSsidList() throws Exception { + Set ssidList = new HashSet<>(); + ssidList.add(TEST_SSID1); + ssidList.add(TEST_SSID2); + mDeletedEphemeralSsidsStoreData.setSsidList(ssidList); + byte[] actualData = serializeData(false /* shared */); + assertTrue(Arrays.equals(TEST_SSID_LIST_XML_BYTES, actualData)); + } + + /** + * Verify that user store SSID list is deserialized correctly using the predefined test XML + * data. + * + * @throws Exception + */ + @Test + public void deserializeSsidList() throws Exception { + Set ssidList = new HashSet<>(); + ssidList.add(TEST_SSID1); + ssidList.add(TEST_SSID2); + assertEquals(ssidList, deserializeData(TEST_SSID_LIST_XML_BYTES, false /* shared */)); + } +} diff --git a/tests/wifitests/src/com/android/server/wifi/NetworkListStoreDataTest.java b/tests/wifitests/src/com/android/server/wifi/NetworkListStoreDataTest.java new file mode 100644 index 000000000..a1f0057e2 --- /dev/null +++ b/tests/wifitests/src/com/android/server/wifi/NetworkListStoreDataTest.java @@ -0,0 +1,414 @@ +/* + * Copyright (C) 2017 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.android.server.wifi; + +import static org.junit.Assert.*; +import static org.mockito.Mockito.*; + +import android.net.wifi.WifiConfiguration; +import android.test.suitebuilder.annotation.SmallTest; +import android.util.Xml; + +import com.android.internal.util.FastXmlSerializer; + +import org.junit.Before; +import org.junit.Test; +import org.xmlpull.v1.XmlPullParser; +import org.xmlpull.v1.XmlPullParserException; +import org.xmlpull.v1.XmlSerializer; + +import java.io.ByteArrayInputStream; +import java.io.ByteArrayOutputStream; +import java.nio.charset.StandardCharsets; +import java.util.ArrayList; +import java.util.Arrays; +import java.util.List; + +/** + * Unit tests for {@link com.android.server.wifi.NetworksListStoreData}. + */ +@SmallTest +public class NetworkListStoreDataTest { + + private static final String TEST_SSID = "WifiConfigStoreDataSSID_"; + private static final String TEST_CONNECT_CHOICE = "XmlUtilConnectChoice"; + private static final long TEST_CONNECT_CHOICE_TIMESTAMP = 0x4566; + private static final String SINGLE_OPEN_NETWORK_DATA_XML_STRING_FORMAT = + "\n" + + "\n" + + "%s\n" + + "%s\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "01\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "NETWORK_SELECTION_ENABLED\n" + + "NETWORK_SELECTION_ENABLE\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "DHCP\n" + + "NONE\n" + + "\n" + + "\n"; + + private static final String SINGLE_EAP_NETWORK_DATA_XML_STRING_FORMAT = + "\n" + + "\n" + + "%s\n" + + "%s\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "0c\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "NETWORK_SELECTION_ENABLED\n" + + "NETWORK_SELECTION_ENABLE\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "DHCP\n" + + "NONE\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n"; + + private NetworkListStoreData mNetworkListStoreData; + + @Before + public void setUp() throws Exception { + mNetworkListStoreData = new NetworkListStoreData(); + } + + /** + * Helper function for serializing configuration data to a XML block. + * + * @param shared Flag indicating serializing shared or user configurations + * @return byte[] of the XML data + * @throws Exception + */ + private byte[] serializeData(boolean shared) throws Exception { + final XmlSerializer out = new FastXmlSerializer(); + final ByteArrayOutputStream outputStream = new ByteArrayOutputStream(); + out.setOutput(outputStream, StandardCharsets.UTF_8.name()); + mNetworkListStoreData.serializeData(out, shared); + out.flush(); + return outputStream.toByteArray(); + } + + /** + * Helper function for parsing configuration data from a XML block. + * + * @param data XML data to parse from + * @param shared Flag indicating parsing of shared or user configurations + * @return List of WifiConfiguration parsed + * @throws Exception + */ + private List deserializeData(byte[] data, boolean shared) throws Exception { + final XmlPullParser in = Xml.newPullParser(); + final ByteArrayInputStream inputStream = new ByteArrayInputStream(data); + in.setInput(inputStream, StandardCharsets.UTF_8.name()); + mNetworkListStoreData.deserializeData(in, in.getDepth(), shared); + if (shared) { + return mNetworkListStoreData.getSharedConfigurations(); + } else { + return mNetworkListStoreData.getUserConfigurations(); + } + } + + /** + * Helper function for generating a network list for testing purpose. The network list + * will contained an open and an EAP network. + * + * @param shared Flag indicating shared network + * @return List of WifiConfiguration + */ + private List getTestNetworksConfig(boolean shared) { + WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork(); + openNetwork.shared = shared; + openNetwork.setIpConfiguration( + WifiConfigurationTestUtil.createDHCPIpConfigurationWithNoProxy()); + WifiConfiguration eapNetwork = WifiConfigurationTestUtil.createEapNetwork(); + eapNetwork.shared = shared; + eapNetwork.setIpConfiguration( + WifiConfigurationTestUtil.createDHCPIpConfigurationWithNoProxy()); + List networkList = new ArrayList<>(); + networkList.add(openNetwork); + networkList.add(eapNetwork); + return networkList; + } + + /** + * Helper function for generating XML block containing two networks, an open and an EAP + * network. + * + * @param openNetwork The WifiConfiguration for an open network + * @param eapNetwork The WifiConfiguration for an EAP network + * @return byte[] of the XML data + */ + private byte[] getTestNetworksXmlBytes(WifiConfiguration openNetwork, + WifiConfiguration eapNetwork) { + String openNetworkXml = String.format(SINGLE_OPEN_NETWORK_DATA_XML_STRING_FORMAT, + openNetwork.configKey().replaceAll("\"", """), + openNetwork.SSID.replaceAll("\"", """), + openNetwork.shared, openNetwork.creatorUid); + String eapNetworkXml = String.format(SINGLE_EAP_NETWORK_DATA_XML_STRING_FORMAT, + eapNetwork.configKey().replaceAll("\"", """), + eapNetwork.SSID.replaceAll("\"", """), + eapNetwork.shared, eapNetwork.creatorUid); + return (openNetworkXml + eapNetworkXml).getBytes(StandardCharsets.UTF_8); + } + + /** + * Verify that serializing the store data without any configuration doesn't cause any crash + * and no data should be serialized. + * + * @throws Exception + */ + @Test + public void serializeEmptyConfigs() throws Exception { + assertEquals(0, serializeData(true /* shared */).length); + assertEquals(0, serializeData(false /* shared */).length); + } + + /** + * Verify that parsing an empty data doesn't cause any crash and no configuration should + * be parsed. + * + * @throws Exception + */ + @Test + public void deserializeEmptyData() throws Exception { + assertTrue(deserializeData(new byte[0], true /* shared */).isEmpty()); + assertTrue(deserializeData(new byte[0], false /* shared */).isEmpty()); + } + + /** + * Verify that NetworkListStoreData does support share data. + * + * @throws Exception + */ + @Test + public void supportShareData() throws Exception { + assertTrue(mNetworkListStoreData.supportShareData()); + } + + /** + * Verify that the shared configurations (containing an open and an EAP network) are serialized + * correctly, matching the expected XML string. + * + * @throws Exception + */ + @Test + public void serializeSharedConfigurations() throws Exception { + List networkList = getTestNetworksConfig(true /* shared */); + mNetworkListStoreData.setSharedConfigurations(networkList); + byte[] expectedData = getTestNetworksXmlBytes(networkList.get(0), networkList.get(1)); + assertTrue(Arrays.equals(expectedData, serializeData(true /* shared */))); + } + + /** + * Verify that the shared configurations are parsed correctly from a XML string containing + * test networks (an open and an EAP network). + * @throws Exception + */ + @Test + public void deserializeSharedConfigurations() throws Exception { + List networkList = getTestNetworksConfig(true /* shared */); + byte[] xmlData = getTestNetworksXmlBytes(networkList.get(0), networkList.get(1)); + WifiConfigurationTestUtil.assertConfigurationsEqualForConfigStore( + networkList, deserializeData(xmlData, true /* shared */)); + } + + /** + * Verify that the user configurations (containing an open and an EAP network) are serialized + * correctly, matching the expected XML string. + * + * @throws Exception + */ + @Test + public void serializeUserConfigurations() throws Exception { + List networkList = getTestNetworksConfig(false /* shared */); + mNetworkListStoreData.setUserConfigurations(networkList); + byte[] expectedData = getTestNetworksXmlBytes(networkList.get(0), networkList.get(1)); + assertTrue(Arrays.equals(expectedData, serializeData(false /* shared */))); + } + + /** + * Verify that the user configurations are parsed correctly from a XML string containing + * test networks (an open and an EAP network). + * @throws Exception + */ + @Test + public void deserializeUserConfigurations() throws Exception { + List networkList = getTestNetworksConfig(false /* shared */); + byte[] xmlData = getTestNetworksXmlBytes(networkList.get(0), networkList.get(1)); + WifiConfigurationTestUtil.assertConfigurationsEqualForConfigStore( + networkList, deserializeData(xmlData, false /* shared */)); + } + + /** + * Verify that a XmlPullParserException will be thrown when parsing a block + * containing an unknown tag. + * + * @throws Exception + */ + @Test(expected = XmlPullParserException.class) + public void parseNetworkWithUnknownTag() throws Exception { + String configFormat = + "\n" + + "\n" + + "%s\n" + + "%s\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "01\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "NETWORK_SELECTION_ENABLED\n" + + "NETWORK_SELECTION_ENABLE\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "DHCP\n" + + "NONE\n" + + "\n" + + "" // Unknown tag. + + "\n" + + "" + + "\n"; + WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork(); + byte[] xmlData = String.format(configFormat, + openNetwork.configKey().replaceAll("\"", """), + openNetwork.SSID.replaceAll("\"", """), + openNetwork.shared, openNetwork.creatorUid).getBytes(StandardCharsets.UTF_8); + deserializeData(xmlData, true); + } + + /** + * Verify that a XmlPullParseException will be thrown when parsing a network configuration + * containing a mismatched config key. + * + * @throws Exception + */ + @Test(expected = XmlPullParserException.class) + public void parseNetworkWithMismatchConfigKey() throws Exception { + WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork(); + byte[] xmlData = String.format(SINGLE_OPEN_NETWORK_DATA_XML_STRING_FORMAT, + "InvalidConfigKey", + openNetwork.SSID.replaceAll("\"", """), + openNetwork.shared, openNetwork.creatorUid).getBytes(StandardCharsets.UTF_8); + deserializeData(xmlData, true); + } +} diff --git a/tests/wifitests/src/com/android/server/wifi/WifiConfigManagerTest.java b/tests/wifitests/src/com/android/server/wifi/WifiConfigManagerTest.java index 8c0163dda..892081423 100644 --- a/tests/wifitests/src/com/android/server/wifi/WifiConfigManagerTest.java +++ b/tests/wifitests/src/com/android/server/wifi/WifiConfigManagerTest.java @@ -40,6 +40,7 @@ import android.os.UserManager; import android.telephony.TelephonyManager; import android.test.suitebuilder.annotation.SmallTest; import android.text.TextUtils; +import android.util.Pair; import com.android.internal.R; import com.android.server.wifi.WifiConfigStoreLegacy.WifiConfigStoreDataLegacy; @@ -103,9 +104,12 @@ public class WifiConfigManagerTest { @Mock private PackageManager mPackageManager; @Mock private DevicePolicyManagerInternal mDevicePolicyManagerInternal; @Mock private WifiPermissionsWrapper mWifiPermissionsWrapper; + @Mock private NetworkListStoreData mNetworkListStoreData; + @Mock private DeletedEphemeralSsidsStoreData mDeletedEphemeralSsidsStoreData; private MockResources mResources; private InOrder mContextConfigStoreMockOrder; + private InOrder mNetworkListStoreDataMockOrder; private WifiConfigManager mWifiConfigManager; /** @@ -118,6 +122,7 @@ public class WifiConfigManagerTest { // Set up the inorder for verifications. This is needed to verify that the broadcasts, // store writes for network updates followed by network additions are in the expected order. mContextConfigStoreMockOrder = inOrder(mContext, mWifiConfigStore); + mNetworkListStoreDataMockOrder = inOrder(mNetworkListStoreData); // Set up the package name stuff & permission override. when(mContext.getPackageManager()).thenReturn(mPackageManager); @@ -173,9 +178,6 @@ public class WifiConfigManagerTest { .thenReturn(true); when(mWifiConfigStore.areStoresPresent()).thenReturn(true); - when(mWifiConfigStore.read()) - .thenReturn(new WifiConfigStoreData(new ArrayList(), - new ArrayList(), new HashSet())); when(mDevicePolicyManagerInternal.isActiveAdminWithPolicy(anyInt(), anyInt())) .thenReturn(false); @@ -285,9 +287,13 @@ public class WifiConfigManagerTest { assertTrue(addNetworkToWifiConfigManager(openNetwork).isSuccess()); // The open network addition should trigger a store write. - WifiConfigStoreData storeData = captureWriteStoreData(); - assertFalse(isNetworkInConfigStoreData(ephemeralNetwork, storeData)); - assertTrue(isNetworkInConfigStoreData(openNetwork, storeData)); + Pair, List> networkListStoreData = + captureWriteNetworksListStoreData(); + List networkList = new ArrayList<>(); + networkList.addAll(networkListStoreData.first); + networkList.addAll(networkListStoreData.second); + assertFalse(isNetworkInConfigStoreData(ephemeralNetwork, networkList)); + assertTrue(isNetworkInConfigStoreData(openNetwork, networkList)); } /** @@ -1822,10 +1828,9 @@ public class WifiConfigManagerTest { add(user1Network); } }; - WifiConfigStoreData loadStoreData = - new WifiConfigStoreData(sharedNetworks, user1Networks, new HashSet()); - when(mWifiConfigStore.read()).thenReturn(loadStoreData); + setupStoreDataForRead(sharedNetworks, user1Networks, new HashSet()); assertTrue(mWifiConfigManager.loadFromStore()); + verify(mWifiConfigStore).read(); // Fetch the network ID's assigned to the shared networks initially. int sharedNetwork1Id = WifiConfiguration.INVALID_NETWORK_ID; @@ -1848,14 +1853,11 @@ public class WifiConfigManagerTest { add(user2Network); } }; - WifiConfigStoreData newUserStoreData = - new WifiConfigStoreData(new ArrayList(), user2Networks, - new HashSet()); - when(mWifiConfigStore.switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class))) - .thenReturn(newUserStoreData); + setupStoreDataForUserRead(user2Networks, new HashSet()); // Now switch the user to user 2 and ensure that shared network's IDs have not changed. when(mUserManager.isUserUnlockingOrUnlocked(user2)).thenReturn(true); mWifiConfigManager.handleUserSwitch(user2); + verify(mWifiConfigStore).switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class)); // Again fetch the network ID's assigned to the shared networks and ensure they have not // changed. @@ -1908,10 +1910,9 @@ public class WifiConfigManagerTest { add(user1Network); } }; - WifiConfigStoreData loadStoreData = - new WifiConfigStoreData(sharedNetworks, user1Networks, new HashSet()); - when(mWifiConfigStore.read()).thenReturn(loadStoreData); + setupStoreDataForRead(sharedNetworks, user1Networks, new HashSet()); assertTrue(mWifiConfigManager.loadFromStore()); + verify(mWifiConfigStore).read(); // Fetch the network ID assigned to the user 1 network initially. int user1NetworkId = WifiConfiguration.INVALID_NETWORK_ID; @@ -1929,14 +1930,11 @@ public class WifiConfigManagerTest { add(user2Network); } }; - WifiConfigStoreData newUserStoreData = - new WifiConfigStoreData(new ArrayList(), user2Networks, - new HashSet()); - when(mWifiConfigStore.switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class))) - .thenReturn(newUserStoreData); + setupStoreDataForUserRead(user2Networks, new HashSet()); // Now switch the user to user 2 and ensure that user 1's private network has been removed. when(mUserManager.isUserUnlockingOrUnlocked(user2)).thenReturn(true); Set removedNetworks = mWifiConfigManager.handleUserSwitch(user2); + verify(mWifiConfigStore).switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class)); assertTrue((removedNetworks.size() == 1) && (removedNetworks.contains(user1NetworkId))); // Set the expected networks to be |sharedNetwork| and |user2Network|. @@ -1983,11 +1981,10 @@ public class WifiConfigManagerTest { add(sharedNetwork); } }; - WifiConfigStoreData loadStoreData = - new WifiConfigStoreData(sharedNetworks, new ArrayList(), - new HashSet()); - when(mWifiConfigStore.read()).thenReturn(loadStoreData); + setupStoreDataForRead(sharedNetworks, new ArrayList(), + new HashSet()); assertTrue(mWifiConfigManager.loadFromStore()); + verify(mWifiConfigStore).read(); // Set up the user 2 store data that is loaded at user switch. List user2Networks = new ArrayList() { @@ -1995,14 +1992,11 @@ public class WifiConfigManagerTest { add(user2Network); } }; - WifiConfigStoreData newUserStoreData = - new WifiConfigStoreData(new ArrayList(), user2Networks, - new HashSet()); - when(mWifiConfigStore.switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class))) - .thenReturn(newUserStoreData); + setupStoreDataForUserRead(user2Networks, new HashSet()); // Now switch the user to user 2 and ensure that no private network has been removed. when(mUserManager.isUserUnlockingOrUnlocked(user2)).thenReturn(true); Set removedNetworks = mWifiConfigManager.handleUserSwitch(user2); + verify(mWifiConfigStore).switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class)); assertTrue(removedNetworks.isEmpty()); } @@ -2040,11 +2034,10 @@ public class WifiConfigManagerTest { add(user2Network); } }; - WifiConfigStoreData loadStoreData = - new WifiConfigStoreData(sharedNetworks, new ArrayList(), - new HashSet()); - when(mWifiConfigStore.read()).thenReturn(loadStoreData); + setupStoreDataForRead(sharedNetworks, new ArrayList(), + new HashSet()); assertTrue(mWifiConfigManager.loadFromStore()); + verify(mWifiConfigStore).read(); // Set up the user store data that is loaded at user unlock. List userNetworks = new ArrayList() { @@ -2052,19 +2045,17 @@ public class WifiConfigManagerTest { add(user1Network); } }; - WifiConfigStoreData unlockLoadStoreData = - new WifiConfigStoreData(new ArrayList(), userNetworks, - new HashSet()); - when(mWifiConfigStore.switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class))) - .thenReturn(unlockLoadStoreData); + setupStoreDataForUserRead(userNetworks, new HashSet()); mWifiConfigManager.handleUserUnlock(user1); + verify(mWifiConfigStore).switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class)); // Capture the written data for the user 1 and ensure that it corresponds to what was // setup. - WifiConfigStoreData writtenStoreData = captureWriteStoreData(); + Pair, List> writtenNetworkList = + captureWriteNetworksListStoreData(); WifiConfigurationTestUtil.assertConfigurationsEqualForConfigManagerAddOrUpdate( - sharedNetworks, writtenStoreData.getSharedConfigurations()); + sharedNetworks, writtenNetworkList.first); WifiConfigurationTestUtil.assertConfigurationsEqualForConfigManagerAddOrUpdate( - userNetworks, writtenStoreData.getUserConfigurations()); + userNetworks, writtenNetworkList.second); // Now switch the user to user2 and ensure that user 2's private network has been moved to // the user store. @@ -2087,19 +2078,19 @@ public class WifiConfigManagerTest { }; // Capture the first written data triggered for saving the old user's network // configurations. - writtenStoreData = captureWriteStoreData(); + writtenNetworkList = captureWriteNetworksListStoreData(); WifiConfigurationTestUtil.assertConfigurationsEqualForConfigManagerAddOrUpdate( - sharedNetworks, writtenStoreData.getSharedConfigurations()); + sharedNetworks, writtenNetworkList.first); WifiConfigurationTestUtil.assertConfigurationsEqualForConfigManagerAddOrUpdate( - userNetworks, writtenStoreData.getUserConfigurations()); + userNetworks, writtenNetworkList.second); // Now capture the next written data triggered after the switch and ensure that user 2's // network is now in user store data. - writtenStoreData = captureWriteStoreData(); + writtenNetworkList = captureWriteNetworksListStoreData(); WifiConfigurationTestUtil.assertConfigurationsEqualForConfigManagerAddOrUpdate( - expectedSharedNetworks, writtenStoreData.getSharedConfigurations()); + expectedSharedNetworks, writtenNetworkList.first); WifiConfigurationTestUtil.assertConfigurationsEqualForConfigManagerAddOrUpdate( - expectedUserNetworks, writtenStoreData.getUserConfigurations()); + expectedUserNetworks, writtenNetworkList.second); } /** @@ -2116,11 +2107,7 @@ public class WifiConfigManagerTest { // Set up the internal data first. assertTrue(mWifiConfigManager.loadFromStore()); - when(mWifiConfigStore.switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class))) - .thenReturn(new WifiConfigStoreData( - new ArrayList(), new ArrayList(), - new HashSet())); - + setupStoreDataForUserRead(new ArrayList(), new HashSet()); // user2 is unlocked and switched to foreground. when(mUserManager.isUserUnlockingOrUnlocked(user2)).thenReturn(true); mWifiConfigManager.handleUserSwitch(user2); @@ -2155,11 +2142,7 @@ public class WifiConfigManagerTest { mContextConfigStoreMockOrder.verify(mWifiConfigStore, never()) .switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class)); - when(mWifiConfigStore.switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class))) - .thenReturn(new WifiConfigStoreData( - new ArrayList(), new ArrayList(), - new HashSet())); - + setupStoreDataForUserRead(new ArrayList(), new HashSet()); // Unlock the user2 and ensure that we read the data now. mWifiConfigManager.handleUserUnlock(user2); mContextConfigStoreMockOrder.verify(mWifiConfigStore) @@ -2186,8 +2169,7 @@ public class WifiConfigManagerTest { mWifiConfigManager.handleUserStop(user1); mContextConfigStoreMockOrder.verify(mWifiConfigStore, never()) .switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class)); - mContextConfigStoreMockOrder.verify(mWifiConfigStore).write( - anyBoolean(), any(WifiConfigStoreData.class)); + mContextConfigStoreMockOrder.verify(mWifiConfigStore).write(anyBoolean()); } /** @@ -2201,23 +2183,17 @@ public class WifiConfigManagerTest { // Set up the internal data first. assertTrue(mWifiConfigManager.loadFromStore()); mContextConfigStoreMockOrder.verify(mWifiConfigStore).read(); - mContextConfigStoreMockOrder.verify(mWifiConfigStore, never()) - .write(anyBoolean(), any(WifiConfigStoreData.class)); + mContextConfigStoreMockOrder.verify(mWifiConfigStore, never()).write(anyBoolean()); mContextConfigStoreMockOrder.verify(mWifiConfigStore, never()) .switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class)); - when(mWifiConfigStore.switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class))) - .thenReturn(new WifiConfigStoreData( - new ArrayList(), new ArrayList(), - new HashSet())); - + setupStoreDataForUserRead(new ArrayList(), new HashSet()); // Unlock the user1 (default user) for the first time and ensure that we read the data. mWifiConfigManager.handleUserUnlock(user1); mContextConfigStoreMockOrder.verify(mWifiConfigStore, never()).read(); mContextConfigStoreMockOrder.verify(mWifiConfigStore) .switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class)); - mContextConfigStoreMockOrder.verify(mWifiConfigStore) - .write(anyBoolean(), any(WifiConfigStoreData.class)); + mContextConfigStoreMockOrder.verify(mWifiConfigStore).write(anyBoolean()); } /** @@ -2233,23 +2209,17 @@ public class WifiConfigManagerTest { // data. mWifiConfigManager.handleUserUnlock(user1); mContextConfigStoreMockOrder.verify(mWifiConfigStore, never()).read(); - mContextConfigStoreMockOrder.verify(mWifiConfigStore, never()) - .write(anyBoolean(), any(WifiConfigStoreData.class)); + mContextConfigStoreMockOrder.verify(mWifiConfigStore, never()).write(anyBoolean()); mContextConfigStoreMockOrder.verify(mWifiConfigStore, never()) .switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class)); - when(mWifiConfigStore.switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class))) - .thenReturn(new WifiConfigStoreData( - new ArrayList(), new ArrayList(), - new HashSet())); - + setupStoreDataForUserRead(new ArrayList(), new HashSet()); // Read from store now. assertTrue(mWifiConfigManager.loadFromStore()); mContextConfigStoreMockOrder.verify(mWifiConfigStore).read(); mContextConfigStoreMockOrder.verify(mWifiConfigStore) .switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class)); - mContextConfigStoreMockOrder.verify(mWifiConfigStore) - .write(anyBoolean(), any(WifiConfigStoreData.class)); + mContextConfigStoreMockOrder.verify(mWifiConfigStore).write(anyBoolean()); } /** @@ -2265,11 +2235,7 @@ public class WifiConfigManagerTest { // Set up the internal data first. assertTrue(mWifiConfigManager.loadFromStore()); - when(mWifiConfigStore.switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class))) - .thenReturn(new WifiConfigStoreData( - new ArrayList(), new ArrayList(), - new HashSet())); - + setupStoreDataForUserRead(new ArrayList(), new HashSet()); // user2 is unlocked and switched to foreground. when(mUserManager.isUserUnlockingOrUnlocked(user2)).thenReturn(true); mWifiConfigManager.handleUserSwitch(user2); @@ -2297,8 +2263,7 @@ public class WifiConfigManagerTest { mWifiConfigManager.handleUserSwitch(user2); mContextConfigStoreMockOrder.verify(mWifiConfigStore, never()) .switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class)); - mContextConfigStoreMockOrder.verify(mWifiConfigStore, never()) - .write(anyBoolean(), any(WifiConfigStoreData.class)); + mContextConfigStoreMockOrder.verify(mWifiConfigStore, never()).write(anyBoolean()); } /** @@ -2314,8 +2279,7 @@ public class WifiConfigManagerTest { mWifiConfigManager.handleUserUnlock(user1); mContextConfigStoreMockOrder.verify(mWifiConfigStore, never()) .switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class)); - mContextConfigStoreMockOrder.verify(mWifiConfigStore, never()) - .write(anyBoolean(), any(WifiConfigStoreData.class)); + mContextConfigStoreMockOrder.verify(mWifiConfigStore, never()).write(anyBoolean()); } /** @@ -2439,10 +2403,7 @@ public class WifiConfigManagerTest { verify(mWifiConfigStore, never()).read(); verify(mWifiConfigStoreLegacy, never()).read(); - when(mWifiConfigStore.switchUserStoreAndRead(any(WifiConfigStore.StoreFile.class))) - .thenReturn(new WifiConfigStoreData( - new ArrayList(), new ArrayList(), - new HashSet())); + setupStoreDataForUserRead(new ArrayList(), new HashSet()); // Now switch the user to user 2. when(mUserManager.isUserUnlockingOrUnlocked(user2)).thenReturn(true); mWifiConfigManager.handleUserSwitch(user2); @@ -2563,8 +2524,7 @@ public class WifiConfigManagerTest { // This should have triggered 2 buffered writes. 1 for setting the connect choice, 1 for // clearing it after network removal. - mContextConfigStoreMockOrder.verify(mWifiConfigStore, times(2)) - .write(eq(false), any(WifiConfigStoreData.class)); + mContextConfigStoreMockOrder.verify(mWifiConfigStore, times(2)).write(eq(false)); } /** @@ -3147,7 +3107,8 @@ public class WifiConfigManagerTest { new WifiConfigManager( mContext, mFrameworkFacade, mClock, mUserManager, mTelephonyManager, mWifiKeyStore, mWifiConfigStore, mWifiConfigStoreLegacy, - mWifiPermissionsWrapper); + mWifiPermissionsWrapper, mNetworkListStoreData, + mDeletedEphemeralSsidsStoreData); mWifiConfigManager.enableVerboseLogging(1); } @@ -3270,15 +3231,22 @@ public class WifiConfigManagerTest { } /** - * Helper method to capture the store data written in WifiConfigStore.write() method. + * Helper method to capture the networks list store data that will be written by + * WifiConfigStore.write() method. */ - private WifiConfigStoreData captureWriteStoreData() { + private Pair, List> + captureWriteNetworksListStoreData() { try { - ArgumentCaptor storeDataCaptor = - ArgumentCaptor.forClass(WifiConfigStoreData.class); - mContextConfigStoreMockOrder.verify(mWifiConfigStore) - .write(anyBoolean(), storeDataCaptor.capture()); - return storeDataCaptor.getValue(); + ArgumentCaptor sharedConfigsCaptor = + ArgumentCaptor.forClass(ArrayList.class); + ArgumentCaptor userConfigsCaptor = + ArgumentCaptor.forClass(ArrayList.class); + mNetworkListStoreDataMockOrder.verify(mNetworkListStoreData) + .setSharedConfigurations(sharedConfigsCaptor.capture()); + mNetworkListStoreDataMockOrder.verify(mNetworkListStoreData) + .setUserConfigurations(userConfigsCaptor.capture()); + mContextConfigStoreMockOrder.verify(mWifiConfigStore).write(anyBoolean()); + return Pair.create(sharedConfigsCaptor.getValue(), userConfigsCaptor.getValue()); } catch (Exception e) { fail("Exception encountered during write " + e); } @@ -3289,20 +3257,24 @@ public class WifiConfigManagerTest { * Returns whether the provided network was in the store data or not. */ private boolean isNetworkInConfigStoreData(WifiConfiguration configuration) { - WifiConfigStoreData storeData = captureWriteStoreData(); - if (storeData == null) { + Pair, List> networkListStoreData = + captureWriteNetworksListStoreData(); + if (networkListStoreData == null) { return false; } - return isNetworkInConfigStoreData(configuration, storeData); + List networkList = new ArrayList<>(); + networkList.addAll(networkListStoreData.first); + networkList.addAll(networkListStoreData.second); + return isNetworkInConfigStoreData(configuration, networkList); } /** * Returns whether the provided network was in the store data or not. */ private boolean isNetworkInConfigStoreData( - WifiConfiguration configuration, WifiConfigStoreData storeData) { + WifiConfiguration configuration, List networkList) { boolean foundNetworkInStoreData = false; - for (WifiConfiguration retrievedConfig : storeData.getConfigurations()) { + for (WifiConfiguration retrievedConfig : networkList) { if (retrievedConfig.configKey().equals(configuration.configKey())) { foundNetworkInStoreData = true; break; @@ -3311,6 +3283,28 @@ public class WifiConfigManagerTest { return foundNetworkInStoreData; } + /** + * Setup expectations for WifiNetworksListStoreData and DeletedEphemeralSsidsStoreData + * after WifiConfigStore#read. + */ + private void setupStoreDataForRead(List sharedConfigurations, + List userConfigurations, Set deletedEphemeralSsids) { + when(mNetworkListStoreData.getSharedConfigurations()) + .thenReturn(sharedConfigurations); + when(mNetworkListStoreData.getUserConfigurations()).thenReturn(userConfigurations); + when(mDeletedEphemeralSsidsStoreData.getSsidList()).thenReturn(deletedEphemeralSsids); + } + + /** + * Setup expectations for WifiNetworksListStoreData and DeletedEphemeralSsidsStoreData + * after WifiConfigStore#switchUserStoreAndRead. + */ + private void setupStoreDataForUserRead(List userConfigurations, + Set deletedEphemeralSsids) { + when(mNetworkListStoreData.getUserConfigurations()).thenReturn(userConfigurations); + when(mDeletedEphemeralSsidsStoreData.getSsidList()).thenReturn(deletedEphemeralSsids); + } + /** * Verifies that the provided network was not present in the last config store write. */ @@ -3441,8 +3435,7 @@ public class WifiConfigManagerTest { verifyNetworkAddBroadcast(configuration); // Ensure that the write was not invoked for ephemeral network addition. - mContextConfigStoreMockOrder.verify(mWifiConfigStore, never()) - .write(anyBoolean(), any(WifiConfigStoreData.class)); + mContextConfigStoreMockOrder.verify(mWifiConfigStore, never()).write(anyBoolean()); return result; } @@ -3462,8 +3455,7 @@ public class WifiConfigManagerTest { any(WifiConfiguration.class)); verifyNetworkAddBroadcast(configuration); // Ensure that the write was not invoked for Passpoint network addition. - mContextConfigStoreMockOrder.verify(mWifiConfigStore, never()) - .write(anyBoolean(), any(WifiConfigStoreData.class)); + mContextConfigStoreMockOrder.verify(mWifiConfigStore, never()).write(anyBoolean()); return result; } @@ -3541,8 +3533,7 @@ public class WifiConfigManagerTest { verifyNetworkRemoveBroadcast(configuration); // Ensure that the write was not invoked for ephemeral network remove. - mContextConfigStoreMockOrder.verify(mWifiConfigStore, never()) - .write(anyBoolean(), any(WifiConfigStoreData.class)); + mContextConfigStoreMockOrder.verify(mWifiConfigStore, never()).write(anyBoolean()); } /** @@ -3556,8 +3547,7 @@ public class WifiConfigManagerTest { verify(mWifiKeyStore, never()).removeKeys(any(WifiEnterpriseConfig.class)); verifyNetworkRemoveBroadcast(configuration); // Ensure that the write was not invoked for Passpoint network remove. - mContextConfigStoreMockOrder.verify(mWifiConfigStore, never()) - .write(anyBoolean(), any(WifiConfigStoreData.class)); + mContextConfigStoreMockOrder.verify(mWifiConfigStore, never()).write(anyBoolean()); } /** diff --git a/tests/wifitests/src/com/android/server/wifi/WifiConfigStoreDataTest.java b/tests/wifitests/src/com/android/server/wifi/WifiConfigStoreDataTest.java deleted file mode 100644 index 3fa5d3dab..000000000 --- a/tests/wifitests/src/com/android/server/wifi/WifiConfigStoreDataTest.java +++ /dev/null @@ -1,446 +0,0 @@ -/* - * Copyright (C) 2016 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -package com.android.server.wifi; - -import static org.junit.Assert.*; -import static org.mockito.Mockito.*; - -import android.net.wifi.WifiConfiguration; -import android.net.wifi.WifiEnterpriseConfig; -import android.net.wifi.WifiConfiguration.NetworkSelectionStatus; -import android.test.suitebuilder.annotation.SmallTest; - -import org.junit.Test; -import org.xmlpull.v1.XmlPullParserException; - -import java.io.IOException; -import java.nio.charset.StandardCharsets; -import java.util.ArrayList; -import java.util.Arrays; -import java.util.HashSet; -import java.util.List; -import java.util.Random; -import java.util.Set; - -/** - * Unit tests for {@link com.android.server.wifi.WifiConfigStoreData}. - */ -@SmallTest -public class WifiConfigStoreDataTest { - - private static final String TEST_SSID = "WifiConfigStoreDataSSID_"; - private static final String TEST_CONNECT_CHOICE = "XmlUtilConnectChoice"; - private static final long TEST_CONNECT_CHOICE_TIMESTAMP = 0x4566; - private static final Set TEST_DELETED_EPHEMERAL_LIST = new HashSet() { - { - add("\"" + TEST_SSID + "1\""); - add("\"" + TEST_SSID + "2\""); - } - }; - private static final String SINGLE_OPEN_NETWORK_LIST_XML_STRING_FORMAT = - "\n" - + "\n" - + "\n" - + "%s\n" - + "%s\n" - + "\n" - + "\n" - + "\n" - + "\n" - + "\n" - + "\n" - + "01\n" - + "\n" - + "\n" - + "\n" - + "\n" - + "\n" - + "\n" - + "\n" - + "\n" - + "\n" - + "\n" - + "\n" - + "\n" - + "\n" - + "\n" - + "\n" - + "\n" - + "\n" - + "\n" - + "\n" - + "\n" - + "\n" - + "\n" - + "\n" - + "NETWORK_SELECTION_ENABLED\n" - + "NETWORK_SELECTION_ENABLE\n" - + "\n" - + "\n" - + "\n" - + "\n" - + "\n" - + "DHCP\n" - + "NONE\n" - + "\n" - + "\n" - + "\n"; - private static final String SINGLE_OPEN_NETWORK_SHARED_DATA_XML_STRING_FORMAT = - "\n" - + "\n" - + "\n" - + SINGLE_OPEN_NETWORK_LIST_XML_STRING_FORMAT - + "\n"; - private static final String SINGLE_OPEN_NETWORK_USER_DATA_XML_STRING_FORMAT = - "\n" - + "\n" - + "\n" - + SINGLE_OPEN_NETWORK_LIST_XML_STRING_FORMAT - + "\n" - + "\n" - + "\n" - + "\n"; - - /** - * Asserts that the 2 config store data are equal. - */ - public static void assertConfigStoreDataEqual( - WifiConfigStoreData expected, WifiConfigStoreData actual) { - WifiConfigurationTestUtil.assertConfigurationsEqualForConfigStore( - expected.getConfigurations(), actual.getConfigurations()); - assertEquals(expected.getDeletedEphemeralSSIDs(), actual.getDeletedEphemeralSSIDs()); - } - - /** - * Verify that multiple shared networks with different credential types and IpConfiguration - * types are serialized and deserialized correctly. - */ - @Test - public void testMultipleNetworkAllShared() - throws XmlPullParserException, IOException { - List configurations = createNetworks(true); - serializeDeserializeConfigStoreData(configurations, new ArrayList()); - } - - /** - * Verify that multiple user networks with different credential types and IpConfiguration - * types are serialized and deserialized correctly. - */ - @Test - public void testMultipleNetworksAllUser() - throws XmlPullParserException, IOException { - List configurations = createNetworks(false); - serializeDeserializeConfigStoreData(new ArrayList(), configurations); - } - - /** - * Verify that multiple networks with different credential types and IpConfiguration - * types are serialized and deserialized correctly when both user & shared networks are present. - */ - @Test - public void testMultipleNetworksSharedAndUserNetworks() - throws XmlPullParserException, IOException { - List configurations = createNetworks(); - // Let's split the list of networks into 2 and make all the networks in the first list - // shared and the second list all user networks. - int listSize = configurations.size(); - List sharedConfigurations = configurations.subList(0, listSize / 2); - List userConfigurations = configurations.subList(listSize / 2, listSize); - for (WifiConfiguration config : sharedConfigurations) { - config.shared = true; - } - for (WifiConfiguration config : userConfigurations) { - config.shared = false; - } - serializeDeserializeConfigStoreData(sharedConfigurations, userConfigurations); - } - - /** - * Verify that multiple shared networks with different credential types and IpConfiguration - * types are serialized and deserialized correctly when the shared data bytes are null in - * |parseRawData| method. - */ - @Test - public void testMultipleNetworksSharedDataNullInParseRawData() - throws XmlPullParserException, IOException { - List configurations = createNetworks(false); - serializeDeserializeConfigStoreData( - new ArrayList(), configurations, true, false); - } - - /** - * Verify that multiple shared networks with different credential types and IpConfiguration - * types are serialized and deserialized correctly when the user data bytes are null in - * |parseRawData| method. - */ - @Test - public void testMultipleNetworksUserDataNullInParseRawData() - throws XmlPullParserException, IOException { - List configurations = createNetworks(true); - serializeDeserializeConfigStoreData( - configurations, new ArrayList(), false, true); - } - - /** - * Verify that a network with invalid entepriseConfig data is serialized/deserialized - * correctly. - */ - @Test - public void testInvalidEnterpriseConfig() - throws XmlPullParserException, IOException { - WifiConfiguration eapNetwork = WifiConfigurationTestUtil.createEapNetwork(); - eapNetwork.enterpriseConfig = new WifiEnterpriseConfig(); - List configurations = Arrays.asList(eapNetwork); - serializeDeserializeConfigStoreData( - new ArrayList(), configurations, false, false); - } - - /** - * Verify that the manually populated xml string for is deserialized/serialized correctly. - * This generates a store data corresponding to the XML string and verifies that the string - * is indeed parsed correctly to the store data. - */ - @Test - public void testManualConfigStoreDataParse() { - WifiConfiguration sharedNetwork = WifiConfigurationTestUtil.createOpenNetwork(); - sharedNetwork.shared = true; - sharedNetwork.setIpConfiguration(WifiConfigurationTestUtil.createDHCPIpConfigurationWithNoProxy()); - WifiConfiguration userNetwork = WifiConfigurationTestUtil.createOpenNetwork(); - userNetwork.setIpConfiguration(WifiConfigurationTestUtil.createDHCPIpConfigurationWithNoProxy()); - userNetwork.shared = false; - - // Create the store data for comparison. - List sharedNetworks = new ArrayList<>(); - List userNetworks = new ArrayList<>(); - sharedNetworks.add(sharedNetwork); - userNetworks.add(userNetwork); - WifiConfigStoreData storeData = - new WifiConfigStoreData(sharedNetworks, userNetworks, new HashSet()); - - String sharedStoreXmlString = - String.format(SINGLE_OPEN_NETWORK_SHARED_DATA_XML_STRING_FORMAT, - sharedNetwork.configKey().replaceAll("\"", """), - sharedNetwork.SSID.replaceAll("\"", """), - sharedNetwork.shared, sharedNetwork.creatorUid); - String userStoreXmlString = - String.format(SINGLE_OPEN_NETWORK_USER_DATA_XML_STRING_FORMAT, - userNetwork.configKey().replaceAll("\"", """), - userNetwork.SSID.replaceAll("\"", """), - userNetwork.shared, userNetwork.creatorUid); - byte[] rawSharedData = sharedStoreXmlString.getBytes(); - byte[] rawUserData = userStoreXmlString.getBytes(); - WifiConfigStoreData retrievedStoreData = null; - try { - retrievedStoreData = WifiConfigStoreData.parseRawData(rawSharedData, rawUserData); - } catch (Exception e) { - // Assert if an exception was raised. - fail("Error in parsing the xml data: " + e - + ". Shared data: " + sharedStoreXmlString - + ", User data: " + userStoreXmlString); - } - // Compare the retrieved config store data with the original. - assertConfigStoreDataEqual(storeData, retrievedStoreData); - - // Now convert the store data to XML bytes and compare the output with the expected string. - byte[] retrievedSharedStoreXmlBytes = null; - byte[] retrievedUserStoreXmlBytes = null; - try { - retrievedSharedStoreXmlBytes = retrievedStoreData.createSharedRawData(); - retrievedUserStoreXmlBytes = retrievedStoreData.createUserRawData(); - } catch (Exception e) { - // Assert if an exception was raised. - fail("Error in writing the xml data: " + e); - } - String retrievedSharedStoreXmlString = - new String(retrievedSharedStoreXmlBytes, StandardCharsets.UTF_8); - String retrievedUserStoreXmlString = - new String(retrievedUserStoreXmlBytes, StandardCharsets.UTF_8); - assertEquals("Retrieved: " + retrievedSharedStoreXmlString - + ", Expected: " + sharedStoreXmlString, - sharedStoreXmlString, retrievedSharedStoreXmlString); - assertEquals("Retrieved: " + retrievedUserStoreXmlString - + ", Expected: " + userStoreXmlString, - userStoreXmlString, retrievedUserStoreXmlString); - } - - /** - * Verify that XML with corrupted version provided to WifiConfigStoreData is ignored correctly. - */ - @Test - public void testCorruptVersionConfigStoreData() { - String storeDataAsString = - "\n" - + "\n" - + "\n" - + "\n"; - byte[] rawData = storeDataAsString.getBytes(); - try { - WifiConfigStoreData storeData = WifiConfigStoreData.parseRawData(rawData, rawData); - } catch (Exception e) { - return; - } - // Assert if there was no exception was raised. - fail(); - } - - /** - * Verify that XML with no network list provided to WifiConfigStoreData is ignored correctly. - */ - @Test - public void testCorruptNetworkListConfigStoreData() { - String storeDataAsString = - "\n" - + "\n" - + "\n" - + "\n"; - byte[] rawData = storeDataAsString.getBytes(); - try { - WifiConfigStoreData storeData = WifiConfigStoreData.parseRawData(rawData, rawData); - } catch (Exception e) { - return; - } - // Assert if there was no exception was raised. - fail(); - } - - /** - * Verify that any corrupted data provided to WifiConfigStoreData is ignored correctly. - */ - @Test - public void testRandomCorruptConfigStoreData() { - Random random = new Random(); - byte[] rawData = new byte[100]; - random.nextBytes(rawData); - try { - WifiConfigStoreData storeData = WifiConfigStoreData.parseRawData(rawData, rawData); - } catch (Exception e) { - return; - } - // Assert if there was no exception was raised. - fail(); - } - - /** - * Helper method to add 4 networks with different credential types, IpConfiguration - * types for all tests in the class. - * - * @return - */ - private List createNetworks() { - List configurations = new ArrayList<>(); - - WifiConfiguration wepNetwork = WifiConfigurationTestUtil.createWepNetwork(); - wepNetwork.setIpConfiguration(WifiConfigurationTestUtil.createDHCPIpConfigurationWithPacProxy()); - wepNetwork.getNetworkSelectionStatus().setNetworkSelectionStatus( - NetworkSelectionStatus.NETWORK_SELECTION_ENABLED); - configurations.add(wepNetwork); - - WifiConfiguration pskNetwork = WifiConfigurationTestUtil.createPskNetwork(); - pskNetwork.setIpConfiguration(WifiConfigurationTestUtil.createStaticIpConfigurationWithPacProxy()); - pskNetwork.getNetworkSelectionStatus().setNetworkSelectionStatus( - NetworkSelectionStatus.NETWORK_SELECTION_TEMPORARY_DISABLED); - pskNetwork.getNetworkSelectionStatus().setNetworkSelectionDisableReason( - NetworkSelectionStatus.DISABLED_ASSOCIATION_REJECTION); - configurations.add(pskNetwork); - - WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork(); - openNetwork.setIpConfiguration(WifiConfigurationTestUtil.createStaticIpConfigurationWithStaticProxy()); - openNetwork.getNetworkSelectionStatus().setNetworkSelectionStatus( - NetworkSelectionStatus.NETWORK_SELECTION_PERMANENTLY_DISABLED); - openNetwork.getNetworkSelectionStatus().setNetworkSelectionDisableReason( - NetworkSelectionStatus.DISABLED_BY_WIFI_MANAGER); - configurations.add(openNetwork); - - WifiConfiguration eapNetwork = WifiConfigurationTestUtil.createEapNetwork(); - eapNetwork.setIpConfiguration(WifiConfigurationTestUtil.createPartialStaticIpConfigurationWithPacProxy()); - eapNetwork.getNetworkSelectionStatus().setConnectChoice(TEST_CONNECT_CHOICE); - eapNetwork.getNetworkSelectionStatus().setConnectChoiceTimestamp( - TEST_CONNECT_CHOICE_TIMESTAMP); - eapNetwork.getNetworkSelectionStatus().setHasEverConnected(true); - configurations.add(eapNetwork); - - return configurations; - } - - private List createNetworks(boolean shared) { - List configurations = createNetworks(); - for (WifiConfiguration config : configurations) { - config.shared = shared; - } - return configurations; - } - - /** - * Helper method to serialize/deserialize store data. - */ - private void serializeDeserializeConfigStoreData( - List sharedConfigurations, - List userConfigurations) - throws XmlPullParserException, IOException { - serializeDeserializeConfigStoreData(sharedConfigurations, userConfigurations, false, false); - } - - /** - * Helper method to ensure the the provided config store data is serialized/deserialized - * correctly. - * This method serialize the provided config store data instance to raw bytes in XML format - * and then deserialzes the raw bytes back to a config store data instance. It then - * compares that the original config store data matches with the deserialzed instance. - * - * @param sharedConfigurations list of configurations to be added in the shared store data instance. - * @param userConfigurations list of configurations to be added in the user store data instance. - * @param setSharedDataNull whether to set the shared data to null to simulate the non-existence - * of the shared store file. - * @param setUserDataNull whether to set the user data to null to simulate the non-existence - * of the user store file. - */ - private void serializeDeserializeConfigStoreData( - List sharedConfigurations, - List userConfigurations, - boolean setSharedDataNull, boolean setUserDataNull) - throws XmlPullParserException, IOException { - // Will not work if both the flags are set because then we need to ignore the configuration - // list as well. - assertFalse(setSharedDataNull & setUserDataNull); - - Set deletedEphemeralList; - if (setUserDataNull) { - deletedEphemeralList = new HashSet<>(); - } else { - deletedEphemeralList = TEST_DELETED_EPHEMERAL_LIST; - } - - // Serialize the data. - WifiConfigStoreData storeData = - new WifiConfigStoreData( - sharedConfigurations, userConfigurations, deletedEphemeralList); - - byte[] sharedDataBytes = null; - byte[] userDataBytes = null; - if (!setSharedDataNull) { - sharedDataBytes = storeData.createSharedRawData(); - } - if (!setUserDataNull) { - userDataBytes = storeData.createUserRawData(); - } - - // Deserialize the data. - WifiConfigStoreData retrievedStoreData = - WifiConfigStoreData.parseRawData(sharedDataBytes, userDataBytes); - assertConfigStoreDataEqual(storeData, retrievedStoreData); - } -} diff --git a/tests/wifitests/src/com/android/server/wifi/WifiConfigStoreTest.java b/tests/wifitests/src/com/android/server/wifi/WifiConfigStoreTest.java index f567ef6d5..b7e642c91 100644 --- a/tests/wifitests/src/com/android/server/wifi/WifiConfigStoreTest.java +++ b/tests/wifitests/src/com/android/server/wifi/WifiConfigStoreTest.java @@ -16,8 +16,6 @@ package com.android.server.wifi; -import static com.android.server.wifi.WifiConfigStoreDataTest.assertConfigStoreDataEqual; - import static org.junit.Assert.*; import static org.mockito.Mockito.*; @@ -28,23 +26,99 @@ import android.os.test.TestLooper; import android.test.suitebuilder.annotation.SmallTest; import com.android.server.wifi.WifiConfigStore.StoreFile; +import com.android.server.wifi.util.XmlUtil; import org.junit.After; import org.junit.Before; import org.junit.Test; import org.mockito.Mock; import org.mockito.MockitoAnnotations; +import org.xmlpull.v1.XmlPullParser; +import org.xmlpull.v1.XmlPullParserException; +import org.xmlpull.v1.XmlSerializer; import java.io.File; +import java.io.IOException; +import java.nio.charset.StandardCharsets; import java.util.ArrayList; +import java.util.Arrays; import java.util.HashSet; import java.util.List; +import java.util.Set; /** * Unit tests for {@link com.android.server.wifi.WifiConfigStore}. */ @SmallTest public class WifiConfigStoreTest { + // Store file content without any data. + private static final String EMPTY_FILE_CONTENT = + "\n" + + "\n" + + "\n" + + "\n"; + + private static final String TEST_USER_DATA = "UserData"; + private static final String TEST_SHARE_DATA = "ShareData"; + + private static final String TEST_DATA_XML_STRING_FORMAT = + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "%s\n" + + "%s\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "01\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "NETWORK_SELECTION_ENABLED\n" + + "NETWORK_SELECTION_ENABLE\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "DHCP\n" + + "NONE\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "\n" + + "%s\n" + + "\n" + + "\n" + + "\n"; + // Test mocks @Mock private Context mContext; private TestAlarmManager mAlarmManager; @@ -52,6 +126,7 @@ public class WifiConfigStoreTest { @Mock private Clock mClock; private MockStoreFile mSharedStore; private MockStoreFile mUserStore; + private MockStoreData mStoreData; /** * Test instance of WifiConfigStore. @@ -69,6 +144,7 @@ public class WifiConfigStoreTest { .thenReturn(mAlarmManager.getAlarmManager()); mUserStore = new MockStoreFile(); mSharedStore = new MockStoreFile(); + mStoreData = new MockStoreData(); } /** @@ -79,7 +155,6 @@ public class WifiConfigStoreTest { setupMocks(); mWifiConfigStore = new WifiConfigStore(mContext, mLooper.getLooper(), mClock, mSharedStore); - // Enable verbose logging before tests. mWifiConfigStore.enableVerboseLogging(true); } @@ -92,6 +167,27 @@ public class WifiConfigStoreTest { validateMockitoUsage(); } + /** + * Verify the contents of the config file with empty data. The data content should be the + * same as {@link #EMPTY_FILE_CONTENT}. + * + * @throws Exception + */ + @Test + public void testWriteWithEmptyData() throws Exception { + // Perform force write to both share and user store file. + mWifiConfigStore.switchUserStoreAndRead(mUserStore); + mWifiConfigStore.write(true); + + assertFalse(mAlarmManager.isPending(WifiConfigStore.BUFFERED_WRITE_ALARM_TAG)); + assertTrue(mSharedStore.isStoreWritten()); + assertTrue(mUserStore.isStoreWritten()); + assertTrue(Arrays.equals(EMPTY_FILE_CONTENT.getBytes(StandardCharsets.UTF_8), + mSharedStore.getStoreBytes())); + assertTrue(Arrays.equals(EMPTY_FILE_CONTENT.getBytes(StandardCharsets.UTF_8), + mUserStore.getStoreBytes())); + } + /** * Tests the write API with the force flag set to true. * Expected behavior: This should trigger an immediate write to the store files and no alarms @@ -100,7 +196,7 @@ public class WifiConfigStoreTest { @Test public void testForceWrite() throws Exception { mWifiConfigStore.switchUserStoreAndRead(mUserStore); - mWifiConfigStore.write(true, getEmptyStoreData()); + mWifiConfigStore.write(true); assertFalse(mAlarmManager.isPending(WifiConfigStore.BUFFERED_WRITE_ALARM_TAG)); assertTrue(mSharedStore.isStoreWritten()); @@ -114,7 +210,7 @@ public class WifiConfigStoreTest { @Test public void testBufferedWrite() throws Exception { mWifiConfigStore.switchUserStoreAndRead(mUserStore); - mWifiConfigStore.write(false, getEmptyStoreData()); + mWifiConfigStore.write(false); assertTrue(mAlarmManager.isPending(WifiConfigStore.BUFFERED_WRITE_ALARM_TAG)); assertFalse(mSharedStore.isStoreWritten()); @@ -134,30 +230,33 @@ public class WifiConfigStoreTest { */ @Test public void testForceWriteAfterBufferedWrite() throws Exception { - WifiConfigStoreData bufferedStoreData = createSingleOpenNetworkStoreData(); + // Register a test data container with bogus data. + mWifiConfigStore.registerStoreData(mStoreData); + mStoreData.setShareData("abcds"); + mStoreData.setUserData("asdfa"); + + // Perform buffered write for both user and share store file. mWifiConfigStore.switchUserStoreAndRead(mUserStore); - mWifiConfigStore.write(false, bufferedStoreData); + mWifiConfigStore.write(false); assertTrue(mAlarmManager.isPending(WifiConfigStore.BUFFERED_WRITE_ALARM_TAG)); assertFalse(mSharedStore.isStoreWritten()); assertFalse(mUserStore.isStoreWritten()); - // Now send a force write and ensure that the writes have been performed and alarms have - // been stopped. - WifiConfigStoreData forcedStoreData = createSinglePskNetworkStoreData(); - mWifiConfigStore.write(true, forcedStoreData); + // Update the container with new set of data. The send a force write and ensure that the + // writes have been performed and alarms have been stopped and updated data are written. + mStoreData.setUserData(TEST_USER_DATA); + mStoreData.setShareData(TEST_SHARE_DATA); + mWifiConfigStore.write(true); assertFalse(mAlarmManager.isPending(WifiConfigStore.BUFFERED_WRITE_ALARM_TAG)); assertTrue(mSharedStore.isStoreWritten()); assertTrue(mUserStore.isStoreWritten()); - // Now deserialize the data and ensure that the configuration retrieved matches the force - // write data. - WifiConfigStoreData retrievedStoreData = - WifiConfigStoreData.parseRawData( - mSharedStore.getStoreBytes(), mUserStore.getStoreBytes()); - - assertConfigStoreDataEqual(forcedStoreData, retrievedStoreData); + // Verify correct data are loaded to the data container after a read. + mWifiConfigStore.read(); + assertEquals(TEST_USER_DATA, mStoreData.getUserData()); + assertEquals(TEST_SHARE_DATA, mStoreData.getShareData()); } /** @@ -166,12 +265,25 @@ public class WifiConfigStoreTest { */ @Test public void testReadAfterWrite() throws Exception { - WifiConfigStoreData writeData = createSingleOpenNetworkStoreData(); + // Register data container. + mWifiConfigStore.registerStoreData(mStoreData); + + // Read both share and user config store. mWifiConfigStore.switchUserStoreAndRead(mUserStore); - mWifiConfigStore.write(true, writeData); - WifiConfigStoreData readData = mWifiConfigStore.read(); - assertConfigStoreDataEqual(writeData, readData); + // Verify no data is read. + assertNull(mStoreData.getUserData()); + assertNull(mStoreData.getShareData()); + + // Write share and user data. + mStoreData.setUserData(TEST_USER_DATA); + mStoreData.setShareData(TEST_SHARE_DATA); + mWifiConfigStore.write(true); + + // Read and verify the data content in the data container. + mWifiConfigStore.read(); + assertEquals(TEST_USER_DATA, mStoreData.getUserData()); + assertEquals(TEST_SHARE_DATA, mStoreData.getShareData()); } /** @@ -183,9 +295,13 @@ public class WifiConfigStoreTest { public void testReadWithNoStoreFile() throws Exception { // Reading the mock store without a write should simulate the file not found case because // |readRawData| would return null. + mWifiConfigStore.registerStoreData(mStoreData); assertFalse(mWifiConfigStore.areStoresPresent()); - WifiConfigStoreData readData = mWifiConfigStore.read(); - assertConfigStoreDataEqual(getEmptyStoreData(), readData); + mWifiConfigStore.read(); + + // Empty data. + assertNull(mStoreData.getUserData()); + assertNull(mStoreData.getShareData()); } /** @@ -195,40 +311,164 @@ public class WifiConfigStoreTest { */ @Test public void testReadAfterWriteWithNoUserStore() throws Exception { - WifiConfigStoreData writeData = createSingleOpenNetworkStoreData(); - mWifiConfigStore.write(true, writeData); - WifiConfigStoreData readData = mWifiConfigStore.read(); + // Setup data container. + mWifiConfigStore.registerStoreData(mStoreData); + mStoreData.setUserData(TEST_USER_DATA); + mStoreData.setShareData(TEST_SHARE_DATA); + + // Perform write for the share store file. + mWifiConfigStore.write(true); + mWifiConfigStore.read(); + // Verify data content for both user and share data. + assertEquals(TEST_SHARE_DATA, mStoreData.getShareData()); + assertNull(mStoreData.getUserData()); + } + + /** + * Verifies that a read operation will reset the data in the data container, to avoid + * any stale data from previous read. + * + * @throws Exception + */ + @Test + public void testReadWillResetStoreData() throws Exception { + // Register and setup store data. + mWifiConfigStore.registerStoreData(mStoreData); + + // Perform force write with empty data content to both user and share store file. + mWifiConfigStore.switchUserStoreAndRead(mUserStore); + mWifiConfigStore.write(true); - assertConfigStoreDataEqual(writeData, readData); + // Setup data container with some value. + mStoreData.setUserData(TEST_USER_DATA); + mStoreData.setShareData(TEST_SHARE_DATA); + + // Perform read of both user and share store file and verify data in the data container + // is in sync (empty) with what is in the file. + mWifiConfigStore.read(); + assertNull(mStoreData.getShareData()); + assertNull(mStoreData.getUserData()); + } + + /** + * Verify that a store file contained WiFi configuration store data (network list and + * deleted ephemeral SSID list) using the predefined test XML data is read and parsed + * correctly. + * + * @throws Exception + */ + @Test + public void testReadWifiConfigStoreData() throws Exception { + // Setup network list. + NetworkListStoreData networkList = new NetworkListStoreData(); + mWifiConfigStore.registerStoreData(networkList); + WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork(); + openNetwork.setIpConfiguration( + WifiConfigurationTestUtil.createDHCPIpConfigurationWithNoProxy()); + List userConfigs = new ArrayList<>(); + userConfigs.add(openNetwork); + + // Setup deleted ephemeral SSID list. + DeletedEphemeralSsidsStoreData deletedEphemeralSsids = + new DeletedEphemeralSsidsStoreData(); + mWifiConfigStore.registerStoreData(deletedEphemeralSsids); + String testSsid = "Test SSID"; + Set ssidList = new HashSet<>(); + ssidList.add(testSsid); + + // Setup user store XML bytes. + String xmlString = String.format(TEST_DATA_XML_STRING_FORMAT, + openNetwork.configKey().replaceAll("\"", """), + openNetwork.SSID.replaceAll("\"", """), + openNetwork.shared, openNetwork.creatorUid, testSsid); + byte[] xmlBytes = xmlString.getBytes(StandardCharsets.UTF_8); + mUserStore.storeRawDataToWrite(xmlBytes); + + mWifiConfigStore.switchUserStoreAndRead(mUserStore); + WifiConfigurationTestUtil.assertConfigurationsEqualForConfigStore( + userConfigs, networkList.getUserConfigurations()); + assertEquals(ssidList, deletedEphemeralSsids.getSsidList()); } /** - * Returns an empty store data object. + * Verify that the WiFi configuration store data containing network list and deleted + * ephemeral SSID list are serialized correctly, matches the predefined test XML data. + * + * @throws Exception */ - private WifiConfigStoreData getEmptyStoreData() { - return new WifiConfigStoreData( - new ArrayList(), new ArrayList(), - new HashSet()); + @Test + public void testWriteWifiConfigStoreData() throws Exception { + // Setup user store. + mWifiConfigStore.switchUserStoreAndRead(mUserStore); + + // Setup network list store data. + NetworkListStoreData networkList = new NetworkListStoreData(); + mWifiConfigStore.registerStoreData(networkList); + WifiConfiguration openNetwork = WifiConfigurationTestUtil.createOpenNetwork(); + openNetwork.setIpConfiguration( + WifiConfigurationTestUtil.createDHCPIpConfigurationWithNoProxy()); + List userConfigs = new ArrayList<>(); + userConfigs.add(openNetwork); + networkList.setUserConfigurations(userConfigs); + + // Setup deleted ephemeral SSID list store data. + DeletedEphemeralSsidsStoreData deletedEphemeralSsids = + new DeletedEphemeralSsidsStoreData(); + mWifiConfigStore.registerStoreData(deletedEphemeralSsids); + String testSsid = "Test SSID"; + Set ssidList = new HashSet<>(); + ssidList.add(testSsid); + deletedEphemeralSsids.setSsidList(ssidList); + + // Setup expected XML bytes. + String xmlString = String.format(TEST_DATA_XML_STRING_FORMAT, + openNetwork.configKey().replaceAll("\"", """), + openNetwork.SSID.replaceAll("\"", """), + openNetwork.shared, openNetwork.creatorUid, testSsid); + byte[] xmlBytes = xmlString.getBytes(StandardCharsets.UTF_8); + + mWifiConfigStore.write(true); + assertEquals(xmlBytes.length, mUserStore.getStoreBytes().length); + // Verify the user store content. + assertTrue(Arrays.equals(xmlBytes, mUserStore.getStoreBytes())); } /** - * Returns an store data object with a single open network. + * Verify that a XmlPullParserException will be thrown when reading an user store file + * containing unknown data. + * + * @throws Exception */ - private WifiConfigStoreData createSingleOpenNetworkStoreData() { - List configurations = new ArrayList<>(); - configurations.add(WifiConfigurationTestUtil.createOpenNetwork()); - return new WifiConfigStoreData( - configurations, new ArrayList(), new HashSet()); + @Test(expected = XmlPullParserException.class) + public void testReadUserStoreContainedUnknownData() throws Exception { + String storeFileData = + "\n" + + "\n" + + "\n" + + "\n" // No StoreData registered to handle this tag. + + "\n" + + "\n"; + mUserStore.storeRawDataToWrite(storeFileData.getBytes(StandardCharsets.UTF_8)); + mWifiConfigStore.switchUserStoreAndRead(mUserStore); } /** - * Returns an store data object with a single psk network. + * Verify that a XmlPullParserException will be thrown when reading the share store file + * containing unknown data. + * + * @throws Exception */ - private WifiConfigStoreData createSinglePskNetworkStoreData() { - List configurations = new ArrayList<>(); - configurations.add(WifiConfigurationTestUtil.createPskNetwork()); - return new WifiConfigStoreData( - configurations, new ArrayList(), new HashSet()); + @Test(expected = XmlPullParserException.class) + public void testReadShareStoreContainedUnknownData() throws Exception { + String storeFileData = + "\n" + + "\n" + + "\n" + + "\n" // No StoreData registered to handle this tag. + + "\n" + + "\n"; + mSharedStore.storeRawDataToWrite(storeFileData.getBytes(StandardCharsets.UTF_8)); + mWifiConfigStore.read(); } /** @@ -259,6 +499,7 @@ public class WifiConfigStoreTest { return (mStoreBytes != null); } + @Override public void writeBufferedRawData() { mStoreWritten = true; } @@ -271,4 +512,72 @@ public class WifiConfigStoreTest { return mStoreWritten; } } + + /** + * Mock data container for providing test data for the store file. + */ + private class MockStoreData implements WifiConfigStore.StoreData { + private static final String XML_TAG_TEST_HEADER = "TestHeader"; + private static final String XML_TAG_TEST_DATA = "TestData"; + + private String mShareData; + private String mUserData; + + MockStoreData() {} + + @Override + public void serializeData(XmlSerializer out, boolean shared) + throws XmlPullParserException, IOException { + if (shared) { + XmlUtil.writeNextValue(out, XML_TAG_TEST_DATA, mShareData); + } else { + XmlUtil.writeNextValue(out, XML_TAG_TEST_DATA, mUserData); + } + } + + @Override + public void deserializeData(XmlPullParser in, int outerTagDepth, boolean shared) + throws XmlPullParserException, IOException { + if (shared) { + mShareData = (String) XmlUtil.readNextValueWithName(in, XML_TAG_TEST_DATA); + } else { + mUserData = (String) XmlUtil.readNextValueWithName(in, XML_TAG_TEST_DATA); + } + } + + @Override + public void resetData(boolean shared) { + if (shared) { + mShareData = null; + } else { + mUserData = null; + } + } + + @Override + public String getName() { + return XML_TAG_TEST_HEADER; + } + + @Override + public boolean supportShareData() { + return true; + } + + public String getShareData() { + return mShareData; + } + + public void setShareData(String shareData) { + mShareData = shareData; + } + + public String getUserData() { + return mUserData; + } + + public void setUserData(String userData) { + mUserData = userData; + } + } } -- cgit v1.2.3