blob: 951fd6f410bc0a5cedd4bb25f4162e1ec7d72427 [file] [log] [blame]
mukesh agrawal8a3188d2011-12-01 20:56:44 +00001// Copyright (c) 2012 The Chromium OS Authors. All rights reserved.
Chris Masone9be4a9d2011-05-16 15:44:09 -07002// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
Chris Masone3bd3c8c2011-06-13 08:20:26 -07004
5#include "shill/manager.h"
6
Jason Glasgowdf7c5532012-05-14 14:41:45 -04007#include <map>
Chris Masone6791a432011-07-12 13:23:19 -07008#include <set>
9
Chris Masone9be4a9d2011-05-16 15:44:09 -070010#include <glib.h>
11
Paul Stewarte73d05c2012-03-29 16:26:05 -070012#include <base/file_util.h>
Paul Stewart5ad16062013-02-21 18:10:48 -080013#include <base/files/scoped_temp_dir.h>
Eric Shienbrood3e20a232012-02-16 11:35:56 -050014#include <base/stl_util.h>
Paul Stewart5dc40aa2011-10-28 19:43:43 -070015#include <base/stringprintf.h>
Chris Masone3bd3c8c2011-06-13 08:20:26 -070016#include <chromeos/dbus/service_constants.h>
Chris Masone7156c922011-08-23 20:36:21 -070017#include <gmock/gmock.h>
Chris Masone2ae797d2011-08-23 20:41:00 -070018#include <gtest/gtest.h>
Chris Masone9be4a9d2011-05-16 15:44:09 -070019
mukesh agrawal32399322011-09-01 10:53:43 -070020#include "shill/adaptor_interfaces.h"
Chris Masone6515aab2011-10-12 16:19:09 -070021#include "shill/ephemeral_profile.h"
mukesh agrawal32399322011-09-01 10:53:43 -070022#include "shill/error.h"
Chris Masone6515aab2011-10-12 16:19:09 -070023#include "shill/glib.h"
24#include "shill/key_file_store.h"
mukesh agrawal7a4e4002011-09-06 11:26:05 -070025#include "shill/key_value_store.h"
mukesh agrawal00752532013-05-03 15:46:55 -070026#include "shill/link_monitor.h"
Christopher Wiley3e7635e2012-08-15 09:46:17 -070027#include "shill/logging.h"
mukesh agrawal32399322011-09-01 10:53:43 -070028#include "shill/mock_adaptors.h"
Paul Stewartc1dec4d2011-12-08 15:25:28 -080029#include "shill/mock_connection.h"
Chris Masoned7732e42011-05-20 11:08:56 -070030#include "shill/mock_control.h"
Christopher Wiley1057cd72013-02-28 15:21:29 -080031#include "shill/mock_crypto_util_proxy.h"
Chris Masone9be4a9d2011-05-16 15:44:09 -070032#include "shill/mock_device.h"
Paul Stewartc1dec4d2011-12-08 15:25:28 -080033#include "shill/mock_device_info.h"
Paul Stewart35eff132013-04-12 12:08:40 -070034#include "shill/mock_ethernet_eap_provider.h"
Chris Masone7aa5f902011-07-11 11:13:35 -070035#include "shill/mock_glib.h"
Thieu Lea20cbc22012-01-09 22:01:43 +000036#include "shill/mock_metrics.h"
Darin Petkovca621542012-07-25 14:25:56 +020037#include "shill/mock_power_manager.h"
Chris Masone7aa5f902011-07-11 11:13:35 -070038#include "shill/mock_profile.h"
Paul Stewart4d5efb72012-09-17 12:24:34 -070039#include "shill/mock_resolver.h"
Chris Masone9be4a9d2011-05-16 15:44:09 -070040#include "shill/mock_service.h"
Chris Masoneb9c00592011-10-06 13:10:39 -070041#include "shill/mock_store.h"
Paul Stewart3c504012013-01-17 17:49:58 -080042#include "shill/mock_wifi_provider.h"
Paul Stewart7f61e522012-03-22 11:13:45 -070043#include "shill/mock_wifi_service.h"
mukesh agrawal00752532013-05-03 15:46:55 -070044#include "shill/portal_detector.h"
Chris Masone3bd3c8c2011-06-13 08:20:26 -070045#include "shill/property_store_unittest.h"
Darin Petkovca621542012-07-25 14:25:56 +020046#include "shill/proxy_factory.h"
mukesh agrawal00752532013-05-03 15:46:55 -070047#include "shill/resolver.h"
Chris Masone6515aab2011-10-12 16:19:09 -070048#include "shill/service_under_test.h"
mukesh agrawal7a4e4002011-09-06 11:26:05 -070049#include "shill/wifi_service.h"
Darin Petkovc63dcf02012-05-24 11:51:43 +020050#include "shill/wimax_service.h"
Chris Masone3bd3c8c2011-06-13 08:20:26 -070051
Christopher Wiley1057cd72013-02-28 15:21:29 -080052using base::Bind;
Albert Chaulk0e1cdea2013-02-27 15:32:55 -080053using base::FilePath;
Paul Stewart5ad16062013-02-21 18:10:48 -080054using base::ScopedTempDir;
Chris Masone3bd3c8c2011-06-13 08:20:26 -070055using std::map;
Chris Masone6791a432011-07-12 13:23:19 -070056using std::set;
Chris Masone3bd3c8c2011-06-13 08:20:26 -070057using std::string;
58using std::vector;
59
Chris Masone9be4a9d2011-05-16 15:44:09 -070060namespace shill {
Chris Masone9be4a9d2011-05-16 15:44:09 -070061using ::testing::_;
Chris Masone6515aab2011-10-12 16:19:09 -070062using ::testing::AnyNumber;
Gaurav Shah435de2c2011-11-17 19:01:07 -080063using ::testing::ContainerEq;
Paul Stewart7f5ad572012-06-04 15:18:54 -070064using ::testing::DoAll;
Paul Stewarte2bad7c2012-03-14 08:55:33 -070065using ::testing::InSequence;
mukesh agrawal46c27cc2013-07-10 16:39:10 -070066using ::testing::Invoke;
mukesh agrawal784566d2012-08-08 18:32:58 -070067using ::testing::Mock;
Paul Stewart22aa71b2011-09-16 12:15:11 -070068using ::testing::Ne;
Chris Masone9be4a9d2011-05-16 15:44:09 -070069using ::testing::NiceMock;
Paul Stewart967eaeb2013-04-25 19:53:07 -070070using ::testing::Ref;
Chris Masone9be4a9d2011-05-16 15:44:09 -070071using ::testing::Return;
Paul Stewartce4ec192012-03-14 12:53:46 -070072using ::testing::ReturnRef;
Paul Stewart7f5ad572012-06-04 15:18:54 -070073using ::testing::SaveArg;
Daniel Erat0818cca2012-12-14 10:16:21 -080074using ::testing::SetArgumentPointee;
Gaurav Shah435de2c2011-11-17 19:01:07 -080075using ::testing::StrEq;
Paul Stewart3d9bcf52011-12-12 15:02:22 -080076using ::testing::StrictMock;
Chris Masone9d779932011-08-25 16:33:41 -070077using ::testing::Test;
mukesh agrawal46c27cc2013-07-10 16:39:10 -070078using ::testing::WithArg;
Chris Masone9be4a9d2011-05-16 15:44:09 -070079
Chris Masone3bd3c8c2011-06-13 08:20:26 -070080class ManagerTest : public PropertyStoreTest {
Chris Masone9be4a9d2011-05-16 15:44:09 -070081 public:
Chris Masone3c3f6a12011-07-01 10:01:41 -070082 ManagerTest()
Darin Petkov3ec55342012-09-28 14:04:44 +020083 : power_manager_(new MockPowerManager(NULL, &proxy_factory_)),
Paul Stewartc1dec4d2011-12-08 15:25:28 -080084 device_info_(new NiceMock<MockDeviceInfo>(
85 control_interface(),
86 reinterpret_cast<EventDispatcher*>(NULL),
Thieu Le3426c8f2012-01-11 17:35:11 -080087 reinterpret_cast<Metrics*>(NULL),
Paul Stewartc1dec4d2011-12-08 15:25:28 -080088 reinterpret_cast<Manager*>(NULL))),
Paul Stewart3c504012013-01-17 17:49:58 -080089 manager_adaptor_(new NiceMock<ManagerMockAdaptor>()),
Paul Stewart35eff132013-04-12 12:08:40 -070090 ethernet_eap_provider_(new NiceMock<MockEthernetEapProvider>()),
Christopher Wiley1057cd72013-02-28 15:21:29 -080091 wifi_provider_(new NiceMock<MockWiFiProvider>()),
92 crypto_util_proxy_(new NiceMock<MockCryptoUtilProxy>(dispatcher(),
93 glib())) {
Paul Stewart22aa71b2011-09-16 12:15:11 -070094 mock_devices_.push_back(new NiceMock<MockDevice>(control_interface(),
95 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -080096 metrics(),
Paul Stewart22aa71b2011-09-16 12:15:11 -070097 manager(),
98 "null0",
99 "addr0",
100 0));
101 mock_devices_.push_back(new NiceMock<MockDevice>(control_interface(),
102 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800103 metrics(),
Paul Stewart22aa71b2011-09-16 12:15:11 -0700104 manager(),
105 "null1",
106 "addr1",
107 1));
108 mock_devices_.push_back(new NiceMock<MockDevice>(control_interface(),
109 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800110 metrics(),
Paul Stewart22aa71b2011-09-16 12:15:11 -0700111 manager(),
112 "null2",
113 "addr2",
114 2));
Gaurav Shah435de2c2011-11-17 19:01:07 -0800115 mock_devices_.push_back(new NiceMock<MockDevice>(control_interface(),
116 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800117 metrics(),
Gaurav Shah435de2c2011-11-17 19:01:07 -0800118 manager(),
119 "null3",
120 "addr3",
121 3));
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700122 manager()->connect_profiles_to_rpc_ = false;
Paul Stewart63864b62012-11-07 15:10:55 -0800123 SetRunning(true);
Paul Stewartc1dec4d2011-12-08 15:25:28 -0800124
125 // Replace the manager's adaptor with a quieter one, and one
126 // we can do EXPECT*() against. Passes ownership.
127 manager()->adaptor_.reset(manager_adaptor_);
Paul Stewart3c504012013-01-17 17:49:58 -0800128
Paul Stewart35eff132013-04-12 12:08:40 -0700129 // Replace the manager's Ethernet EAP provider with our mock.
130 // Passes ownership.
131 manager()->ethernet_eap_provider_.reset(ethernet_eap_provider_);
132
Paul Stewart3c504012013-01-17 17:49:58 -0800133 // Replace the manager's WiFi provider with our mock. Passes
134 // ownership.
135 manager()->wifi_provider_.reset(wifi_provider_);
Christopher Wiley1057cd72013-02-28 15:21:29 -0800136
137 // Replace the manager's crypto util proxy with our mock. Passes
138 // ownership.
139 manager()->crypto_util_proxy_.reset(crypto_util_proxy_);
Paul Stewart9dd253e2013-04-22 08:32:59 -0700140
141 // Reset service serial number so service sorting by unique_name()
142 // (and by extension, sorting by order of creation) is predictable.
143 Service::serial_number_ = 10000;
Chris Masone3c3f6a12011-07-01 10:01:41 -0700144 }
Chris Masone3bd3c8c2011-06-13 08:20:26 -0700145 virtual ~ManagerTest() {}
Chris Masone9be4a9d2011-05-16 15:44:09 -0700146
Darin Petkov4cbff5b2013-01-29 16:29:05 +0100147 void SetMetrics(Metrics *metrics) {
148 manager()->set_metrics(metrics);
149 }
150
Paul Stewartfdd16072011-09-16 12:41:35 -0700151 bool IsDeviceRegistered(const DeviceRefPtr &device,
152 Technology::Identifier tech) {
Chris Masonec1e50412011-06-07 13:04:53 -0700153 vector<DeviceRefPtr> devices;
Chris Masone9d779932011-08-25 16:33:41 -0700154 manager()->FilterByTechnology(tech, &devices);
Chris Masone2b105542011-06-22 10:58:09 -0700155 return (devices.size() == 1 && devices[0].get() == device.get());
Chris Masone9be4a9d2011-05-16 15:44:09 -0700156 }
Paul Stewart22aa71b2011-09-16 12:15:11 -0700157 bool ServiceOrderIs(ServiceRefPtr svc1, ServiceRefPtr svc2);
Chris Masone9be4a9d2011-05-16 15:44:09 -0700158
Paul Stewarta849a3d2011-11-03 05:54:09 -0700159 void AdoptProfile(Manager *manager, ProfileRefPtr profile) {
160 manager->profiles_.push_back(profile);
161 }
162
Paul Stewart63864b62012-11-07 15:10:55 -0800163 void SetRunning(bool running) {
164 manager()->running_ = running;
165 }
166
Paul Stewart75225512012-01-26 22:51:33 -0800167 ProfileRefPtr GetEphemeralProfile(Manager *manager) {
168 return manager->ephemeral_profile_;
169 }
170
Paul Stewart307c2502013-03-23 12:32:10 -0700171 vector<ProfileRefPtr> &GetProfiles(Manager *manager) {
172 return manager->profiles_;
173 }
174
Chris Masone6515aab2011-10-12 16:19:09 -0700175 Profile *CreateProfileForManager(Manager *manager, GLib *glib) {
176 Profile::Identifier id("rather", "irrelevant");
Chris Masone6515aab2011-10-12 16:19:09 -0700177 FilePath final_path(storage_path());
178 final_path = final_path.Append("test.profile");
179 scoped_ptr<KeyFileStore> storage(new KeyFileStore(glib));
180 storage->set_path(final_path);
181 if (!storage->Open())
182 return NULL;
Paul Stewart5ad16062013-02-21 18:10:48 -0800183 Profile *profile(new Profile(control_interface(),
Thieu Le5133b712013-02-19 14:47:21 -0800184 metrics(),
Paul Stewart5ad16062013-02-21 18:10:48 -0800185 manager,
186 id,
187 "",
188 false));
189 profile->set_storage(storage.release()); // Passes ownership of "storage".
190 return profile; // Passes onwership of "profile".
Chris Masone6515aab2011-10-12 16:19:09 -0700191 }
192
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700193 bool CreateBackingStoreForService(ScopedTempDir *temp_dir,
194 const string &profile_identifier,
195 const string &service_name) {
196 GLib glib;
197 KeyFileStore store(&glib);
198 store.set_path(temp_dir->path().Append(profile_identifier + ".profile"));
199 return store.Open() &&
200 store.SetString(service_name, "rather", "irrelevant") &&
201 store.Close();
202 }
203
204 Error::Type TestCreateProfile(Manager *manager, const string &name) {
205 Error error;
Paul Stewart19c871d2011-12-15 16:10:13 -0800206 string path;
207 manager->CreateProfile(name, &path, &error);
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700208 return error.type();
209 }
210
211 Error::Type TestPopAnyProfile(Manager *manager) {
212 Error error;
213 manager->PopAnyProfile(&error);
214 return error.type();
215 }
216
Paul Stewart307c2502013-03-23 12:32:10 -0700217 Error::Type TestPopAllUserProfiles(Manager *manager) {
218 Error error;
219 manager->PopAllUserProfiles(&error);
220 return error.type();
221 }
222
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700223 Error::Type TestPopProfile(Manager *manager, const string &name) {
224 Error error;
225 manager->PopProfile(name, &error);
226 return error.type();
227 }
228
229 Error::Type TestPushProfile(Manager *manager, const string &name) {
230 Error error;
Paul Stewart19c871d2011-12-15 16:10:13 -0800231 string path;
232 manager->PushProfile(name, &path, &error);
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700233 return error.type();
234 }
mukesh agrawal8a3188d2011-12-01 20:56:44 +0000235
Paul Stewartf3eced92013-04-17 12:18:22 -0700236 Error::Type TestInsertUserProfile(Manager *manager,
237 const string &name,
238 const string &user_hash) {
239 Error error;
240 string path;
241 manager->InsertUserProfile(name, user_hash, &path, &error);
242 return error.type();
243 }
244
Paul Stewartd2e1c362013-03-03 19:06:07 -0800245 scoped_refptr<MockProfile> AddNamedMockProfileToManager(
246 Manager *manager, const string &name) {
Paul Stewartcb3eb892012-06-07 14:24:46 -0700247 scoped_refptr<MockProfile> profile(
Thieu Le5133b712013-02-19 14:47:21 -0800248 new MockProfile(control_interface(), metrics(), manager, ""));
Paul Stewartd2e1c362013-03-03 19:06:07 -0800249 EXPECT_CALL(*profile, GetRpcIdentifier()).WillRepeatedly(Return(name));
Darin Petkove7c6ad32012-06-29 10:22:09 +0200250 EXPECT_CALL(*profile, UpdateDevice(_)).WillRepeatedly(Return(false));
Paul Stewartcb3eb892012-06-07 14:24:46 -0700251 AdoptProfile(manager, profile);
Paul Stewartd2e1c362013-03-03 19:06:07 -0800252 return profile;
253 }
254
255 void AddMockProfileToManager(Manager *manager) {
256 AddNamedMockProfileToManager(manager, "/");
Paul Stewartcb3eb892012-06-07 14:24:46 -0700257 }
258
Paul Stewartdfa46052012-06-26 09:44:14 -0700259 void CompleteServiceSort() {
260 EXPECT_FALSE(manager()->sort_services_task_.IsCancelled());
261 dispatcher()->DispatchPendingEvents();
262 EXPECT_TRUE(manager()->sort_services_task_.IsCancelled());
263 }
264
Paul Stewart49739c02012-08-08 17:24:03 -0700265 RpcIdentifier GetDefaultServiceRpcIdentifier() {
266 return manager()->GetDefaultServiceRpcIdentifier(NULL);
267 }
268
Paul Stewart4d5efb72012-09-17 12:24:34 -0700269 void SetResolver(Resolver *resolver) {
270 manager()->resolver_ = resolver;
271 }
272
mukesh agrawalbebf1b82013-04-23 15:06:33 -0700273 bool SetIgnoredDNSSearchPaths(const string &search_paths, Error *error) {
274 return manager()->SetIgnoredDNSSearchPaths(search_paths, error);
275 }
276
277 bool SetCheckPortalList(const string &check_portal_list, Error *error) {
278 return manager()->SetCheckPortalList(check_portal_list, error);
Paul Stewart4d5efb72012-09-17 12:24:34 -0700279 }
280
281 const string &GetIgnoredDNSSearchPaths() {
282 return manager()->props_.ignored_dns_search_paths;
283 }
284
Paul Stewartd2e1c362013-03-03 19:06:07 -0800285 WiFiServiceRefPtr ReleaseTempMockService() {
286 // Take a reference to hold during this function.
287 WiFiServiceRefPtr temp_service = temp_mock_service_;
288 temp_mock_service_ = NULL;
289 return temp_service;
290 }
291
Paul Stewartf1ce5d22011-05-19 13:10:20 -0700292 protected:
mukesh agrawal8a3188d2011-12-01 20:56:44 +0000293 typedef scoped_refptr<MockService> MockServiceRefPtr;
294
Darin Petkova5e07ef2012-07-09 14:27:57 +0200295 class ServiceWatcher : public base::SupportsWeakPtr<ServiceWatcher> {
296 public:
297 ServiceWatcher() {}
298 virtual ~ServiceWatcher() {}
299
300 MOCK_METHOD1(OnDefaultServiceChanged, void(const ServiceRefPtr &service));
301
302 private:
303 DISALLOW_COPY_AND_ASSIGN(ServiceWatcher);
304 };
305
Darin Petkovca621542012-07-25 14:25:56 +0200306 class TestProxyFactory : public ProxyFactory {
307 public:
308 TestProxyFactory() {}
309
310 virtual PowerManagerProxyInterface *CreatePowerManagerProxy(
311 PowerManagerProxyDelegate */*delegate*/) {
312 return NULL;
313 }
314
315 private:
316 DISALLOW_COPY_AND_ASSIGN(TestProxyFactory);
317 };
318
Darin Petkov3ec55342012-09-28 14:04:44 +0200319 class TerminationActionTest :
320 public base::SupportsWeakPtr<TerminationActionTest> {
321 public:
322 static const char kActionName[];
323
324 TerminationActionTest() : manager_(NULL) {}
325 virtual ~TerminationActionTest() {}
326
327 MOCK_METHOD1(Done, void(const Error &error));
328
329 void Action() {
330 manager_->TerminationActionComplete("action");
331 }
332
333 void set_manager(Manager *manager) { manager_ = manager; }
334
335 private:
336 Manager *manager_;
337 DISALLOW_COPY_AND_ASSIGN(TerminationActionTest);
338 };
339
Christopher Wiley1057cd72013-02-28 15:21:29 -0800340 class DestinationVerificationTest :
341 public base::SupportsWeakPtr<DestinationVerificationTest> {
342 public:
343 DestinationVerificationTest() {}
344 virtual ~DestinationVerificationTest() {}
345
346 MOCK_METHOD2(ResultBoolCallbackStub, void(const Error &result, bool flag));
347 MOCK_METHOD2(ResultStringCallbackStub, void(const Error &result,
348 const string &value));
349 private:
350 DISALLOW_COPY_AND_ASSIGN(DestinationVerificationTest);
351 };
352
mukesh agrawal46c27cc2013-07-10 16:39:10 -0700353 class DisableTechnologyReplyHandler :
354 public base::SupportsWeakPtr<DisableTechnologyReplyHandler> {
355 public:
356 DisableTechnologyReplyHandler() {}
357 virtual ~DisableTechnologyReplyHandler() {}
358
359 MOCK_METHOD1(ReportResult, void(const Error &));
360
361 private:
362 DISALLOW_COPY_AND_ASSIGN(DisableTechnologyReplyHandler);
363 };
364
Darin Petkovca621542012-07-25 14:25:56 +0200365 void SetPowerState(PowerManagerProxyDelegate::SuspendState state) {
366 power_manager_->power_state_ = state;
367 }
368
369 void SetPowerManager() {
370 manager()->set_power_manager(power_manager_.release());
371 }
372
Darin Petkov3ec55342012-09-28 14:04:44 +0200373 HookTable *GetTerminationActions() {
374 return &manager()->termination_actions_;
375 }
376
Darin Petkovca621542012-07-25 14:25:56 +0200377 void OnPowerStateChanged(PowerManagerProxyDelegate::SuspendState state) {
378 manager()->OnPowerStateChanged(state);
379 }
380
Daniel Erat0818cca2012-12-14 10:16:21 -0800381 void OnSuspendImminent(int suspend_id) {
382 manager()->OnSuspendImminent(suspend_id);
Darin Petkov3ec55342012-09-28 14:04:44 +0200383 }
384
Daniel Erat0818cca2012-12-14 10:16:21 -0800385 void OnSuspendActionsComplete(int suspend_id, const Error &error) {
386 manager()->OnSuspendActionsComplete(suspend_id, error);
Darin Petkov3ec55342012-09-28 14:04:44 +0200387 }
388
Paul Stewartbfb82552012-10-24 16:48:48 -0700389 vector<string> EnumerateAvailableServices() {
390 return manager()->EnumerateAvailableServices(NULL);
391 }
392
393 vector<string> EnumerateWatchedServices() {
394 return manager()->EnumerateWatchedServices(NULL);
395 }
396
mukesh agrawal8a3188d2011-12-01 20:56:44 +0000397 MockServiceRefPtr MakeAutoConnectableService() {
398 MockServiceRefPtr service = new NiceMock<MockService>(control_interface(),
399 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800400 metrics(),
mukesh agrawal8a3188d2011-12-01 20:56:44 +0000401 manager());
402 service->MakeFavorite();
mukesh agrawalcbfb34e2013-04-17 19:33:25 -0700403 service->SetConnectable(true);
mukesh agrawal8a3188d2011-12-01 20:56:44 +0000404 return service;
405 }
406
Paul Stewart35eff132013-04-12 12:08:40 -0700407 void SetEapProviderService(const ServiceRefPtr &service) {
408 ethernet_eap_provider_->set_service(service);
409 }
410
Darin Petkovca621542012-07-25 14:25:56 +0200411 TestProxyFactory proxy_factory_;
412 scoped_ptr<MockPowerManager> power_manager_;
Paul Stewart22aa71b2011-09-16 12:15:11 -0700413 vector<scoped_refptr<MockDevice> > mock_devices_;
Paul Stewartc1dec4d2011-12-08 15:25:28 -0800414 scoped_ptr<MockDeviceInfo> device_info_;
415
Paul Stewartd2e1c362013-03-03 19:06:07 -0800416 // This service is held for the manager, and given ownership in a mock
417 // function. This ensures that when the Manager takes ownership, there
418 // is only one reference left.
419 scoped_refptr<MockWiFiService> temp_mock_service_;
420
Paul Stewart3c504012013-01-17 17:49:58 -0800421 // These pointers are owned by the manager, and only tracked here for
422 // EXPECT*()
Paul Stewartc1dec4d2011-12-08 15:25:28 -0800423 ManagerMockAdaptor *manager_adaptor_;
Paul Stewart35eff132013-04-12 12:08:40 -0700424 MockEthernetEapProvider *ethernet_eap_provider_;
Paul Stewart3c504012013-01-17 17:49:58 -0800425 MockWiFiProvider *wifi_provider_;
Christopher Wiley1057cd72013-02-28 15:21:29 -0800426 MockCryptoUtilProxy *crypto_util_proxy_;
Chris Masone9be4a9d2011-05-16 15:44:09 -0700427};
428
Darin Petkov3ec55342012-09-28 14:04:44 +0200429const char ManagerTest::TerminationActionTest::kActionName[] = "action";
430
Paul Stewart22aa71b2011-09-16 12:15:11 -0700431bool ManagerTest::ServiceOrderIs(ServiceRefPtr svc0, ServiceRefPtr svc1) {
Paul Stewartdfa46052012-06-26 09:44:14 -0700432 if (!manager()->sort_services_task_.IsCancelled()) {
433 manager()->SortServicesTask();
434 }
Paul Stewart22aa71b2011-09-16 12:15:11 -0700435 return (svc0.get() == manager()->services_[0].get() &&
436 svc1.get() == manager()->services_[1].get());
437}
438
mukesh agrawal46c27cc2013-07-10 16:39:10 -0700439void SetErrorPermissionDenied(Error *error) {
440 error->Populate(Error::kPermissionDenied);
441}
442
Chris Masone3bd3c8c2011-06-13 08:20:26 -0700443TEST_F(ManagerTest, Contains) {
mukesh agrawalde29fa82011-09-16 16:16:36 -0700444 EXPECT_TRUE(manager()->store().Contains(flimflam::kStateProperty));
445 EXPECT_FALSE(manager()->store().Contains(""));
Chris Masone3bd3c8c2011-06-13 08:20:26 -0700446}
447
Chris Masone9be4a9d2011-05-16 15:44:09 -0700448TEST_F(ManagerTest, DeviceRegistration) {
Joshua Krollda798622012-06-05 12:30:48 -0700449 ON_CALL(*mock_devices_[0].get(), technology())
450 .WillByDefault(Return(Technology::kEthernet));
451 ON_CALL(*mock_devices_[1].get(), technology())
452 .WillByDefault(Return(Technology::kWifi));
453 ON_CALL(*mock_devices_[2].get(), technology())
454 .WillByDefault(Return(Technology::kCellular));
Chris Masone9be4a9d2011-05-16 15:44:09 -0700455
Paul Stewart22aa71b2011-09-16 12:15:11 -0700456 manager()->RegisterDevice(mock_devices_[0]);
457 manager()->RegisterDevice(mock_devices_[1]);
458 manager()->RegisterDevice(mock_devices_[2]);
Chris Masone9be4a9d2011-05-16 15:44:09 -0700459
Paul Stewart22aa71b2011-09-16 12:15:11 -0700460 EXPECT_TRUE(IsDeviceRegistered(mock_devices_[0], Technology::kEthernet));
461 EXPECT_TRUE(IsDeviceRegistered(mock_devices_[1], Technology::kWifi));
462 EXPECT_TRUE(IsDeviceRegistered(mock_devices_[2], Technology::kCellular));
Chris Masone9be4a9d2011-05-16 15:44:09 -0700463}
464
Paul Stewarta41e38d2011-11-11 07:47:29 -0800465TEST_F(ManagerTest, DeviceRegistrationAndStart) {
466 manager()->running_ = true;
Eric Shienbrood9a245532012-03-07 14:20:39 -0500467 mock_devices_[0]->enabled_persistent_ = true;
468 mock_devices_[1]->enabled_persistent_ = false;
469 EXPECT_CALL(*mock_devices_[0].get(), SetEnabled(true))
Paul Stewarta41e38d2011-11-11 07:47:29 -0800470 .Times(1);
Eric Shienbrood9a245532012-03-07 14:20:39 -0500471 EXPECT_CALL(*mock_devices_[1].get(), SetEnabled(_))
Paul Stewarta41e38d2011-11-11 07:47:29 -0800472 .Times(0);
473 manager()->RegisterDevice(mock_devices_[0]);
474 manager()->RegisterDevice(mock_devices_[1]);
475}
476
477TEST_F(ManagerTest, DeviceRegistrationWithProfile) {
Thieu Le5133b712013-02-19 14:47:21 -0800478 MockProfile *profile =
479 new MockProfile(control_interface(), metrics(), manager(), "");
Paul Stewarta41e38d2011-11-11 07:47:29 -0800480 DeviceRefPtr device_ref(mock_devices_[0].get());
481 AdoptProfile(manager(), profile); // Passes ownership.
482 EXPECT_CALL(*profile, ConfigureDevice(device_ref));
Darin Petkove7c6ad32012-06-29 10:22:09 +0200483 EXPECT_CALL(*profile, UpdateDevice(device_ref));
Paul Stewarta41e38d2011-11-11 07:47:29 -0800484 manager()->RegisterDevice(mock_devices_[0]);
485}
486
Chris Masone9be4a9d2011-05-16 15:44:09 -0700487TEST_F(ManagerTest, DeviceDeregistration) {
Joshua Krollda798622012-06-05 12:30:48 -0700488 ON_CALL(*mock_devices_[0].get(), technology())
489 .WillByDefault(Return(Technology::kEthernet));
490 ON_CALL(*mock_devices_[1].get(), technology())
491 .WillByDefault(Return(Technology::kWifi));
Chris Masone9be4a9d2011-05-16 15:44:09 -0700492
Gaurav Shah435de2c2011-11-17 19:01:07 -0800493 manager()->RegisterDevice(mock_devices_[0]);
494 manager()->RegisterDevice(mock_devices_[1]);
Chris Masone9be4a9d2011-05-16 15:44:09 -0700495
Paul Stewart22aa71b2011-09-16 12:15:11 -0700496 ASSERT_TRUE(IsDeviceRegistered(mock_devices_[0], Technology::kEthernet));
497 ASSERT_TRUE(IsDeviceRegistered(mock_devices_[1], Technology::kWifi));
Chris Masone9be4a9d2011-05-16 15:44:09 -0700498
Thieu Le5133b712013-02-19 14:47:21 -0800499 MockProfile *profile =
500 new MockProfile(control_interface(), metrics(), manager(), "");
Paul Stewart212d60f2012-07-12 10:59:13 -0700501 AdoptProfile(manager(), profile); // Passes ownership.
502
Eric Shienbrood9a245532012-03-07 14:20:39 -0500503 EXPECT_CALL(*mock_devices_[0].get(), SetEnabled(false));
Paul Stewart212d60f2012-07-12 10:59:13 -0700504 EXPECT_CALL(*profile, UpdateDevice(DeviceRefPtr(mock_devices_[0])));
Gaurav Shah435de2c2011-11-17 19:01:07 -0800505 manager()->DeregisterDevice(mock_devices_[0]);
Paul Stewart22aa71b2011-09-16 12:15:11 -0700506 EXPECT_FALSE(IsDeviceRegistered(mock_devices_[0], Technology::kEthernet));
Chris Masone9be4a9d2011-05-16 15:44:09 -0700507
Eric Shienbrood9a245532012-03-07 14:20:39 -0500508 EXPECT_CALL(*mock_devices_[1].get(), SetEnabled(false));
Paul Stewart212d60f2012-07-12 10:59:13 -0700509 EXPECT_CALL(*profile, UpdateDevice(DeviceRefPtr(mock_devices_[1])));
Gaurav Shah435de2c2011-11-17 19:01:07 -0800510 manager()->DeregisterDevice(mock_devices_[1]);
Paul Stewart22aa71b2011-09-16 12:15:11 -0700511 EXPECT_FALSE(IsDeviceRegistered(mock_devices_[1], Technology::kWifi));
Chris Masone9be4a9d2011-05-16 15:44:09 -0700512}
513
514TEST_F(ManagerTest, ServiceRegistration) {
Chris Masone9d779932011-08-25 16:33:41 -0700515 // It's much easier and safer to use a real GLib for this test.
516 GLib glib;
Chris Masone2176a882011-09-14 22:29:15 -0700517 Manager manager(control_interface(),
518 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800519 metrics(),
Chris Masone9d779932011-08-25 16:33:41 -0700520 &glib,
521 run_path(),
522 storage_path(),
523 string());
Chris Masone6515aab2011-10-12 16:19:09 -0700524 ProfileRefPtr profile(CreateProfileForManager(&manager, &glib));
525 ASSERT_TRUE(profile.get());
Paul Stewarta849a3d2011-11-03 05:54:09 -0700526 AdoptProfile(&manager, profile);
Chris Masone6515aab2011-10-12 16:19:09 -0700527
Chris Masone9be4a9d2011-05-16 15:44:09 -0700528 scoped_refptr<MockService> mock_service(
Chris Masone2176a882011-09-14 22:29:15 -0700529 new NiceMock<MockService>(control_interface(),
530 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800531 metrics(),
Chris Masone9d779932011-08-25 16:33:41 -0700532 &manager));
Chris Masone9be4a9d2011-05-16 15:44:09 -0700533 scoped_refptr<MockService> mock_service2(
Chris Masone2176a882011-09-14 22:29:15 -0700534 new NiceMock<MockService>(control_interface(),
535 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800536 metrics(),
Chris Masone9d779932011-08-25 16:33:41 -0700537 &manager));
Paul Stewartce4ec192012-03-14 12:53:46 -0700538
Darin Petkov457728b2013-01-09 09:49:08 +0100539 string service1_name(mock_service->unique_name());
540 string service2_name(mock_service2->unique_name());
mukesh agrawal51a7e932011-07-27 16:18:26 -0700541
542 EXPECT_CALL(*mock_service.get(), GetRpcIdentifier())
543 .WillRepeatedly(Return(service1_name));
Chris Masone6791a432011-07-12 13:23:19 -0700544 EXPECT_CALL(*mock_service2.get(), GetRpcIdentifier())
mukesh agrawal51a7e932011-07-27 16:18:26 -0700545 .WillRepeatedly(Return(service2_name));
Paul Stewartee6b3d72013-07-12 16:07:51 -0700546 // TODO(quiche): make this EXPECT_CALL work (crbug.com/203247)
Chris Masone9d779932011-08-25 16:33:41 -0700547 // EXPECT_CALL(*dynamic_cast<ManagerMockAdaptor *>(manager.adaptor_.get()),
mukesh agrawal32399322011-09-01 10:53:43 -0700548 // EmitRpcIdentifierArrayChanged(flimflam::kServicesProperty, _));
Chris Masone9be4a9d2011-05-16 15:44:09 -0700549
Chris Masone9d779932011-08-25 16:33:41 -0700550 manager.RegisterService(mock_service);
551 manager.RegisterService(mock_service2);
Chris Masone9be4a9d2011-05-16 15:44:09 -0700552
Gaurav Shah1b7a6162011-11-09 11:41:01 -0800553 Error error;
554 vector<string> rpc_ids = manager.EnumerateAvailableServices(&error);
Chris Masone6791a432011-07-12 13:23:19 -0700555 set<string> ids(rpc_ids.begin(), rpc_ids.end());
mukesh agrawal51a7e932011-07-27 16:18:26 -0700556 EXPECT_EQ(2, ids.size());
557 EXPECT_TRUE(ContainsKey(ids, mock_service->GetRpcIdentifier()));
558 EXPECT_TRUE(ContainsKey(ids, mock_service2->GetRpcIdentifier()));
Chris Masone6791a432011-07-12 13:23:19 -0700559
Chris Masone9d779932011-08-25 16:33:41 -0700560 EXPECT_TRUE(manager.FindService(service1_name).get() != NULL);
561 EXPECT_TRUE(manager.FindService(service2_name).get() != NULL);
562
563 manager.Stop();
Chris Masone9be4a9d2011-05-16 15:44:09 -0700564}
565
Chris Masone6515aab2011-10-12 16:19:09 -0700566TEST_F(ManagerTest, RegisterKnownService) {
567 // It's much easier and safer to use a real GLib for this test.
568 GLib glib;
569 Manager manager(control_interface(),
570 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800571 metrics(),
Chris Masone6515aab2011-10-12 16:19:09 -0700572 &glib,
573 run_path(),
574 storage_path(),
575 string());
576 ProfileRefPtr profile(CreateProfileForManager(&manager, &glib));
577 ASSERT_TRUE(profile.get());
Paul Stewarta849a3d2011-11-03 05:54:09 -0700578 AdoptProfile(&manager, profile);
Chris Masone6515aab2011-10-12 16:19:09 -0700579 {
580 ServiceRefPtr service1(new ServiceUnderTest(control_interface(),
581 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800582 metrics(),
Chris Masone6515aab2011-10-12 16:19:09 -0700583 &manager));
Chris Masone6515aab2011-10-12 16:19:09 -0700584 ASSERT_TRUE(profile->AdoptService(service1));
585 ASSERT_TRUE(profile->ContainsService(service1));
586 } // Force destruction of service1.
587
588 ServiceRefPtr service2(new ServiceUnderTest(control_interface(),
589 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800590 metrics(),
Chris Masone6515aab2011-10-12 16:19:09 -0700591 &manager));
592 manager.RegisterService(service2);
593 EXPECT_EQ(service2->profile().get(), profile.get());
594 manager.Stop();
595}
596
597TEST_F(ManagerTest, RegisterUnknownService) {
598 // It's much easier and safer to use a real GLib for this test.
599 GLib glib;
600 Manager manager(control_interface(),
601 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800602 metrics(),
Chris Masone6515aab2011-10-12 16:19:09 -0700603 &glib,
604 run_path(),
605 storage_path(),
606 string());
607 ProfileRefPtr profile(CreateProfileForManager(&manager, &glib));
608 ASSERT_TRUE(profile.get());
Paul Stewarta849a3d2011-11-03 05:54:09 -0700609 AdoptProfile(&manager, profile);
Chris Masone6515aab2011-10-12 16:19:09 -0700610 {
611 ServiceRefPtr service1(new ServiceUnderTest(control_interface(),
612 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800613 metrics(),
Chris Masone6515aab2011-10-12 16:19:09 -0700614 &manager));
Chris Masone6515aab2011-10-12 16:19:09 -0700615 ASSERT_TRUE(profile->AdoptService(service1));
616 ASSERT_TRUE(profile->ContainsService(service1));
617 } // Force destruction of service1.
618 scoped_refptr<MockService> mock_service2(
619 new NiceMock<MockService>(control_interface(),
620 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800621 metrics(),
Chris Masone6515aab2011-10-12 16:19:09 -0700622 &manager));
623 EXPECT_CALL(*mock_service2.get(), GetStorageIdentifier())
Darin Petkov457728b2013-01-09 09:49:08 +0100624 .WillRepeatedly(Return(mock_service2->unique_name()));
Chris Masone6515aab2011-10-12 16:19:09 -0700625 manager.RegisterService(mock_service2);
626 EXPECT_NE(mock_service2->profile().get(), profile.get());
627 manager.Stop();
628}
629
mukesh agrawal8a3188d2011-12-01 20:56:44 +0000630TEST_F(ManagerTest, DeregisterUnregisteredService) {
631 // WiFi assumes that it can deregister a service that is not
632 // registered. (E.g. a hidden service can be deregistered when it
633 // loses its last endpoint, and again when WiFi is Stop()-ed.)
634 //
635 // So test that doing so doesn't cause a crash.
636 MockServiceRefPtr service = new NiceMock<MockService>(control_interface(),
637 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800638 metrics(),
mukesh agrawal8a3188d2011-12-01 20:56:44 +0000639 manager());
640 manager()->DeregisterService(service);
641}
642
Chris Masonea8a2c252011-06-27 22:16:30 -0700643TEST_F(ManagerTest, GetProperties) {
Paul Stewartcb3eb892012-06-07 14:24:46 -0700644 AddMockProfileToManager(manager());
Chris Masonea8a2c252011-06-27 22:16:30 -0700645 map<string, ::DBus::Variant> props;
646 Error error(Error::kInvalidProperty, "");
647 {
648 ::DBus::Error dbus_error;
649 string expected("portal_list");
mukesh agrawalde29fa82011-09-16 16:16:36 -0700650 manager()->mutable_store()->SetStringProperty(
651 flimflam::kCheckPortalListProperty,
652 expected,
653 &error);
Chris Masone9d779932011-08-25 16:33:41 -0700654 DBusAdaptor::GetProperties(manager()->store(), &props, &dbus_error);
Chris Masonea8a2c252011-06-27 22:16:30 -0700655 ASSERT_FALSE(props.find(flimflam::kCheckPortalListProperty) == props.end());
656 EXPECT_EQ(props[flimflam::kCheckPortalListProperty].reader().get_string(),
657 expected);
658 }
659 {
660 ::DBus::Error dbus_error;
661 bool expected = true;
mukesh agrawalde29fa82011-09-16 16:16:36 -0700662 manager()->mutable_store()->SetBoolProperty(flimflam::kOfflineModeProperty,
663 expected,
664 &error);
Chris Masone9d779932011-08-25 16:33:41 -0700665 DBusAdaptor::GetProperties(manager()->store(), &props, &dbus_error);
Chris Masonea8a2c252011-06-27 22:16:30 -0700666 ASSERT_FALSE(props.find(flimflam::kOfflineModeProperty) == props.end());
667 EXPECT_EQ(props[flimflam::kOfflineModeProperty].reader().get_bool(),
668 expected);
669 }
670}
671
Chris Masone3c3f6a12011-07-01 10:01:41 -0700672TEST_F(ManagerTest, GetDevicesProperty) {
Paul Stewartcb3eb892012-06-07 14:24:46 -0700673 AddMockProfileToManager(manager());
Gaurav Shah435de2c2011-11-17 19:01:07 -0800674 manager()->RegisterDevice(mock_devices_[0]);
675 manager()->RegisterDevice(mock_devices_[1]);
Chris Masone3c3f6a12011-07-01 10:01:41 -0700676 {
677 map<string, ::DBus::Variant> props;
678 ::DBus::Error dbus_error;
Chris Masone9d779932011-08-25 16:33:41 -0700679 DBusAdaptor::GetProperties(manager()->store(), &props, &dbus_error);
Chris Masone3c3f6a12011-07-01 10:01:41 -0700680 ASSERT_FALSE(props.find(flimflam::kDevicesProperty) == props.end());
Paul Stewartcb3eb892012-06-07 14:24:46 -0700681 vector < ::DBus::Path> devices =
682 props[flimflam::kDevicesProperty].operator vector< ::DBus::Path>();
Chris Masone3c3f6a12011-07-01 10:01:41 -0700683 EXPECT_EQ(2, devices.size());
684 }
Chris Masone3c3f6a12011-07-01 10:01:41 -0700685}
686
mukesh agrawal2366eed2012-03-20 18:21:50 -0700687TEST_F(ManagerTest, GetServicesProperty) {
Paul Stewartcb3eb892012-06-07 14:24:46 -0700688 AddMockProfileToManager(manager());
mukesh agrawal2366eed2012-03-20 18:21:50 -0700689 map<string, ::DBus::Variant> props;
690 ::DBus::Error dbus_error;
691 DBusAdaptor::GetProperties(manager()->store(), &props, &dbus_error);
692 map<string, ::DBus::Variant>::const_iterator prop =
693 props.find(flimflam::kServicesProperty);
694 ASSERT_FALSE(prop == props.end());
695 const ::DBus::Variant &variant = prop->second;
696 ASSERT_TRUE(DBusAdaptor::IsPaths(variant.signature()));
697}
698
Chris Masone6791a432011-07-12 13:23:19 -0700699TEST_F(ManagerTest, MoveService) {
Chris Masone2176a882011-09-14 22:29:15 -0700700 Manager manager(control_interface(),
701 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800702 metrics(),
Chris Masone6515aab2011-10-12 16:19:09 -0700703 glib(),
Chris Masone9d779932011-08-25 16:33:41 -0700704 run_path(),
705 storage_path(),
706 string());
Chris Masone6515aab2011-10-12 16:19:09 -0700707 scoped_refptr<MockService> s2(new MockService(control_interface(),
708 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800709 metrics(),
Chris Masone6515aab2011-10-12 16:19:09 -0700710 &manager));
711 // Inject an actual profile, backed by a fake StoreInterface
Chris Masoneb9c00592011-10-06 13:10:39 -0700712 {
Chris Masone6515aab2011-10-12 16:19:09 -0700713 Profile::Identifier id("irrelevant");
Chris Masoneb9c00592011-10-06 13:10:39 -0700714 ProfileRefPtr profile(
Thieu Le5133b712013-02-19 14:47:21 -0800715 new Profile(control_interface(), metrics(), &manager, id, "", false));
Chris Masoneb9c00592011-10-06 13:10:39 -0700716 MockStore *storage = new MockStore;
Chris Masone6515aab2011-10-12 16:19:09 -0700717 EXPECT_CALL(*storage, ContainsGroup(s2->GetStorageIdentifier()))
Chris Masone6515aab2011-10-12 16:19:09 -0700718 .WillRepeatedly(Return(true));
719 EXPECT_CALL(*storage, Flush())
720 .Times(AnyNumber())
721 .WillRepeatedly(Return(true));
Chris Masoneb9c00592011-10-06 13:10:39 -0700722 profile->set_storage(storage);
Paul Stewarta849a3d2011-11-03 05:54:09 -0700723 AdoptProfile(&manager, profile);
Chris Masoneb9c00592011-10-06 13:10:39 -0700724 }
Chris Masone6515aab2011-10-12 16:19:09 -0700725 // Create a profile that already has |s2| in it.
Thieu Le5133b712013-02-19 14:47:21 -0800726 ProfileRefPtr profile(
727 new EphemeralProfile(control_interface(), metrics(), &manager));
Paul Stewart451aa7f2012-04-11 19:07:58 -0700728 EXPECT_TRUE(profile->AdoptService(s2));
Chris Masone9d779932011-08-25 16:33:41 -0700729
Chris Masone6515aab2011-10-12 16:19:09 -0700730 // Now, move the Service |s2| to another profile.
731 EXPECT_CALL(*s2.get(), Save(_)).WillOnce(Return(true));
732 ASSERT_TRUE(manager.MoveServiceToProfile(s2, manager.ActiveProfile()));
Chris Masone6791a432011-07-12 13:23:19 -0700733
734 // Force destruction of the original Profile, to ensure that the Service
735 // is kept alive and populated with data.
736 profile = NULL;
Chris Masone6515aab2011-10-12 16:19:09 -0700737 ASSERT_TRUE(manager.ActiveProfile()->ContainsService(s2));
Chris Masone9d779932011-08-25 16:33:41 -0700738 manager.Stop();
Chris Masone6791a432011-07-12 13:23:19 -0700739}
740
Paul Stewart7f61e522012-03-22 11:13:45 -0700741TEST_F(ManagerTest, LookupProfileByRpcIdentifier) {
742 scoped_refptr<MockProfile> mock_profile(
Thieu Le5133b712013-02-19 14:47:21 -0800743 new MockProfile(control_interface(), metrics(), manager(), ""));
Paul Stewart7f61e522012-03-22 11:13:45 -0700744 const string kProfileName("profile0");
745 EXPECT_CALL(*mock_profile, GetRpcIdentifier())
746 .WillRepeatedly(Return(kProfileName));
747 AdoptProfile(manager(), mock_profile);
748
749 EXPECT_FALSE(manager()->LookupProfileByRpcIdentifier("foo"));
750 ProfileRefPtr profile = manager()->LookupProfileByRpcIdentifier(kProfileName);
751 EXPECT_EQ(mock_profile.get(), profile.get());
752}
753
Paul Stewart1b1a7f22012-01-06 16:24:06 -0800754TEST_F(ManagerTest, SetProfileForService) {
755 scoped_refptr<MockProfile> profile0(
Thieu Le5133b712013-02-19 14:47:21 -0800756 new MockProfile(control_interface(), metrics(), manager(), ""));
Paul Stewart1b1a7f22012-01-06 16:24:06 -0800757 string profile_name0("profile0");
758 EXPECT_CALL(*profile0, GetRpcIdentifier())
759 .WillRepeatedly(Return(profile_name0));
760 AdoptProfile(manager(), profile0);
761 scoped_refptr<MockService> service(new MockService(control_interface(),
762 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800763 metrics(),
Paul Stewart1b1a7f22012-01-06 16:24:06 -0800764 manager()));
Paul Stewart649f3a42012-04-24 23:22:16 -0700765 EXPECT_FALSE(manager()->HasService(service));
766 {
767 Error error;
768 EXPECT_CALL(*profile0, AdoptService(_))
769 .WillOnce(Return(true));
770 // Expect that setting the profile of a service that does not already
771 // have one assigned does not cause a crash.
772 manager()->SetProfileForService(service, "profile0", &error);
773 EXPECT_TRUE(error.IsSuccess());
774 }
775
776 // The service should be registered as a side-effect of the profile being
777 // set for this service.
778 EXPECT_TRUE(manager()->HasService(service));
779
780 // Since we have mocked Profile::AdoptServie() above, the service's
781 // profile was not actually changed. Do so explicitly now.
Paul Stewart1b1a7f22012-01-06 16:24:06 -0800782 service->set_profile(profile0);
783
784 {
785 Error error;
786 manager()->SetProfileForService(service, "foo", &error);
787 EXPECT_EQ(Error::kInvalidArguments, error.type());
Paul Stewart7f61e522012-03-22 11:13:45 -0700788 EXPECT_EQ("Unknown Profile foo requested for Service", error.message());
Paul Stewart1b1a7f22012-01-06 16:24:06 -0800789 }
790
791 {
792 Error error;
793 manager()->SetProfileForService(service, profile_name0, &error);
794 EXPECT_EQ(Error::kInvalidArguments, error.type());
795 EXPECT_EQ("Service is already connected to this profile", error.message());
796 }
797
798 scoped_refptr<MockProfile> profile1(
Thieu Le5133b712013-02-19 14:47:21 -0800799 new MockProfile(control_interface(), metrics(), manager(), ""));
Paul Stewart1b1a7f22012-01-06 16:24:06 -0800800 string profile_name1("profile1");
801 EXPECT_CALL(*profile1, GetRpcIdentifier())
802 .WillRepeatedly(Return(profile_name1));
803 AdoptProfile(manager(), profile1);
804
805 {
806 Error error;
807 EXPECT_CALL(*profile1, AdoptService(_))
808 .WillOnce(Return(true));
809 EXPECT_CALL(*profile0, AbandonService(_))
810 .WillOnce(Return(true));
811 manager()->SetProfileForService(service, profile_name1, &error);
812 EXPECT_TRUE(error.IsSuccess());
813 }
814}
815
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700816TEST_F(ManagerTest, CreateProfile) {
817 // It's much easier to use real Glib here since we want the storage
818 // side-effects.
819 GLib glib;
820 ScopedTempDir temp_dir;
821 ASSERT_TRUE(temp_dir.CreateUniqueTempDir());
822
823 Manager manager(control_interface(),
824 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800825 metrics(),
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700826 &glib,
827 run_path(),
828 storage_path(),
829 temp_dir.path().value());
830
831 // Invalid name should be rejected.
832 EXPECT_EQ(Error::kInvalidArguments, TestCreateProfile(&manager, ""));
833
Paul Stewartd0a3b812012-03-28 22:48:22 -0700834 // A profile with invalid characters in it should similarly be rejected.
835 EXPECT_EQ(Error::kInvalidArguments,
836 TestCreateProfile(&manager, "valid_profile"));
837
838 // We should be able to create a machine profile.
839 EXPECT_EQ(Error::kSuccess, TestCreateProfile(&manager, "valid"));
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700840
Gary Morainb672d352012-04-25 09:19:06 -0700841 // We should succeed in creating a valid user profile. Verify the returned
842 // path.
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700843 const char kProfile[] = "~user/profile";
Gary Morainb672d352012-04-25 09:19:06 -0700844 {
845 Error error;
846 string path;
847 manager.CreateProfile(kProfile, &path, &error);
848 EXPECT_EQ(Error::kSuccess, error.type());
849 EXPECT_EQ("/profile_rpc", path);
850 }
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700851
852 // We should fail in creating it a second time (already exists).
853 EXPECT_EQ(Error::kAlreadyExists, TestCreateProfile(&manager, kProfile));
854}
855
Christopher Wiley3e7635e2012-08-15 09:46:17 -0700856// We receive PopProfile when a user logs out, and it should always trigger a
857// MemoryLog Clear() call.
858TEST_F(ManagerTest, PopProfileShouldClearMemoryLog) {
859 GLib glib;
860 ScopedTempDir temp_dir;
861 ASSERT_TRUE(temp_dir.CreateUniqueTempDir());
862 Manager manager(control_interface(),
863 dispatcher(),
864 metrics(),
865 &glib,
866 run_path(),
867 storage_path(),
868 temp_dir.path().value());
869 const char kProfile0[] = "~user/profile0";
870 const char kPurgedMessage[] = "This message should be purged";
871 // Create a profile and push it on the stack, leave one uncreated
872 ASSERT_EQ(Error::kSuccess, TestCreateProfile(&manager, kProfile0));
873 EXPECT_EQ(Error::kSuccess, TestPushProfile(&manager, kProfile0));
874
875 // Popping a profile which isn't on top should still clear the log.
876 LOG(INFO) << kPurgedMessage;
877 EXPECT_TRUE(MemoryLog::GetInstance()->TestContainsMessageWithText(
878 kPurgedMessage));
879 EXPECT_EQ(Error::kNotSupported, TestPopProfile(&manager, "~user/profile1"));
880 EXPECT_FALSE(MemoryLog::GetInstance()->TestContainsMessageWithText(
881 kPurgedMessage));
882
883 // Popping an invalid profile name should do the same thing.
884 LOG(INFO) << kPurgedMessage;
885 EXPECT_TRUE(MemoryLog::GetInstance()->TestContainsMessageWithText(
886 kPurgedMessage));
887 EXPECT_EQ(Error::kInvalidArguments, TestPopProfile(&manager, "~"));
888 EXPECT_FALSE(MemoryLog::GetInstance()->TestContainsMessageWithText(
889 kPurgedMessage));
890
891 // Successful pops also purge the message log.
892 LOG(INFO) << kPurgedMessage;
893 EXPECT_TRUE(MemoryLog::GetInstance()->TestContainsMessageWithText(
894 kPurgedMessage));
895 EXPECT_EQ(Error::kSuccess, TestPopProfile(&manager, kProfile0));
896 EXPECT_FALSE(MemoryLog::GetInstance()->TestContainsMessageWithText(
897 kPurgedMessage));
898}
899
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700900TEST_F(ManagerTest, PushPopProfile) {
901 // It's much easier to use real Glib in creating a Manager for this
902 // test here since we want the storage side-effects.
903 GLib glib;
904 ScopedTempDir temp_dir;
905 ASSERT_TRUE(temp_dir.CreateUniqueTempDir());
906 Manager manager(control_interface(),
907 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800908 metrics(),
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700909 &glib,
910 run_path(),
911 storage_path(),
912 temp_dir.path().value());
913
914 // Pushing an invalid profile should fail.
915 EXPECT_EQ(Error::kInvalidArguments, TestPushProfile(&manager, ""));
916
Paul Stewartd0a3b812012-03-28 22:48:22 -0700917 // Pushing a default profile that does not exist should fail.
918 EXPECT_EQ(Error::kNotFound, TestPushProfile(&manager, "default"));
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700919
920 const char kProfile0[] = "~user/profile0";
921 const char kProfile1[] = "~user/profile1";
922
923 // Create a couple of profiles.
924 ASSERT_EQ(Error::kSuccess, TestCreateProfile(&manager, kProfile0));
925 ASSERT_EQ(Error::kSuccess, TestCreateProfile(&manager, kProfile1));
926
927 // Push these profiles on the stack.
928 EXPECT_EQ(Error::kSuccess, TestPushProfile(&manager, kProfile0));
929 EXPECT_EQ(Error::kSuccess, TestPushProfile(&manager, kProfile1));
930
931 // Pushing a profile a second time should fail.
932 EXPECT_EQ(Error::kAlreadyExists, TestPushProfile(&manager, kProfile0));
933 EXPECT_EQ(Error::kAlreadyExists, TestPushProfile(&manager, kProfile1));
934
Gaurav Shah1b7a6162011-11-09 11:41:01 -0800935 Error error;
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700936 // Active profile should be the last one we pushed.
Paul Stewart1b253142012-01-26 14:05:52 -0800937 EXPECT_EQ(kProfile1, "~" + manager.ActiveProfile()->GetFriendlyName());
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700938
939 // Make sure a profile name that doesn't exist fails.
940 const char kProfile2Id[] = "profile2";
941 const string kProfile2 = base::StringPrintf("~user/%s", kProfile2Id);
942 EXPECT_EQ(Error::kNotFound, TestPushProfile(&manager, kProfile2));
943
944 // Create a new service, with a specific storage name.
945 scoped_refptr<MockService> service(
946 new NiceMock<MockService>(control_interface(),
947 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800948 metrics(),
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700949 &manager));
950 const char kServiceName[] = "service_storage_name";
951 EXPECT_CALL(*service.get(), GetStorageIdentifier())
952 .WillRepeatedly(Return(kServiceName));
953 EXPECT_CALL(*service.get(), Load(_))
954 .WillRepeatedly(Return(true));
955
956 // Add this service to the manager -- it should end up in the ephemeral
957 // profile.
958 manager.RegisterService(service);
Paul Stewart75225512012-01-26 22:51:33 -0800959 ASSERT_EQ(GetEphemeralProfile(&manager), service->profile());
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700960
961 // Create storage for a profile that contains the service storage name.
962 ASSERT_TRUE(CreateBackingStoreForService(&temp_dir, kProfile2Id,
963 kServiceName));
964
965 // When we push the profile, the service should move away from the
966 // ephemeral profile to this new profile since it has an entry for
967 // this service.
968 EXPECT_EQ(Error::kSuccess, TestPushProfile(&manager, kProfile2));
Paul Stewart75225512012-01-26 22:51:33 -0800969 EXPECT_NE(GetEphemeralProfile(&manager), service->profile());
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700970 EXPECT_EQ(kProfile2, "~" + service->profile()->GetFriendlyName());
971
972 // Insert another profile that should supersede ownership of the service.
973 const char kProfile3Id[] = "profile3";
974 const string kProfile3 = base::StringPrintf("~user/%s", kProfile3Id);
975 ASSERT_TRUE(CreateBackingStoreForService(&temp_dir, kProfile3Id,
976 kServiceName));
977 EXPECT_EQ(Error::kSuccess, TestPushProfile(&manager, kProfile3));
978 EXPECT_EQ(kProfile3, "~" + service->profile()->GetFriendlyName());
979
980 // Popping an invalid profile name should fail.
981 EXPECT_EQ(Error::kInvalidArguments, TestPopProfile(&manager, "~"));
982
983 // Popping an profile that is not at the top of the stack should fail.
984 EXPECT_EQ(Error::kNotSupported, TestPopProfile(&manager, kProfile0));
985
986 // Popping the top profile should succeed.
987 EXPECT_EQ(Error::kSuccess, TestPopProfile(&manager, kProfile3));
988
989 // Moreover the service should have switched profiles to profile 2.
990 EXPECT_EQ(kProfile2, "~" + service->profile()->GetFriendlyName());
991
992 // Popping the top profile should succeed.
993 EXPECT_EQ(Error::kSuccess, TestPopAnyProfile(&manager));
994
995 // The service should now revert to the ephemeral profile.
Paul Stewart75225512012-01-26 22:51:33 -0800996 EXPECT_EQ(GetEphemeralProfile(&manager), service->profile());
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700997
998 // Pop the remaining two services off the stack.
999 EXPECT_EQ(Error::kSuccess, TestPopAnyProfile(&manager));
1000 EXPECT_EQ(Error::kSuccess, TestPopAnyProfile(&manager));
1001
1002 // Next pop should fail with "stack is empty".
1003 EXPECT_EQ(Error::kNotFound, TestPopAnyProfile(&manager));
Paul Stewartd0a3b812012-03-28 22:48:22 -07001004
1005 const char kMachineProfile0[] = "machineprofile0";
1006 const char kMachineProfile1[] = "machineprofile1";
1007 ASSERT_EQ(Error::kSuccess, TestCreateProfile(&manager, kMachineProfile0));
1008 ASSERT_EQ(Error::kSuccess, TestCreateProfile(&manager, kMachineProfile1));
1009
1010 // Should be able to push a machine profile.
1011 EXPECT_EQ(Error::kSuccess, TestPushProfile(&manager, kMachineProfile0));
1012
1013 // Should be able to push a user profile atop a machine profile.
1014 EXPECT_EQ(Error::kSuccess, TestPushProfile(&manager, kProfile0));
1015
1016 // Pushing a system-wide profile on top of a user profile should fail.
1017 EXPECT_EQ(Error::kInvalidArguments,
1018 TestPushProfile(&manager, kMachineProfile1));
1019
1020 // However if we pop the user profile, we should be able stack another
1021 // machine profile on.
1022 EXPECT_EQ(Error::kSuccess, TestPopAnyProfile(&manager));
1023 EXPECT_EQ(Error::kSuccess, TestPushProfile(&manager, kMachineProfile1));
Paul Stewart307c2502013-03-23 12:32:10 -07001024
1025 // Add two user profiles to the top of the stack.
1026 EXPECT_EQ(Error::kSuccess, TestPushProfile(&manager, kProfile0));
1027 EXPECT_EQ(Error::kSuccess, TestPushProfile(&manager, kProfile1));
1028 vector<ProfileRefPtr> &profiles = GetProfiles(&manager);
1029 EXPECT_EQ(4, profiles.size());
1030
1031 // PopAllUserProfiles should remove both user profiles, leaving the two
1032 // machine profiles.
1033 EXPECT_EQ(Error::kSuccess, TestPopAllUserProfiles(&manager));
1034 EXPECT_EQ(2, profiles.size());
1035 EXPECT_TRUE(profiles[0]->GetUser().empty());
1036 EXPECT_TRUE(profiles[1]->GetUser().empty());
Paul Stewartf3eced92013-04-17 12:18:22 -07001037
1038 // Use InsertUserProfile() instead. Although a machine profile is valid
1039 // in this state, it cannot be added via InsertUserProfile.
1040 EXPECT_EQ(Error::kSuccess, TestPopProfile(&manager, kMachineProfile1));
1041 EXPECT_EQ(Error::kInvalidArguments,
1042 TestInsertUserProfile(&manager, kMachineProfile1, "machinehash1"));
1043 const char kUserHash0[] = "userhash0";
1044 const char kUserHash1[] = "userhash1";
1045 EXPECT_EQ(Error::kSuccess,
1046 TestInsertUserProfile(&manager, kProfile0, kUserHash0));
1047 EXPECT_EQ(Error::kSuccess,
1048 TestInsertUserProfile(&manager, kProfile1, kUserHash1));
1049 EXPECT_EQ(3, profiles.size());
1050 EXPECT_EQ(kUserHash0, profiles[1]->GetUserHash());
1051 EXPECT_EQ(kUserHash1, profiles[2]->GetUserHash());
Paul Stewart5dc40aa2011-10-28 19:43:43 -07001052}
1053
Paul Stewarte73d05c2012-03-29 16:26:05 -07001054TEST_F(ManagerTest, RemoveProfile) {
1055 // It's much easier to use real Glib in creating a Manager for this
1056 // test here since we want the storage side-effects.
1057 GLib glib;
1058 ScopedTempDir temp_dir;
1059 ASSERT_TRUE(temp_dir.CreateUniqueTempDir());
1060 Manager manager(control_interface(),
1061 dispatcher(),
1062 metrics(),
1063 &glib,
1064 run_path(),
1065 storage_path(),
1066 temp_dir.path().value());
1067
1068 const char kProfile0[] = "profile0";
1069 FilePath profile_path(
1070 FilePath(storage_path()).Append(string(kProfile0) + ".profile"));
1071
1072 ASSERT_EQ(Error::kSuccess, TestCreateProfile(&manager, kProfile0));
1073 ASSERT_TRUE(file_util::PathExists(profile_path));
1074
1075 EXPECT_EQ(Error::kSuccess, TestPushProfile(&manager, kProfile0));
1076
1077 // Remove should fail since the profile is still on the stack.
1078 {
1079 Error error;
1080 manager.RemoveProfile(kProfile0, &error);
1081 EXPECT_EQ(Error::kInvalidArguments, error.type());
1082 }
1083
1084 // Profile path should still exist.
1085 EXPECT_TRUE(file_util::PathExists(profile_path));
1086
1087 EXPECT_EQ(Error::kSuccess, TestPopAnyProfile(&manager));
1088
1089 // This should succeed now that the profile is off the stack.
1090 {
1091 Error error;
1092 manager.RemoveProfile(kProfile0, &error);
1093 EXPECT_EQ(Error::kSuccess, error.type());
1094 }
1095
1096 // Profile path should no longer exist.
1097 EXPECT_FALSE(file_util::PathExists(profile_path));
1098
1099 // Another remove succeeds, due to a foible in file_util::Delete --
1100 // it is not an error to delete a file that does not exist.
1101 {
1102 Error error;
1103 manager.RemoveProfile(kProfile0, &error);
1104 EXPECT_EQ(Error::kSuccess, error.type());
1105 }
1106
1107 // Let's create an error case that will "work". Create a non-empty
1108 // directory in the place of the profile pathname.
1109 ASSERT_TRUE(file_util::CreateDirectory(profile_path.Append("foo")));
1110 {
1111 Error error;
1112 manager.RemoveProfile(kProfile0, &error);
1113 EXPECT_EQ(Error::kOperationFailed, error.type());
1114 }
1115}
1116
Paul Stewartfc9a1da2012-06-27 15:54:52 -07001117TEST_F(ManagerTest, CreateDuplicateProfileWithMissingKeyfile) {
1118 // It's much easier to use real Glib in creating a Manager for this
1119 // test here since we want the storage side-effects.
1120 GLib glib;
1121 ScopedTempDir temp_dir;
1122 ASSERT_TRUE(temp_dir.CreateUniqueTempDir());
1123 Manager manager(control_interface(),
1124 dispatcher(),
1125 metrics(),
1126 &glib,
1127 run_path(),
1128 storage_path(),
1129 temp_dir.path().value());
1130
1131 const char kProfile0[] = "profile0";
1132 FilePath profile_path(
1133 FilePath(storage_path()).Append(string(kProfile0) + ".profile"));
1134
1135 ASSERT_EQ(Error::kSuccess, TestCreateProfile(&manager, kProfile0));
1136 ASSERT_TRUE(file_util::PathExists(profile_path));
1137 EXPECT_EQ(Error::kSuccess, TestPushProfile(&manager, kProfile0));
1138
1139 // Ensure that even if the backing filestore is removed, we still can't
1140 // create a profile twice.
1141 ASSERT_TRUE(file_util::Delete(profile_path, false));
1142 EXPECT_EQ(Error::kAlreadyExists, TestCreateProfile(&manager, kProfile0));
1143}
1144
Paul Stewart75225512012-01-26 22:51:33 -08001145// Use this matcher instead of passing RefPtrs directly into the arguments
1146// of EXPECT_CALL() because otherwise we may create un-cleaned-up references at
1147// system teardown.
1148MATCHER_P(IsRefPtrTo, ref_address, "") {
1149 return arg.get() == ref_address;
1150}
1151
1152TEST_F(ManagerTest, HandleProfileEntryDeletion) {
1153 MockServiceRefPtr s_not_in_profile(
1154 new NiceMock<MockService>(control_interface(),
1155 dispatcher(),
1156 metrics(),
1157 manager()));
1158 MockServiceRefPtr s_not_in_group(
1159 new NiceMock<MockService>(control_interface(),
1160 dispatcher(),
1161 metrics(),
1162 manager()));
1163 MockServiceRefPtr s_configure_fail(
1164 new NiceMock<MockService>(control_interface(),
1165 dispatcher(),
1166 metrics(),
1167 manager()));
1168 MockServiceRefPtr s_configure_succeed(
1169 new NiceMock<MockService>(control_interface(),
1170 dispatcher(),
1171 metrics(),
1172 manager()));
1173
1174 string entry_name("entry_name");
1175 EXPECT_CALL(*s_not_in_profile.get(), GetStorageIdentifier()).Times(0);
1176 EXPECT_CALL(*s_not_in_group.get(), GetStorageIdentifier())
1177 .WillRepeatedly(Return("not_entry_name"));
1178 EXPECT_CALL(*s_configure_fail.get(), GetStorageIdentifier())
1179 .WillRepeatedly(Return(entry_name));
1180 EXPECT_CALL(*s_configure_succeed.get(), GetStorageIdentifier())
1181 .WillRepeatedly(Return(entry_name));
1182
1183 manager()->RegisterService(s_not_in_profile);
1184 manager()->RegisterService(s_not_in_group);
1185 manager()->RegisterService(s_configure_fail);
1186 manager()->RegisterService(s_configure_succeed);
1187
1188 scoped_refptr<MockProfile> profile0(
Thieu Le5133b712013-02-19 14:47:21 -08001189 new StrictMock<MockProfile>(
1190 control_interface(), metrics(), manager(), ""));
Paul Stewart75225512012-01-26 22:51:33 -08001191 scoped_refptr<MockProfile> profile1(
Thieu Le5133b712013-02-19 14:47:21 -08001192 new StrictMock<MockProfile>(
1193 control_interface(), metrics(), manager(), ""));
Paul Stewart75225512012-01-26 22:51:33 -08001194
1195 s_not_in_group->set_profile(profile1);
1196 s_configure_fail->set_profile(profile1);
1197 s_configure_succeed->set_profile(profile1);
1198
1199 AdoptProfile(manager(), profile0);
1200 AdoptProfile(manager(), profile1);
1201
1202 // No services are a member of this profile.
1203 EXPECT_FALSE(manager()->HandleProfileEntryDeletion(profile0, entry_name));
1204
1205 // No services that are members of this profile have this entry name.
1206 EXPECT_FALSE(manager()->HandleProfileEntryDeletion(profile1, ""));
1207
1208 // Only services that are members of the profile and group will be abandoned.
1209 EXPECT_CALL(*profile1.get(),
1210 AbandonService(IsRefPtrTo(s_not_in_profile.get()))).Times(0);
1211 EXPECT_CALL(*profile1.get(),
1212 AbandonService(IsRefPtrTo(s_not_in_group.get()))).Times(0);
1213 EXPECT_CALL(*profile1.get(),
1214 AbandonService(IsRefPtrTo(s_configure_fail.get())))
1215 .WillOnce(Return(true));
1216 EXPECT_CALL(*profile1.get(),
1217 AbandonService(IsRefPtrTo(s_configure_succeed.get())))
1218 .WillOnce(Return(true));
1219
1220 // Never allow services to re-join profile1.
1221 EXPECT_CALL(*profile1.get(), ConfigureService(_))
1222 .WillRepeatedly(Return(false));
1223
1224 // Only allow one of the members of the profile and group to successfully
1225 // join profile0.
1226 EXPECT_CALL(*profile0.get(),
1227 ConfigureService(IsRefPtrTo(s_not_in_profile.get()))).Times(0);
1228 EXPECT_CALL(*profile0.get(),
1229 ConfigureService(IsRefPtrTo(s_not_in_group.get()))).Times(0);
1230 EXPECT_CALL(*profile0.get(),
1231 ConfigureService(IsRefPtrTo(s_configure_fail.get())))
1232 .WillOnce(Return(false));
1233 EXPECT_CALL(*profile0.get(),
1234 ConfigureService(IsRefPtrTo(s_configure_succeed.get())))
1235 .WillOnce(Return(true));
1236
1237 // Expect the failed-to-configure service to have Unload() called on it.
1238 EXPECT_CALL(*s_not_in_profile.get(), Unload()).Times(0);
1239 EXPECT_CALL(*s_not_in_group.get(), Unload()).Times(0);
1240 EXPECT_CALL(*s_configure_fail.get(), Unload()).Times(1);
1241 EXPECT_CALL(*s_configure_succeed.get(), Unload()).Times(0);
1242
1243 EXPECT_TRUE(manager()->HandleProfileEntryDeletion(profile1, entry_name));
1244
1245 EXPECT_EQ(GetEphemeralProfile(manager()), s_not_in_profile->profile().get());
1246 EXPECT_EQ(profile1, s_not_in_group->profile());
1247 EXPECT_EQ(GetEphemeralProfile(manager()), s_configure_fail->profile());
1248
1249 // Since we are using a MockProfile, the profile does not actually change,
1250 // since ConfigureService was not actually called on the service.
1251 EXPECT_EQ(profile1, s_configure_succeed->profile());
1252}
1253
Paul Stewart65512e12012-03-26 18:01:08 -07001254TEST_F(ManagerTest, HandleProfileEntryDeletionWithUnload) {
1255 MockServiceRefPtr s_will_remove0(
1256 new NiceMock<MockService>(control_interface(),
1257 dispatcher(),
1258 metrics(),
1259 manager()));
1260 MockServiceRefPtr s_will_remove1(
1261 new NiceMock<MockService>(control_interface(),
1262 dispatcher(),
1263 metrics(),
1264 manager()));
1265 MockServiceRefPtr s_will_not_remove0(
1266 new NiceMock<MockService>(control_interface(),
1267 dispatcher(),
1268 metrics(),
1269 manager()));
1270 MockServiceRefPtr s_will_not_remove1(
1271 new NiceMock<MockService>(control_interface(),
1272 dispatcher(),
1273 metrics(),
1274 manager()));
1275
1276 EXPECT_CALL(*metrics(), NotifyDefaultServiceChanged(NULL))
1277 .Times(4); // Once for each registration.
1278
1279 string entry_name("entry_name");
1280 EXPECT_CALL(*s_will_remove0.get(), GetStorageIdentifier())
1281 .WillRepeatedly(Return(entry_name));
1282 EXPECT_CALL(*s_will_remove1.get(), GetStorageIdentifier())
1283 .WillRepeatedly(Return(entry_name));
1284 EXPECT_CALL(*s_will_not_remove0.get(), GetStorageIdentifier())
1285 .WillRepeatedly(Return(entry_name));
1286 EXPECT_CALL(*s_will_not_remove1.get(), GetStorageIdentifier())
1287 .WillRepeatedly(Return(entry_name));
1288
1289 manager()->RegisterService(s_will_remove0);
Paul Stewartdfa46052012-06-26 09:44:14 -07001290 CompleteServiceSort();
Paul Stewart65512e12012-03-26 18:01:08 -07001291 manager()->RegisterService(s_will_not_remove0);
Paul Stewartdfa46052012-06-26 09:44:14 -07001292 CompleteServiceSort();
Paul Stewart65512e12012-03-26 18:01:08 -07001293 manager()->RegisterService(s_will_remove1);
Paul Stewartdfa46052012-06-26 09:44:14 -07001294 CompleteServiceSort();
Paul Stewart65512e12012-03-26 18:01:08 -07001295 manager()->RegisterService(s_will_not_remove1);
Paul Stewartdfa46052012-06-26 09:44:14 -07001296 CompleteServiceSort();
Paul Stewart65512e12012-03-26 18:01:08 -07001297
1298 // One for each service added above.
1299 ASSERT_EQ(4, manager()->services_.size());
1300
1301 scoped_refptr<MockProfile> profile(
Thieu Le5133b712013-02-19 14:47:21 -08001302 new StrictMock<MockProfile>(
1303 control_interface(), metrics(), manager(), ""));
Paul Stewart65512e12012-03-26 18:01:08 -07001304
1305 s_will_remove0->set_profile(profile);
1306 s_will_remove1->set_profile(profile);
1307 s_will_not_remove0->set_profile(profile);
1308 s_will_not_remove1->set_profile(profile);
1309
1310 AdoptProfile(manager(), profile);
1311
1312 // Deny any of the services re-entry to the profile.
1313 EXPECT_CALL(*profile, ConfigureService(_))
1314 .WillRepeatedly(Return(false));
1315
1316 EXPECT_CALL(*profile, AbandonService(ServiceRefPtr(s_will_remove0)))
1317 .WillOnce(Return(true));
1318 EXPECT_CALL(*profile, AbandonService(ServiceRefPtr(s_will_remove1)))
1319 .WillOnce(Return(true));
1320 EXPECT_CALL(*profile, AbandonService(ServiceRefPtr(s_will_not_remove0)))
1321 .WillOnce(Return(true));
1322 EXPECT_CALL(*profile, AbandonService(ServiceRefPtr(s_will_not_remove1)))
1323 .WillOnce(Return(true));
1324
1325 EXPECT_CALL(*s_will_remove0, Unload())
1326 .WillOnce(Return(true));
1327 EXPECT_CALL(*s_will_remove1, Unload())
1328 .WillOnce(Return(true));
1329 EXPECT_CALL(*s_will_not_remove0, Unload())
1330 .WillOnce(Return(false));
1331 EXPECT_CALL(*s_will_not_remove1, Unload())
1332 .WillOnce(Return(false));
1333
1334
1335 // This will cause all the profiles to be unloaded.
1336 EXPECT_TRUE(manager()->HandleProfileEntryDeletion(profile, entry_name));
1337
1338 // 2 of the 4 services added above should have been unregistered and
1339 // removed, leaving 2.
1340 EXPECT_EQ(2, manager()->services_.size());
1341 EXPECT_EQ(s_will_not_remove0.get(), manager()->services_[0].get());
1342 EXPECT_EQ(s_will_not_remove1.get(), manager()->services_[1].get());
1343}
1344
1345TEST_F(ManagerTest, PopProfileWithUnload) {
1346 MockServiceRefPtr s_will_remove0(
1347 new NiceMock<MockService>(control_interface(),
1348 dispatcher(),
1349 metrics(),
1350 manager()));
1351 MockServiceRefPtr s_will_remove1(
1352 new NiceMock<MockService>(control_interface(),
1353 dispatcher(),
1354 metrics(),
1355 manager()));
1356 MockServiceRefPtr s_will_not_remove0(
1357 new NiceMock<MockService>(control_interface(),
1358 dispatcher(),
1359 metrics(),
1360 manager()));
1361 MockServiceRefPtr s_will_not_remove1(
1362 new NiceMock<MockService>(control_interface(),
1363 dispatcher(),
1364 metrics(),
1365 manager()));
1366
1367 EXPECT_CALL(*metrics(), NotifyDefaultServiceChanged(NULL))
1368 .Times(5); // Once for each registration, and one after profile pop.
1369
1370 manager()->RegisterService(s_will_remove0);
Paul Stewartdfa46052012-06-26 09:44:14 -07001371 CompleteServiceSort();
Paul Stewart65512e12012-03-26 18:01:08 -07001372 manager()->RegisterService(s_will_not_remove0);
Paul Stewartdfa46052012-06-26 09:44:14 -07001373 CompleteServiceSort();
Paul Stewart65512e12012-03-26 18:01:08 -07001374 manager()->RegisterService(s_will_remove1);
Paul Stewartdfa46052012-06-26 09:44:14 -07001375 CompleteServiceSort();
Paul Stewart65512e12012-03-26 18:01:08 -07001376 manager()->RegisterService(s_will_not_remove1);
Paul Stewartdfa46052012-06-26 09:44:14 -07001377 CompleteServiceSort();
Paul Stewart65512e12012-03-26 18:01:08 -07001378
1379 // One for each service added above.
1380 ASSERT_EQ(4, manager()->services_.size());
1381
1382 scoped_refptr<MockProfile> profile0(
Thieu Le5133b712013-02-19 14:47:21 -08001383 new StrictMock<MockProfile>(
1384 control_interface(), metrics(), manager(), ""));
Paul Stewart65512e12012-03-26 18:01:08 -07001385 scoped_refptr<MockProfile> profile1(
Thieu Le5133b712013-02-19 14:47:21 -08001386 new StrictMock<MockProfile>(
1387 control_interface(), metrics(), manager(), ""));
Paul Stewart65512e12012-03-26 18:01:08 -07001388
1389 s_will_remove0->set_profile(profile1);
1390 s_will_remove1->set_profile(profile1);
1391 s_will_not_remove0->set_profile(profile1);
1392 s_will_not_remove1->set_profile(profile1);
1393
1394 AdoptProfile(manager(), profile0);
1395 AdoptProfile(manager(), profile1);
1396
1397 // Deny any of the services entry to profile0, so they will all be unloaded.
1398 EXPECT_CALL(*profile0, ConfigureService(_))
1399 .WillRepeatedly(Return(false));
1400
1401 EXPECT_CALL(*s_will_remove0, Unload())
1402 .WillOnce(Return(true));
1403 EXPECT_CALL(*s_will_remove1, Unload())
1404 .WillOnce(Return(true));
1405 EXPECT_CALL(*s_will_not_remove0, Unload())
Paul Stewartfc9a1da2012-06-27 15:54:52 -07001406 .WillRepeatedly(Return(false));
Paul Stewart65512e12012-03-26 18:01:08 -07001407 EXPECT_CALL(*s_will_not_remove1, Unload())
1408 .WillOnce(Return(false));
1409
Philipp Neubeck79173602012-11-13 21:10:09 +01001410 // Ignore calls to Profile::GetRpcIdentifier because of emitted changes of the
1411 // profile list.
1412 EXPECT_CALL(*profile0, GetRpcIdentifier()).Times(AnyNumber());
1413 EXPECT_CALL(*profile1, GetRpcIdentifier()).Times(AnyNumber());
1414
Paul Stewart65512e12012-03-26 18:01:08 -07001415 // This will pop profile1, which should cause all our profiles to unload.
1416 manager()->PopProfileInternal();
Paul Stewartdfa46052012-06-26 09:44:14 -07001417 CompleteServiceSort();
Paul Stewart65512e12012-03-26 18:01:08 -07001418
1419 // 2 of the 4 services added above should have been unregistered and
1420 // removed, leaving 2.
1421 EXPECT_EQ(2, manager()->services_.size());
1422 EXPECT_EQ(s_will_not_remove0.get(), manager()->services_[0].get());
1423 EXPECT_EQ(s_will_not_remove1.get(), manager()->services_[1].get());
Paul Stewartfc9a1da2012-06-27 15:54:52 -07001424
1425 // Expect the unloaded services to lose their profile reference.
1426 EXPECT_FALSE(s_will_remove0->profile());
1427 EXPECT_FALSE(s_will_remove1->profile());
1428
1429 // If we explicitly deregister a service, the effect should be the same
1430 // with respect to the profile reference.
1431 ASSERT_TRUE(s_will_not_remove0->profile());
1432 manager()->DeregisterService(s_will_not_remove0);
1433 EXPECT_FALSE(s_will_not_remove0->profile());
Paul Stewart65512e12012-03-26 18:01:08 -07001434}
1435
mukesh agrawal6bb9e7c2012-01-30 14:57:54 -08001436TEST_F(ManagerTest, SetProperty) {
Chris Masonea8a2c252011-06-27 22:16:30 -07001437 {
1438 ::DBus::Error error;
mukesh agrawalbebf1b82013-04-23 15:06:33 -07001439 ::DBus::Variant offline_mode;
1440 offline_mode.writer().append_bool(true);
mukesh agrawal6bb9e7c2012-01-30 14:57:54 -08001441 EXPECT_TRUE(DBusAdaptor::SetProperty(manager()->mutable_store(),
1442 flimflam::kOfflineModeProperty,
mukesh agrawalbebf1b82013-04-23 15:06:33 -07001443 offline_mode,
mukesh agrawal6bb9e7c2012-01-30 14:57:54 -08001444 &error));
Chris Masonea8a2c252011-06-27 22:16:30 -07001445 }
1446 {
1447 ::DBus::Error error;
mukesh agrawalbebf1b82013-04-23 15:06:33 -07001448 ::DBus::Variant country;
1449 country.writer().append_string("a_country");
mukesh agrawal6bb9e7c2012-01-30 14:57:54 -08001450 EXPECT_TRUE(DBusAdaptor::SetProperty(manager()->mutable_store(),
1451 flimflam::kCountryProperty,
mukesh agrawalbebf1b82013-04-23 15:06:33 -07001452 country,
mukesh agrawal6bb9e7c2012-01-30 14:57:54 -08001453 &error));
Chris Masonea8a2c252011-06-27 22:16:30 -07001454 }
Chris Masoneb925cc82011-06-22 15:39:57 -07001455 // Attempt to write with value of wrong type should return InvalidArgs.
Chris Masonea8a2c252011-06-27 22:16:30 -07001456 {
1457 ::DBus::Error error;
mukesh agrawal6bb9e7c2012-01-30 14:57:54 -08001458 EXPECT_FALSE(DBusAdaptor::SetProperty(manager()->mutable_store(),
1459 flimflam::kCountryProperty,
1460 PropertyStoreTest::kBoolV,
1461 &error));
Chris Masone9d779932011-08-25 16:33:41 -07001462 EXPECT_EQ(invalid_args(), error.name());
Chris Masonea8a2c252011-06-27 22:16:30 -07001463 }
1464 {
1465 ::DBus::Error error;
mukesh agrawal6bb9e7c2012-01-30 14:57:54 -08001466 EXPECT_FALSE(DBusAdaptor::SetProperty(manager()->mutable_store(),
1467 flimflam::kOfflineModeProperty,
1468 PropertyStoreTest::kStringV,
1469 &error));
Chris Masone9d779932011-08-25 16:33:41 -07001470 EXPECT_EQ(invalid_args(), error.name());
Chris Masonea8a2c252011-06-27 22:16:30 -07001471 }
Chris Masoneb925cc82011-06-22 15:39:57 -07001472 // Attempt to write R/O property should return InvalidArgs.
Chris Masonea8a2c252011-06-27 22:16:30 -07001473 {
1474 ::DBus::Error error;
mukesh agrawal6bb9e7c2012-01-30 14:57:54 -08001475 EXPECT_FALSE(DBusAdaptor::SetProperty(
mukesh agrawalde29fa82011-09-16 16:16:36 -07001476 manager()->mutable_store(),
Chris Masonea8a2c252011-06-27 22:16:30 -07001477 flimflam::kEnabledTechnologiesProperty,
1478 PropertyStoreTest::kStringsV,
1479 &error));
Chris Masone9d779932011-08-25 16:33:41 -07001480 EXPECT_EQ(invalid_args(), error.name());
Chris Masonea8a2c252011-06-27 22:16:30 -07001481 }
Chris Masone3bd3c8c2011-06-13 08:20:26 -07001482}
1483
mukesh agrawal32399322011-09-01 10:53:43 -07001484TEST_F(ManagerTest, RequestScan) {
1485 {
1486 Error error;
Paul Stewart22aa71b2011-09-16 12:15:11 -07001487 manager()->RegisterDevice(mock_devices_[0].get());
1488 manager()->RegisterDevice(mock_devices_[1].get());
Joshua Krollda798622012-06-05 12:30:48 -07001489 EXPECT_CALL(*mock_devices_[0], technology())
1490 .WillRepeatedly(Return(Technology::kWifi));
Wade Guthrie4823f4f2013-07-25 10:03:03 -07001491 EXPECT_CALL(*mock_devices_[0], Scan(Device::kFullScan, _, _));
Joshua Krollda798622012-06-05 12:30:48 -07001492 EXPECT_CALL(*mock_devices_[1], technology())
1493 .WillRepeatedly(Return(Technology::kUnknown));
Wade Guthrie4823f4f2013-07-25 10:03:03 -07001494 EXPECT_CALL(*mock_devices_[1], Scan(_, _, _)).Times(0);
Wade Guthrie68d41092013-04-02 12:56:02 -07001495 manager()->RequestScan(Device::kFullScan, flimflam::kTypeWifi, &error);
mukesh agrawal32399322011-09-01 10:53:43 -07001496 }
1497
1498 {
1499 Error error;
Wade Guthrie68d41092013-04-02 12:56:02 -07001500 manager()->RequestScan(Device::kFullScan, "bogus_device_type", &error);
mukesh agrawal32399322011-09-01 10:53:43 -07001501 EXPECT_EQ(Error::kInvalidArguments, error.type());
1502 }
1503}
1504
Darin Petkovb65c2452012-02-23 15:17:06 +01001505TEST_F(ManagerTest, GetServiceNoType) {
mukesh agrawal7a4e4002011-09-06 11:26:05 -07001506 KeyValueStore args;
1507 Error e;
Darin Petkovb65c2452012-02-23 15:17:06 +01001508 manager()->GetService(args, &e);
1509 EXPECT_EQ(Error::kInvalidArguments, e.type());
1510 EXPECT_EQ("must specify service type", e.message());
1511}
1512
1513TEST_F(ManagerTest, GetServiceUnknownType) {
1514 KeyValueStore args;
1515 Error e;
1516 args.SetString(flimflam::kTypeProperty, flimflam::kTypeEthernet);
1517 manager()->GetService(args, &e);
1518 EXPECT_EQ(Error::kNotSupported, e.type());
1519 EXPECT_EQ("service type is unsupported", e.message());
1520}
1521
Paul Stewart35eff132013-04-12 12:08:40 -07001522TEST_F(ManagerTest, GetServiceEthernetEap) {
1523 KeyValueStore args;
1524 Error e;
Paul Stewart55fc64c2013-07-18 09:51:35 -07001525 ServiceRefPtr service = new NiceMock<MockService>(control_interface(),
1526 dispatcher(),
1527 metrics(),
1528 manager());
Paul Stewart35eff132013-04-12 12:08:40 -07001529 args.SetString(flimflam::kTypeProperty, kTypeEthernetEap);
1530 SetEapProviderService(service);
1531 EXPECT_EQ(service, manager()->GetService(args, &e));
1532 EXPECT_TRUE(e.IsSuccess());
1533}
1534
Darin Petkovb65c2452012-02-23 15:17:06 +01001535TEST_F(ManagerTest, GetServiceWifi) {
mukesh agrawal7a4e4002011-09-06 11:26:05 -07001536 KeyValueStore args;
1537 Error e;
1538 WiFiServiceRefPtr wifi_service;
Darin Petkovb65c2452012-02-23 15:17:06 +01001539 args.SetString(flimflam::kTypeProperty, flimflam::kTypeWifi);
Paul Stewart3c504012013-01-17 17:49:58 -08001540 EXPECT_CALL(*wifi_provider_, GetService(_, _))
mukesh agrawal7a4e4002011-09-06 11:26:05 -07001541 .WillRepeatedly(Return(wifi_service));
Darin Petkovb65c2452012-02-23 15:17:06 +01001542 manager()->GetService(args, &e);
1543 EXPECT_TRUE(e.IsSuccess());
1544}
1545
Darin Petkov33af05c2012-02-28 10:10:30 +01001546TEST_F(ManagerTest, GetServiceVPNUnknownType) {
1547 KeyValueStore args;
1548 Error e;
1549 args.SetString(flimflam::kTypeProperty, flimflam::kTypeVPN);
Paul Stewart7f5ad572012-06-04 15:18:54 -07001550 scoped_refptr<MockProfile> profile(
Thieu Le5133b712013-02-19 14:47:21 -08001551 new StrictMock<MockProfile>(
1552 control_interface(), metrics(), manager(), ""));
Paul Stewart7f5ad572012-06-04 15:18:54 -07001553 AdoptProfile(manager(), profile);
Darin Petkov33af05c2012-02-28 10:10:30 +01001554 ServiceRefPtr service = manager()->GetService(args, &e);
1555 EXPECT_EQ(Error::kNotSupported, e.type());
1556 EXPECT_FALSE(service);
1557}
1558
Darin Petkovb65c2452012-02-23 15:17:06 +01001559TEST_F(ManagerTest, GetServiceVPN) {
1560 KeyValueStore args;
1561 Error e;
Darin Petkovb65c2452012-02-23 15:17:06 +01001562 args.SetString(flimflam::kTypeProperty, flimflam::kTypeVPN);
Darin Petkov33af05c2012-02-28 10:10:30 +01001563 args.SetString(flimflam::kProviderTypeProperty, flimflam::kProviderOpenVpn);
Darin Petkov02867712012-03-12 14:25:05 +01001564 args.SetString(flimflam::kProviderHostProperty, "10.8.0.1");
Darin Petkov4e02ba22013-04-02 13:44:08 +02001565 args.SetString(flimflam::kNameProperty, "vpn-name");
Paul Stewart7f5ad572012-06-04 15:18:54 -07001566 scoped_refptr<MockProfile> profile(
Thieu Le5133b712013-02-19 14:47:21 -08001567 new StrictMock<MockProfile>(
1568 control_interface(), metrics(), manager(), ""));
Paul Stewart7f5ad572012-06-04 15:18:54 -07001569 AdoptProfile(manager(), profile);
Darin Petkovc3505a52013-03-18 15:13:29 +01001570
1571#if defined(DISABLE_VPN)
1572
1573 ServiceRefPtr service = manager()->GetService(args, &e);
1574 EXPECT_EQ(Error::kNotSupported, e.type());
1575 EXPECT_FALSE(service);
1576
1577#else
1578
Paul Stewart7f5ad572012-06-04 15:18:54 -07001579 ServiceRefPtr updated_service;
1580 EXPECT_CALL(*profile, UpdateService(_))
1581 .WillOnce(DoAll(SaveArg<0>(&updated_service), Return(true)));
1582 ServiceRefPtr configured_service;
Paul Stewart2c575d22012-12-07 12:28:57 -08001583 EXPECT_CALL(*profile, LoadService(_))
1584 .WillOnce(Return(false));
Paul Stewart7f5ad572012-06-04 15:18:54 -07001585 EXPECT_CALL(*profile, ConfigureService(_))
1586 .WillOnce(DoAll(SaveArg<0>(&configured_service), Return(true)));
Darin Petkov33af05c2012-02-28 10:10:30 +01001587 ServiceRefPtr service = manager()->GetService(args, &e);
1588 EXPECT_TRUE(e.IsSuccess());
1589 EXPECT_TRUE(service);
Paul Stewart7f5ad572012-06-04 15:18:54 -07001590 EXPECT_EQ(service, updated_service);
1591 EXPECT_EQ(service, configured_service);
Darin Petkovc3505a52013-03-18 15:13:29 +01001592
1593#endif // DISABLE_VPN
mukesh agrawal7a4e4002011-09-06 11:26:05 -07001594}
1595
Darin Petkovc63dcf02012-05-24 11:51:43 +02001596TEST_F(ManagerTest, GetServiceWiMaxNoNetworkId) {
1597 KeyValueStore args;
1598 Error e;
1599 args.SetString(flimflam::kTypeProperty, flimflam::kTypeWimax);
1600 ServiceRefPtr service = manager()->GetService(args, &e);
1601 EXPECT_EQ(Error::kInvalidArguments, e.type());
1602 EXPECT_EQ("Missing WiMAX network id.", e.message());
1603 EXPECT_FALSE(service);
1604}
1605
Darin Petkovd1cd7972012-05-22 15:26:15 +02001606TEST_F(ManagerTest, GetServiceWiMax) {
1607 KeyValueStore args;
1608 Error e;
1609 args.SetString(flimflam::kTypeProperty, flimflam::kTypeWimax);
Darin Petkovc63dcf02012-05-24 11:51:43 +02001610 args.SetString(WiMaxService::kNetworkIdProperty, "01234567");
1611 args.SetString(flimflam::kNameProperty, "WiMAX Network");
1612 ServiceRefPtr service = manager()->GetService(args, &e);
1613 EXPECT_TRUE(e.IsSuccess());
1614 EXPECT_TRUE(service);
Darin Petkovd1cd7972012-05-22 15:26:15 +02001615}
1616
Paul Stewart7f61e522012-03-22 11:13:45 -07001617TEST_F(ManagerTest, ConfigureServiceWithInvalidProfile) {
1618 // Manager calls ActiveProfile() so we need at least one profile installed.
1619 scoped_refptr<MockProfile> profile(
Thieu Le5133b712013-02-19 14:47:21 -08001620 new NiceMock<MockProfile>(
1621 control_interface(), metrics(), manager(), ""));
Paul Stewart7f61e522012-03-22 11:13:45 -07001622 AdoptProfile(manager(), profile);
1623
1624 KeyValueStore args;
1625 args.SetString(flimflam::kProfileProperty, "xxx");
1626 Error error;
1627 manager()->ConfigureService(args, &error);
1628 EXPECT_EQ(Error::kInvalidArguments, error.type());
1629 EXPECT_EQ("Invalid profile name xxx", error.message());
1630}
1631
1632TEST_F(ManagerTest, ConfigureServiceWithGetServiceFailure) {
1633 // Manager calls ActiveProfile() so we need at least one profile installed.
1634 scoped_refptr<MockProfile> profile(
Thieu Le5133b712013-02-19 14:47:21 -08001635 new NiceMock<MockProfile>(
1636 control_interface(), metrics(), manager(), ""));
Paul Stewart7f61e522012-03-22 11:13:45 -07001637 AdoptProfile(manager(), profile);
1638
1639 KeyValueStore args;
1640 Error error;
1641 manager()->ConfigureService(args, &error);
1642 EXPECT_EQ(Error::kInvalidArguments, error.type());
1643 EXPECT_EQ("must specify service type", error.message());
1644}
1645
1646// A registered service in the ephemeral profile should be moved to the
1647// active profile as a part of configuration if no profile was explicitly
1648// specified.
1649TEST_F(ManagerTest, ConfigureRegisteredServiceWithoutProfile) {
1650 scoped_refptr<MockProfile> profile(
Thieu Le5133b712013-02-19 14:47:21 -08001651 new NiceMock<MockProfile>(
1652 control_interface(), metrics(), manager(), ""));
Paul Stewart7f61e522012-03-22 11:13:45 -07001653
1654 AdoptProfile(manager(), profile); // This is now the active profile.
1655
Paul Stewartd2e1c362013-03-03 19:06:07 -08001656 const vector<uint8_t> ssid;
Paul Stewart7f61e522012-03-22 11:13:45 -07001657 scoped_refptr<MockWiFiService> service(
1658 new NiceMock<MockWiFiService>(control_interface(),
1659 dispatcher(),
1660 metrics(),
1661 manager(),
Paul Stewart3c504012013-01-17 17:49:58 -08001662 wifi_provider_,
Paul Stewart7f61e522012-03-22 11:13:45 -07001663 ssid,
1664 "",
1665 "",
1666 false));
1667
1668 manager()->RegisterService(service);
1669 service->set_profile(GetEphemeralProfile(manager()));
1670
Paul Stewart3c504012013-01-17 17:49:58 -08001671 EXPECT_CALL(*wifi_provider_, GetService(_, _))
Paul Stewart7f61e522012-03-22 11:13:45 -07001672 .WillOnce(Return(service));
1673 EXPECT_CALL(*profile, UpdateService(ServiceRefPtr(service.get())))
1674 .WillOnce(Return(true));
1675 EXPECT_CALL(*profile, AdoptService(ServiceRefPtr(service.get())))
1676 .WillOnce(Return(true));
1677
1678 KeyValueStore args;
1679 args.SetString(flimflam::kTypeProperty, flimflam::kTypeWifi);
1680 Error error;
1681 manager()->ConfigureService(args, &error);
1682 EXPECT_TRUE(error.IsSuccess());
1683}
1684
Paul Stewart2c575d22012-12-07 12:28:57 -08001685// If we configure a service that was already registered and explicitly
Paul Stewart7f61e522012-03-22 11:13:45 -07001686// specify a profile, it should be moved from the profile it was previously
1687// in to the specified profile if one was requested.
1688TEST_F(ManagerTest, ConfigureRegisteredServiceWithProfile) {
1689 scoped_refptr<MockProfile> profile0(
Thieu Le5133b712013-02-19 14:47:21 -08001690 new NiceMock<MockProfile>(
1691 control_interface(), metrics(), manager(), ""));
Paul Stewart7f61e522012-03-22 11:13:45 -07001692 scoped_refptr<MockProfile> profile1(
Thieu Le5133b712013-02-19 14:47:21 -08001693 new NiceMock<MockProfile>(
1694 control_interface(), metrics(), manager(), ""));
Paul Stewart7f61e522012-03-22 11:13:45 -07001695
1696 const string kProfileName0 = "profile0";
1697 const string kProfileName1 = "profile1";
1698
1699 EXPECT_CALL(*profile0, GetRpcIdentifier())
1700 .WillRepeatedly(Return(kProfileName0));
1701 EXPECT_CALL(*profile1, GetRpcIdentifier())
1702 .WillRepeatedly(Return(kProfileName1));
1703
1704 AdoptProfile(manager(), profile0);
1705 AdoptProfile(manager(), profile1); // profile1 is now the ActiveProfile.
1706
Paul Stewartd2e1c362013-03-03 19:06:07 -08001707 const vector<uint8_t> ssid;
Paul Stewart7f61e522012-03-22 11:13:45 -07001708 scoped_refptr<MockWiFiService> service(
1709 new NiceMock<MockWiFiService>(control_interface(),
1710 dispatcher(),
1711 metrics(),
1712 manager(),
Paul Stewart3c504012013-01-17 17:49:58 -08001713 wifi_provider_,
Paul Stewart7f61e522012-03-22 11:13:45 -07001714 ssid,
1715 "",
1716 "",
1717 false));
1718
1719 manager()->RegisterService(service);
1720 service->set_profile(profile1);
1721
Paul Stewart3c504012013-01-17 17:49:58 -08001722 EXPECT_CALL(*wifi_provider_, GetService(_, _))
Paul Stewart7f61e522012-03-22 11:13:45 -07001723 .WillOnce(Return(service));
Paul Stewart2c575d22012-12-07 12:28:57 -08001724 EXPECT_CALL(*profile0, LoadService(ServiceRefPtr(service.get())))
1725 .WillOnce(Return(true));
Paul Stewart7f61e522012-03-22 11:13:45 -07001726 EXPECT_CALL(*profile0, UpdateService(ServiceRefPtr(service.get())))
1727 .WillOnce(Return(true));
1728 EXPECT_CALL(*profile0, AdoptService(ServiceRefPtr(service.get())))
1729 .WillOnce(Return(true));
1730 EXPECT_CALL(*profile1, AbandonService(ServiceRefPtr(service.get())))
1731 .WillOnce(Return(true));
1732
1733 KeyValueStore args;
1734 args.SetString(flimflam::kTypeProperty, flimflam::kTypeWifi);
1735 args.SetString(flimflam::kProfileProperty, kProfileName0);
1736 Error error;
1737 manager()->ConfigureService(args, &error);
1738 EXPECT_TRUE(error.IsSuccess());
1739 service->set_profile(NULL); // Breaks refcounting loop.
1740}
1741
Paul Stewart2c575d22012-12-07 12:28:57 -08001742// If we configure a service that is already a member of the specified
1743// profile, the Manager should not call LoadService or AdoptService again
1744// on this service.
1745TEST_F(ManagerTest, ConfigureRegisteredServiceWithSameProfile) {
1746 scoped_refptr<MockProfile> profile0(
Thieu Le5133b712013-02-19 14:47:21 -08001747 new NiceMock<MockProfile>(
1748 control_interface(), metrics(), manager(), ""));
Paul Stewart2c575d22012-12-07 12:28:57 -08001749
1750 const string kProfileName0 = "profile0";
1751
1752 EXPECT_CALL(*profile0, GetRpcIdentifier())
1753 .WillRepeatedly(Return(kProfileName0));
1754
1755 AdoptProfile(manager(), profile0); // profile0 is now the ActiveProfile.
1756
Paul Stewartd2e1c362013-03-03 19:06:07 -08001757 const vector<uint8_t> ssid;
Paul Stewart2c575d22012-12-07 12:28:57 -08001758 scoped_refptr<MockWiFiService> service(
1759 new NiceMock<MockWiFiService>(control_interface(),
1760 dispatcher(),
1761 metrics(),
1762 manager(),
Paul Stewart3c504012013-01-17 17:49:58 -08001763 wifi_provider_,
Paul Stewart2c575d22012-12-07 12:28:57 -08001764 ssid,
1765 "",
1766 "",
1767 false));
1768
1769 manager()->RegisterService(service);
1770 service->set_profile(profile0);
1771
Paul Stewart3c504012013-01-17 17:49:58 -08001772 EXPECT_CALL(*wifi_provider_, GetService(_, _))
Paul Stewart2c575d22012-12-07 12:28:57 -08001773 .WillOnce(Return(service));
1774 EXPECT_CALL(*profile0, LoadService(ServiceRefPtr(service.get())))
1775 .Times(0);
1776 EXPECT_CALL(*profile0, UpdateService(ServiceRefPtr(service.get())))
1777 .WillOnce(Return(true));
1778 EXPECT_CALL(*profile0, AdoptService(ServiceRefPtr(service.get())))
1779 .Times(0);
1780
1781 KeyValueStore args;
1782 args.SetString(flimflam::kTypeProperty, flimflam::kTypeWifi);
1783 args.SetString(flimflam::kProfileProperty, kProfileName0);
1784 Error error;
1785 manager()->ConfigureService(args, &error);
1786 EXPECT_TRUE(error.IsSuccess());
1787 service->set_profile(NULL); // Breaks refcounting loop.
1788}
1789
Paul Stewart7f61e522012-03-22 11:13:45 -07001790// An unregistered service should remain unregistered, but its contents should
1791// be saved to the specified profile nonetheless.
1792TEST_F(ManagerTest, ConfigureUnregisteredServiceWithProfile) {
1793 scoped_refptr<MockProfile> profile0(
Thieu Le5133b712013-02-19 14:47:21 -08001794 new NiceMock<MockProfile>(
1795 control_interface(), metrics(), manager(), ""));
Paul Stewart7f61e522012-03-22 11:13:45 -07001796 scoped_refptr<MockProfile> profile1(
Thieu Le5133b712013-02-19 14:47:21 -08001797 new NiceMock<MockProfile>(
1798 control_interface(), metrics(), manager(), ""));
Paul Stewart7f61e522012-03-22 11:13:45 -07001799
1800 const string kProfileName0 = "profile0";
1801 const string kProfileName1 = "profile1";
1802
1803 EXPECT_CALL(*profile0, GetRpcIdentifier())
1804 .WillRepeatedly(Return(kProfileName0));
1805 EXPECT_CALL(*profile1, GetRpcIdentifier())
1806 .WillRepeatedly(Return(kProfileName1));
1807
1808 AdoptProfile(manager(), profile0);
1809 AdoptProfile(manager(), profile1); // profile1 is now the ActiveProfile.
1810
Paul Stewartd2e1c362013-03-03 19:06:07 -08001811 const vector<uint8_t> ssid;
Paul Stewart7f61e522012-03-22 11:13:45 -07001812 scoped_refptr<MockWiFiService> service(
1813 new NiceMock<MockWiFiService>(control_interface(),
1814 dispatcher(),
1815 metrics(),
1816 manager(),
Paul Stewart3c504012013-01-17 17:49:58 -08001817 wifi_provider_,
Paul Stewart7f61e522012-03-22 11:13:45 -07001818 ssid,
1819 "",
1820 "",
1821 false));
1822
1823 service->set_profile(profile1);
1824
Paul Stewart3c504012013-01-17 17:49:58 -08001825 EXPECT_CALL(*wifi_provider_, GetService(_, _))
Paul Stewart7f61e522012-03-22 11:13:45 -07001826 .WillOnce(Return(service));
1827 EXPECT_CALL(*profile0, UpdateService(ServiceRefPtr(service.get())))
1828 .WillOnce(Return(true));
1829 EXPECT_CALL(*profile0, AdoptService(_))
1830 .Times(0);
1831 EXPECT_CALL(*profile1, AdoptService(_))
1832 .Times(0);
1833
1834 KeyValueStore args;
1835 args.SetString(flimflam::kTypeProperty, flimflam::kTypeWifi);
1836 args.SetString(flimflam::kProfileProperty, kProfileName0);
1837 Error error;
1838 manager()->ConfigureService(args, &error);
1839 EXPECT_TRUE(error.IsSuccess());
1840}
1841
Paul Stewartd2e1c362013-03-03 19:06:07 -08001842TEST_F(ManagerTest, ConfigureServiceForProfileWithNoType) {
1843 KeyValueStore args;
1844 Error error;
1845 ServiceRefPtr service =
1846 manager()->ConfigureServiceForProfile("", args, &error);
1847 EXPECT_EQ(Error::kNotSupported, error.type());
1848 EXPECT_EQ("This method only supports WiFi services", error.message());
1849 EXPECT_EQ(NULL, service.get());
1850}
1851
1852TEST_F(ManagerTest, ConfigureServiceForProfileWithWrongType) {
1853 KeyValueStore args;
1854 args.SetString(flimflam::kTypeProperty, flimflam::kTypeCellular);
1855 Error error;
1856 ServiceRefPtr service =
1857 manager()->ConfigureServiceForProfile("", args, &error);
1858 EXPECT_EQ(Error::kNotSupported, error.type());
1859 EXPECT_EQ("This method only supports WiFi services", error.message());
1860 EXPECT_EQ(NULL, service.get());
1861}
1862
1863TEST_F(ManagerTest, ConfigureServiceForProfileWithMissingProfile) {
1864 KeyValueStore args;
1865 args.SetString(flimflam::kTypeProperty, flimflam::kTypeWifi);
1866 Error error;
1867 ServiceRefPtr service =
1868 manager()->ConfigureServiceForProfile("/profile/foo", args, &error);
1869 EXPECT_EQ(Error::kNotFound, error.type());
1870 EXPECT_EQ("Profile specified was not found", error.message());
1871 EXPECT_EQ(NULL, service.get());
1872}
1873
1874TEST_F(ManagerTest, ConfigureServiceForProfileWithProfileMismatch) {
1875 const string kProfileName0 = "profile0";
1876 const string kProfileName1 = "profile1";
1877 scoped_refptr<MockProfile> profile0(
1878 AddNamedMockProfileToManager(manager(), kProfileName0));
1879
1880 KeyValueStore args;
1881 args.SetString(flimflam::kTypeProperty, flimflam::kTypeWifi);
1882 args.SetString(flimflam::kProfileProperty, kProfileName1);
1883 Error error;
1884 ServiceRefPtr service =
1885 manager()->ConfigureServiceForProfile(kProfileName0, args, &error);
1886 EXPECT_EQ(Error::kInvalidArguments, error.type());
1887 EXPECT_EQ("Profile argument does not match that in "
1888 "the configuration arguments", error.message());
1889 EXPECT_EQ(NULL, service.get());
1890}
1891
1892TEST_F(ManagerTest,
1893 ConfigureServiceForProfileWithNoMatchingServiceFailGetService) {
1894 const string kProfileName0 = "profile0";
1895 scoped_refptr<MockProfile> profile0(
1896 AddNamedMockProfileToManager(manager(), kProfileName0));
1897 KeyValueStore args;
1898 args.SetString(flimflam::kTypeProperty, flimflam::kTypeWifi);
1899 args.SetString(flimflam::kProfileProperty, kProfileName0);
1900
1901 EXPECT_CALL(*wifi_provider_, FindSimilarService(_, _))
1902 .WillOnce(Return(WiFiServiceRefPtr()));
1903 EXPECT_CALL(*wifi_provider_, GetService(_, _))
1904 .WillOnce(Return(WiFiServiceRefPtr()));
1905 Error error;
1906 ServiceRefPtr service =
1907 manager()->ConfigureServiceForProfile(kProfileName0, args, &error);
1908 // Since we didn't set the error in the GetService expectation above...
1909 EXPECT_TRUE(error.IsSuccess());
1910 EXPECT_EQ(NULL, service.get());
1911}
1912
1913TEST_F(ManagerTest, ConfigureServiceForProfileCreateNewService) {
1914 const string kProfileName0 = "profile0";
1915 scoped_refptr<MockProfile> profile0(
1916 AddNamedMockProfileToManager(manager(), kProfileName0));
1917
1918 KeyValueStore args;
1919 args.SetString(flimflam::kTypeProperty, flimflam::kTypeWifi);
1920
1921 scoped_refptr<MockWiFiService> mock_service(
1922 new NiceMock<MockWiFiService>(control_interface(),
1923 dispatcher(),
1924 metrics(),
1925 manager(),
1926 wifi_provider_,
1927 vector<uint8_t>(),
1928 flimflam::kModeManaged,
1929 flimflam::kSecurityNone,
1930 false));
1931 ServiceRefPtr mock_service_generic(mock_service.get());
1932 mock_service->set_profile(profile0);
1933 EXPECT_CALL(*wifi_provider_, FindSimilarService(_, _))
1934 .WillOnce(Return(WiFiServiceRefPtr()));
1935 EXPECT_CALL(*wifi_provider_, GetService(_, _)).WillOnce(Return(mock_service));
1936 EXPECT_CALL(*profile0, UpdateService(mock_service_generic))
1937 .WillOnce(Return(true));
1938 Error error;
1939 ServiceRefPtr service =
1940 manager()->ConfigureServiceForProfile(kProfileName0, args, &error);
1941 EXPECT_TRUE(error.IsSuccess());
1942 EXPECT_EQ(mock_service.get(), service.get());
1943 mock_service->set_profile(NULL); // Breaks reference cycle.
1944}
1945
1946TEST_F(ManagerTest, ConfigureServiceForProfileMatchingServiceByGUID) {
1947 scoped_refptr<MockService> mock_service(
1948 new NiceMock<MockService>(control_interface(),
1949 dispatcher(),
1950 metrics(),
1951 manager()));
1952 const string kGUID = "a guid";
mukesh agrawalcbfb34e2013-04-17 19:33:25 -07001953 mock_service->SetGuid(kGUID, NULL);
Paul Stewartd2e1c362013-03-03 19:06:07 -08001954 manager()->RegisterService(mock_service);
1955 ServiceRefPtr mock_service_generic(mock_service.get());
1956
1957 const string kProfileName = "profile";
1958 scoped_refptr<MockProfile> profile(
1959 AddNamedMockProfileToManager(manager(), kProfileName));
1960 mock_service->set_profile(profile);
1961
1962 EXPECT_CALL(*mock_service, technology())
1963 .WillOnce(Return(Technology::kCellular))
1964 .WillOnce(Return(Technology::kWifi));
1965
1966 EXPECT_CALL(*wifi_provider_, FindSimilarService(_, _)).Times(0);
1967 EXPECT_CALL(*wifi_provider_, GetService(_, _)).Times(0);
1968 EXPECT_CALL(*profile, AdoptService(mock_service_generic)).Times(0);
1969
1970 KeyValueStore args;
1971 args.SetString(flimflam::kTypeProperty, flimflam::kTypeWifi);
1972 args.SetString(flimflam::kGuidProperty, kGUID);
1973
1974 // The first attempt should fail because the service reports a technology
1975 // other than "WiFi".
1976 {
1977 Error error;
1978 ServiceRefPtr service =
1979 manager()->ConfigureServiceForProfile(kProfileName, args, &error);
1980 EXPECT_EQ(NULL, service.get());
1981 EXPECT_EQ(Error::kNotSupported, error.type());
1982 EXPECT_EQ("This GUID matches a non-WiFi service", error.message());
1983 }
1984
1985 EXPECT_CALL(*mock_service, Configure(_, _)).Times(1);
1986 EXPECT_CALL(*profile, UpdateService(mock_service_generic)).Times(1);
1987
1988 {
1989 Error error;
1990 ServiceRefPtr service =
1991 manager()->ConfigureServiceForProfile(kProfileName, args, &error);
1992 EXPECT_TRUE(error.IsSuccess());
1993 EXPECT_EQ(mock_service.get(), service.get());
1994 EXPECT_EQ(profile.get(), service->profile().get());
1995 }
1996 mock_service->set_profile(NULL); // Breaks reference cycle.
1997}
1998
1999TEST_F(ManagerTest, ConfigureServiceForProfileMatchingServiceAndProfile) {
2000 const string kProfileName = "profile";
2001 scoped_refptr<MockProfile> profile(
2002 AddNamedMockProfileToManager(manager(), kProfileName));
2003
2004 scoped_refptr<MockWiFiService> mock_service(
2005 new NiceMock<MockWiFiService>(control_interface(),
2006 dispatcher(),
2007 metrics(),
2008 manager(),
2009 wifi_provider_,
2010 vector<uint8_t>(),
2011 flimflam::kModeManaged,
2012 flimflam::kSecurityNone,
2013 false));
2014 mock_service->set_profile(profile);
2015 ServiceRefPtr mock_service_generic(mock_service.get());
2016
2017 KeyValueStore args;
2018 args.SetString(flimflam::kTypeProperty, flimflam::kTypeWifi);
2019 EXPECT_CALL(*wifi_provider_, FindSimilarService(_, _))
2020 .WillOnce(Return(mock_service));
2021 EXPECT_CALL(*wifi_provider_, GetService(_, _)).Times(0);
2022 EXPECT_CALL(*profile, AdoptService(mock_service_generic)).Times(0);
2023 EXPECT_CALL(*mock_service, Configure(_, _)).Times(1);
2024 EXPECT_CALL(*profile, UpdateService(mock_service_generic)).Times(1);
2025
2026 Error error;
2027 ServiceRefPtr service =
2028 manager()->ConfigureServiceForProfile(kProfileName, args, &error);
2029 EXPECT_TRUE(error.IsSuccess());
2030 EXPECT_EQ(mock_service.get(), service.get());
2031 EXPECT_EQ(profile.get(), service->profile().get());
2032 mock_service->set_profile(NULL); // Breaks reference cycle.
2033}
2034
2035TEST_F(ManagerTest, ConfigureServiceForProfileMatchingServiceEphemeralProfile) {
2036 const string kProfileName = "profile";
2037 scoped_refptr<MockProfile> profile(
2038 AddNamedMockProfileToManager(manager(), kProfileName));
2039
2040 scoped_refptr<MockWiFiService> mock_service(
2041 new NiceMock<MockWiFiService>(control_interface(),
2042 dispatcher(),
2043 metrics(),
2044 manager(),
2045 wifi_provider_,
2046 vector<uint8_t>(),
2047 flimflam::kModeManaged,
2048 flimflam::kSecurityNone,
2049 false));
2050 mock_service->set_profile(GetEphemeralProfile(manager()));
2051 ServiceRefPtr mock_service_generic(mock_service.get());
2052
2053 KeyValueStore args;
2054 args.SetString(flimflam::kTypeProperty, flimflam::kTypeWifi);
2055 EXPECT_CALL(*wifi_provider_, FindSimilarService(_, _))
2056 .WillOnce(Return(mock_service));
2057 EXPECT_CALL(*wifi_provider_, GetService(_, _)).Times(0);
2058 EXPECT_CALL(*mock_service, Configure(_, _)).Times(1);
2059 EXPECT_CALL(*profile, UpdateService(mock_service_generic)).Times(1);
2060
2061 Error error;
2062 ServiceRefPtr service =
2063 manager()->ConfigureServiceForProfile(kProfileName, args, &error);
2064 EXPECT_TRUE(error.IsSuccess());
2065 EXPECT_EQ(mock_service.get(), service.get());
2066 EXPECT_EQ(profile.get(), service->profile().get());
2067 mock_service->set_profile(NULL); // Breaks reference cycle.
2068}
2069
2070TEST_F(ManagerTest, ConfigureServiceForProfileMatchingServicePrecedingProfile) {
2071 const string kProfileName0 = "profile0";
2072 scoped_refptr<MockProfile> profile0(
2073 AddNamedMockProfileToManager(manager(), kProfileName0));
2074 const string kProfileName1 = "profile1";
2075 scoped_refptr<MockProfile> profile1(
2076 AddNamedMockProfileToManager(manager(), kProfileName1));
2077
2078 scoped_refptr<MockWiFiService> mock_service(
2079 new NiceMock<MockWiFiService>(control_interface(),
2080 dispatcher(),
2081 metrics(),
2082 manager(),
2083 wifi_provider_,
2084 vector<uint8_t>(),
2085 flimflam::kModeManaged,
2086 flimflam::kSecurityNone,
2087 false));
2088 manager()->RegisterService(mock_service);
2089 mock_service->set_profile(profile0);
2090 ServiceRefPtr mock_service_generic(mock_service.get());
2091
2092 KeyValueStore args;
2093 args.SetString(flimflam::kTypeProperty, flimflam::kTypeWifi);
2094 EXPECT_CALL(*wifi_provider_, FindSimilarService(_, _))
2095 .WillOnce(Return(mock_service));
2096 EXPECT_CALL(*wifi_provider_, GetService(_, _)).Times(0);
2097 EXPECT_CALL(*profile0, AbandonService(_)).Times(0);
2098 EXPECT_CALL(*profile1, AdoptService(_)).Times(0);
2099 // This happens once to make the service loadable for the ConfigureService
2100 // below, and a second time after the service is modified.
2101 EXPECT_CALL(*profile1, ConfigureService(mock_service_generic)).Times(0);
2102 EXPECT_CALL(*wifi_provider_, CreateTemporaryService(_, _)).Times(0);
2103 EXPECT_CALL(*mock_service, Configure(_, _)).Times(1);
2104 EXPECT_CALL(*profile1, UpdateService(mock_service_generic)).Times(1);
2105
2106 Error error;
2107 ServiceRefPtr service =
2108 manager()->ConfigureServiceForProfile(kProfileName1, args, &error);
2109 EXPECT_TRUE(error.IsSuccess());
2110 EXPECT_EQ(mock_service.get(), service.get());
2111 mock_service->set_profile(NULL); // Breaks reference cycle.
2112}
2113
2114TEST_F(ManagerTest,
2115 ConfigureServiceForProfileMatchingServiceProceedingProfile) {
2116 const string kProfileName0 = "profile0";
2117 scoped_refptr<MockProfile> profile0(
2118 AddNamedMockProfileToManager(manager(), kProfileName0));
2119 const string kProfileName1 = "profile1";
2120 scoped_refptr<MockProfile> profile1(
2121 AddNamedMockProfileToManager(manager(), kProfileName1));
2122
2123 scoped_refptr<MockWiFiService> matching_service(
2124 new StrictMock<MockWiFiService>(control_interface(),
2125 dispatcher(),
2126 metrics(),
2127 manager(),
2128 wifi_provider_,
2129 vector<uint8_t>(),
2130 flimflam::kModeManaged,
2131 flimflam::kSecurityNone,
2132 false));
2133 matching_service->set_profile(profile1);
2134
2135 // We need to get rid of our reference to this mock service as soon
2136 // as Manager::ConfigureServiceForProfile() takes a reference in its
2137 // call to WiFiProvider::CreateTemporaryService(). This way the
2138 // latter function can keep a DCHECK(service->HasOneRef() even in
2139 // unit tests.
2140 temp_mock_service_ =
2141 new NiceMock<MockWiFiService>(control_interface(),
2142 dispatcher(),
2143 metrics(),
2144 manager(),
2145 wifi_provider_,
2146 vector<uint8_t>(),
2147 flimflam::kModeManaged,
2148 flimflam::kSecurityNone,
2149 false);
2150
2151 // Only hold a pointer here so we don't affect the refcount.
2152 MockWiFiService *mock_service_ptr = temp_mock_service_.get();
2153
2154 KeyValueStore args;
2155 args.SetString(flimflam::kTypeProperty, flimflam::kTypeWifi);
2156 EXPECT_CALL(*wifi_provider_, FindSimilarService(_, _))
2157 .WillOnce(Return(matching_service));
2158 EXPECT_CALL(*wifi_provider_, GetService(_, _)).Times(0);
2159 EXPECT_CALL(*profile1, AbandonService(_)).Times(0);
2160 EXPECT_CALL(*profile0, AdoptService(_)).Times(0);
2161 EXPECT_CALL(*wifi_provider_, CreateTemporaryService(_, _))
2162 .WillOnce(InvokeWithoutArgs(this, &ManagerTest::ReleaseTempMockService));
2163 EXPECT_CALL(*profile0, ConfigureService(IsRefPtrTo(mock_service_ptr)))
2164 .Times(1);
2165 EXPECT_CALL(*mock_service_ptr, Configure(_, _)).Times(1);
2166 EXPECT_CALL(*profile0, UpdateService(IsRefPtrTo(mock_service_ptr))).Times(1);
2167
2168 Error error;
2169 ServiceRefPtr service =
2170 manager()->ConfigureServiceForProfile(kProfileName0, args, &error);
2171 EXPECT_TRUE(error.IsSuccess());
2172 EXPECT_EQ(NULL, service.get());
2173 EXPECT_EQ(profile1.get(), matching_service->profile().get());
2174}
2175
Paul Stewart7a20aa42013-01-17 12:21:41 -08002176TEST_F(ManagerTest, FindMatchingService) {
2177 KeyValueStore args;
2178 {
2179 Error error;
2180 ServiceRefPtr service = manager()->FindMatchingService(args, &error);
2181 EXPECT_EQ(Error::kNotFound, error.type());
2182 }
2183
2184 scoped_refptr<MockService> mock_service0(
2185 new NiceMock<MockService>(control_interface(),
2186 dispatcher(),
2187 metrics(),
2188 manager()));
2189 scoped_refptr<MockService> mock_service1(
2190 new NiceMock<MockService>(control_interface(),
2191 dispatcher(),
2192 metrics(),
2193 manager()));
2194 manager()->RegisterService(mock_service0);
2195 manager()->RegisterService(mock_service1);
2196 EXPECT_CALL(*mock_service0, DoPropertiesMatch(_))
2197 .WillOnce(Return(true))
2198 .WillRepeatedly(Return(false));
2199 {
2200 Error error;
2201 EXPECT_EQ(mock_service0, manager()->FindMatchingService(args, &error));
2202 EXPECT_TRUE(error.IsSuccess());
2203 }
2204 EXPECT_CALL(*mock_service1, DoPropertiesMatch(_))
2205 .WillOnce(Return(true))
2206 .WillRepeatedly(Return(false));
2207 {
2208 Error error;
2209 EXPECT_EQ(mock_service1, manager()->FindMatchingService(args, &error));
2210 EXPECT_TRUE(error.IsSuccess());
2211 }
2212 {
2213 Error error;
2214 EXPECT_FALSE(manager()->FindMatchingService(args, &error));
2215 EXPECT_EQ(Error::kNotFound, error.type());
2216 }
2217}
2218
Paul Stewart22aa71b2011-09-16 12:15:11 -07002219TEST_F(ManagerTest, TechnologyOrder) {
2220 Error error;
2221 manager()->SetTechnologyOrder(string(flimflam::kTypeEthernet) + "," +
2222 string(flimflam::kTypeWifi), &error);
2223 ASSERT_TRUE(error.IsSuccess());
2224 EXPECT_EQ(manager()->GetTechnologyOrder(),
2225 string(flimflam::kTypeEthernet) + "," +
2226 string(flimflam::kTypeWifi));
2227
2228 manager()->SetTechnologyOrder(string(flimflam::kTypeEthernet) + "x," +
2229 string(flimflam::kTypeWifi), &error);
2230 ASSERT_FALSE(error.IsSuccess());
2231 EXPECT_EQ(Error::kInvalidArguments, error.type());
2232 EXPECT_EQ(string(flimflam::kTypeEthernet) + "," +
2233 string(flimflam::kTypeWifi),
2234 manager()->GetTechnologyOrder());
2235}
2236
2237TEST_F(ManagerTest, SortServices) {
mukesh agrawal00917ce2011-11-22 23:56:55 +00002238 // TODO(quiche): Some of these tests would probably fit better in
2239 // service_unittest, since the actual comparison of Services is
Paul Stewartee6b3d72013-07-12 16:07:51 -07002240 // implemented in Service. (crbug.com/206367)
mukesh agrawal00917ce2011-11-22 23:56:55 +00002241
Paul Stewart22aa71b2011-09-16 12:15:11 -07002242 scoped_refptr<MockService> mock_service0(
2243 new NiceMock<MockService>(control_interface(),
2244 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -08002245 metrics(),
Paul Stewart22aa71b2011-09-16 12:15:11 -07002246 manager()));
2247 scoped_refptr<MockService> mock_service1(
2248 new NiceMock<MockService>(control_interface(),
2249 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -08002250 metrics(),
Paul Stewart22aa71b2011-09-16 12:15:11 -07002251 manager()));
Paul Stewart22aa71b2011-09-16 12:15:11 -07002252
2253 manager()->RegisterService(mock_service0);
2254 manager()->RegisterService(mock_service1);
2255
Darin Petkov457728b2013-01-09 09:49:08 +01002256 // Services should already be sorted by |unique_name_|
Paul Stewart22aa71b2011-09-16 12:15:11 -07002257 EXPECT_TRUE(ServiceOrderIs(mock_service0, mock_service1));
2258
2259 // Asking explictly to sort services should not change anything
Paul Stewartdfa46052012-06-26 09:44:14 -07002260 manager()->SortServicesTask();
Paul Stewart22aa71b2011-09-16 12:15:11 -07002261 EXPECT_TRUE(ServiceOrderIs(mock_service0, mock_service1));
2262
2263 // Two otherwise equal services should be reordered by strength
Darin Petkovd78ee7e2012-01-12 11:21:10 +01002264 mock_service1->SetStrength(1);
Paul Stewart22aa71b2011-09-16 12:15:11 -07002265 manager()->UpdateService(mock_service1);
2266 EXPECT_TRUE(ServiceOrderIs(mock_service1, mock_service0));
2267
2268 // Security
mukesh agrawal43970a22013-02-15 16:00:07 -08002269 mock_service0->SetSecurity(Service::kCryptoAes, true, true);
Paul Stewart22aa71b2011-09-16 12:15:11 -07002270 manager()->UpdateService(mock_service0);
2271 EXPECT_TRUE(ServiceOrderIs(mock_service0, mock_service1));
2272
2273 // Technology
Joshua Kroll053fa822012-06-05 09:50:43 -07002274 EXPECT_CALL(*mock_service0.get(), technology())
2275 .WillRepeatedly(Return((Technology::kWifi)));
2276 EXPECT_CALL(*mock_service1.get(), technology())
2277 .WillRepeatedly(Return(Technology::kEthernet));
Paul Stewart22aa71b2011-09-16 12:15:11 -07002278
2279 Error error;
mukesh agrawal84de5d22012-02-17 19:29:15 -08002280 // Default technology ordering should favor Ethernet over WiFi.
Paul Stewartdfa46052012-06-26 09:44:14 -07002281 manager()->SortServicesTask();
Paul Stewart22aa71b2011-09-16 12:15:11 -07002282 EXPECT_TRUE(ServiceOrderIs(mock_service1, mock_service0));
2283
2284 manager()->SetTechnologyOrder(string(flimflam::kTypeWifi) + "," +
2285 string(flimflam::kTypeEthernet), &error);
2286 EXPECT_TRUE(error.IsSuccess());
2287 EXPECT_TRUE(ServiceOrderIs(mock_service0, mock_service1));
2288
Gaurav Shah435de2c2011-11-17 19:01:07 -08002289 // Priority.
mukesh agrawalcbfb34e2013-04-17 19:33:25 -07002290 mock_service0->SetPriority(1, NULL);
Paul Stewart22aa71b2011-09-16 12:15:11 -07002291 manager()->UpdateService(mock_service0);
2292 EXPECT_TRUE(ServiceOrderIs(mock_service0, mock_service1));
2293
mukesh agrawal8a3188d2011-12-01 20:56:44 +00002294 // Favorite.
mukesh agrawal00917ce2011-11-22 23:56:55 +00002295 mock_service1->MakeFavorite();
Paul Stewart22aa71b2011-09-16 12:15:11 -07002296 manager()->UpdateService(mock_service1);
2297 EXPECT_TRUE(ServiceOrderIs(mock_service1, mock_service0));
2298
mukesh agrawal8a3188d2011-12-01 20:56:44 +00002299 // Auto-connect.
mukesh agrawalcbfb34e2013-04-17 19:33:25 -07002300 mock_service0->SetAutoConnect(true);
Paul Stewart22aa71b2011-09-16 12:15:11 -07002301 manager()->UpdateService(mock_service0);
mukesh agrawalcbfb34e2013-04-17 19:33:25 -07002302 mock_service1->SetAutoConnect(false);
mukesh agrawal8a3188d2011-12-01 20:56:44 +00002303 manager()->UpdateService(mock_service1);
Paul Stewart22aa71b2011-09-16 12:15:11 -07002304 EXPECT_TRUE(ServiceOrderIs(mock_service0, mock_service1));
2305
Paul Stewartdf3c0a82012-11-09 15:54:33 -08002306 // Test is-dependent-on. It doesn't make sense to have this ranking compare
2307 // to any of the others below, so we reset to the default state after
2308 // testing.
2309 EXPECT_CALL(*mock_service1.get(),
2310 IsDependentOn(ServiceRefPtr(mock_service0.get())))
2311 .WillOnce(Return(true))
2312 .WillRepeatedly(Return(false));
2313 manager()->UpdateService(mock_service1);
2314 EXPECT_TRUE(ServiceOrderIs(mock_service1, mock_service0));
2315 manager()->UpdateService(mock_service0);
2316 EXPECT_TRUE(ServiceOrderIs(mock_service0, mock_service1));
2317
mukesh agrawal8a3188d2011-12-01 20:56:44 +00002318 // Connectable.
mukesh agrawalcbfb34e2013-04-17 19:33:25 -07002319 mock_service1->SetConnectable(true);
mukesh agrawal8a3188d2011-12-01 20:56:44 +00002320 manager()->UpdateService(mock_service1);
mukesh agrawalcbfb34e2013-04-17 19:33:25 -07002321 mock_service0->SetConnectable(false);
mukesh agrawal8a3188d2011-12-01 20:56:44 +00002322 manager()->UpdateService(mock_service0);
2323 EXPECT_TRUE(ServiceOrderIs(mock_service1, mock_service0));
2324
2325 // IsFailed.
2326 EXPECT_CALL(*mock_service0.get(), state())
2327 .WillRepeatedly(Return(Service::kStateIdle));
2328 EXPECT_CALL(*mock_service0.get(), IsFailed())
2329 .WillRepeatedly(Return(false));
2330 manager()->UpdateService(mock_service0);
2331 EXPECT_CALL(*mock_service0.get(), state())
2332 .WillRepeatedly(Return(Service::kStateFailure));
2333 EXPECT_CALL(*mock_service1.get(), IsFailed())
2334 .WillRepeatedly(Return(true));
2335 manager()->UpdateService(mock_service1);
2336 EXPECT_TRUE(ServiceOrderIs(mock_service0, mock_service1));
2337
2338 // Connecting.
Paul Stewart22aa71b2011-09-16 12:15:11 -07002339 EXPECT_CALL(*mock_service1.get(), state())
mukesh agrawal8a3188d2011-12-01 20:56:44 +00002340 .WillRepeatedly(Return(Service::kStateAssociating));
2341 EXPECT_CALL(*mock_service1.get(), IsConnecting())
Gaurav Shah435de2c2011-11-17 19:01:07 -08002342 .WillRepeatedly(Return(true));
Paul Stewart22aa71b2011-09-16 12:15:11 -07002343 manager()->UpdateService(mock_service1);
2344 EXPECT_TRUE(ServiceOrderIs(mock_service1, mock_service0));
2345
mukesh agrawal8a3188d2011-12-01 20:56:44 +00002346 // Connected.
2347 EXPECT_CALL(*mock_service0.get(), state())
Paul Stewarta121c442012-06-09 14:12:58 -07002348 .WillRepeatedly(Return(Service::kStatePortal));
mukesh agrawal8a3188d2011-12-01 20:56:44 +00002349 EXPECT_CALL(*mock_service0.get(), IsConnected())
2350 .WillRepeatedly(Return(true));
2351 manager()->UpdateService(mock_service0);
2352 EXPECT_TRUE(ServiceOrderIs(mock_service0, mock_service1));
2353
Paul Stewarta121c442012-06-09 14:12:58 -07002354 // Portal.
2355 EXPECT_CALL(*mock_service1.get(), state())
2356 .WillRepeatedly(Return(Service::kStateConnected));
2357 EXPECT_CALL(*mock_service1.get(), IsConnected())
2358 .WillRepeatedly(Return(true));
2359 manager()->UpdateService(mock_service1);
2360 EXPECT_TRUE(ServiceOrderIs(mock_service1, mock_service0));
2361
Paul Stewart22aa71b2011-09-16 12:15:11 -07002362 manager()->DeregisterService(mock_service0);
2363 manager()->DeregisterService(mock_service1);
2364}
2365
Paul Stewartc1dec4d2011-12-08 15:25:28 -08002366TEST_F(ManagerTest, SortServicesWithConnection) {
Thieu Le6c1e3bb2013-02-06 15:20:35 -08002367 MockMetrics mock_metrics(dispatcher());
Darin Petkov4cbff5b2013-01-29 16:29:05 +01002368 SetMetrics(&mock_metrics);
Thieu Lea20cbc22012-01-09 22:01:43 +00002369
Paul Stewartc1dec4d2011-12-08 15:25:28 -08002370 scoped_refptr<MockService> mock_service0(
2371 new NiceMock<MockService>(control_interface(),
2372 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -08002373 metrics(),
Paul Stewartc1dec4d2011-12-08 15:25:28 -08002374 manager()));
2375 scoped_refptr<MockService> mock_service1(
2376 new NiceMock<MockService>(control_interface(),
2377 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -08002378 metrics(),
Paul Stewartc1dec4d2011-12-08 15:25:28 -08002379 manager()));
2380
2381 scoped_refptr<MockConnection> mock_connection0(
2382 new NiceMock<MockConnection>(device_info_.get()));
2383 scoped_refptr<MockConnection> mock_connection1(
2384 new NiceMock<MockConnection>(device_info_.get()));
2385
Paul Stewarte2bad7c2012-03-14 08:55:33 -07002386 EXPECT_CALL(mock_metrics, NotifyDefaultServiceChanged(NULL));
Paul Stewartc1dec4d2011-12-08 15:25:28 -08002387 manager()->RegisterService(mock_service0);
Paul Stewartdfa46052012-06-26 09:44:14 -07002388 CompleteServiceSort();
Paul Stewarte2bad7c2012-03-14 08:55:33 -07002389 EXPECT_CALL(mock_metrics, NotifyDefaultServiceChanged(NULL));
Paul Stewartc1dec4d2011-12-08 15:25:28 -08002390 manager()->RegisterService(mock_service1);
Paul Stewartdfa46052012-06-26 09:44:14 -07002391 CompleteServiceSort();
Paul Stewartc1dec4d2011-12-08 15:25:28 -08002392
Paul Stewarte2bad7c2012-03-14 08:55:33 -07002393 EXPECT_CALL(mock_metrics, NotifyDefaultServiceChanged(NULL));
Paul Stewartdfa46052012-06-26 09:44:14 -07002394 manager()->SortServicesTask();
Paul Stewarte2bad7c2012-03-14 08:55:33 -07002395
mukesh agrawalcbfb34e2013-04-17 19:33:25 -07002396 mock_service1->SetPriority(1, NULL);
Paul Stewarte2bad7c2012-03-14 08:55:33 -07002397 EXPECT_CALL(mock_metrics, NotifyDefaultServiceChanged(NULL));
Paul Stewartdfa46052012-06-26 09:44:14 -07002398 manager()->SortServicesTask();
Paul Stewarte2bad7c2012-03-14 08:55:33 -07002399
mukesh agrawalcbfb34e2013-04-17 19:33:25 -07002400 mock_service1->SetPriority(0, NULL);
Paul Stewarte2bad7c2012-03-14 08:55:33 -07002401 EXPECT_CALL(mock_metrics, NotifyDefaultServiceChanged(NULL));
Paul Stewartdfa46052012-06-26 09:44:14 -07002402 manager()->SortServicesTask();
Paul Stewarte2bad7c2012-03-14 08:55:33 -07002403
Paul Stewartce4ec192012-03-14 12:53:46 -07002404 mock_service0->set_mock_connection(mock_connection0);
2405 mock_service1->set_mock_connection(mock_connection1);
Paul Stewartc1dec4d2011-12-08 15:25:28 -08002406
2407 EXPECT_CALL(*mock_connection0.get(), SetIsDefault(true));
Thieu Lea20cbc22012-01-09 22:01:43 +00002408 EXPECT_CALL(mock_metrics, NotifyDefaultServiceChanged(mock_service0.get()));
Paul Stewartdfa46052012-06-26 09:44:14 -07002409 manager()->SortServicesTask();
Paul Stewartc1dec4d2011-12-08 15:25:28 -08002410
Darin Petkova5e07ef2012-07-09 14:27:57 +02002411 ServiceWatcher service_watcher;
2412 int tag =
2413 manager()->RegisterDefaultServiceCallback(
2414 Bind(&ServiceWatcher::OnDefaultServiceChanged,
2415 service_watcher.AsWeakPtr()));
2416 EXPECT_EQ(1, tag);
2417
mukesh agrawalcbfb34e2013-04-17 19:33:25 -07002418 mock_service1->SetPriority(1, NULL);
Paul Stewartc1dec4d2011-12-08 15:25:28 -08002419 EXPECT_CALL(*mock_connection0.get(), SetIsDefault(false));
2420 EXPECT_CALL(*mock_connection1.get(), SetIsDefault(true));
Darin Petkova5e07ef2012-07-09 14:27:57 +02002421 EXPECT_CALL(service_watcher, OnDefaultServiceChanged(_));
Thieu Lea20cbc22012-01-09 22:01:43 +00002422 EXPECT_CALL(mock_metrics, NotifyDefaultServiceChanged(mock_service1.get()));
Paul Stewartdfa46052012-06-26 09:44:14 -07002423 manager()->SortServicesTask();
Paul Stewartc1dec4d2011-12-08 15:25:28 -08002424
Darin Petkova5e07ef2012-07-09 14:27:57 +02002425 manager()->DeregisterDefaultServiceCallback(tag);
Paul Stewartc1dec4d2011-12-08 15:25:28 -08002426 EXPECT_CALL(*mock_connection0.get(), SetIsDefault(true));
Darin Petkova5e07ef2012-07-09 14:27:57 +02002427 EXPECT_CALL(service_watcher, OnDefaultServiceChanged(_)).Times(0);
Thieu Lea20cbc22012-01-09 22:01:43 +00002428 EXPECT_CALL(mock_metrics, NotifyDefaultServiceChanged(mock_service0.get()));
Paul Stewartce4ec192012-03-14 12:53:46 -07002429 mock_service1->set_mock_connection(NULL);
Paul Stewartc1dec4d2011-12-08 15:25:28 -08002430 manager()->DeregisterService(mock_service1);
Paul Stewartdfa46052012-06-26 09:44:14 -07002431 CompleteServiceSort();
Paul Stewartc1dec4d2011-12-08 15:25:28 -08002432
Paul Stewartce4ec192012-03-14 12:53:46 -07002433 mock_service0->set_mock_connection(NULL);
Paul Stewarte2bad7c2012-03-14 08:55:33 -07002434 EXPECT_CALL(mock_metrics, NotifyDefaultServiceChanged(NULL));
Paul Stewartc1dec4d2011-12-08 15:25:28 -08002435 manager()->DeregisterService(mock_service0);
Paul Stewartdfa46052012-06-26 09:44:14 -07002436 CompleteServiceSort();
Paul Stewarte2bad7c2012-03-14 08:55:33 -07002437
2438 EXPECT_CALL(mock_metrics, NotifyDefaultServiceChanged(NULL));
Paul Stewartdfa46052012-06-26 09:44:14 -07002439 manager()->SortServicesTask();
Paul Stewartc1dec4d2011-12-08 15:25:28 -08002440}
2441
Darin Petkova5e07ef2012-07-09 14:27:57 +02002442TEST_F(ManagerTest, NotifyDefaultServiceChanged) {
2443 EXPECT_EQ(0, manager()->default_service_callback_tag_);
2444 EXPECT_TRUE(manager()->default_service_callbacks_.empty());
2445
Thieu Le6c1e3bb2013-02-06 15:20:35 -08002446 MockMetrics mock_metrics(dispatcher());
Darin Petkov4cbff5b2013-01-29 16:29:05 +01002447 SetMetrics(&mock_metrics);
Darin Petkova5e07ef2012-07-09 14:27:57 +02002448
2449 scoped_refptr<MockService> mock_service(
2450 new NiceMock<MockService>(
2451 control_interface(), dispatcher(), metrics(), manager()));
2452 ServiceRefPtr service = mock_service;
2453 ServiceRefPtr null_service;
2454
2455 EXPECT_CALL(mock_metrics, NotifyDefaultServiceChanged(NULL));
2456 manager()->NotifyDefaultServiceChanged(null_service);
2457
2458 ServiceWatcher service_watcher1;
2459 ServiceWatcher service_watcher2;
2460 int tag1 =
2461 manager()->RegisterDefaultServiceCallback(
2462 Bind(&ServiceWatcher::OnDefaultServiceChanged,
2463 service_watcher1.AsWeakPtr()));
2464 EXPECT_EQ(1, tag1);
2465 int tag2 =
2466 manager()->RegisterDefaultServiceCallback(
2467 Bind(&ServiceWatcher::OnDefaultServiceChanged,
2468 service_watcher2.AsWeakPtr()));
2469 EXPECT_EQ(2, tag2);
2470
2471 EXPECT_CALL(service_watcher1, OnDefaultServiceChanged(null_service));
2472 EXPECT_CALL(service_watcher2, OnDefaultServiceChanged(null_service));
2473 EXPECT_CALL(mock_metrics, NotifyDefaultServiceChanged(NULL));
2474 manager()->NotifyDefaultServiceChanged(null_service);
2475
2476 EXPECT_CALL(service_watcher1, OnDefaultServiceChanged(service));
2477 EXPECT_CALL(service_watcher2, OnDefaultServiceChanged(service));
2478 EXPECT_CALL(mock_metrics, NotifyDefaultServiceChanged(service.get()));
2479 manager()->NotifyDefaultServiceChanged(mock_service);
2480
2481 manager()->DeregisterDefaultServiceCallback(tag1);
2482 EXPECT_CALL(service_watcher1, OnDefaultServiceChanged(_)).Times(0);
2483 EXPECT_CALL(service_watcher2, OnDefaultServiceChanged(service));
2484 EXPECT_CALL(mock_metrics, NotifyDefaultServiceChanged(service.get()));
2485 manager()->NotifyDefaultServiceChanged(mock_service);
2486 EXPECT_EQ(1, manager()->default_service_callbacks_.size());
2487
2488 manager()->DeregisterDefaultServiceCallback(tag2);
2489 EXPECT_CALL(service_watcher2, OnDefaultServiceChanged(_)).Times(0);
2490 EXPECT_CALL(mock_metrics, NotifyDefaultServiceChanged(service.get()));
2491 manager()->NotifyDefaultServiceChanged(mock_service);
2492
2493 EXPECT_EQ(2, manager()->default_service_callback_tag_);
2494 EXPECT_TRUE(manager()->default_service_callbacks_.empty());
2495}
2496
Gaurav Shah435de2c2011-11-17 19:01:07 -08002497TEST_F(ManagerTest, AvailableTechnologies) {
2498 mock_devices_.push_back(new NiceMock<MockDevice>(control_interface(),
2499 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -08002500 metrics(),
Gaurav Shah435de2c2011-11-17 19:01:07 -08002501 manager(),
2502 "null4",
2503 "addr4",
2504 0));
2505 manager()->RegisterDevice(mock_devices_[0]);
2506 manager()->RegisterDevice(mock_devices_[1]);
2507 manager()->RegisterDevice(mock_devices_[2]);
2508 manager()->RegisterDevice(mock_devices_[3]);
2509
2510 ON_CALL(*mock_devices_[0].get(), technology())
2511 .WillByDefault(Return(Technology::kEthernet));
2512 ON_CALL(*mock_devices_[1].get(), technology())
2513 .WillByDefault(Return(Technology::kWifi));
2514 ON_CALL(*mock_devices_[2].get(), technology())
2515 .WillByDefault(Return(Technology::kCellular));
2516 ON_CALL(*mock_devices_[3].get(), technology())
2517 .WillByDefault(Return(Technology::kWifi));
2518
2519 set<string> expected_technologies;
2520 expected_technologies.insert(Technology::NameFromIdentifier(
2521 Technology::kEthernet));
2522 expected_technologies.insert(Technology::NameFromIdentifier(
2523 Technology::kWifi));
2524 expected_technologies.insert(Technology::NameFromIdentifier(
2525 Technology::kCellular));
2526 Error error;
2527 vector<string> technologies = manager()->AvailableTechnologies(&error);
2528
2529 EXPECT_THAT(set<string>(technologies.begin(), technologies.end()),
2530 ContainerEq(expected_technologies));
2531}
2532
2533TEST_F(ManagerTest, ConnectedTechnologies) {
2534 scoped_refptr<MockService> connected_service1(
2535 new NiceMock<MockService>(control_interface(),
2536 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -08002537 metrics(),
Gaurav Shah435de2c2011-11-17 19:01:07 -08002538 manager()));
2539 scoped_refptr<MockService> connected_service2(
2540 new NiceMock<MockService>(control_interface(),
2541 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -08002542 metrics(),
Gaurav Shah435de2c2011-11-17 19:01:07 -08002543 manager()));
2544 scoped_refptr<MockService> disconnected_service1(
2545 new NiceMock<MockService>(control_interface(),
2546 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -08002547 metrics(),
Gaurav Shah435de2c2011-11-17 19:01:07 -08002548 manager()));
2549 scoped_refptr<MockService> disconnected_service2(
2550 new NiceMock<MockService>(control_interface(),
2551 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -08002552 metrics(),
Gaurav Shah435de2c2011-11-17 19:01:07 -08002553 manager()));
2554
2555 ON_CALL(*connected_service1.get(), IsConnected())
2556 .WillByDefault(Return(true));
2557 ON_CALL(*connected_service2.get(), IsConnected())
2558 .WillByDefault(Return(true));
2559
2560 manager()->RegisterService(connected_service1);
2561 manager()->RegisterService(connected_service2);
2562 manager()->RegisterService(disconnected_service1);
2563 manager()->RegisterService(disconnected_service2);
2564
2565 manager()->RegisterDevice(mock_devices_[0]);
2566 manager()->RegisterDevice(mock_devices_[1]);
2567 manager()->RegisterDevice(mock_devices_[2]);
2568 manager()->RegisterDevice(mock_devices_[3]);
2569
2570 ON_CALL(*mock_devices_[0].get(), technology())
2571 .WillByDefault(Return(Technology::kEthernet));
2572 ON_CALL(*mock_devices_[1].get(), technology())
2573 .WillByDefault(Return(Technology::kWifi));
2574 ON_CALL(*mock_devices_[2].get(), technology())
2575 .WillByDefault(Return(Technology::kCellular));
2576 ON_CALL(*mock_devices_[3].get(), technology())
2577 .WillByDefault(Return(Technology::kWifi));
2578
2579 mock_devices_[0]->SelectService(connected_service1);
2580 mock_devices_[1]->SelectService(disconnected_service1);
2581 mock_devices_[2]->SelectService(disconnected_service2);
2582 mock_devices_[3]->SelectService(connected_service2);
2583
2584 set<string> expected_technologies;
2585 expected_technologies.insert(Technology::NameFromIdentifier(
2586 Technology::kEthernet));
2587 expected_technologies.insert(Technology::NameFromIdentifier(
2588 Technology::kWifi));
2589 Error error;
2590
2591 vector<string> technologies = manager()->ConnectedTechnologies(&error);
2592 EXPECT_THAT(set<string>(technologies.begin(), technologies.end()),
2593 ContainerEq(expected_technologies));
2594}
2595
2596TEST_F(ManagerTest, DefaultTechnology) {
2597 scoped_refptr<MockService> connected_service(
2598 new NiceMock<MockService>(control_interface(),
2599 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -08002600 metrics(),
Gaurav Shah435de2c2011-11-17 19:01:07 -08002601 manager()));
2602 scoped_refptr<MockService> disconnected_service(
2603 new NiceMock<MockService>(control_interface(),
2604 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -08002605 metrics(),
Gaurav Shah435de2c2011-11-17 19:01:07 -08002606 manager()));
2607
2608 // Connected. WiFi.
2609 ON_CALL(*connected_service.get(), IsConnected())
2610 .WillByDefault(Return(true));
2611 ON_CALL(*connected_service.get(), state())
2612 .WillByDefault(Return(Service::kStateConnected));
2613 ON_CALL(*connected_service.get(), technology())
2614 .WillByDefault(Return(Technology::kWifi));
2615
2616 // Disconnected. Ethernet.
2617 ON_CALL(*disconnected_service.get(), technology())
2618 .WillByDefault(Return(Technology::kEthernet));
2619
2620 manager()->RegisterService(disconnected_service);
Paul Stewartdfa46052012-06-26 09:44:14 -07002621 CompleteServiceSort();
Gaurav Shah435de2c2011-11-17 19:01:07 -08002622 Error error;
2623 EXPECT_THAT(manager()->DefaultTechnology(&error), StrEq(""));
2624
2625
2626 manager()->RegisterService(connected_service);
Paul Stewartdfa46052012-06-26 09:44:14 -07002627 CompleteServiceSort();
Gaurav Shah435de2c2011-11-17 19:01:07 -08002628 // Connected service should be brought to the front now.
2629 string expected_technology =
2630 Technology::NameFromIdentifier(Technology::kWifi);
2631 EXPECT_THAT(manager()->DefaultTechnology(&error), StrEq(expected_technology));
2632}
2633
Paul Stewart212d60f2012-07-12 10:59:13 -07002634TEST_F(ManagerTest, Stop) {
2635 scoped_refptr<MockProfile> profile(
Thieu Le5133b712013-02-19 14:47:21 -08002636 new NiceMock<MockProfile>(
2637 control_interface(), metrics(), manager(), ""));
Paul Stewart212d60f2012-07-12 10:59:13 -07002638 AdoptProfile(manager(), profile);
2639 scoped_refptr<MockService> service(
Thieu Le1271d682011-11-02 22:48:19 +00002640 new NiceMock<MockService>(control_interface(),
2641 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -08002642 metrics(),
Thieu Le1271d682011-11-02 22:48:19 +00002643 manager()));
Paul Stewart212d60f2012-07-12 10:59:13 -07002644 manager()->RegisterService(service);
2645 manager()->RegisterDevice(mock_devices_[0]);
2646 EXPECT_CALL(*profile.get(),
2647 UpdateDevice(DeviceRefPtr(mock_devices_[0].get())))
2648 .WillOnce(Return(true));
Wade Guthrie60a37062013-04-02 11:39:09 -07002649 EXPECT_CALL(*profile.get(), UpdateWiFiProvider(_)).WillOnce(Return(true));
Paul Stewart212d60f2012-07-12 10:59:13 -07002650 EXPECT_CALL(*profile.get(), Save()).WillOnce(Return(true));
2651 EXPECT_CALL(*service.get(), Disconnect(_)).Times(1);
Thieu Le1271d682011-11-02 22:48:19 +00002652 manager()->Stop();
2653}
2654
mukesh agrawal00917ce2011-11-22 23:56:55 +00002655TEST_F(ManagerTest, UpdateServiceConnected) {
2656 scoped_refptr<MockService> mock_service(
2657 new NiceMock<MockService>(control_interface(),
2658 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -08002659 metrics(),
mukesh agrawal00917ce2011-11-22 23:56:55 +00002660 manager()));
2661 manager()->RegisterService(mock_service);
2662 EXPECT_FALSE(mock_service->favorite());
2663 EXPECT_FALSE(mock_service->auto_connect());
2664
Gaurav Shah435de2c2011-11-17 19:01:07 -08002665 EXPECT_CALL(*mock_service.get(), IsConnected())
2666 .WillRepeatedly(Return(true));
mukesh agrawal00917ce2011-11-22 23:56:55 +00002667 manager()->UpdateService(mock_service);
2668 // We can't EXPECT_CALL(..., MakeFavorite), because that requires us
2669 // to mock out MakeFavorite. And mocking that out would break the
Paul Stewartee6b3d72013-07-12 16:07:51 -07002670 // SortServices test. (crbug.com/206367)
mukesh agrawal00917ce2011-11-22 23:56:55 +00002671 EXPECT_TRUE(mock_service->favorite());
2672 EXPECT_TRUE(mock_service->auto_connect());
2673}
2674
Thieu Led4e9e552012-02-16 16:26:07 -08002675TEST_F(ManagerTest, UpdateServiceConnectedPersistFavorite) {
2676 // This tests the case where the user connects to a service that is
2677 // currently associated with a profile. We want to make sure that the
2678 // favorite flag is set and that the flag is saved to the current
2679 // profile.
2680 scoped_refptr<MockService> mock_service(
2681 new NiceMock<MockService>(control_interface(),
2682 dispatcher(),
2683 metrics(),
2684 manager()));
2685 manager()->RegisterService(mock_service);
2686 EXPECT_FALSE(mock_service->favorite());
2687 EXPECT_FALSE(mock_service->auto_connect());
2688
Gary Moraind93615e2012-04-27 11:50:03 -07002689 scoped_refptr<MockProfile> profile(
Thieu Le5133b712013-02-19 14:47:21 -08002690 new MockProfile(
2691 control_interface(), metrics(), manager(), ""));
Thieu Led4e9e552012-02-16 16:26:07 -08002692
Gary Moraind93615e2012-04-27 11:50:03 -07002693 mock_service->set_profile(profile);
2694 EXPECT_CALL(*mock_service, IsConnected())
Thieu Led4e9e552012-02-16 16:26:07 -08002695 .WillRepeatedly(Return(true));
Gary Moraind93615e2012-04-27 11:50:03 -07002696 EXPECT_CALL(*profile,
2697 UpdateService(static_cast<ServiceRefPtr>(mock_service)));
Thieu Led4e9e552012-02-16 16:26:07 -08002698 manager()->UpdateService(mock_service);
2699 // We can't EXPECT_CALL(..., MakeFavorite), because that requires us
2700 // to mock out MakeFavorite. And mocking that out would break the
Paul Stewartee6b3d72013-07-12 16:07:51 -07002701 // SortServices test. (crbug.com/206367)
Thieu Led4e9e552012-02-16 16:26:07 -08002702 EXPECT_TRUE(mock_service->favorite());
2703 EXPECT_TRUE(mock_service->auto_connect());
Gary Moraind93615e2012-04-27 11:50:03 -07002704 // This releases the ref on the mock profile.
2705 mock_service->set_profile(NULL);
Thieu Led4e9e552012-02-16 16:26:07 -08002706}
2707
Paul Stewart3d9bcf52011-12-12 15:02:22 -08002708TEST_F(ManagerTest, SaveSuccessfulService) {
2709 scoped_refptr<MockProfile> profile(
Thieu Le5133b712013-02-19 14:47:21 -08002710 new StrictMock<MockProfile>(
2711 control_interface(), metrics(), manager(), ""));
Paul Stewart3d9bcf52011-12-12 15:02:22 -08002712 AdoptProfile(manager(), profile);
2713 scoped_refptr<MockService> service(
2714 new NiceMock<MockService>(control_interface(),
2715 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -08002716 metrics(),
Paul Stewart3d9bcf52011-12-12 15:02:22 -08002717 manager()));
2718
2719 // Re-cast this back to a ServiceRefPtr, so EXPECT arguments work correctly.
2720 ServiceRefPtr expect_service(service.get());
2721
2722 EXPECT_CALL(*profile.get(), ConfigureService(expect_service))
2723 .WillOnce(Return(false));
2724 manager()->RegisterService(service);
2725
2726 EXPECT_CALL(*service.get(), state())
2727 .WillRepeatedly(Return(Service::kStateConnected));
2728 EXPECT_CALL(*service.get(), IsConnected())
2729 .WillRepeatedly(Return(true));
2730 EXPECT_CALL(*profile.get(), AdoptService(expect_service))
2731 .WillOnce(Return(true));
2732 manager()->UpdateService(service);
2733}
2734
Darin Petkove7c6ad32012-06-29 10:22:09 +02002735TEST_F(ManagerTest, UpdateDevice) {
Thieu Le5133b712013-02-19 14:47:21 -08002736 MockProfile *profile0 =
2737 new MockProfile(control_interface(), metrics(), manager(), "");
2738 MockProfile *profile1 =
2739 new MockProfile(control_interface(), metrics(), manager(), "");
2740 MockProfile *profile2 =
2741 new MockProfile(control_interface(), metrics(), manager(), "");
Darin Petkove7c6ad32012-06-29 10:22:09 +02002742 AdoptProfile(manager(), profile0); // Passes ownership.
2743 AdoptProfile(manager(), profile1); // Passes ownership.
2744 AdoptProfile(manager(), profile2); // Passes ownership.
2745 DeviceRefPtr device_ref(mock_devices_[0].get());
2746 EXPECT_CALL(*profile0, UpdateDevice(device_ref)).Times(0);
2747 EXPECT_CALL(*profile1, UpdateDevice(device_ref)).WillOnce(Return(true));
2748 EXPECT_CALL(*profile2, UpdateDevice(device_ref)).WillOnce(Return(false));
2749 manager()->UpdateDevice(mock_devices_[0]);
2750}
2751
Paul Stewart1b253142012-01-26 14:05:52 -08002752TEST_F(ManagerTest, EnumerateProfiles) {
2753 vector<string> profile_paths;
2754 for (size_t i = 0; i < 10; i++) {
2755 scoped_refptr<MockProfile> profile(
Thieu Le5133b712013-02-19 14:47:21 -08002756 new StrictMock<MockProfile>(
2757 control_interface(), metrics(), manager(), ""));
Jason Glasgow5d8197b2012-01-27 08:37:32 -05002758 profile_paths.push_back(base::StringPrintf("/profile/%zd", i));
Paul Stewart1b253142012-01-26 14:05:52 -08002759 EXPECT_CALL(*profile.get(), GetRpcIdentifier())
2760 .WillOnce(Return(profile_paths.back()));
2761 AdoptProfile(manager(), profile);
2762 }
2763
2764 Error error;
2765 vector<string> returned_paths = manager()->EnumerateProfiles(&error);
2766 EXPECT_TRUE(error.IsSuccess());
2767 EXPECT_EQ(profile_paths.size(), returned_paths.size());
2768 for (size_t i = 0; i < profile_paths.size(); i++) {
2769 EXPECT_EQ(profile_paths[i], returned_paths[i]);
2770 }
2771}
2772
mukesh agrawal8a3188d2011-12-01 20:56:44 +00002773TEST_F(ManagerTest, AutoConnectOnRegister) {
2774 MockServiceRefPtr service = MakeAutoConnectableService();
2775 EXPECT_CALL(*service.get(), AutoConnect());
2776 manager()->RegisterService(service);
2777 dispatcher()->DispatchPendingEvents();
2778}
2779
2780TEST_F(ManagerTest, AutoConnectOnUpdate) {
2781 MockServiceRefPtr service1 = MakeAutoConnectableService();
mukesh agrawalcbfb34e2013-04-17 19:33:25 -07002782 service1->SetPriority(1, NULL);
mukesh agrawal8a3188d2011-12-01 20:56:44 +00002783 MockServiceRefPtr service2 = MakeAutoConnectableService();
mukesh agrawalcbfb34e2013-04-17 19:33:25 -07002784 service2->SetPriority(2, NULL);
mukesh agrawal8a3188d2011-12-01 20:56:44 +00002785 manager()->RegisterService(service1);
2786 manager()->RegisterService(service2);
2787 dispatcher()->DispatchPendingEvents();
2788
2789 EXPECT_CALL(*service1.get(), AutoConnect());
2790 EXPECT_CALL(*service2.get(), state())
2791 .WillRepeatedly(Return(Service::kStateFailure));
2792 EXPECT_CALL(*service2.get(), IsFailed())
2793 .WillRepeatedly(Return(true));
2794 EXPECT_CALL(*service2.get(), IsConnected())
2795 .WillRepeatedly(Return(false));
2796 manager()->UpdateService(service2);
2797 dispatcher()->DispatchPendingEvents();
2798}
2799
2800TEST_F(ManagerTest, AutoConnectOnDeregister) {
2801 MockServiceRefPtr service1 = MakeAutoConnectableService();
mukesh agrawalcbfb34e2013-04-17 19:33:25 -07002802 service1->SetPriority(1, NULL);
mukesh agrawal8a3188d2011-12-01 20:56:44 +00002803 MockServiceRefPtr service2 = MakeAutoConnectableService();
mukesh agrawalcbfb34e2013-04-17 19:33:25 -07002804 service2->SetPriority(2, NULL);
mukesh agrawal8a3188d2011-12-01 20:56:44 +00002805 manager()->RegisterService(service1);
2806 manager()->RegisterService(service2);
2807 dispatcher()->DispatchPendingEvents();
2808
2809 EXPECT_CALL(*service1.get(), AutoConnect());
2810 manager()->DeregisterService(service2);
2811 dispatcher()->DispatchPendingEvents();
2812}
2813
Darin Petkov3ec55342012-09-28 14:04:44 +02002814TEST_F(ManagerTest, AutoConnectOnPowerStateSuspending) {
2815 MockServiceRefPtr service = MakeAutoConnectableService();
2816 SetPowerState(PowerManagerProxyDelegate::kSuspending);
2817 SetPowerManager();
2818 EXPECT_CALL(*service, AutoConnect()).Times(0);
2819 manager()->RegisterService(service);
2820 dispatcher()->DispatchPendingEvents();
2821}
2822
Darin Petkovca621542012-07-25 14:25:56 +02002823TEST_F(ManagerTest, AutoConnectOnPowerStateMem) {
2824 MockServiceRefPtr service = MakeAutoConnectableService();
2825 SetPowerState(PowerManagerProxyDelegate::kMem);
2826 SetPowerManager();
2827 EXPECT_CALL(*service, AutoConnect()).Times(0);
2828 manager()->RegisterService(service);
2829 dispatcher()->DispatchPendingEvents();
2830}
2831
2832TEST_F(ManagerTest, AutoConnectOnPowerStateOn) {
2833 MockServiceRefPtr service = MakeAutoConnectableService();
2834 SetPowerState(PowerManagerProxyDelegate::kOn);
2835 SetPowerManager();
2836 EXPECT_CALL(*service, AutoConnect());
2837 manager()->RegisterService(service);
2838 dispatcher()->DispatchPendingEvents();
2839}
2840
2841TEST_F(ManagerTest, AutoConnectOnPowerStateUnknown) {
2842 MockServiceRefPtr service = MakeAutoConnectableService();
2843 SetPowerState(PowerManagerProxyDelegate::kUnknown);
2844 SetPowerManager();
2845 EXPECT_CALL(*service, AutoConnect());
2846 manager()->RegisterService(service);
2847 dispatcher()->DispatchPendingEvents();
2848}
2849
Paul Stewart63864b62012-11-07 15:10:55 -08002850TEST_F(ManagerTest, AutoConnectWhileNotRunning) {
2851 SetRunning(false);
2852 MockServiceRefPtr service = MakeAutoConnectableService();
2853 EXPECT_CALL(*service, AutoConnect()).Times(0);
2854 manager()->RegisterService(service);
2855 dispatcher()->DispatchPendingEvents();
2856}
2857
Darin Petkovca621542012-07-25 14:25:56 +02002858TEST_F(ManagerTest, OnPowerStateChanged) {
2859 MockServiceRefPtr service = MakeAutoConnectableService();
2860 SetPowerState(PowerManagerProxyDelegate::kOn);
2861 SetPowerManager();
2862 EXPECT_CALL(*service, AutoConnect());
2863 manager()->RegisterService(service);
mukesh agrawal784566d2012-08-08 18:32:58 -07002864 manager()->RegisterDevice(mock_devices_[0]);
Darin Petkovca621542012-07-25 14:25:56 +02002865 dispatcher()->DispatchPendingEvents();
2866
mukesh agrawal784566d2012-08-08 18:32:58 -07002867 EXPECT_CALL(*mock_devices_[0], OnAfterResume());
Darin Petkovca621542012-07-25 14:25:56 +02002868 OnPowerStateChanged(PowerManagerProxyDelegate::kOn);
2869 EXPECT_CALL(*service, AutoConnect());
2870 dispatcher()->DispatchPendingEvents();
mukesh agrawal784566d2012-08-08 18:32:58 -07002871 Mock::VerifyAndClearExpectations(mock_devices_[0]);
Darin Petkovca621542012-07-25 14:25:56 +02002872
mukesh agrawal784566d2012-08-08 18:32:58 -07002873 EXPECT_CALL(*mock_devices_[0], OnBeforeSuspend());
Darin Petkovca621542012-07-25 14:25:56 +02002874 OnPowerStateChanged(PowerManagerProxyDelegate::kMem);
2875 EXPECT_CALL(*service, AutoConnect()).Times(0);
2876 dispatcher()->DispatchPendingEvents();
mukesh agrawal784566d2012-08-08 18:32:58 -07002877 Mock::VerifyAndClearExpectations(mock_devices_[0]);
Darin Petkovca621542012-07-25 14:25:56 +02002878}
2879
Darin Petkov3ec55342012-09-28 14:04:44 +02002880TEST_F(ManagerTest, AddTerminationAction) {
2881 EXPECT_CALL(*power_manager_, AddSuspendDelayCallback(_, _));
Daniel Eratf9753672013-01-24 10:17:02 -08002882 EXPECT_CALL(*power_manager_, RegisterSuspendDelay(_, _, _));
Darin Petkov3ec55342012-09-28 14:04:44 +02002883 SetPowerManager();
2884 EXPECT_TRUE(GetTerminationActions()->IsEmpty());
2885 manager()->AddTerminationAction("action1", base::Closure());
2886 EXPECT_FALSE(GetTerminationActions()->IsEmpty());
2887 manager()->AddTerminationAction("action2", base::Closure());
2888}
2889
2890TEST_F(ManagerTest, RemoveTerminationAction) {
Daniel Erat0818cca2012-12-14 10:16:21 -08002891 const char kKey1[] = "action1";
2892 const char kKey2[] = "action2";
2893 const int kSuspendDelayId = 123;
Darin Petkov3ec55342012-09-28 14:04:44 +02002894
2895 MockPowerManager &power_manager = *power_manager_;
2896 SetPowerManager();
2897
2898 // Removing an action when the hook table is empty should not result in any
2899 // calls to the power manager.
Daniel Erat0818cca2012-12-14 10:16:21 -08002900 EXPECT_CALL(power_manager, UnregisterSuspendDelay(_)).Times(0);
Darin Petkov3ec55342012-09-28 14:04:44 +02002901 EXPECT_CALL(power_manager, RemoveSuspendDelayCallback(_)).Times(0);
2902 EXPECT_TRUE(GetTerminationActions()->IsEmpty());
2903 manager()->RemoveTerminationAction("unknown");
2904 Mock::VerifyAndClearExpectations(&power_manager);
2905
Daniel Eratf9753672013-01-24 10:17:02 -08002906 EXPECT_CALL(power_manager, RegisterSuspendDelay(_, _, _))
2907 .WillOnce(DoAll(SetArgumentPointee<2>(kSuspendDelayId), Return(true)));
Daniel Erat0818cca2012-12-14 10:16:21 -08002908 EXPECT_CALL(power_manager, AddSuspendDelayCallback(_, _)).Times(1);
Darin Petkov3ec55342012-09-28 14:04:44 +02002909 manager()->AddTerminationAction(kKey1, base::Closure());
2910 EXPECT_FALSE(GetTerminationActions()->IsEmpty());
2911 manager()->AddTerminationAction(kKey2, base::Closure());
2912
2913 // Removing an action that ends up with a non-empty hook table should not
2914 // result in any calls to the power manager.
Daniel Erat0818cca2012-12-14 10:16:21 -08002915 EXPECT_CALL(power_manager, UnregisterSuspendDelay(_)).Times(0);
Darin Petkov3ec55342012-09-28 14:04:44 +02002916 EXPECT_CALL(power_manager, RemoveSuspendDelayCallback(_)).Times(0);
2917 manager()->RemoveTerminationAction(kKey1);
2918 EXPECT_FALSE(GetTerminationActions()->IsEmpty());
2919 Mock::VerifyAndClearExpectations(&power_manager);
2920
2921 // Removing the last action should trigger unregistering from the power
2922 // manager.
Daniel Erat0818cca2012-12-14 10:16:21 -08002923 EXPECT_CALL(power_manager, UnregisterSuspendDelay(kSuspendDelayId))
2924 .WillOnce(Return(true));
Darin Petkov3ec55342012-09-28 14:04:44 +02002925 EXPECT_CALL(power_manager, RemoveSuspendDelayCallback(_));
2926 manager()->RemoveTerminationAction(kKey2);
2927 EXPECT_TRUE(GetTerminationActions()->IsEmpty());
2928}
2929
2930TEST_F(ManagerTest, RunTerminationActions) {
2931 TerminationActionTest test_action;
2932 const string kActionName = "action";
2933
2934 EXPECT_CALL(test_action, Done(_));
2935 manager()->RunTerminationActions(Bind(&TerminationActionTest::Done,
2936 test_action.AsWeakPtr()));
2937
2938 manager()->AddTerminationAction(TerminationActionTest::kActionName,
2939 Bind(&TerminationActionTest::Action,
2940 test_action.AsWeakPtr()));
2941 test_action.set_manager(manager());
2942 EXPECT_CALL(test_action, Done(_));
2943 manager()->RunTerminationActions(Bind(&TerminationActionTest::Done,
2944 test_action.AsWeakPtr()));
2945}
2946
Daniel Erat0818cca2012-12-14 10:16:21 -08002947TEST_F(ManagerTest, OnSuspendImminent) {
2948 const int kSuspendId = 123;
Darin Petkov3ec55342012-09-28 14:04:44 +02002949 EXPECT_TRUE(GetTerminationActions()->IsEmpty());
Daniel Erat0818cca2012-12-14 10:16:21 -08002950 EXPECT_CALL(*power_manager_,
2951 ReportSuspendReadiness(
2952 manager()->suspend_delay_id_for_testing(), kSuspendId));
Darin Petkov3ec55342012-09-28 14:04:44 +02002953 SetPowerManager();
Daniel Erat0818cca2012-12-14 10:16:21 -08002954 OnSuspendImminent(kSuspendId);
Darin Petkov3ec55342012-09-28 14:04:44 +02002955}
2956
2957TEST_F(ManagerTest, OnSuspendActionsComplete) {
Daniel Erat0818cca2012-12-14 10:16:21 -08002958 const int kSuspendId = 54321;
Darin Petkov3ec55342012-09-28 14:04:44 +02002959 Error error;
Daniel Erat0818cca2012-12-14 10:16:21 -08002960 EXPECT_CALL(*power_manager_,
2961 ReportSuspendReadiness(
2962 manager()->suspend_delay_id_for_testing(), kSuspendId));
Darin Petkov3ec55342012-09-28 14:04:44 +02002963 SetPowerManager();
Daniel Erat0818cca2012-12-14 10:16:21 -08002964 OnSuspendActionsComplete(kSuspendId, error);
Darin Petkov3ec55342012-09-28 14:04:44 +02002965}
2966
Paul Stewartc681fa02012-03-02 19:40:04 -08002967TEST_F(ManagerTest, RecheckPortal) {
2968 EXPECT_CALL(*mock_devices_[0].get(), RequestPortalDetection())
2969 .WillOnce(Return(false));
2970 EXPECT_CALL(*mock_devices_[1].get(), RequestPortalDetection())
2971 .WillOnce(Return(true));
2972 EXPECT_CALL(*mock_devices_[2].get(), RequestPortalDetection())
2973 .Times(0);
2974
2975 manager()->RegisterDevice(mock_devices_[0]);
2976 manager()->RegisterDevice(mock_devices_[1]);
2977 manager()->RegisterDevice(mock_devices_[2]);
2978
2979 manager()->RecheckPortal(NULL);
2980}
2981
Paul Stewartd215af62012-04-24 23:25:50 -07002982TEST_F(ManagerTest, RecheckPortalOnService) {
2983 MockServiceRefPtr service = new NiceMock<MockService>(control_interface(),
2984 dispatcher(),
2985 metrics(),
2986 manager());
2987 EXPECT_CALL(*mock_devices_[0].get(),
2988 IsConnectedToService(IsRefPtrTo(service)))
2989 .WillOnce(Return(false));
2990 EXPECT_CALL(*mock_devices_[1].get(),
2991 IsConnectedToService(IsRefPtrTo(service)))
2992 .WillOnce(Return(true));
2993 EXPECT_CALL(*mock_devices_[1].get(), RestartPortalDetection())
2994 .WillOnce(Return(true));
2995 EXPECT_CALL(*mock_devices_[2].get(), IsConnectedToService(_))
2996 .Times(0);
2997
2998 manager()->RegisterDevice(mock_devices_[0]);
2999 manager()->RegisterDevice(mock_devices_[1]);
3000 manager()->RegisterDevice(mock_devices_[2]);
3001
3002 manager()->RecheckPortalOnService(service);
3003}
3004
Paul Stewarte2bad7c2012-03-14 08:55:33 -07003005TEST_F(ManagerTest, GetDefaultService) {
3006 EXPECT_FALSE(manager()->GetDefaultService().get());
Paul Stewart49739c02012-08-08 17:24:03 -07003007 EXPECT_EQ("/", GetDefaultServiceRpcIdentifier());
Paul Stewarte2bad7c2012-03-14 08:55:33 -07003008
3009 scoped_refptr<MockService> mock_service(
3010 new NiceMock<MockService>(control_interface(),
3011 dispatcher(),
3012 metrics(),
3013 manager()));
3014
3015 manager()->RegisterService(mock_service);
3016 EXPECT_FALSE(manager()->GetDefaultService().get());
Paul Stewart49739c02012-08-08 17:24:03 -07003017 EXPECT_EQ("/", GetDefaultServiceRpcIdentifier());
Paul Stewarte2bad7c2012-03-14 08:55:33 -07003018
3019 scoped_refptr<MockConnection> mock_connection(
3020 new NiceMock<MockConnection>(device_info_.get()));
Paul Stewartce4ec192012-03-14 12:53:46 -07003021 mock_service->set_mock_connection(mock_connection);
Paul Stewarte2bad7c2012-03-14 08:55:33 -07003022 EXPECT_EQ(mock_service.get(), manager()->GetDefaultService().get());
Paul Stewart49739c02012-08-08 17:24:03 -07003023 EXPECT_EQ(mock_service->GetRpcIdentifier(), GetDefaultServiceRpcIdentifier());
Paul Stewarte2bad7c2012-03-14 08:55:33 -07003024
Paul Stewartce4ec192012-03-14 12:53:46 -07003025 mock_service->set_mock_connection(NULL);
Paul Stewarte2bad7c2012-03-14 08:55:33 -07003026 manager()->DeregisterService(mock_service);
3027}
3028
Paul Stewart13ed2252012-03-21 12:52:46 -07003029TEST_F(ManagerTest, GetServiceWithGUID) {
3030 scoped_refptr<MockService> mock_service0(
3031 new NiceMock<MockService>(control_interface(),
3032 dispatcher(),
3033 metrics(),
3034 manager()));
3035
3036 scoped_refptr<MockService> mock_service1(
3037 new NiceMock<MockService>(control_interface(),
3038 dispatcher(),
3039 metrics(),
3040 manager()));
3041
Paul Stewartcb59fed2012-03-21 21:14:46 -07003042 EXPECT_CALL(*mock_service0.get(), Configure(_, _))
3043 .Times(0);
3044 EXPECT_CALL(*mock_service1.get(), Configure(_, _))
3045 .Times(0);
3046
Paul Stewart13ed2252012-03-21 12:52:46 -07003047 manager()->RegisterService(mock_service0);
3048 manager()->RegisterService(mock_service1);
3049
3050 const string kGUID0 = "GUID0";
3051 const string kGUID1 = "GUID1";
3052
3053 {
3054 Error error;
3055 ServiceRefPtr service = manager()->GetServiceWithGUID(kGUID0, &error);
3056 EXPECT_FALSE(error.IsSuccess());
3057 EXPECT_FALSE(service);
3058 }
3059
3060 KeyValueStore args;
3061 args.SetString(flimflam::kGuidProperty, kGUID1);
3062
3063 {
3064 Error error;
3065 ServiceRefPtr service = manager()->GetService(args, &error);
3066 EXPECT_EQ(Error::kInvalidArguments, error.type());
3067 EXPECT_FALSE(service);
3068 }
3069
mukesh agrawalcbfb34e2013-04-17 19:33:25 -07003070 mock_service0->SetGuid(kGUID0, NULL);
3071 mock_service1->SetGuid(kGUID1, NULL);
Paul Stewart13ed2252012-03-21 12:52:46 -07003072
3073 {
3074 Error error;
3075 ServiceRefPtr service = manager()->GetServiceWithGUID(kGUID0, &error);
3076 EXPECT_TRUE(error.IsSuccess());
3077 EXPECT_EQ(mock_service0.get(), service.get());
3078 }
3079
3080 {
3081 Error error;
Paul Stewartcb59fed2012-03-21 21:14:46 -07003082 EXPECT_CALL(*mock_service1.get(), Configure(_, &error))
3083 .Times(1);
Paul Stewart13ed2252012-03-21 12:52:46 -07003084 ServiceRefPtr service = manager()->GetService(args, &error);
3085 EXPECT_TRUE(error.IsSuccess());
3086 EXPECT_EQ(mock_service1.get(), service.get());
3087 }
3088
3089 manager()->DeregisterService(mock_service0);
3090 manager()->DeregisterService(mock_service1);
3091}
3092
Gary Morain028545d2012-04-07 14:55:52 -07003093
3094TEST_F(ManagerTest, CalculateStateOffline) {
Darin Petkov4cbff5b2013-01-29 16:29:05 +01003095 EXPECT_FALSE(manager()->IsOnline());
3096 EXPECT_EQ("offline", manager()->CalculateState(NULL));
3097
Thieu Le6c1e3bb2013-02-06 15:20:35 -08003098 MockMetrics mock_metrics(dispatcher());
Darin Petkov4cbff5b2013-01-29 16:29:05 +01003099 SetMetrics(&mock_metrics);
Gary Morain028545d2012-04-07 14:55:52 -07003100 EXPECT_CALL(mock_metrics, NotifyDefaultServiceChanged(_))
3101 .Times(AnyNumber());
3102 scoped_refptr<MockService> mock_service0(
3103 new NiceMock<MockService>(control_interface(),
3104 dispatcher(),
3105 metrics(),
3106 manager()));
3107
3108 scoped_refptr<MockService> mock_service1(
3109 new NiceMock<MockService>(control_interface(),
3110 dispatcher(),
3111 metrics(),
3112 manager()));
3113
3114 EXPECT_CALL(*mock_service0.get(), IsConnected())
3115 .WillRepeatedly(Return(false));
3116 EXPECT_CALL(*mock_service1.get(), IsConnected())
3117 .WillRepeatedly(Return(false));
3118
3119 manager()->RegisterService(mock_service0);
3120 manager()->RegisterService(mock_service1);
3121
Darin Petkov4cbff5b2013-01-29 16:29:05 +01003122 EXPECT_FALSE(manager()->IsOnline());
Gary Morain028545d2012-04-07 14:55:52 -07003123 EXPECT_EQ("offline", manager()->CalculateState(NULL));
3124
3125 manager()->DeregisterService(mock_service0);
3126 manager()->DeregisterService(mock_service1);
3127}
3128
3129TEST_F(ManagerTest, CalculateStateOnline) {
Thieu Le6c1e3bb2013-02-06 15:20:35 -08003130 MockMetrics mock_metrics(dispatcher());
Darin Petkov4cbff5b2013-01-29 16:29:05 +01003131 SetMetrics(&mock_metrics);
Gary Morain028545d2012-04-07 14:55:52 -07003132 EXPECT_CALL(mock_metrics, NotifyDefaultServiceChanged(_))
3133 .Times(AnyNumber());
3134 scoped_refptr<MockService> mock_service0(
3135 new NiceMock<MockService>(control_interface(),
3136 dispatcher(),
3137 metrics(),
3138 manager()));
3139
3140 scoped_refptr<MockService> mock_service1(
3141 new NiceMock<MockService>(control_interface(),
3142 dispatcher(),
3143 metrics(),
3144 manager()));
3145
3146 EXPECT_CALL(*mock_service0.get(), IsConnected())
3147 .WillRepeatedly(Return(false));
3148 EXPECT_CALL(*mock_service1.get(), IsConnected())
3149 .WillRepeatedly(Return(true));
3150 EXPECT_CALL(*mock_service0.get(), state())
3151 .WillRepeatedly(Return(Service::kStateIdle));
3152 EXPECT_CALL(*mock_service1.get(), state())
3153 .WillRepeatedly(Return(Service::kStateConnected));
3154
3155 manager()->RegisterService(mock_service0);
3156 manager()->RegisterService(mock_service1);
Paul Stewartdfa46052012-06-26 09:44:14 -07003157 CompleteServiceSort();
Gary Morain028545d2012-04-07 14:55:52 -07003158
Darin Petkov4cbff5b2013-01-29 16:29:05 +01003159 EXPECT_TRUE(manager()->IsOnline());
Gary Morain028545d2012-04-07 14:55:52 -07003160 EXPECT_EQ("online", manager()->CalculateState(NULL));
3161
3162 manager()->DeregisterService(mock_service0);
3163 manager()->DeregisterService(mock_service1);
3164}
3165
Paul Stewart10e9e4e2012-04-26 19:46:28 -07003166TEST_F(ManagerTest, StartupPortalList) {
3167 // Simulate loading value from the default profile.
3168 const string kProfileValue("wifi,vpn");
3169 manager()->props_.check_portal_list = kProfileValue;
3170
3171 EXPECT_EQ(kProfileValue, manager()->GetCheckPortalList(NULL));
3172 EXPECT_TRUE(manager()->IsPortalDetectionEnabled(Technology::kWifi));
3173 EXPECT_FALSE(manager()->IsPortalDetectionEnabled(Technology::kCellular));
3174
3175 const string kStartupValue("cellular,ethernet");
3176 manager()->SetStartupPortalList(kStartupValue);
3177 // Ensure profile value is not overwritten, so when we save the default
3178 // profile, the correct value will still be written.
3179 EXPECT_EQ(kProfileValue, manager()->props_.check_portal_list);
3180
3181 // However we should read back a different list.
3182 EXPECT_EQ(kStartupValue, manager()->GetCheckPortalList(NULL));
3183 EXPECT_FALSE(manager()->IsPortalDetectionEnabled(Technology::kWifi));
3184 EXPECT_TRUE(manager()->IsPortalDetectionEnabled(Technology::kCellular));
3185
3186 const string kRuntimeValue("ppp");
3187 // Setting a runtime value over the control API should overwrite both
3188 // the profile value and what we read back.
3189 Error error;
3190 manager()->mutable_store()->SetStringProperty(
3191 flimflam::kCheckPortalListProperty,
3192 kRuntimeValue,
3193 &error);
3194 ASSERT_TRUE(error.IsSuccess());
3195 EXPECT_EQ(kRuntimeValue, manager()->GetCheckPortalList(NULL));
3196 EXPECT_EQ(kRuntimeValue, manager()->props_.check_portal_list);
3197 EXPECT_FALSE(manager()->IsPortalDetectionEnabled(Technology::kCellular));
3198 EXPECT_TRUE(manager()->IsPortalDetectionEnabled(Technology::kPPP));
3199}
3200
Paul Stewart036dba02012-08-07 12:34:41 -07003201TEST_F(ManagerTest, LinkMonitorEnabled) {
3202 const string kEnabledTechnologies("wifi,vpn");
3203 manager()->props_.link_monitor_technologies = kEnabledTechnologies;
3204 EXPECT_TRUE(manager()->IsTechnologyLinkMonitorEnabled(Technology::kWifi));
3205 EXPECT_FALSE(
3206 manager()->IsTechnologyLinkMonitorEnabled(Technology::kCellular));
3207}
3208
Paul Stewart85aea152013-01-22 09:31:56 -08003209TEST_F(ManagerTest, IsDefaultProfile) {
Paul Stewart3c504012013-01-17 17:49:58 -08003210 EXPECT_TRUE(manager()->IsDefaultProfile(NULL));
Paul Stewart85aea152013-01-22 09:31:56 -08003211 scoped_ptr<MockStore> store0(new MockStore);
Paul Stewart3c504012013-01-17 17:49:58 -08003212 EXPECT_TRUE(manager()->IsDefaultProfile(store0.get()));
Paul Stewart85aea152013-01-22 09:31:56 -08003213 scoped_refptr<MockProfile> profile(
Thieu Le5133b712013-02-19 14:47:21 -08003214 new MockProfile(control_interface(), metrics(), manager(), ""));
Paul Stewart85aea152013-01-22 09:31:56 -08003215 EXPECT_CALL(*profile, GetConstStorage()).WillRepeatedly(Return(store0.get()));
3216 AdoptProfile(manager(), profile);
3217 EXPECT_TRUE(manager()->IsDefaultProfile(store0.get()));
3218 EXPECT_FALSE(manager()->IsDefaultProfile(NULL));
3219 scoped_ptr<MockStore> store1(new MockStore);
3220 EXPECT_FALSE(manager()->IsDefaultProfile(store1.get()));
3221}
3222
mukesh agrawal46c27cc2013-07-10 16:39:10 -07003223TEST_F(ManagerTest, SetEnabledStateForTechnology) {
Jason Glasgowdf7c5532012-05-14 14:41:45 -04003224 Error error(Error::kOperationInitiated);
mukesh agrawal46c27cc2013-07-10 16:39:10 -07003225 DisableTechnologyReplyHandler disable_technology_reply_handler;
3226 ResultCallback disable_technology_callback(
3227 Bind(&DisableTechnologyReplyHandler::ReportResult,
3228 disable_technology_reply_handler.AsWeakPtr()));
3229 EXPECT_CALL(disable_technology_reply_handler, ReportResult(_)).Times(0);
3230
3231 manager()->SetEnabledStateForTechnology(flimflam::kTypeEthernet, false,
3232 &error, disable_technology_callback);
Jason Glasgowdf7c5532012-05-14 14:41:45 -04003233 EXPECT_TRUE(error.IsSuccess());
3234
Joshua Krollda798622012-06-05 12:30:48 -07003235 ON_CALL(*mock_devices_[0], technology())
3236 .WillByDefault(Return(Technology::kEthernet));
mukesh agrawal46c27cc2013-07-10 16:39:10 -07003237 ON_CALL(*mock_devices_[1], technology())
3238 .WillByDefault(Return(Technology::kCellular));
3239 ON_CALL(*mock_devices_[2], technology())
3240 .WillByDefault(Return(Technology::kCellular));
Jason Glasgowdf7c5532012-05-14 14:41:45 -04003241
3242 manager()->RegisterDevice(mock_devices_[0]);
mukesh agrawal46c27cc2013-07-10 16:39:10 -07003243 manager()->RegisterDevice(mock_devices_[1]);
Jason Glasgowdf7c5532012-05-14 14:41:45 -04003244
mukesh agrawal46c27cc2013-07-10 16:39:10 -07003245 // Ethernet Device is disabled, so disable succeeds immediately.
Jason Glasgowdf7c5532012-05-14 14:41:45 -04003246 error.Populate(Error::kOperationInitiated);
mukesh agrawal46c27cc2013-07-10 16:39:10 -07003247 manager()->SetEnabledStateForTechnology(flimflam::kTypeEthernet, false,
3248 &error, disable_technology_callback);
Jason Glasgowdf7c5532012-05-14 14:41:45 -04003249 EXPECT_TRUE(error.IsSuccess());
3250
mukesh agrawal46c27cc2013-07-10 16:39:10 -07003251 // Ethernet Device is enabled, and mock doesn't change error from
3252 // kOperationInitiated, so expect disable to say operation in progress.
Jason Glasgowdf7c5532012-05-14 14:41:45 -04003253 EXPECT_CALL(*mock_devices_[0], SetEnabledPersistent(false, _, _));
3254 mock_devices_[0]->enabled_ = true;
3255 error.Populate(Error::kOperationInitiated);
mukesh agrawal46c27cc2013-07-10 16:39:10 -07003256 manager()->SetEnabledStateForTechnology(flimflam::kTypeEthernet, false,
3257 &error, disable_technology_callback);
Jason Glasgowdf7c5532012-05-14 14:41:45 -04003258 EXPECT_TRUE(error.IsOngoing());
mukesh agrawal46c27cc2013-07-10 16:39:10 -07003259
3260 // Ethernet Device is disabled, and mock doesn't change error from
3261 // kOperationInitiated, so expect enable to say operation in progress.
3262 EXPECT_CALL(*mock_devices_[0], SetEnabledPersistent(true, _, _));
3263 mock_devices_[0]->enabled_ = false;
3264 error.Populate(Error::kOperationInitiated);
3265 manager()->SetEnabledStateForTechnology(flimflam::kTypeEthernet, true,
3266 &error, disable_technology_callback);
3267 EXPECT_TRUE(error.IsOngoing());
3268
3269 // Cellular Device is enabled, but disable failed.
3270 EXPECT_CALL(*mock_devices_[1], SetEnabledPersistent(false, _, _))
3271 .WillOnce(WithArg<1>(Invoke(SetErrorPermissionDenied)));
3272 mock_devices_[1]->enabled_ = true;
3273 error.Populate(Error::kOperationInitiated);
3274 manager()->SetEnabledStateForTechnology(flimflam::kTypeCellular, false,
3275 &error, disable_technology_callback);
3276 EXPECT_EQ(Error::kPermissionDenied, error.type());
3277
3278 // Multiple Cellular Devices in enabled state. Should indicate IsOngoing
3279 // if one is in progress (even if the other completed immediately).
3280 manager()->RegisterDevice(mock_devices_[2]);
3281 EXPECT_CALL(*mock_devices_[1], SetEnabledPersistent(false, _, _))
3282 .WillOnce(WithArg<1>(Invoke(SetErrorPermissionDenied)));
3283 EXPECT_CALL(*mock_devices_[2], SetEnabledPersistent(false, _, _));
3284 mock_devices_[1]->enabled_ = true;
3285 mock_devices_[2]->enabled_ = true;
3286 error.Populate(Error::kOperationInitiated);
3287 manager()->SetEnabledStateForTechnology(flimflam::kTypeCellular, false,
3288 &error, disable_technology_callback);
3289 EXPECT_TRUE(error.IsOngoing());
3290
3291 // ...and order doesn't matter.
3292 EXPECT_CALL(*mock_devices_[1], SetEnabledPersistent(false, _, _));
3293 EXPECT_CALL(*mock_devices_[2], SetEnabledPersistent(false, _, _))
3294 .WillOnce(WithArg<1>(Invoke(SetErrorPermissionDenied)));
3295 mock_devices_[1]->enabled_ = true;
3296 mock_devices_[2]->enabled_ = true;
3297 error.Populate(Error::kOperationInitiated);
3298 manager()->SetEnabledStateForTechnology(flimflam::kTypeCellular, false,
3299 &error, disable_technology_callback);
3300 EXPECT_TRUE(error.IsOngoing());
3301 Mock::VerifyAndClearExpectations(&disable_technology_reply_handler);
3302
3303 // Multiple Cellular Devices in enabled state. Even if all disable
3304 // operations complete asynchronously, we only get one call to the
3305 // DisableTechnologyReplyHandler::ReportResult.
3306 ResultCallback device1_result_callback;
3307 ResultCallback device2_result_callback;
3308 EXPECT_CALL(*mock_devices_[1], SetEnabledPersistent(false, _, _))
3309 .WillOnce(SaveArg<2>(&device1_result_callback));
3310 EXPECT_CALL(*mock_devices_[2], SetEnabledPersistent(false, _, _))
3311 .WillOnce(DoAll(WithArg<1>(Invoke(SetErrorPermissionDenied)),
3312 SaveArg<2>(&device2_result_callback)));
3313 EXPECT_CALL(disable_technology_reply_handler, ReportResult(_));
3314 mock_devices_[1]->enabled_ = true;
3315 mock_devices_[2]->enabled_ = true;
3316 error.Populate(Error::kOperationInitiated);
3317 manager()->SetEnabledStateForTechnology(flimflam::kTypeCellular, false,
3318 &error, disable_technology_callback);
3319 EXPECT_TRUE(error.IsOngoing());
3320 device1_result_callback.Run(Error(Error::kSuccess));
3321 device2_result_callback.Run(Error(Error::kSuccess));
Jason Glasgowdf7c5532012-05-14 14:41:45 -04003322}
3323
Paul Stewart4d5efb72012-09-17 12:24:34 -07003324TEST_F(ManagerTest, IgnoredSearchList) {
3325 scoped_ptr<MockResolver> resolver(new StrictMock<MockResolver>());
Paul Stewart4d5efb72012-09-17 12:24:34 -07003326 vector<string> ignored_paths;
mukesh agrawalbebf1b82013-04-23 15:06:33 -07003327 SetResolver(resolver.get());
Paul Stewart4d5efb72012-09-17 12:24:34 -07003328
3329 const string kIgnored0 = "chromium.org";
3330 ignored_paths.push_back(kIgnored0);
3331 EXPECT_CALL(*resolver.get(), set_ignored_search_list(ignored_paths));
mukesh agrawalbebf1b82013-04-23 15:06:33 -07003332 SetIgnoredDNSSearchPaths(kIgnored0, NULL);
Paul Stewart4d5efb72012-09-17 12:24:34 -07003333 EXPECT_EQ(kIgnored0, GetIgnoredDNSSearchPaths());
3334
3335 const string kIgnored1 = "google.com";
3336 const string kIgnoredSum = kIgnored0 + "," + kIgnored1;
3337 ignored_paths.push_back(kIgnored1);
3338 EXPECT_CALL(*resolver.get(), set_ignored_search_list(ignored_paths));
mukesh agrawalbebf1b82013-04-23 15:06:33 -07003339 SetIgnoredDNSSearchPaths(kIgnoredSum, NULL);
Paul Stewart4d5efb72012-09-17 12:24:34 -07003340 EXPECT_EQ(kIgnoredSum, GetIgnoredDNSSearchPaths());
3341
mukesh agrawalbebf1b82013-04-23 15:06:33 -07003342 ignored_paths.clear();
3343 EXPECT_CALL(*resolver.get(), set_ignored_search_list(ignored_paths));
3344 SetIgnoredDNSSearchPaths("", NULL);
3345 EXPECT_EQ("", GetIgnoredDNSSearchPaths());
3346
Paul Stewart4d5efb72012-09-17 12:24:34 -07003347 SetResolver(Resolver::GetInstance());
3348}
3349
Paul Stewartbfb82552012-10-24 16:48:48 -07003350TEST_F(ManagerTest, ServiceStateChangeEmitsServices) {
3351 // Test to make sure that every service state-change causes the
3352 // Manager to emit a new service list.
3353 scoped_refptr<MockService> mock_service(
3354 new NiceMock<MockService>(control_interface(),
3355 dispatcher(),
3356 metrics(),
3357 manager()));
3358 EXPECT_CALL(*mock_service, state())
3359 .WillRepeatedly(Return(Service::kStateIdle));
3360
3361 manager()->RegisterService(mock_service);
3362 EXPECT_CALL(
3363 *manager_adaptor_, EmitRpcIdentifierArrayChanged(
3364 flimflam::kServicesProperty, _)).Times(1);
3365 EXPECT_CALL(
3366 *manager_adaptor_, EmitRpcIdentifierArrayChanged(
3367 flimflam::kServiceWatchListProperty, _)).Times(1);
3368 CompleteServiceSort();
3369
3370 Mock::VerifyAndClearExpectations(manager_adaptor_);
3371 EXPECT_CALL(
3372 *manager_adaptor_, EmitRpcIdentifierArrayChanged(
3373 flimflam::kServicesProperty, _)).Times(1);
3374 EXPECT_CALL(
3375 *manager_adaptor_, EmitRpcIdentifierArrayChanged(
3376 flimflam::kServiceWatchListProperty, _)).Times(1);
3377 manager()->UpdateService(mock_service.get());
3378 CompleteServiceSort();
3379
3380 manager()->DeregisterService(mock_service);
3381}
3382
3383TEST_F(ManagerTest, EnumerateServices) {
3384 scoped_refptr<MockService> mock_service(
3385 new NiceMock<MockService>(control_interface(),
3386 dispatcher(),
3387 metrics(),
3388 manager()));
3389 manager()->RegisterService(mock_service);
3390
3391 EXPECT_CALL(*mock_service, state())
3392 .WillRepeatedly(Return(Service::kStateConnected));
3393 EXPECT_CALL(*mock_service, IsVisible())
3394 .WillRepeatedly(Return(false));
3395 EXPECT_TRUE(EnumerateAvailableServices().empty());
3396 EXPECT_TRUE(EnumerateWatchedServices().empty());
3397
3398 EXPECT_CALL(*mock_service, state())
3399 .WillRepeatedly(Return(Service::kStateIdle));
3400 EXPECT_TRUE(EnumerateAvailableServices().empty());
3401 EXPECT_TRUE(EnumerateWatchedServices().empty());
3402
3403 EXPECT_CALL(*mock_service, IsVisible())
3404 .WillRepeatedly(Return(true));
3405 Service::ConnectState unwatched_states[] = {
3406 Service::kStateUnknown,
3407 Service::kStateIdle,
3408 Service::kStateFailure
3409 };
3410 for (size_t i = 0; i < arraysize(unwatched_states); ++i) {
3411 EXPECT_CALL(*mock_service, state())
3412 .WillRepeatedly(Return(unwatched_states[i]));
3413 EXPECT_FALSE(EnumerateAvailableServices().empty());
3414 EXPECT_TRUE(EnumerateWatchedServices().empty());
3415 }
3416
3417 Service::ConnectState watched_states[] = {
3418 Service::kStateAssociating,
3419 Service::kStateConfiguring,
3420 Service::kStateConnected,
Paul Stewartbfb82552012-10-24 16:48:48 -07003421 Service::kStatePortal,
3422 Service::kStateOnline
3423 };
3424 for (size_t i = 0; i < arraysize(watched_states); ++i) {
3425 EXPECT_CALL(*mock_service, state())
3426 .WillRepeatedly(Return(watched_states[i]));
3427 EXPECT_FALSE(EnumerateAvailableServices().empty());
3428 EXPECT_FALSE(EnumerateWatchedServices().empty());
3429 }
3430
3431 manager()->DeregisterService(mock_service);
3432}
3433
Paul Stewart39db5ca2013-03-18 14:15:17 -07003434TEST_F(ManagerTest, ConnectToBestServices) {
3435 scoped_refptr<MockService> wifi_service0(
3436 new NiceMock<MockService>(control_interface(),
3437 dispatcher(),
3438 metrics(),
3439 manager()));
3440 EXPECT_CALL(*wifi_service0.get(), state())
3441 .WillRepeatedly(Return(Service::kStateIdle));
3442 EXPECT_CALL(*wifi_service0.get(), IsConnected())
3443 .WillRepeatedly(Return(false));
mukesh agrawalcbfb34e2013-04-17 19:33:25 -07003444 wifi_service0->SetConnectable(true);
3445 wifi_service0->SetAutoConnect(true);
Paul Stewart39db5ca2013-03-18 14:15:17 -07003446 wifi_service0->SetSecurity(Service::kCryptoAes, true, true);
3447 EXPECT_CALL(*wifi_service0.get(), technology())
3448 .WillRepeatedly(Return(Technology::kWifi));
Paul Stewartf7d7d3f2013-04-24 14:47:44 -07003449 EXPECT_CALL(*wifi_service0.get(), IsVisible())
3450 .WillRepeatedly(Return(false));
Paul Stewart39db5ca2013-03-18 14:15:17 -07003451
3452 scoped_refptr<MockService> wifi_service1(
3453 new NiceMock<MockService>(control_interface(),
3454 dispatcher(),
3455 metrics(),
3456 manager()));
3457 EXPECT_CALL(*wifi_service1.get(), state())
3458 .WillRepeatedly(Return(Service::kStateIdle));
Paul Stewartf7d7d3f2013-04-24 14:47:44 -07003459 EXPECT_CALL(*wifi_service1.get(), IsVisible())
3460 .WillRepeatedly(Return(true));
Paul Stewart39db5ca2013-03-18 14:15:17 -07003461 EXPECT_CALL(*wifi_service1.get(), IsConnected())
3462 .WillRepeatedly(Return(false));
mukesh agrawalcbfb34e2013-04-17 19:33:25 -07003463 wifi_service1->SetAutoConnect(true);
3464 wifi_service1->SetConnectable(true);
Paul Stewart39db5ca2013-03-18 14:15:17 -07003465 wifi_service1->SetSecurity(Service::kCryptoRc4, true, true);
3466 EXPECT_CALL(*wifi_service1.get(), technology())
3467 .WillRepeatedly(Return(Technology::kWifi));
3468
3469 scoped_refptr<MockService> wifi_service2(
3470 new NiceMock<MockService>(control_interface(),
3471 dispatcher(),
3472 metrics(),
3473 manager()));
3474 EXPECT_CALL(*wifi_service2.get(), state())
3475 .WillRepeatedly(Return(Service::kStateConnected));
3476 EXPECT_CALL(*wifi_service2.get(), IsConnected())
3477 .WillRepeatedly(Return(true));
Paul Stewartf7d7d3f2013-04-24 14:47:44 -07003478 EXPECT_CALL(*wifi_service2.get(), IsVisible())
3479 .WillRepeatedly(Return(true));
mukesh agrawalcbfb34e2013-04-17 19:33:25 -07003480 wifi_service2->SetAutoConnect(true);
3481 wifi_service2->SetConnectable(true);
Paul Stewart39db5ca2013-03-18 14:15:17 -07003482 wifi_service2->SetSecurity(Service::kCryptoNone, false, false);
3483 EXPECT_CALL(*wifi_service2.get(), technology())
3484 .WillRepeatedly(Return(Technology::kWifi));
3485
3486 manager()->RegisterService(wifi_service0);
3487 manager()->RegisterService(wifi_service1);
3488 manager()->RegisterService(wifi_service2);
3489
3490 CompleteServiceSort();
3491 EXPECT_TRUE(ServiceOrderIs(wifi_service2, wifi_service0));
3492
3493 scoped_refptr<MockService> cell_service(
3494 new NiceMock<MockService>(control_interface(),
3495 dispatcher(),
3496 metrics(),
3497 manager()));
3498
3499 EXPECT_CALL(*cell_service.get(), state())
3500 .WillRepeatedly(Return(Service::kStateConnected));
3501 EXPECT_CALL(*cell_service.get(), IsConnected())
3502 .WillRepeatedly(Return(true));
Paul Stewartf7d7d3f2013-04-24 14:47:44 -07003503 EXPECT_CALL(*cell_service.get(), IsVisible())
3504 .WillRepeatedly(Return(true));
mukesh agrawalcbfb34e2013-04-17 19:33:25 -07003505 wifi_service2->SetAutoConnect(true);
3506 cell_service->SetConnectable(true);
Paul Stewart39db5ca2013-03-18 14:15:17 -07003507 EXPECT_CALL(*cell_service.get(), technology())
3508 .WillRepeatedly(Return(Technology::kCellular));
3509 manager()->RegisterService(cell_service);
3510
3511 scoped_refptr<MockService> vpn_service(
3512 new NiceMock<MockService>(control_interface(),
3513 dispatcher(),
3514 metrics(),
3515 manager()));
3516
3517 EXPECT_CALL(*vpn_service.get(), state())
3518 .WillRepeatedly(Return(Service::kStateIdle));
3519 EXPECT_CALL(*vpn_service.get(), IsConnected())
3520 .WillRepeatedly(Return(false));
Paul Stewartf7d7d3f2013-04-24 14:47:44 -07003521 EXPECT_CALL(*vpn_service.get(), IsVisible())
3522 .WillRepeatedly(Return(true));
mukesh agrawalcbfb34e2013-04-17 19:33:25 -07003523 wifi_service2->SetAutoConnect(false);
3524 vpn_service->SetConnectable(true);
Paul Stewart39db5ca2013-03-18 14:15:17 -07003525 EXPECT_CALL(*vpn_service.get(), technology())
3526 .WillRepeatedly(Return(Technology::kVPN));
3527 manager()->RegisterService(vpn_service);
3528
3529 // The connected services should be at the top.
3530 EXPECT_TRUE(ServiceOrderIs(wifi_service2, cell_service));
3531
Paul Stewartf7d7d3f2013-04-24 14:47:44 -07003532 EXPECT_CALL(*wifi_service0.get(), Connect(_, _)).Times(0); // Not visible.
3533 EXPECT_CALL(*wifi_service1.get(), Connect(_, _));
mukesh agrawaldc7b8442012-09-27 13:48:14 -07003534 EXPECT_CALL(*wifi_service2.get(), Connect(_, _)).Times(0); // Lower prio.
3535 EXPECT_CALL(*cell_service.get(), Connect(_, _)).Times(0); // Is connected.
3536 EXPECT_CALL(*vpn_service.get(), Connect(_, _)).Times(0); // Not autoconnect.
Paul Stewart39db5ca2013-03-18 14:15:17 -07003537
3538 manager()->ConnectToBestServices(NULL);
3539 dispatcher()->DispatchPendingEvents();
3540
3541 // After this operation, since the Connect calls above are mocked and
3542 // no actual state changes have occurred, we should expect that the
3543 // service sorting order will not have changed.
3544 EXPECT_TRUE(ServiceOrderIs(wifi_service2, cell_service));
3545}
3546
Christopher Wiley83889862013-05-02 15:55:09 -07003547TEST_F(ManagerTest, VerifyWhenNotConnected) {
3548 const string kFakeCertificate("fake cert");
3549 const string kFakePublicKey("fake public key");
3550 const string kFakeNonce("fake public key");
3551 const string kFakeSignedData("fake signed data");
3552 const string kFakeUdn("fake udn");
3553 const vector<uint8_t> kSSID(10, 87);
3554 const string kConfiguredSSID("AConfiguredDestination");
3555 const vector<uint8_t> kConfiguredSSIDVector(kConfiguredSSID.begin(),
3556 kConfiguredSSID.end());
3557 const string kConfiguredBSSID("aa:bb:aa:bb:aa:bb");
3558 scoped_refptr<MockWiFiService> mock_destination(
3559 new NiceMock<MockWiFiService>(control_interface(), dispatcher(),
3560 metrics(), manager(), wifi_provider_,
3561 kSSID, "", "none", false));
3562 // Register this service, but don't mark it as connected.
3563 manager()->RegisterService(mock_destination);
3564 // Verify that if we're not connected to anything, verification fails.
3565 {
3566 LOG(INFO) << "Can't verify if not connected.";
3567 EXPECT_CALL(*crypto_util_proxy_,
3568 VerifyDestination(_, _, _, _, _, _, _, _, _)).Times(0);
3569 Error error(Error::kOperationInitiated);
3570 manager()->VerifyDestination(kFakeCertificate, kFakePublicKey, kFakeNonce,
3571 kFakeSignedData, kFakeUdn, "", "",
3572 ResultBoolCallback(), &error);
3573 EXPECT_TRUE(error.IsFailure());
3574 Mock::VerifyAndClearExpectations(crypto_util_proxy_);
3575 }
3576 {
3577 // However, if the destination is already configured, we might be
3578 // connected to it via something other than WiFi, and we shouldn't
3579 // enforce the WiFi check.
3580 EXPECT_CALL(*crypto_util_proxy_,
3581 VerifyDestination(kFakeCertificate, kFakePublicKey, kFakeNonce,
3582 kFakeSignedData, kFakeUdn,
3583 kConfiguredSSIDVector, kConfiguredBSSID,
3584 _, _)).Times(1).WillOnce(Return(true));
3585 Error error(Error::kOperationInitiated);
3586 manager()->VerifyDestination(kFakeCertificate, kFakePublicKey, kFakeNonce,
3587 kFakeSignedData, kFakeUdn, kConfiguredSSID,
3588 kConfiguredBSSID, ResultBoolCallback(),
3589 &error);
3590 EXPECT_FALSE(error.IsFailure());
3591 Mock::VerifyAndClearExpectations(crypto_util_proxy_);
3592 }
3593}
3594
Christopher Wiley1057cd72013-02-28 15:21:29 -08003595TEST_F(ManagerTest, VerifyDestination) {
3596 const string kFakeCertificate("fake cert");
3597 const string kFakePublicKey("fake public key");
3598 const string kFakeNonce("fake public key");
3599 const string kFakeSignedData("fake signed data");
3600 const string kFakeUdn("fake udn");
3601 const char kSSIDStr[] = "fake ssid";
3602 const vector<uint8_t> kSSID(kSSIDStr, kSSIDStr + arraysize(kSSIDStr));
Christopher Wileycdde79f2013-05-01 14:26:56 -07003603 const string kConfiguredSSID("AConfiguredDestination");
3604 const vector<uint8_t> kConfiguredSSIDVector(kConfiguredSSID.begin(),
3605 kConfiguredSSID.end());
3606 const string kConfiguredBSSID("aa:bb:aa:bb:aa:bb");
Christopher Wiley1057cd72013-02-28 15:21:29 -08003607 const string kFakeData("muffin man");
3608 scoped_refptr<MockWiFiService> mock_destination(
3609 new NiceMock<MockWiFiService>(control_interface(),
3610 dispatcher(),
3611 metrics(),
3612 manager(),
3613 wifi_provider_,
3614 kSSID,
3615 "",
3616 "none",
3617 false));
3618 manager()->RegisterService(mock_destination);
Christopher Wiley1057cd72013-02-28 15:21:29 -08003619 // Making the service look online will let service lookup in
3620 // VerifyDestinatoin succeed.
3621 EXPECT_CALL(*mock_destination.get(), IsConnected())
3622 .WillRepeatedly(Return(true));
Christopher Wiley83889862013-05-02 15:55:09 -07003623 StrictMock<DestinationVerificationTest> dv_test;
Christopher Wiley1057cd72013-02-28 15:21:29 -08003624
3625 // Lead off by verifying that the basic VerifyDestination flow works.
3626 {
Christopher Wileycdde79f2013-05-01 14:26:56 -07003627 LOG(INFO) << "Basic VerifyDestination flow.";
Christopher Wiley1057cd72013-02-28 15:21:29 -08003628 ResultBoolCallback passed_down_callback;
3629 EXPECT_CALL(*crypto_util_proxy_, VerifyDestination(kFakeCertificate,
3630 kFakePublicKey,
3631 kFakeNonce,
3632 kFakeSignedData,
3633 kFakeUdn,
3634 kSSID,
3635 _,
3636 _,
3637 _))
3638 .Times(1)
3639 .WillOnce(DoAll(SaveArg<7>(&passed_down_callback), Return(true)));
3640 // Ask the manager to verify the current destination. This should look
3641 // up our previously registered service, and pass some metadata about
3642 // that service down to the CryptoUtilProxy to verify.
3643 Error error(Error::kOperationInitiated);
3644 ResultBoolCallback cb = Bind(
3645 &DestinationVerificationTest::ResultBoolCallbackStub,
3646 dv_test.AsWeakPtr());
3647 manager()->VerifyDestination(kFakeCertificate,
3648 kFakePublicKey,
3649 kFakeNonce,
3650 kFakeSignedData,
3651 kFakeUdn,
Christopher Wileycdde79f2013-05-01 14:26:56 -07003652 // Ask to be verified against that service.
3653 "", "",
3654 cb,
3655 &error);
3656 // We assert here, because if the operation is not ongoing, it is
3657 // inconsistent with shim behavior to call the callback anyway.
3658 ASSERT_TRUE(error.IsOngoing());
3659 Mock::VerifyAndClearExpectations(crypto_util_proxy_);
3660 EXPECT_CALL(dv_test, ResultBoolCallbackStub(_, true)).Times(1);
3661 // Call the callback passed into the CryptoUtilProxy, which
3662 // should find its way into the callback passed into the manager.
3663 // In real code, that callback passed into the manager is from the
3664 // DBus adaptor.
3665 Error e;
3666 passed_down_callback.Run(e, true);
3667 Mock::VerifyAndClearExpectations(&dv_test);
3668 }
3669
Christopher Wiley1057cd72013-02-28 15:21:29 -08003670 // Now for a slightly more complex variant. When we encrypt data,
3671 // we do the same verification step but monkey with the callback to
3672 // link ourselves to an encrypt step afterward.
3673 {
Christopher Wileycdde79f2013-05-01 14:26:56 -07003674 LOG(INFO) << "Basic VerifyAndEncryptData";
Christopher Wiley1057cd72013-02-28 15:21:29 -08003675 ResultBoolCallback passed_down_callback;
3676 EXPECT_CALL(*crypto_util_proxy_, VerifyDestination(kFakeCertificate,
3677 kFakePublicKey,
3678 kFakeNonce,
3679 kFakeSignedData,
3680 kFakeUdn,
3681 kSSID,
3682 _,
3683 _,
3684 _))
3685 .WillOnce(DoAll(SaveArg<7>(&passed_down_callback), Return(true)));
3686
3687 Error error(Error::kOperationInitiated);
3688 ResultStringCallback cb = Bind(
3689 &DestinationVerificationTest::ResultStringCallbackStub,
3690 dv_test.AsWeakPtr());
3691 manager()->VerifyAndEncryptData(kFakeCertificate,
3692 kFakePublicKey,
3693 kFakeNonce,
3694 kFakeSignedData,
3695 kFakeUdn,
Christopher Wileycdde79f2013-05-01 14:26:56 -07003696 "", "",
Christopher Wiley1057cd72013-02-28 15:21:29 -08003697 kFakeData,
3698 cb,
3699 &error);
3700 ASSERT_TRUE(error.IsOngoing());
3701 Mock::VerifyAndClearExpectations(crypto_util_proxy_);
3702 // Now, if we call that passed down callback, we should see encrypt being
3703 // called.
3704 ResultStringCallback second_passed_down_callback;
3705 EXPECT_CALL(*crypto_util_proxy_, EncryptData(kFakePublicKey,
3706 kFakeData,
3707 _,
3708 _))
3709 .Times(1)
3710 .WillOnce(DoAll(SaveArg<2>(&second_passed_down_callback),
3711 Return(true)));
3712 Error e;
3713 passed_down_callback.Run(e, true);
3714 Mock::VerifyAndClearExpectations(crypto_util_proxy_);
3715 EXPECT_CALL(dv_test, ResultStringCallbackStub(_, _)).Times(1);
3716 // And if we call the second passed down callback, we should see the
3717 // original function we passed down to VerifyDestination getting called.
3718 e.Reset();
3719 second_passed_down_callback.Run(e, "");
3720 Mock::VerifyAndClearExpectations(&dv_test);
3721 }
3722
3723 // If verification fails on the way to trying to encrypt, we should ditch
3724 // without calling encrypt at all.
3725 {
Christopher Wileycdde79f2013-05-01 14:26:56 -07003726 LOG(INFO) << "Failed VerifyAndEncryptData";
Christopher Wiley1057cd72013-02-28 15:21:29 -08003727 ResultBoolCallback passed_down_callback;
3728 EXPECT_CALL(*crypto_util_proxy_, VerifyDestination(kFakeCertificate,
3729 kFakePublicKey,
3730 kFakeNonce,
3731 kFakeSignedData,
3732 kFakeUdn,
3733 kSSID,
3734 _,
3735 _,
3736 _))
3737 .WillOnce(DoAll(SaveArg<7>(&passed_down_callback), Return(true)));
3738
3739 Error error(Error::kOperationInitiated);
3740 ResultStringCallback cb = Bind(
3741 &DestinationVerificationTest::ResultStringCallbackStub,
3742 dv_test.AsWeakPtr());
3743 manager()->VerifyAndEncryptData(kFakeCertificate,
3744 kFakePublicKey,
3745 kFakeNonce,
3746 kFakeSignedData,
3747 kFakeUdn,
Christopher Wileycdde79f2013-05-01 14:26:56 -07003748 "", "",
Christopher Wiley1057cd72013-02-28 15:21:29 -08003749 kFakeData,
3750 cb,
3751 &error);
3752 ASSERT_TRUE(error.IsOngoing());
3753 Mock::VerifyAndClearExpectations(crypto_util_proxy_);
3754 Error e(Error::kOperationFailed);
3755 EXPECT_CALL(*crypto_util_proxy_, EncryptData(_, _, _, _)).Times(0);
3756 // Although we're ditching, this callback is what cleans up the pending
3757 // DBus call.
3758 EXPECT_CALL(dv_test, ResultStringCallbackStub(_, string(""))).Times(1);
3759 passed_down_callback.Run(e, false);
3760 Mock::VerifyAndClearExpectations(&dv_test);
3761 }
3762}
3763
Paul Stewartd2e1c362013-03-03 19:06:07 -08003764TEST_F(ManagerTest, IsProfileBefore) {
3765 scoped_refptr<MockProfile> profile0(
3766 new NiceMock<MockProfile>(
3767 control_interface(), metrics(), manager(), ""));
3768 scoped_refptr<MockProfile> profile1(
3769 new NiceMock<MockProfile>(
3770 control_interface(), metrics(), manager(), ""));
3771
3772 AdoptProfile(manager(), profile0);
3773 AdoptProfile(manager(), profile1); // profile1 is after profile0.
3774 EXPECT_TRUE(manager()->IsProfileBefore(profile0, profile1));
3775 EXPECT_FALSE(manager()->IsProfileBefore(profile1, profile0));
3776
3777 // A few abnormal cases, but it's good to track their behavior.
3778 scoped_refptr<MockProfile> profile2(
3779 new NiceMock<MockProfile>(
3780 control_interface(), metrics(), manager(), ""));
3781 EXPECT_TRUE(manager()->IsProfileBefore(profile0, profile2));
3782 EXPECT_TRUE(manager()->IsProfileBefore(profile1, profile2));
3783 EXPECT_FALSE(manager()->IsProfileBefore(profile2, profile0));
3784 EXPECT_FALSE(manager()->IsProfileBefore(profile2, profile1));
3785}
3786
Paul Stewart967eaeb2013-04-25 19:53:07 -07003787TEST_F(ManagerTest, GetLoadableProfileEntriesForService) {
3788 MockStore storage0;
3789 MockStore storage1;
3790 MockStore storage2;
3791
3792 scoped_refptr<MockProfile> profile0(
3793 new NiceMock<MockProfile>(
3794 control_interface(), metrics(), manager(), ""));
3795 scoped_refptr<MockProfile> profile1(
3796 new NiceMock<MockProfile>(
3797 control_interface(), metrics(), manager(), ""));
3798 scoped_refptr<MockProfile> profile2(
3799 new NiceMock<MockProfile>(
3800 control_interface(), metrics(), manager(), ""));
3801
3802 AdoptProfile(manager(), profile0);
3803 AdoptProfile(manager(), profile1);
3804 AdoptProfile(manager(), profile2);
3805
3806 scoped_refptr<MockService> service(
3807 new NiceMock<MockService>(control_interface(),
3808 dispatcher(),
3809 metrics(),
3810 manager()));
3811
3812 EXPECT_CALL(*profile0, GetConstStorage()).WillOnce(Return(&storage0));
3813 EXPECT_CALL(*profile1, GetConstStorage()).WillOnce(Return(&storage1));
3814 EXPECT_CALL(*profile2, GetConstStorage()).WillOnce(Return(&storage2));
3815
3816 const string kEntry0("aluminum_crutch");
3817 const string kEntry2("rehashed_faces");
3818
3819 EXPECT_CALL(*service, GetLoadableStorageIdentifier(Ref(storage0)))
3820 .WillOnce(Return(kEntry0));
3821 EXPECT_CALL(*service, GetLoadableStorageIdentifier(Ref(storage1)))
3822 .WillOnce(Return(""));
3823 EXPECT_CALL(*service, GetLoadableStorageIdentifier(Ref(storage2)))
3824 .WillOnce(Return(kEntry2));
3825
3826 const string kProfileRpc0("service_station");
3827 const string kProfileRpc2("crystal_tiaras");
3828
3829 EXPECT_CALL(*profile0, GetRpcIdentifier()).WillOnce(Return(kProfileRpc0));
3830 EXPECT_CALL(*profile1, GetRpcIdentifier()).Times(0);
3831 EXPECT_CALL(*profile2, GetRpcIdentifier()).WillOnce(Return(kProfileRpc2));
3832
3833 map<string, string> entries =
3834 manager()->GetLoadableProfileEntriesForService(service);
3835 EXPECT_EQ(2, entries.size());
3836 EXPECT_TRUE(ContainsKey(entries, kProfileRpc0));
3837 EXPECT_TRUE(ContainsKey(entries, kProfileRpc2));
3838 EXPECT_EQ(kEntry0, entries[kProfileRpc0]);
3839 EXPECT_EQ(kEntry2, entries[kProfileRpc2]);
3840}
3841
mukesh agrawal00752532013-05-03 15:46:55 -07003842TEST_F(ManagerTest, InitializeProfilesInformsProviders) {
mukesh agrawald142fd62013-05-01 16:50:57 -07003843 // We need a real glib here, so that profiles are persisted.
3844 GLib glib;
3845 ScopedTempDir temp_dir;
3846 ASSERT_TRUE(temp_dir.CreateUniqueTempDir());
3847 Manager manager(control_interface(),
3848 dispatcher(),
3849 metrics(),
3850 &glib,
3851 run_path(),
3852 storage_path(),
3853 temp_dir.path().value());
3854 // Can't use |wifi_provider_|, because it's owned by the Manager
3855 // object in the fixture.
3856 MockWiFiProvider *wifi_provider = new NiceMock<MockWiFiProvider>();
3857 manager.wifi_provider_.reset(wifi_provider); // pass ownership
3858 // Give manager a valid place to write the user profile list.
3859 manager.user_profile_list_path_ = temp_dir.path().Append("user_profile_list");
3860
3861 // With no user profiles, the WiFiProvider should be called once
3862 // (for the default profile).
3863 EXPECT_CALL(*wifi_provider, CreateServicesFromProfile(_));
3864 manager.InitializeProfiles();
3865 Mock::VerifyAndClearExpectations(wifi_provider);
3866
3867 // With |n| user profiles, the WiFiProvider should be called |n+1|
3868 // times. First, create 2 user profiles...
3869 const char kProfile0[] = "~user/profile0";
3870 const char kProfile1[] = "~user/profile1";
3871 string profile_rpc_path;
3872 Error error;
3873 manager.CreateProfile(kProfile0, &profile_rpc_path, &error);
3874 manager.PushProfile(kProfile0, &profile_rpc_path, &error);
3875 manager.CreateProfile(kProfile1, &profile_rpc_path, &error);
3876 manager.PushProfile(kProfile1, &profile_rpc_path, &error);
3877
3878 // ... then reset manager state ...
3879 manager.profiles_.clear();
3880
3881 // ...then check that the WiFiProvider is notified about all three
3882 // profiles (one default, two user).
3883 EXPECT_CALL(*wifi_provider, CreateServicesFromProfile(_)).Times(3);
3884 manager.InitializeProfiles();
3885 Mock::VerifyAndClearExpectations(wifi_provider);
3886}
3887
mukesh agrawal00752532013-05-03 15:46:55 -07003888TEST_F(ManagerTest, InitializeProfilesHandlesDefaults) {
3889 // We need a real glib here, so that profiles are persisted.
3890 GLib glib;
3891 ScopedTempDir temp_dir;
3892 scoped_ptr<Manager> manager;
3893 ASSERT_TRUE(temp_dir.CreateUniqueTempDir());
3894
3895 // Instantiate a Manager with empty persistent storage. Check that
3896 // defaults are set.
3897 //
3898 // Note that we use the same directory for default and user profiles.
3899 // This doesn't affect the test results, because we don't push a
3900 // user profile.
3901 manager.reset(new Manager(control_interface(),
3902 dispatcher(),
3903 metrics(),
3904 &glib,
3905 run_path(),
3906 temp_dir.path().value(),
3907 temp_dir.path().value()));
3908 manager->InitializeProfiles();
3909 EXPECT_EQ(PortalDetector::kDefaultCheckPortalList,
3910 manager->props_.check_portal_list);
3911 EXPECT_EQ(Resolver::kDefaultIgnoredSearchList,
3912 manager->props_.ignored_dns_search_paths);
3913 EXPECT_EQ(LinkMonitor::kDefaultLinkMonitorTechnologies,
3914 manager->props_.link_monitor_technologies);
3915 EXPECT_EQ(PortalDetector::kDefaultURL,
3916 manager->props_.portal_url);
3917 EXPECT_EQ(PortalDetector::kDefaultCheckIntervalSeconds,
3918 manager->props_.portal_check_interval_seconds);
3919
3920 // Change one of the settings.
3921 static const string kCustomCheckPortalList = "fiber0";
3922 Error error;
3923 manager->SetCheckPortalList(kCustomCheckPortalList, &error);
3924 manager->profiles_[0]->Save();
3925
3926 // Instantiate a new manager. It should have our settings for
3927 // check_portal_list, rather than the default.
3928 manager.reset(new Manager(control_interface(),
3929 dispatcher(),
3930 metrics(),
3931 &glib,
3932 run_path(),
3933 temp_dir.path().value(),
3934 temp_dir.path().value()));
3935 manager->InitializeProfiles();
3936 EXPECT_EQ(kCustomCheckPortalList, manager->props_.check_portal_list);
3937
3938 // If we clear the persistent storage, we again get the default value.
3939 ASSERT_TRUE(temp_dir.Delete());
3940 ASSERT_TRUE(temp_dir.CreateUniqueTempDir());
3941 manager.reset(new Manager(control_interface(),
3942 dispatcher(),
3943 metrics(),
3944 &glib,
3945 run_path(),
3946 temp_dir.path().value(),
3947 temp_dir.path().value()));
3948 manager->InitializeProfiles();
3949 EXPECT_EQ(PortalDetector::kDefaultCheckPortalList,
3950 manager->props_.check_portal_list);
3951}
3952
mukesh agrawalbebf1b82013-04-23 15:06:33 -07003953// Custom property setters should return false, and make no changes, if
3954// the new value is the same as the old value.
3955TEST_F(ManagerTest, CustomSetterNoopChange) {
3956 // SetCheckPortalList
3957 {
3958 static const string kCheckPortalList = "weird-device,weirder-device";
3959 Error error;
3960 // Set to known value.
3961 EXPECT_TRUE(SetCheckPortalList(kCheckPortalList, &error));
3962 EXPECT_TRUE(error.IsSuccess());
3963 // Set to same value.
3964 EXPECT_FALSE(SetCheckPortalList(kCheckPortalList, &error));
3965 EXPECT_TRUE(error.IsSuccess());
3966 }
3967
3968 // SetIgnoredDNSSearchPaths
3969 {
3970 NiceMock<MockResolver> resolver;
3971 static const string kIgnoredPaths = "example.com,example.org";
3972 Error error;
3973 SetResolver(&resolver);
3974 // Set to known value.
3975 EXPECT_CALL(resolver, set_ignored_search_list(_));
3976 EXPECT_TRUE(SetIgnoredDNSSearchPaths(kIgnoredPaths, &error));
3977 EXPECT_TRUE(error.IsSuccess());
3978 Mock::VerifyAndClearExpectations(&resolver);
3979 // Set to same value.
3980 EXPECT_CALL(resolver, set_ignored_search_list(_)).Times(0);
3981 EXPECT_FALSE(SetIgnoredDNSSearchPaths(kIgnoredPaths, &error));
3982 EXPECT_TRUE(error.IsSuccess());
3983 Mock::VerifyAndClearExpectations(&resolver);
3984 }
3985}
3986
Chris Masone9be4a9d2011-05-16 15:44:09 -07003987} // namespace shill