ap_interface_test.cpp revision 99ebcbd4bbd8ce5d951f84aa5a5f11e0db0294cb
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 17#include <vector> 18 19#include <gtest/gtest.h> 20#include <utils/StrongPointer.h> 21#include <wifi_system/interface_tool.h> 22 23#include "android/net/wifi/IApInterface.h" 24#include "android/net/wifi/IWificond.h" 25#include "wificond/tests/integration/process_utils.h" 26#include "wificond/tests/mock_ap_interface_event_callback.h" 27 28using android::net::wifi::IApInterface; 29using android::net::wifi::IWificond; 30using android::wifi_system::InterfaceTool; 31using android::wificond::MockApInterfaceEventCallback; 32using android::wificond::tests::integration::HostapdIsDead; 33using android::wificond::tests::integration::HostapdIsRunning; 34using android::wificond::tests::integration::ScopedDevModeWificond; 35using android::wificond::tests::integration::WaitForTrue; 36using std::string; 37using std::vector; 38 39namespace android { 40namespace wificond { 41namespace { 42 43constexpr int kHostapdStartupTimeoutSeconds = 3; 44constexpr int kHostapdDeathTimeoutSeconds = 3; 45 46const char kInterfaceName[] = "wlan0"; 47const char kValidSsid[] = "foobar"; 48const char kInvalidSsid[] = "0123456789" 49 "0123456789" 50 "0123456789" 51 "012"; // 33 bytes is too long 52const char kValidPassphrase[] = "super secret"; 53 54} // namespace 55 56TEST(ApInterfaceTest, CanCreateApInterfaces) { 57 ScopedDevModeWificond dev_mode; 58 sp<IWificond> service = dev_mode.EnterDevModeOrDie(); 59 60 // We should be able to create an AP interface. 61 sp<IApInterface> ap_interface; 62 EXPECT_TRUE(service->createApInterface(kInterfaceName, &ap_interface).isOk()); 63 EXPECT_NE(nullptr, ap_interface.get()); 64 65 // The interface should start out down. 66 string if_name; 67 EXPECT_TRUE(ap_interface->getInterfaceName(&if_name).isOk()); 68 EXPECT_TRUE(!if_name.empty()); 69 InterfaceTool if_tool; 70 EXPECT_FALSE(if_tool.GetUpState(if_name.c_str())); 71 72 // Mark the interface as up, just to test that we mark it down on tearDown. 73 EXPECT_TRUE(if_tool.SetUpState(if_name.c_str(), true)); 74 EXPECT_TRUE(if_tool.GetUpState(if_name.c_str())); 75 76 // We should not be able to create two AP interfaces. 77 sp<IApInterface> ap_interface2; 78 EXPECT_TRUE(service->createApInterface( 79 kInterfaceName, &ap_interface2).isOk()); 80 EXPECT_EQ(nullptr, ap_interface2.get()); 81 82 // We can tear down the created interface. 83 bool success = false; 84 EXPECT_TRUE(service->tearDownApInterface(kInterfaceName, &success).isOk()); 85 EXPECT_TRUE(success); 86 EXPECT_FALSE(if_tool.GetUpState(if_name.c_str())); 87 88 // Teardown everything at the end of the test. 89 EXPECT_TRUE(service->tearDownInterfaces().isOk()); 90} 91 92// TODO: b/30311493 this test fails because hostapd fails to set the driver 93// channel every other time. 94TEST(ApInterfaceTest, CanStartStopHostapd) { 95 ScopedDevModeWificond dev_mode; 96 sp<IWificond> service = dev_mode.EnterDevModeOrDie(); 97 sp<IApInterface> ap_interface; 98 EXPECT_TRUE(service->createApInterface(kInterfaceName, &ap_interface).isOk()); 99 ASSERT_NE(nullptr, ap_interface.get()); 100 101 // Interface should start out down. 102 string if_name; 103 EXPECT_TRUE(ap_interface->getInterfaceName(&if_name).isOk()); 104 EXPECT_TRUE(!if_name.empty()); 105 InterfaceTool if_tool; 106 EXPECT_FALSE(if_tool.GetUpState(if_name.c_str())); 107 108 bool wrote_config = false; 109 EXPECT_TRUE(ap_interface->writeHostapdConfig( 110 vector<uint8_t>(kValidSsid, kValidSsid + sizeof(kValidSsid) - 1), 111 false, 112 IApInterface::BAND_5G, 113 IApInterface::ENCRYPTION_TYPE_WPA2, 114 vector<uint8_t>(kValidPassphrase, 115 kValidPassphrase + sizeof(kValidPassphrase) - 1), 116 &wrote_config).isOk()); 117 ASSERT_TRUE(wrote_config); 118 119 sp<MockApInterfaceEventCallback> ap_interface_event_callback( 120 new MockApInterfaceEventCallback()); 121 122 for (int iteration = 0; iteration < 4; iteration++) { 123 bool hostapd_started = false; 124 EXPECT_TRUE( 125 ap_interface 126 ->startHostapd(ap_interface_event_callback, &hostapd_started) 127 .isOk()); 128 EXPECT_TRUE(hostapd_started); 129 130 EXPECT_TRUE(WaitForTrue(HostapdIsRunning, kHostapdStartupTimeoutSeconds)) 131 << "Failed on iteration " << iteration; 132 133 // There are two reasons to do this: 134 // 1) We look for hostapd so quickly that we miss when it dies on startup 135 // 2) If we don't give hostapd enough time to get fully up, killing it 136 // can leave the driver in a poor state. 137 // The latter points to an obvious race, where we cannot fully clean up the 138 // driver on quick transitions. 139 auto InterfaceIsUp = [&if_tool, &if_name] () { 140 return if_tool.GetUpState(if_name.c_str()); 141 }; 142 EXPECT_TRUE(WaitForTrue(InterfaceIsUp, kHostapdStartupTimeoutSeconds)) 143 << "Failed on iteration " << iteration; 144 EXPECT_TRUE(HostapdIsRunning()) << "Failed on iteration " << iteration; 145 146 bool hostapd_stopped = false; 147 EXPECT_TRUE(ap_interface->stopHostapd(&hostapd_stopped).isOk()); 148 EXPECT_TRUE(hostapd_stopped); 149 EXPECT_FALSE(if_tool.GetUpState(if_name.c_str())); 150 151 152 EXPECT_TRUE(WaitForTrue(HostapdIsDead, kHostapdDeathTimeoutSeconds)) 153 << "Failed on iteration " << iteration; 154 } 155} 156 157TEST(ApInterfaceTest, CanWriteHostapdConfig) { 158 ScopedDevModeWificond dev_mode; 159 sp<IWificond> service = dev_mode.EnterDevModeOrDie(); 160 sp<IApInterface> ap_interface; 161 EXPECT_TRUE(service->createApInterface(kInterfaceName, &ap_interface).isOk()); 162 ASSERT_NE(nullptr, ap_interface.get()); 163 164 bool success = false; 165 // Should be able to write out a valid configuration 166 EXPECT_TRUE(ap_interface->writeHostapdConfig( 167 vector<uint8_t>(kValidSsid, kValidSsid + sizeof(kValidSsid) - 1), 168 false, 169 IApInterface::BAND_5G, 170 IApInterface::ENCRYPTION_TYPE_WPA2, 171 vector<uint8_t>(kValidPassphrase, 172 kValidPassphrase + sizeof(kValidPassphrase) - 1), 173 &success).isOk()); 174 EXPECT_TRUE(success) << "Expected to write out a valid config."; 175 176 // SSIDs have to be 32 bytes or less 177 EXPECT_TRUE(ap_interface->writeHostapdConfig( 178 vector<uint8_t>(kInvalidSsid, kInvalidSsid + sizeof(kInvalidSsid) - 1), 179 false, 180 IApInterface::BAND_5G, 181 IApInterface::ENCRYPTION_TYPE_WPA2, 182 vector<uint8_t>(kValidPassphrase, 183 kValidPassphrase + sizeof(kValidPassphrase) - 1), 184 &success).isOk()); 185 EXPECT_FALSE(success) << "Did not expect to write out an invalid config."; 186} 187 188} // namespace wificond 189} // namespace android 190