1326b6cfba5ab73c9e41a7585d1bc95871631122aPeter Qiu// 2326b6cfba5ab73c9e41a7585d1bc95871631122aPeter Qiu// Copyright (C) 2014 The Android Open Source Project 3326b6cfba5ab73c9e41a7585d1bc95871631122aPeter Qiu// 4326b6cfba5ab73c9e41a7585d1bc95871631122aPeter Qiu// Licensed under the Apache License, Version 2.0 (the "License"); 5326b6cfba5ab73c9e41a7585d1bc95871631122aPeter Qiu// you may not use this file except in compliance with the License. 6326b6cfba5ab73c9e41a7585d1bc95871631122aPeter Qiu// You may obtain a copy of the License at 7326b6cfba5ab73c9e41a7585d1bc95871631122aPeter Qiu// 8326b6cfba5ab73c9e41a7585d1bc95871631122aPeter Qiu// http://www.apache.org/licenses/LICENSE-2.0 9326b6cfba5ab73c9e41a7585d1bc95871631122aPeter Qiu// 10326b6cfba5ab73c9e41a7585d1bc95871631122aPeter Qiu// Unless required by applicable law or agreed to in writing, software 11326b6cfba5ab73c9e41a7585d1bc95871631122aPeter Qiu// distributed under the License is distributed on an "AS IS" BASIS, 12326b6cfba5ab73c9e41a7585d1bc95871631122aPeter Qiu// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13326b6cfba5ab73c9e41a7585d1bc95871631122aPeter Qiu// See the License for the specific language governing permissions and 14326b6cfba5ab73c9e41a7585d1bc95871631122aPeter Qiu// limitations under the License. 15326b6cfba5ab73c9e41a7585d1bc95871631122aPeter Qiu// 16376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu 17376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu#include "apmanager/service.h" 18376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu 19376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu#include <string> 20376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu 21376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu#include <base/strings/string_util.h> 22376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu#include <base/strings/stringprintf.h> 238d0c31bb481b712a3b2e6612390679e29053c620Alex Vakulenko#include <brillo/process_mock.h> 24376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu#include <gmock/gmock.h> 25376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu#include <gtest/gtest.h> 26376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu 277a420d3e06aa7fb5eba305dc587624eb58bde7b7Peter Qiu#if !defined(__ANDROID__) 287a420d3e06aa7fb5eba305dc587624eb58bde7b7Peter Qiu#include <chromeos/dbus/service_constants.h> 297a420d3e06aa7fb5eba305dc587624eb58bde7b7Peter Qiu#else 302ea547f45d2a143e1b25b275c46d1f317186b07aPeter Qiu#include <dbus/apmanager/dbus-constants.h> 317a420d3e06aa7fb5eba305dc587624eb58bde7b7Peter Qiu#endif // __ANDROID__ 327a420d3e06aa7fb5eba305dc587624eb58bde7b7Peter Qiu 33d9c79aa078a5df1882848d26a52d48a02b4057a5Peter Qiu#include "apmanager/error.h" 34d9c79aa078a5df1882848d26a52d48a02b4057a5Peter Qiu#include "apmanager/fake_config_adaptor.h" 35376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu#include "apmanager/mock_config.h" 36d9c79aa078a5df1882848d26a52d48a02b4057a5Peter Qiu#include "apmanager/mock_control.h" 37bf8e36cde93c8714b5e1482d205d2e3e424d1290Peter Qiu#include "apmanager/mock_dhcp_server.h" 38bf8e36cde93c8714b5e1482d205d2e3e424d1290Peter Qiu#include "apmanager/mock_dhcp_server_factory.h" 39775173013ee886be244417eba0a3b302c4da11e0Peter Qiu#include "apmanager/mock_file_writer.h" 40fda548ca8f0b29834a37b83e836f4ccc3268fa1dPeter Qiu#include "apmanager/mock_hostapd_monitor.h" 41fb39ba4b2ef92f0c9d19f6910a350cd8a14405a0Peter Qiu#include "apmanager/mock_manager.h" 421dbf9fdfef00d80e151d13e5a4ff016f9d916ad7Peter Qiu#include "apmanager/mock_process_factory.h" 432ea547f45d2a143e1b25b275c46d1f317186b07aPeter Qiu#include "apmanager/mock_service_adaptor.h" 44376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu 458d0c31bb481b712a3b2e6612390679e29053c620Alex Vakulenkousing brillo::ProcessMock; 46376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiuusing ::testing::_; 47376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiuusing ::testing::Mock; 48376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiuusing ::testing::Return; 49d9c79aa078a5df1882848d26a52d48a02b4057a5Peter Qiuusing ::testing::ReturnNew; 50376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiuusing ::testing::SetArgPointee; 51376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu 52376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiunamespace { 53376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu const int kServiceIdentifier = 1; 54376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu const char kHostapdConfig[] = "ssid=test\n"; 556789bcbfbc2cbc7eec7713513b4b2038f7f8c52cPeter Qiu#if !defined(__ANDROID__) 568b9b2540ada6098ac6eb4edc3265016be7170fc3David Pursell const char kBinSleep[] = "/bin/sleep"; 57775173013ee886be244417eba0a3b302c4da11e0Peter Qiu const char kHostapdConfigFilePath[] = 58775173013ee886be244417eba0a3b302c4da11e0Peter Qiu "/var/run/apmanager/hostapd/hostapd-1.conf"; 59015a499835529e3e632e0bb86d76ca03c6121770Peter Qiu#else 606789bcbfbc2cbc7eec7713513b4b2038f7f8c52cPeter Qiu const char kBinSleep[] = "/system/bin/sleep"; 616789bcbfbc2cbc7eec7713513b4b2038f7f8c52cPeter Qiu const char kHostapdConfigFilePath[] = 62015a499835529e3e632e0bb86d76ca03c6121770Peter Qiu "/data/misc/apmanager/hostapd/hostapd-1.conf"; 63015a499835529e3e632e0bb86d76ca03c6121770Peter Qiu#endif // __ANDROID__ 64376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu} // namespace 65376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu 66376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiunamespace apmanager { 67376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu 68376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiuclass ServiceTest : public testing::Test { 69376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu public: 701dbf9fdfef00d80e151d13e5a4ff016f9d916ad7Peter Qiu ServiceTest() 71d9c79aa078a5df1882848d26a52d48a02b4057a5Peter Qiu : manager_(&control_interface_), 72d9c79aa078a5df1882848d26a52d48a02b4057a5Peter Qiu hostapd_monitor_(new MockHostapdMonitor()) { 732ea547f45d2a143e1b25b275c46d1f317186b07aPeter Qiu ON_CALL(control_interface_, CreateServiceAdaptorRaw()) 742ea547f45d2a143e1b25b275c46d1f317186b07aPeter Qiu .WillByDefault(ReturnNew<MockServiceAdaptor>()); 75d9c79aa078a5df1882848d26a52d48a02b4057a5Peter Qiu ON_CALL(control_interface_, CreateConfigAdaptorRaw()) 76d9c79aa078a5df1882848d26a52d48a02b4057a5Peter Qiu .WillByDefault(ReturnNew<FakeConfigAdaptor>()); 77d9c79aa078a5df1882848d26a52d48a02b4057a5Peter Qiu // Defer creation of Service object to allow ControlInterface to 78d9c79aa078a5df1882848d26a52d48a02b4057a5Peter Qiu // setup expectations for generating fake adaptors. 797758d8db3ddb2582fb57bda4a26c9f6f6bd20316Peter Qiu service_ = new Service(&manager_, kServiceIdentifier); 80d9c79aa078a5df1882848d26a52d48a02b4057a5Peter Qiu } 811dbf9fdfef00d80e151d13e5a4ff016f9d916ad7Peter Qiu virtual void SetUp() { 82d9c79aa078a5df1882848d26a52d48a02b4057a5Peter Qiu service_->dhcp_server_factory_ = &dhcp_server_factory_; 83d9c79aa078a5df1882848d26a52d48a02b4057a5Peter Qiu service_->file_writer_ = &file_writer_; 84d9c79aa078a5df1882848d26a52d48a02b4057a5Peter Qiu service_->process_factory_ = &process_factory_; 85d9c79aa078a5df1882848d26a52d48a02b4057a5Peter Qiu service_->hostapd_monitor_.reset(hostapd_monitor_); 861dbf9fdfef00d80e151d13e5a4ff016f9d916ad7Peter Qiu } 87376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu 882ea547f45d2a143e1b25b275c46d1f317186b07aPeter Qiu bool StartService(Error* error) { 89d9c79aa078a5df1882848d26a52d48a02b4057a5Peter Qiu return service_->StartInternal(error); 90682a9324b86ce27fd1c461704fa2e80e40ed043dPeter Qiu } 91682a9324b86ce27fd1c461704fa2e80e40ed043dPeter Qiu 92376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu void StartDummyProcess() { 93d9c79aa078a5df1882848d26a52d48a02b4057a5Peter Qiu service_->hostapd_process_.reset(new brillo::ProcessImpl); 94d9c79aa078a5df1882848d26a52d48a02b4057a5Peter Qiu service_->hostapd_process_->AddArg(kBinSleep); 95d9c79aa078a5df1882848d26a52d48a02b4057a5Peter Qiu service_->hostapd_process_->AddArg("12345"); 96d9c79aa078a5df1882848d26a52d48a02b4057a5Peter Qiu CHECK(service_->hostapd_process_->Start()); 97d9c79aa078a5df1882848d26a52d48a02b4057a5Peter Qiu LOG(INFO) << "DummyProcess: " << service_->hostapd_process_->pid(); 98376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu } 99376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu 100376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu void SetConfig(Config* config) { 101d9c79aa078a5df1882848d26a52d48a02b4057a5Peter Qiu service_->config_.reset(config); 102376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu } 103376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu 1042ea547f45d2a143e1b25b275c46d1f317186b07aPeter Qiu void VerifyError(const Error& error, 1052ea547f45d2a143e1b25b275c46d1f317186b07aPeter Qiu Error::Type expected_type, 1062ea547f45d2a143e1b25b275c46d1f317186b07aPeter Qiu const std::string& expected_message_start) { 1072ea547f45d2a143e1b25b275c46d1f317186b07aPeter Qiu EXPECT_EQ(expected_type, error.type()); 108fca478e3db86521918313d3d92290b1928de3702Alex Vakulenko EXPECT_TRUE(base::StartsWith(error.message(), expected_message_start, 109fca478e3db86521918313d3d92290b1928de3702Alex Vakulenko base::CompareCase::INSENSITIVE_ASCII)); 1102ea547f45d2a143e1b25b275c46d1f317186b07aPeter Qiu } 1112ea547f45d2a143e1b25b275c46d1f317186b07aPeter Qiu 112376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu protected: 113d9c79aa078a5df1882848d26a52d48a02b4057a5Peter Qiu MockControl control_interface_; 114fb39ba4b2ef92f0c9d19f6910a350cd8a14405a0Peter Qiu MockManager manager_; 1156789bcbfbc2cbc7eec7713513b4b2038f7f8c52cPeter Qiu MockDHCPServerFactory dhcp_server_factory_; 1166789bcbfbc2cbc7eec7713513b4b2038f7f8c52cPeter Qiu MockFileWriter file_writer_; 1176789bcbfbc2cbc7eec7713513b4b2038f7f8c52cPeter Qiu MockProcessFactory process_factory_; 118fda548ca8f0b29834a37b83e836f4ccc3268fa1dPeter Qiu MockHostapdMonitor* hostapd_monitor_; 1197758d8db3ddb2582fb57bda4a26c9f6f6bd20316Peter Qiu scoped_refptr<Service> service_; 120376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu}; 121376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu 122376e40426ad6055adfb384240b6e9a5d732f06e5Peter QiuTEST_F(ServiceTest, StartWhenServiceAlreadyRunning) { 123376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu StartDummyProcess(); 124376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu 1252ea547f45d2a143e1b25b275c46d1f317186b07aPeter Qiu Error error; 126682a9324b86ce27fd1c461704fa2e80e40ed043dPeter Qiu EXPECT_FALSE(StartService(&error)); 1272ea547f45d2a143e1b25b275c46d1f317186b07aPeter Qiu VerifyError(error, Error::kInternalError, "Service already running"); 128376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu} 129376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu 130376e40426ad6055adfb384240b6e9a5d732f06e5Peter QiuTEST_F(ServiceTest, StartWhenConfigFileFailed) { 131d9c79aa078a5df1882848d26a52d48a02b4057a5Peter Qiu MockConfig* config = new MockConfig(&manager_); 132376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu SetConfig(config); 133376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu 1342ea547f45d2a143e1b25b275c46d1f317186b07aPeter Qiu Error error; 135376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu EXPECT_CALL(*config, GenerateConfigFile(_, _)).WillOnce(Return(false)); 136682a9324b86ce27fd1c461704fa2e80e40ed043dPeter Qiu EXPECT_FALSE(StartService(&error)); 137376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu} 138376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu 139376e40426ad6055adfb384240b6e9a5d732f06e5Peter QiuTEST_F(ServiceTest, StartSuccess) { 140d9c79aa078a5df1882848d26a52d48a02b4057a5Peter Qiu MockConfig* config = new MockConfig(&manager_); 141376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu SetConfig(config); 142376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu 143bf8e36cde93c8714b5e1482d205d2e3e424d1290Peter Qiu // Setup mock DHCP server. 144bf8e36cde93c8714b5e1482d205d2e3e424d1290Peter Qiu MockDHCPServer* dhcp_server = new MockDHCPServer(); 1451dbf9fdfef00d80e151d13e5a4ff016f9d916ad7Peter Qiu // Setup mock process. 1461dbf9fdfef00d80e151d13e5a4ff016f9d916ad7Peter Qiu ProcessMock* process = new ProcessMock(); 147775173013ee886be244417eba0a3b302c4da11e0Peter Qiu 148376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu std::string config_str(kHostapdConfig); 1492ea547f45d2a143e1b25b275c46d1f317186b07aPeter Qiu Error error; 150376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu EXPECT_CALL(*config, GenerateConfigFile(_, _)).WillOnce( 151376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu DoAll(SetArgPointee<1>(config_str), Return(true))); 1526789bcbfbc2cbc7eec7713513b4b2038f7f8c52cPeter Qiu EXPECT_CALL(file_writer_, Write(kHostapdConfigFilePath, kHostapdConfig)) 153775173013ee886be244417eba0a3b302c4da11e0Peter Qiu .WillOnce(Return(true)); 154fb39ba4b2ef92f0c9d19f6910a350cd8a14405a0Peter Qiu EXPECT_CALL(*config, ClaimDevice()).WillOnce(Return(true)); 1556789bcbfbc2cbc7eec7713513b4b2038f7f8c52cPeter Qiu EXPECT_CALL(process_factory_, CreateProcess()).WillOnce(Return(process)); 1561dbf9fdfef00d80e151d13e5a4ff016f9d916ad7Peter Qiu EXPECT_CALL(*process, Start()).WillOnce(Return(true)); 1576789bcbfbc2cbc7eec7713513b4b2038f7f8c52cPeter Qiu EXPECT_CALL(dhcp_server_factory_, CreateDHCPServer(_, _)) 158bf8e36cde93c8714b5e1482d205d2e3e424d1290Peter Qiu .WillOnce(Return(dhcp_server)); 159bf8e36cde93c8714b5e1482d205d2e3e424d1290Peter Qiu EXPECT_CALL(*dhcp_server, Start()).WillOnce(Return(true)); 160943cf3a0afdad2cc6bea02b181f09e6ff23df628Peter Qiu EXPECT_CALL(manager_, RequestDHCPPortAccess(_)); 161fda548ca8f0b29834a37b83e836f4ccc3268fa1dPeter Qiu EXPECT_CALL(*hostapd_monitor_, Start()); 162682a9324b86ce27fd1c461704fa2e80e40ed043dPeter Qiu EXPECT_TRUE(StartService(&error)); 1632ea547f45d2a143e1b25b275c46d1f317186b07aPeter Qiu EXPECT_TRUE(error.IsSuccess()); 164376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu} 165376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu 166376e40426ad6055adfb384240b6e9a5d732f06e5Peter QiuTEST_F(ServiceTest, StopWhenServiceNotRunning) { 1672ea547f45d2a143e1b25b275c46d1f317186b07aPeter Qiu Error error; 168d9c79aa078a5df1882848d26a52d48a02b4057a5Peter Qiu EXPECT_FALSE(service_->Stop(&error)); 1692ea547f45d2a143e1b25b275c46d1f317186b07aPeter Qiu VerifyError( 1702ea547f45d2a143e1b25b275c46d1f317186b07aPeter Qiu error, Error::kInternalError, "Service is not currently running"); 171376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu} 172376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu 173376e40426ad6055adfb384240b6e9a5d732f06e5Peter QiuTEST_F(ServiceTest, StopSuccess) { 174376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu StartDummyProcess(); 175376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu 176d9c79aa078a5df1882848d26a52d48a02b4057a5Peter Qiu MockConfig* config = new MockConfig(&manager_); 177fb39ba4b2ef92f0c9d19f6910a350cd8a14405a0Peter Qiu SetConfig(config); 1782ea547f45d2a143e1b25b275c46d1f317186b07aPeter Qiu Error error; 179fb39ba4b2ef92f0c9d19f6910a350cd8a14405a0Peter Qiu EXPECT_CALL(*config, ReleaseDevice()).Times(1); 180d9c79aa078a5df1882848d26a52d48a02b4057a5Peter Qiu EXPECT_TRUE(service_->Stop(&error)); 1816789bcbfbc2cbc7eec7713513b4b2038f7f8c52cPeter Qiu Mock::VerifyAndClearExpectations(config); 182376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu} 183376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu 184376e40426ad6055adfb384240b6e9a5d732f06e5Peter Qiu} // namespace apmanager 185