blob: 0d7a1b34e8bf83290a58808a6987b925c084710c [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>
Chris Masone9be4a9d2011-05-16 15:44:09 -070013#include <base/logging.h>
Eric Shienbrood3e20a232012-02-16 11:35:56 -050014#include <base/scoped_temp_dir.h>
15#include <base/stl_util.h>
Paul Stewart5dc40aa2011-10-28 19:43:43 -070016#include <base/stringprintf.h>
Chris Masone3bd3c8c2011-06-13 08:20:26 -070017#include <chromeos/dbus/service_constants.h>
Chris Masone7156c922011-08-23 20:36:21 -070018#include <gmock/gmock.h>
Chris Masone2ae797d2011-08-23 20:41:00 -070019#include <gtest/gtest.h>
Chris Masone9be4a9d2011-05-16 15:44:09 -070020
mukesh agrawal32399322011-09-01 10:53:43 -070021#include "shill/adaptor_interfaces.h"
Chris Masone6515aab2011-10-12 16:19:09 -070022#include "shill/ephemeral_profile.h"
mukesh agrawal32399322011-09-01 10:53:43 -070023#include "shill/error.h"
Chris Masone6515aab2011-10-12 16:19:09 -070024#include "shill/glib.h"
25#include "shill/key_file_store.h"
mukesh agrawal7a4e4002011-09-06 11:26:05 -070026#include "shill/key_value_store.h"
mukesh agrawal32399322011-09-01 10:53:43 -070027#include "shill/mock_adaptors.h"
Paul Stewartc1dec4d2011-12-08 15:25:28 -080028#include "shill/mock_connection.h"
Chris Masoned7732e42011-05-20 11:08:56 -070029#include "shill/mock_control.h"
Chris Masone9be4a9d2011-05-16 15:44:09 -070030#include "shill/mock_device.h"
Paul Stewartc1dec4d2011-12-08 15:25:28 -080031#include "shill/mock_device_info.h"
Chris Masone7aa5f902011-07-11 11:13:35 -070032#include "shill/mock_glib.h"
Thieu Lea20cbc22012-01-09 22:01:43 +000033#include "shill/mock_metrics.h"
Chris Masone7aa5f902011-07-11 11:13:35 -070034#include "shill/mock_profile.h"
Chris Masone9be4a9d2011-05-16 15:44:09 -070035#include "shill/mock_service.h"
Chris Masoneb9c00592011-10-06 13:10:39 -070036#include "shill/mock_store.h"
mukesh agrawal7a4e4002011-09-06 11:26:05 -070037#include "shill/mock_wifi.h"
Paul Stewart7f61e522012-03-22 11:13:45 -070038#include "shill/mock_wifi_service.h"
Chris Masone3bd3c8c2011-06-13 08:20:26 -070039#include "shill/property_store_unittest.h"
Chris Masone6515aab2011-10-12 16:19:09 -070040#include "shill/service_under_test.h"
mukesh agrawal7a4e4002011-09-06 11:26:05 -070041#include "shill/wifi_service.h"
Darin Petkovc63dcf02012-05-24 11:51:43 +020042#include "shill/wimax_service.h"
Chris Masone3bd3c8c2011-06-13 08:20:26 -070043
44using std::map;
Chris Masone6791a432011-07-12 13:23:19 -070045using std::set;
Chris Masone3bd3c8c2011-06-13 08:20:26 -070046using std::string;
47using std::vector;
48
Chris Masone9be4a9d2011-05-16 15:44:09 -070049namespace shill {
Chris Masone9be4a9d2011-05-16 15:44:09 -070050using ::testing::_;
Chris Masone6515aab2011-10-12 16:19:09 -070051using ::testing::AnyNumber;
Gaurav Shah435de2c2011-11-17 19:01:07 -080052using ::testing::ContainerEq;
Paul Stewart7f5ad572012-06-04 15:18:54 -070053using ::testing::DoAll;
Paul Stewarte2bad7c2012-03-14 08:55:33 -070054using ::testing::InSequence;
Paul Stewart22aa71b2011-09-16 12:15:11 -070055using ::testing::Ne;
Chris Masone9be4a9d2011-05-16 15:44:09 -070056using ::testing::NiceMock;
57using ::testing::Return;
Paul Stewartce4ec192012-03-14 12:53:46 -070058using ::testing::ReturnRef;
Paul Stewart7f5ad572012-06-04 15:18:54 -070059using ::testing::SaveArg;
Gaurav Shah435de2c2011-11-17 19:01:07 -080060using ::testing::StrEq;
Paul Stewart3d9bcf52011-12-12 15:02:22 -080061using ::testing::StrictMock;
Chris Masone9d779932011-08-25 16:33:41 -070062using ::testing::Test;
Chris Masone9be4a9d2011-05-16 15:44:09 -070063
Chris Masone3bd3c8c2011-06-13 08:20:26 -070064class ManagerTest : public PropertyStoreTest {
Chris Masone9be4a9d2011-05-16 15:44:09 -070065 public:
Chris Masone3c3f6a12011-07-01 10:01:41 -070066 ManagerTest()
Paul Stewart22aa71b2011-09-16 12:15:11 -070067 : mock_wifi_(new NiceMock<MockWiFi>(control_interface(),
mukesh agrawal7a4e4002011-09-06 11:26:05 -070068 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -080069 metrics(),
mukesh agrawal7a4e4002011-09-06 11:26:05 -070070 manager(),
71 "wifi0",
72 "addr4",
Paul Stewartc1dec4d2011-12-08 15:25:28 -080073 4)),
74 device_info_(new NiceMock<MockDeviceInfo>(
75 control_interface(),
76 reinterpret_cast<EventDispatcher*>(NULL),
Thieu Le3426c8f2012-01-11 17:35:11 -080077 reinterpret_cast<Metrics*>(NULL),
Paul Stewartc1dec4d2011-12-08 15:25:28 -080078 reinterpret_cast<Manager*>(NULL))),
79 manager_adaptor_(new NiceMock<ManagerMockAdaptor>()) {
Paul Stewart22aa71b2011-09-16 12:15:11 -070080 mock_devices_.push_back(new NiceMock<MockDevice>(control_interface(),
81 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -080082 metrics(),
Paul Stewart22aa71b2011-09-16 12:15:11 -070083 manager(),
84 "null0",
85 "addr0",
86 0));
87 mock_devices_.push_back(new NiceMock<MockDevice>(control_interface(),
88 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -080089 metrics(),
Paul Stewart22aa71b2011-09-16 12:15:11 -070090 manager(),
91 "null1",
92 "addr1",
93 1));
94 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 "null2",
99 "addr2",
100 2));
Gaurav Shah435de2c2011-11-17 19:01:07 -0800101 mock_devices_.push_back(new NiceMock<MockDevice>(control_interface(),
102 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800103 metrics(),
Gaurav Shah435de2c2011-11-17 19:01:07 -0800104 manager(),
105 "null3",
106 "addr3",
107 3));
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700108 manager()->connect_profiles_to_rpc_ = false;
Paul Stewartc1dec4d2011-12-08 15:25:28 -0800109
110 // Replace the manager's adaptor with a quieter one, and one
111 // we can do EXPECT*() against. Passes ownership.
112 manager()->adaptor_.reset(manager_adaptor_);
Chris Masone3c3f6a12011-07-01 10:01:41 -0700113 }
Chris Masone3bd3c8c2011-06-13 08:20:26 -0700114 virtual ~ManagerTest() {}
Chris Masone9be4a9d2011-05-16 15:44:09 -0700115
Paul Stewartfdd16072011-09-16 12:41:35 -0700116 bool IsDeviceRegistered(const DeviceRefPtr &device,
117 Technology::Identifier tech) {
Chris Masonec1e50412011-06-07 13:04:53 -0700118 vector<DeviceRefPtr> devices;
Chris Masone9d779932011-08-25 16:33:41 -0700119 manager()->FilterByTechnology(tech, &devices);
Chris Masone2b105542011-06-22 10:58:09 -0700120 return (devices.size() == 1 && devices[0].get() == device.get());
Chris Masone9be4a9d2011-05-16 15:44:09 -0700121 }
Paul Stewart22aa71b2011-09-16 12:15:11 -0700122 bool ServiceOrderIs(ServiceRefPtr svc1, ServiceRefPtr svc2);
Chris Masone9be4a9d2011-05-16 15:44:09 -0700123
Paul Stewarta849a3d2011-11-03 05:54:09 -0700124 void AdoptProfile(Manager *manager, ProfileRefPtr profile) {
125 manager->profiles_.push_back(profile);
126 }
127
Paul Stewart75225512012-01-26 22:51:33 -0800128 ProfileRefPtr GetEphemeralProfile(Manager *manager) {
129 return manager->ephemeral_profile_;
130 }
131
Chris Masone6515aab2011-10-12 16:19:09 -0700132 Profile *CreateProfileForManager(Manager *manager, GLib *glib) {
133 Profile::Identifier id("rather", "irrelevant");
134 scoped_ptr<Profile> profile(new Profile(control_interface(),
135 manager,
136 id,
137 "",
138 false));
139 FilePath final_path(storage_path());
140 final_path = final_path.Append("test.profile");
141 scoped_ptr<KeyFileStore> storage(new KeyFileStore(glib));
142 storage->set_path(final_path);
143 if (!storage->Open())
144 return NULL;
145 profile->set_storage(storage.release()); // Passes ownership.
146 return profile.release();
147 }
148
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700149 bool CreateBackingStoreForService(ScopedTempDir *temp_dir,
150 const string &profile_identifier,
151 const string &service_name) {
152 GLib glib;
153 KeyFileStore store(&glib);
154 store.set_path(temp_dir->path().Append(profile_identifier + ".profile"));
155 return store.Open() &&
156 store.SetString(service_name, "rather", "irrelevant") &&
157 store.Close();
158 }
159
160 Error::Type TestCreateProfile(Manager *manager, const string &name) {
161 Error error;
Paul Stewart19c871d2011-12-15 16:10:13 -0800162 string path;
163 manager->CreateProfile(name, &path, &error);
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700164 return error.type();
165 }
166
167 Error::Type TestPopAnyProfile(Manager *manager) {
168 Error error;
169 manager->PopAnyProfile(&error);
170 return error.type();
171 }
172
173 Error::Type TestPopProfile(Manager *manager, const string &name) {
174 Error error;
175 manager->PopProfile(name, &error);
176 return error.type();
177 }
178
179 Error::Type TestPushProfile(Manager *manager, const string &name) {
180 Error error;
Paul Stewart19c871d2011-12-15 16:10:13 -0800181 string path;
182 manager->PushProfile(name, &path, &error);
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700183 return error.type();
184 }
mukesh agrawal8a3188d2011-12-01 20:56:44 +0000185
Paul Stewartcb3eb892012-06-07 14:24:46 -0700186 void AddMockProfileToManager(Manager *manager) {
187 scoped_refptr<MockProfile> profile(
188 new MockProfile(control_interface(), manager, ""));
Darin Petkove7c6ad32012-06-29 10:22:09 +0200189 EXPECT_CALL(*profile, GetRpcIdentifier()).WillRepeatedly(Return("/"));
190 EXPECT_CALL(*profile, UpdateDevice(_)).WillRepeatedly(Return(false));
Paul Stewartcb3eb892012-06-07 14:24:46 -0700191 AdoptProfile(manager, profile);
192 }
193
Paul Stewartdfa46052012-06-26 09:44:14 -0700194 void CompleteServiceSort() {
195 EXPECT_FALSE(manager()->sort_services_task_.IsCancelled());
196 dispatcher()->DispatchPendingEvents();
197 EXPECT_TRUE(manager()->sort_services_task_.IsCancelled());
198 }
199
Paul Stewartf1ce5d22011-05-19 13:10:20 -0700200 protected:
mukesh agrawal8a3188d2011-12-01 20:56:44 +0000201 typedef scoped_refptr<MockService> MockServiceRefPtr;
202
203 MockServiceRefPtr MakeAutoConnectableService() {
204 MockServiceRefPtr service = new NiceMock<MockService>(control_interface(),
205 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800206 metrics(),
mukesh agrawal8a3188d2011-12-01 20:56:44 +0000207 manager());
208 service->MakeFavorite();
209 service->set_connectable(true);
210 return service;
211 }
212
mukesh agrawal7a4e4002011-09-06 11:26:05 -0700213 scoped_refptr<MockWiFi> mock_wifi_;
Paul Stewart22aa71b2011-09-16 12:15:11 -0700214 vector<scoped_refptr<MockDevice> > mock_devices_;
Paul Stewartc1dec4d2011-12-08 15:25:28 -0800215 scoped_ptr<MockDeviceInfo> device_info_;
216
217 // This pointer is owned by the manager, and only tracked here for EXPECT*()
218 ManagerMockAdaptor *manager_adaptor_;
Chris Masone9be4a9d2011-05-16 15:44:09 -0700219};
220
Paul Stewart22aa71b2011-09-16 12:15:11 -0700221bool ManagerTest::ServiceOrderIs(ServiceRefPtr svc0, ServiceRefPtr svc1) {
Paul Stewartdfa46052012-06-26 09:44:14 -0700222 if (!manager()->sort_services_task_.IsCancelled()) {
223 manager()->SortServicesTask();
224 }
Paul Stewart22aa71b2011-09-16 12:15:11 -0700225 return (svc0.get() == manager()->services_[0].get() &&
226 svc1.get() == manager()->services_[1].get());
227}
228
Chris Masone3bd3c8c2011-06-13 08:20:26 -0700229TEST_F(ManagerTest, Contains) {
mukesh agrawalde29fa82011-09-16 16:16:36 -0700230 EXPECT_TRUE(manager()->store().Contains(flimflam::kStateProperty));
231 EXPECT_FALSE(manager()->store().Contains(""));
Chris Masone3bd3c8c2011-06-13 08:20:26 -0700232}
233
Chris Masone9be4a9d2011-05-16 15:44:09 -0700234TEST_F(ManagerTest, DeviceRegistration) {
Joshua Krollda798622012-06-05 12:30:48 -0700235 ON_CALL(*mock_devices_[0].get(), technology())
236 .WillByDefault(Return(Technology::kEthernet));
237 ON_CALL(*mock_devices_[1].get(), technology())
238 .WillByDefault(Return(Technology::kWifi));
239 ON_CALL(*mock_devices_[2].get(), technology())
240 .WillByDefault(Return(Technology::kCellular));
Chris Masone9be4a9d2011-05-16 15:44:09 -0700241
Paul Stewart22aa71b2011-09-16 12:15:11 -0700242 manager()->RegisterDevice(mock_devices_[0]);
243 manager()->RegisterDevice(mock_devices_[1]);
244 manager()->RegisterDevice(mock_devices_[2]);
Chris Masone9be4a9d2011-05-16 15:44:09 -0700245
Paul Stewart22aa71b2011-09-16 12:15:11 -0700246 EXPECT_TRUE(IsDeviceRegistered(mock_devices_[0], Technology::kEthernet));
247 EXPECT_TRUE(IsDeviceRegistered(mock_devices_[1], Technology::kWifi));
248 EXPECT_TRUE(IsDeviceRegistered(mock_devices_[2], Technology::kCellular));
Chris Masone9be4a9d2011-05-16 15:44:09 -0700249}
250
Paul Stewarta41e38d2011-11-11 07:47:29 -0800251TEST_F(ManagerTest, DeviceRegistrationAndStart) {
252 manager()->running_ = true;
Eric Shienbrood9a245532012-03-07 14:20:39 -0500253 mock_devices_[0]->enabled_persistent_ = true;
254 mock_devices_[1]->enabled_persistent_ = false;
255 EXPECT_CALL(*mock_devices_[0].get(), SetEnabled(true))
Paul Stewarta41e38d2011-11-11 07:47:29 -0800256 .Times(1);
Eric Shienbrood9a245532012-03-07 14:20:39 -0500257 EXPECT_CALL(*mock_devices_[1].get(), SetEnabled(_))
Paul Stewarta41e38d2011-11-11 07:47:29 -0800258 .Times(0);
259 manager()->RegisterDevice(mock_devices_[0]);
260 manager()->RegisterDevice(mock_devices_[1]);
261}
262
263TEST_F(ManagerTest, DeviceRegistrationWithProfile) {
264 MockProfile *profile = new MockProfile(control_interface(), manager(), "");
265 DeviceRefPtr device_ref(mock_devices_[0].get());
266 AdoptProfile(manager(), profile); // Passes ownership.
267 EXPECT_CALL(*profile, ConfigureDevice(device_ref));
Darin Petkove7c6ad32012-06-29 10:22:09 +0200268 EXPECT_CALL(*profile, UpdateDevice(device_ref));
Paul Stewarta41e38d2011-11-11 07:47:29 -0800269 manager()->RegisterDevice(mock_devices_[0]);
270}
271
Chris Masone9be4a9d2011-05-16 15:44:09 -0700272TEST_F(ManagerTest, DeviceDeregistration) {
Joshua Krollda798622012-06-05 12:30:48 -0700273 ON_CALL(*mock_devices_[0].get(), technology())
274 .WillByDefault(Return(Technology::kEthernet));
275 ON_CALL(*mock_devices_[1].get(), technology())
276 .WillByDefault(Return(Technology::kWifi));
Chris Masone9be4a9d2011-05-16 15:44:09 -0700277
Gaurav Shah435de2c2011-11-17 19:01:07 -0800278 manager()->RegisterDevice(mock_devices_[0]);
279 manager()->RegisterDevice(mock_devices_[1]);
Chris Masone9be4a9d2011-05-16 15:44:09 -0700280
Paul Stewart22aa71b2011-09-16 12:15:11 -0700281 ASSERT_TRUE(IsDeviceRegistered(mock_devices_[0], Technology::kEthernet));
282 ASSERT_TRUE(IsDeviceRegistered(mock_devices_[1], Technology::kWifi));
Chris Masone9be4a9d2011-05-16 15:44:09 -0700283
Eric Shienbrood9a245532012-03-07 14:20:39 -0500284 EXPECT_CALL(*mock_devices_[0].get(), SetEnabled(false));
Gaurav Shah435de2c2011-11-17 19:01:07 -0800285 manager()->DeregisterDevice(mock_devices_[0]);
Paul Stewart22aa71b2011-09-16 12:15:11 -0700286 EXPECT_FALSE(IsDeviceRegistered(mock_devices_[0], Technology::kEthernet));
Chris Masone9be4a9d2011-05-16 15:44:09 -0700287
Eric Shienbrood9a245532012-03-07 14:20:39 -0500288 EXPECT_CALL(*mock_devices_[1].get(), SetEnabled(false));
Gaurav Shah435de2c2011-11-17 19:01:07 -0800289 manager()->DeregisterDevice(mock_devices_[1]);
Paul Stewart22aa71b2011-09-16 12:15:11 -0700290 EXPECT_FALSE(IsDeviceRegistered(mock_devices_[1], Technology::kWifi));
Chris Masone9be4a9d2011-05-16 15:44:09 -0700291}
292
293TEST_F(ManagerTest, ServiceRegistration) {
Chris Masone9d779932011-08-25 16:33:41 -0700294 // It's much easier and safer to use a real GLib for this test.
295 GLib glib;
Chris Masone2176a882011-09-14 22:29:15 -0700296 Manager manager(control_interface(),
297 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800298 metrics(),
Chris Masone9d779932011-08-25 16:33:41 -0700299 &glib,
300 run_path(),
301 storage_path(),
302 string());
Chris Masone6515aab2011-10-12 16:19:09 -0700303 ProfileRefPtr profile(CreateProfileForManager(&manager, &glib));
304 ASSERT_TRUE(profile.get());
Paul Stewarta849a3d2011-11-03 05:54:09 -0700305 AdoptProfile(&manager, profile);
Chris Masone6515aab2011-10-12 16:19:09 -0700306
Chris Masone9be4a9d2011-05-16 15:44:09 -0700307 scoped_refptr<MockService> mock_service(
Chris Masone2176a882011-09-14 22:29:15 -0700308 new NiceMock<MockService>(control_interface(),
309 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800310 metrics(),
Chris Masone9d779932011-08-25 16:33:41 -0700311 &manager));
Chris Masone9be4a9d2011-05-16 15:44:09 -0700312 scoped_refptr<MockService> mock_service2(
Chris Masone2176a882011-09-14 22:29:15 -0700313 new NiceMock<MockService>(control_interface(),
314 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800315 metrics(),
Chris Masone9d779932011-08-25 16:33:41 -0700316 &manager));
Paul Stewartce4ec192012-03-14 12:53:46 -0700317
mukesh agrawal51a7e932011-07-27 16:18:26 -0700318 string service1_name(mock_service->UniqueName());
319 string service2_name(mock_service2->UniqueName());
320
321 EXPECT_CALL(*mock_service.get(), GetRpcIdentifier())
322 .WillRepeatedly(Return(service1_name));
Chris Masone6791a432011-07-12 13:23:19 -0700323 EXPECT_CALL(*mock_service2.get(), GetRpcIdentifier())
mukesh agrawal51a7e932011-07-27 16:18:26 -0700324 .WillRepeatedly(Return(service2_name));
mukesh agrawal32399322011-09-01 10:53:43 -0700325 // TODO(quiche): make this EXPECT_CALL work (crosbug.com/20154)
Chris Masone9d779932011-08-25 16:33:41 -0700326 // EXPECT_CALL(*dynamic_cast<ManagerMockAdaptor *>(manager.adaptor_.get()),
mukesh agrawal32399322011-09-01 10:53:43 -0700327 // EmitRpcIdentifierArrayChanged(flimflam::kServicesProperty, _));
Chris Masone9be4a9d2011-05-16 15:44:09 -0700328
Chris Masone9d779932011-08-25 16:33:41 -0700329 manager.RegisterService(mock_service);
330 manager.RegisterService(mock_service2);
Chris Masone9be4a9d2011-05-16 15:44:09 -0700331
Gaurav Shah1b7a6162011-11-09 11:41:01 -0800332 Error error;
333 vector<string> rpc_ids = manager.EnumerateAvailableServices(&error);
Chris Masone6791a432011-07-12 13:23:19 -0700334 set<string> ids(rpc_ids.begin(), rpc_ids.end());
mukesh agrawal51a7e932011-07-27 16:18:26 -0700335 EXPECT_EQ(2, ids.size());
336 EXPECT_TRUE(ContainsKey(ids, mock_service->GetRpcIdentifier()));
337 EXPECT_TRUE(ContainsKey(ids, mock_service2->GetRpcIdentifier()));
Chris Masone6791a432011-07-12 13:23:19 -0700338
Chris Masone9d779932011-08-25 16:33:41 -0700339 EXPECT_TRUE(manager.FindService(service1_name).get() != NULL);
340 EXPECT_TRUE(manager.FindService(service2_name).get() != NULL);
341
342 manager.Stop();
Chris Masone9be4a9d2011-05-16 15:44:09 -0700343}
344
Chris Masone6515aab2011-10-12 16:19:09 -0700345TEST_F(ManagerTest, RegisterKnownService) {
346 // It's much easier and safer to use a real GLib for this test.
347 GLib glib;
348 Manager manager(control_interface(),
349 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800350 metrics(),
Chris Masone6515aab2011-10-12 16:19:09 -0700351 &glib,
352 run_path(),
353 storage_path(),
354 string());
355 ProfileRefPtr profile(CreateProfileForManager(&manager, &glib));
356 ASSERT_TRUE(profile.get());
Paul Stewarta849a3d2011-11-03 05:54:09 -0700357 AdoptProfile(&manager, profile);
Chris Masone6515aab2011-10-12 16:19:09 -0700358 {
359 ServiceRefPtr service1(new ServiceUnderTest(control_interface(),
360 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800361 metrics(),
Chris Masone6515aab2011-10-12 16:19:09 -0700362 &manager));
Chris Masone6515aab2011-10-12 16:19:09 -0700363 ASSERT_TRUE(profile->AdoptService(service1));
364 ASSERT_TRUE(profile->ContainsService(service1));
365 } // Force destruction of service1.
366
367 ServiceRefPtr service2(new ServiceUnderTest(control_interface(),
368 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800369 metrics(),
Chris Masone6515aab2011-10-12 16:19:09 -0700370 &manager));
371 manager.RegisterService(service2);
372 EXPECT_EQ(service2->profile().get(), profile.get());
373 manager.Stop();
374}
375
376TEST_F(ManagerTest, RegisterUnknownService) {
377 // It's much easier and safer to use a real GLib for this test.
378 GLib glib;
379 Manager manager(control_interface(),
380 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800381 metrics(),
Chris Masone6515aab2011-10-12 16:19:09 -0700382 &glib,
383 run_path(),
384 storage_path(),
385 string());
386 ProfileRefPtr profile(CreateProfileForManager(&manager, &glib));
387 ASSERT_TRUE(profile.get());
Paul Stewarta849a3d2011-11-03 05:54:09 -0700388 AdoptProfile(&manager, profile);
Chris Masone6515aab2011-10-12 16:19:09 -0700389 {
390 ServiceRefPtr service1(new ServiceUnderTest(control_interface(),
391 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800392 metrics(),
Chris Masone6515aab2011-10-12 16:19:09 -0700393 &manager));
Chris Masone6515aab2011-10-12 16:19:09 -0700394 ASSERT_TRUE(profile->AdoptService(service1));
395 ASSERT_TRUE(profile->ContainsService(service1));
396 } // Force destruction of service1.
397 scoped_refptr<MockService> mock_service2(
398 new NiceMock<MockService>(control_interface(),
399 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800400 metrics(),
Chris Masone6515aab2011-10-12 16:19:09 -0700401 &manager));
402 EXPECT_CALL(*mock_service2.get(), GetStorageIdentifier())
403 .WillRepeatedly(Return(mock_service2->UniqueName()));
404 manager.RegisterService(mock_service2);
405 EXPECT_NE(mock_service2->profile().get(), profile.get());
406 manager.Stop();
407}
408
mukesh agrawal8a3188d2011-12-01 20:56:44 +0000409TEST_F(ManagerTest, DeregisterUnregisteredService) {
410 // WiFi assumes that it can deregister a service that is not
411 // registered. (E.g. a hidden service can be deregistered when it
412 // loses its last endpoint, and again when WiFi is Stop()-ed.)
413 //
414 // So test that doing so doesn't cause a crash.
415 MockServiceRefPtr service = new NiceMock<MockService>(control_interface(),
416 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800417 metrics(),
mukesh agrawal8a3188d2011-12-01 20:56:44 +0000418 manager());
419 manager()->DeregisterService(service);
420}
421
Chris Masonea8a2c252011-06-27 22:16:30 -0700422TEST_F(ManagerTest, GetProperties) {
Paul Stewartcb3eb892012-06-07 14:24:46 -0700423 AddMockProfileToManager(manager());
Chris Masonea8a2c252011-06-27 22:16:30 -0700424 map<string, ::DBus::Variant> props;
425 Error error(Error::kInvalidProperty, "");
426 {
427 ::DBus::Error dbus_error;
428 string expected("portal_list");
mukesh agrawalde29fa82011-09-16 16:16:36 -0700429 manager()->mutable_store()->SetStringProperty(
430 flimflam::kCheckPortalListProperty,
431 expected,
432 &error);
Chris Masone9d779932011-08-25 16:33:41 -0700433 DBusAdaptor::GetProperties(manager()->store(), &props, &dbus_error);
Chris Masonea8a2c252011-06-27 22:16:30 -0700434 ASSERT_FALSE(props.find(flimflam::kCheckPortalListProperty) == props.end());
435 EXPECT_EQ(props[flimflam::kCheckPortalListProperty].reader().get_string(),
436 expected);
437 }
438 {
439 ::DBus::Error dbus_error;
440 bool expected = true;
mukesh agrawalde29fa82011-09-16 16:16:36 -0700441 manager()->mutable_store()->SetBoolProperty(flimflam::kOfflineModeProperty,
442 expected,
443 &error);
Chris Masone9d779932011-08-25 16:33:41 -0700444 DBusAdaptor::GetProperties(manager()->store(), &props, &dbus_error);
Chris Masonea8a2c252011-06-27 22:16:30 -0700445 ASSERT_FALSE(props.find(flimflam::kOfflineModeProperty) == props.end());
446 EXPECT_EQ(props[flimflam::kOfflineModeProperty].reader().get_bool(),
447 expected);
448 }
449}
450
Chris Masone3c3f6a12011-07-01 10:01:41 -0700451TEST_F(ManagerTest, GetDevicesProperty) {
Paul Stewartcb3eb892012-06-07 14:24:46 -0700452 AddMockProfileToManager(manager());
Gaurav Shah435de2c2011-11-17 19:01:07 -0800453 manager()->RegisterDevice(mock_devices_[0]);
454 manager()->RegisterDevice(mock_devices_[1]);
Chris Masone3c3f6a12011-07-01 10:01:41 -0700455 {
456 map<string, ::DBus::Variant> props;
457 ::DBus::Error dbus_error;
Chris Masone9d779932011-08-25 16:33:41 -0700458 DBusAdaptor::GetProperties(manager()->store(), &props, &dbus_error);
Chris Masone3c3f6a12011-07-01 10:01:41 -0700459 ASSERT_FALSE(props.find(flimflam::kDevicesProperty) == props.end());
Paul Stewartcb3eb892012-06-07 14:24:46 -0700460 vector < ::DBus::Path> devices =
461 props[flimflam::kDevicesProperty].operator vector< ::DBus::Path>();
Chris Masone3c3f6a12011-07-01 10:01:41 -0700462 EXPECT_EQ(2, devices.size());
463 }
Chris Masone3c3f6a12011-07-01 10:01:41 -0700464}
465
mukesh agrawal2366eed2012-03-20 18:21:50 -0700466TEST_F(ManagerTest, GetServicesProperty) {
Paul Stewartcb3eb892012-06-07 14:24:46 -0700467 AddMockProfileToManager(manager());
mukesh agrawal2366eed2012-03-20 18:21:50 -0700468 map<string, ::DBus::Variant> props;
469 ::DBus::Error dbus_error;
470 DBusAdaptor::GetProperties(manager()->store(), &props, &dbus_error);
471 map<string, ::DBus::Variant>::const_iterator prop =
472 props.find(flimflam::kServicesProperty);
473 ASSERT_FALSE(prop == props.end());
474 const ::DBus::Variant &variant = prop->second;
475 ASSERT_TRUE(DBusAdaptor::IsPaths(variant.signature()));
476}
477
Chris Masone6791a432011-07-12 13:23:19 -0700478TEST_F(ManagerTest, MoveService) {
Chris Masone2176a882011-09-14 22:29:15 -0700479 Manager manager(control_interface(),
480 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800481 metrics(),
Chris Masone6515aab2011-10-12 16:19:09 -0700482 glib(),
Chris Masone9d779932011-08-25 16:33:41 -0700483 run_path(),
484 storage_path(),
485 string());
Chris Masone6515aab2011-10-12 16:19:09 -0700486 scoped_refptr<MockService> s2(new MockService(control_interface(),
487 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800488 metrics(),
Chris Masone6515aab2011-10-12 16:19:09 -0700489 &manager));
490 // Inject an actual profile, backed by a fake StoreInterface
Chris Masoneb9c00592011-10-06 13:10:39 -0700491 {
Chris Masone6515aab2011-10-12 16:19:09 -0700492 Profile::Identifier id("irrelevant");
Chris Masoneb9c00592011-10-06 13:10:39 -0700493 ProfileRefPtr profile(
494 new Profile(control_interface(), &manager, id, "", false));
495 MockStore *storage = new MockStore;
Chris Masone6515aab2011-10-12 16:19:09 -0700496 EXPECT_CALL(*storage, ContainsGroup(s2->GetStorageIdentifier()))
Chris Masone6515aab2011-10-12 16:19:09 -0700497 .WillRepeatedly(Return(true));
498 EXPECT_CALL(*storage, Flush())
499 .Times(AnyNumber())
500 .WillRepeatedly(Return(true));
Chris Masoneb9c00592011-10-06 13:10:39 -0700501 profile->set_storage(storage);
Paul Stewarta849a3d2011-11-03 05:54:09 -0700502 AdoptProfile(&manager, profile);
Chris Masoneb9c00592011-10-06 13:10:39 -0700503 }
Chris Masone6515aab2011-10-12 16:19:09 -0700504 // Create a profile that already has |s2| in it.
505 ProfileRefPtr profile(new EphemeralProfile(control_interface(), &manager));
Paul Stewart451aa7f2012-04-11 19:07:58 -0700506 EXPECT_TRUE(profile->AdoptService(s2));
Chris Masone9d779932011-08-25 16:33:41 -0700507
Chris Masone6515aab2011-10-12 16:19:09 -0700508 // Now, move the Service |s2| to another profile.
509 EXPECT_CALL(*s2.get(), Save(_)).WillOnce(Return(true));
510 ASSERT_TRUE(manager.MoveServiceToProfile(s2, manager.ActiveProfile()));
Chris Masone6791a432011-07-12 13:23:19 -0700511
512 // Force destruction of the original Profile, to ensure that the Service
513 // is kept alive and populated with data.
514 profile = NULL;
Chris Masone6515aab2011-10-12 16:19:09 -0700515 ASSERT_TRUE(manager.ActiveProfile()->ContainsService(s2));
Chris Masone9d779932011-08-25 16:33:41 -0700516 manager.Stop();
Chris Masone6791a432011-07-12 13:23:19 -0700517}
518
Paul Stewart7f61e522012-03-22 11:13:45 -0700519TEST_F(ManagerTest, LookupProfileByRpcIdentifier) {
520 scoped_refptr<MockProfile> mock_profile(
521 new MockProfile(control_interface(), manager(), ""));
522 const string kProfileName("profile0");
523 EXPECT_CALL(*mock_profile, GetRpcIdentifier())
524 .WillRepeatedly(Return(kProfileName));
525 AdoptProfile(manager(), mock_profile);
526
527 EXPECT_FALSE(manager()->LookupProfileByRpcIdentifier("foo"));
528 ProfileRefPtr profile = manager()->LookupProfileByRpcIdentifier(kProfileName);
529 EXPECT_EQ(mock_profile.get(), profile.get());
530}
531
Paul Stewart1b1a7f22012-01-06 16:24:06 -0800532TEST_F(ManagerTest, SetProfileForService) {
533 scoped_refptr<MockProfile> profile0(
534 new MockProfile(control_interface(), manager(), ""));
535 string profile_name0("profile0");
536 EXPECT_CALL(*profile0, GetRpcIdentifier())
537 .WillRepeatedly(Return(profile_name0));
538 AdoptProfile(manager(), profile0);
539 scoped_refptr<MockService> service(new MockService(control_interface(),
540 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800541 metrics(),
Paul Stewart1b1a7f22012-01-06 16:24:06 -0800542 manager()));
Paul Stewart649f3a42012-04-24 23:22:16 -0700543 EXPECT_FALSE(manager()->HasService(service));
544 {
545 Error error;
546 EXPECT_CALL(*profile0, AdoptService(_))
547 .WillOnce(Return(true));
548 // Expect that setting the profile of a service that does not already
549 // have one assigned does not cause a crash.
550 manager()->SetProfileForService(service, "profile0", &error);
551 EXPECT_TRUE(error.IsSuccess());
552 }
553
554 // The service should be registered as a side-effect of the profile being
555 // set for this service.
556 EXPECT_TRUE(manager()->HasService(service));
557
558 // Since we have mocked Profile::AdoptServie() above, the service's
559 // profile was not actually changed. Do so explicitly now.
Paul Stewart1b1a7f22012-01-06 16:24:06 -0800560 service->set_profile(profile0);
561
562 {
563 Error error;
564 manager()->SetProfileForService(service, "foo", &error);
565 EXPECT_EQ(Error::kInvalidArguments, error.type());
Paul Stewart7f61e522012-03-22 11:13:45 -0700566 EXPECT_EQ("Unknown Profile foo requested for Service", error.message());
Paul Stewart1b1a7f22012-01-06 16:24:06 -0800567 }
568
569 {
570 Error error;
571 manager()->SetProfileForService(service, profile_name0, &error);
572 EXPECT_EQ(Error::kInvalidArguments, error.type());
573 EXPECT_EQ("Service is already connected to this profile", error.message());
574 }
575
576 scoped_refptr<MockProfile> profile1(
577 new MockProfile(control_interface(), manager(), ""));
578 string profile_name1("profile1");
579 EXPECT_CALL(*profile1, GetRpcIdentifier())
580 .WillRepeatedly(Return(profile_name1));
581 AdoptProfile(manager(), profile1);
582
583 {
584 Error error;
585 EXPECT_CALL(*profile1, AdoptService(_))
586 .WillOnce(Return(true));
587 EXPECT_CALL(*profile0, AbandonService(_))
588 .WillOnce(Return(true));
589 manager()->SetProfileForService(service, profile_name1, &error);
590 EXPECT_TRUE(error.IsSuccess());
591 }
592}
593
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700594TEST_F(ManagerTest, CreateProfile) {
595 // It's much easier to use real Glib here since we want the storage
596 // side-effects.
597 GLib glib;
598 ScopedTempDir temp_dir;
599 ASSERT_TRUE(temp_dir.CreateUniqueTempDir());
600
601 Manager manager(control_interface(),
602 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800603 metrics(),
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700604 &glib,
605 run_path(),
606 storage_path(),
607 temp_dir.path().value());
608
609 // Invalid name should be rejected.
610 EXPECT_EQ(Error::kInvalidArguments, TestCreateProfile(&manager, ""));
611
Paul Stewartd0a3b812012-03-28 22:48:22 -0700612 // A profile with invalid characters in it should similarly be rejected.
613 EXPECT_EQ(Error::kInvalidArguments,
614 TestCreateProfile(&manager, "valid_profile"));
615
616 // We should be able to create a machine profile.
617 EXPECT_EQ(Error::kSuccess, TestCreateProfile(&manager, "valid"));
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700618
Gary Morainb672d352012-04-25 09:19:06 -0700619 // We should succeed in creating a valid user profile. Verify the returned
620 // path.
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700621 const char kProfile[] = "~user/profile";
Gary Morainb672d352012-04-25 09:19:06 -0700622 {
623 Error error;
624 string path;
625 manager.CreateProfile(kProfile, &path, &error);
626 EXPECT_EQ(Error::kSuccess, error.type());
627 EXPECT_EQ("/profile_rpc", path);
628 }
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700629
630 // We should fail in creating it a second time (already exists).
631 EXPECT_EQ(Error::kAlreadyExists, TestCreateProfile(&manager, kProfile));
632}
633
634TEST_F(ManagerTest, PushPopProfile) {
635 // It's much easier to use real Glib in creating a Manager for this
636 // test here since we want the storage side-effects.
637 GLib glib;
638 ScopedTempDir temp_dir;
639 ASSERT_TRUE(temp_dir.CreateUniqueTempDir());
640 Manager manager(control_interface(),
641 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800642 metrics(),
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700643 &glib,
644 run_path(),
645 storage_path(),
646 temp_dir.path().value());
647
648 // Pushing an invalid profile should fail.
649 EXPECT_EQ(Error::kInvalidArguments, TestPushProfile(&manager, ""));
650
Paul Stewartd0a3b812012-03-28 22:48:22 -0700651 // Pushing a default profile that does not exist should fail.
652 EXPECT_EQ(Error::kNotFound, TestPushProfile(&manager, "default"));
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700653
654 const char kProfile0[] = "~user/profile0";
655 const char kProfile1[] = "~user/profile1";
656
657 // Create a couple of profiles.
658 ASSERT_EQ(Error::kSuccess, TestCreateProfile(&manager, kProfile0));
659 ASSERT_EQ(Error::kSuccess, TestCreateProfile(&manager, kProfile1));
660
661 // Push these profiles on the stack.
662 EXPECT_EQ(Error::kSuccess, TestPushProfile(&manager, kProfile0));
663 EXPECT_EQ(Error::kSuccess, TestPushProfile(&manager, kProfile1));
664
665 // Pushing a profile a second time should fail.
666 EXPECT_EQ(Error::kAlreadyExists, TestPushProfile(&manager, kProfile0));
667 EXPECT_EQ(Error::kAlreadyExists, TestPushProfile(&manager, kProfile1));
668
Gaurav Shah1b7a6162011-11-09 11:41:01 -0800669 Error error;
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700670 // Active profile should be the last one we pushed.
Paul Stewart1b253142012-01-26 14:05:52 -0800671 EXPECT_EQ(kProfile1, "~" + manager.ActiveProfile()->GetFriendlyName());
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700672
673 // Make sure a profile name that doesn't exist fails.
674 const char kProfile2Id[] = "profile2";
675 const string kProfile2 = base::StringPrintf("~user/%s", kProfile2Id);
676 EXPECT_EQ(Error::kNotFound, TestPushProfile(&manager, kProfile2));
677
678 // Create a new service, with a specific storage name.
679 scoped_refptr<MockService> service(
680 new NiceMock<MockService>(control_interface(),
681 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -0800682 metrics(),
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700683 &manager));
684 const char kServiceName[] = "service_storage_name";
685 EXPECT_CALL(*service.get(), GetStorageIdentifier())
686 .WillRepeatedly(Return(kServiceName));
687 EXPECT_CALL(*service.get(), Load(_))
688 .WillRepeatedly(Return(true));
689
690 // Add this service to the manager -- it should end up in the ephemeral
691 // profile.
692 manager.RegisterService(service);
Paul Stewart75225512012-01-26 22:51:33 -0800693 ASSERT_EQ(GetEphemeralProfile(&manager), service->profile());
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700694
695 // Create storage for a profile that contains the service storage name.
696 ASSERT_TRUE(CreateBackingStoreForService(&temp_dir, kProfile2Id,
697 kServiceName));
698
699 // When we push the profile, the service should move away from the
700 // ephemeral profile to this new profile since it has an entry for
701 // this service.
702 EXPECT_EQ(Error::kSuccess, TestPushProfile(&manager, kProfile2));
Paul Stewart75225512012-01-26 22:51:33 -0800703 EXPECT_NE(GetEphemeralProfile(&manager), service->profile());
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700704 EXPECT_EQ(kProfile2, "~" + service->profile()->GetFriendlyName());
705
706 // Insert another profile that should supersede ownership of the service.
707 const char kProfile3Id[] = "profile3";
708 const string kProfile3 = base::StringPrintf("~user/%s", kProfile3Id);
709 ASSERT_TRUE(CreateBackingStoreForService(&temp_dir, kProfile3Id,
710 kServiceName));
711 EXPECT_EQ(Error::kSuccess, TestPushProfile(&manager, kProfile3));
712 EXPECT_EQ(kProfile3, "~" + service->profile()->GetFriendlyName());
713
714 // Popping an invalid profile name should fail.
715 EXPECT_EQ(Error::kInvalidArguments, TestPopProfile(&manager, "~"));
716
717 // Popping an profile that is not at the top of the stack should fail.
718 EXPECT_EQ(Error::kNotSupported, TestPopProfile(&manager, kProfile0));
719
720 // Popping the top profile should succeed.
721 EXPECT_EQ(Error::kSuccess, TestPopProfile(&manager, kProfile3));
722
723 // Moreover the service should have switched profiles to profile 2.
724 EXPECT_EQ(kProfile2, "~" + service->profile()->GetFriendlyName());
725
726 // Popping the top profile should succeed.
727 EXPECT_EQ(Error::kSuccess, TestPopAnyProfile(&manager));
728
729 // The service should now revert to the ephemeral profile.
Paul Stewart75225512012-01-26 22:51:33 -0800730 EXPECT_EQ(GetEphemeralProfile(&manager), service->profile());
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700731
732 // Pop the remaining two services off the stack.
733 EXPECT_EQ(Error::kSuccess, TestPopAnyProfile(&manager));
734 EXPECT_EQ(Error::kSuccess, TestPopAnyProfile(&manager));
735
736 // Next pop should fail with "stack is empty".
737 EXPECT_EQ(Error::kNotFound, TestPopAnyProfile(&manager));
Paul Stewartd0a3b812012-03-28 22:48:22 -0700738
739 const char kMachineProfile0[] = "machineprofile0";
740 const char kMachineProfile1[] = "machineprofile1";
741 ASSERT_EQ(Error::kSuccess, TestCreateProfile(&manager, kMachineProfile0));
742 ASSERT_EQ(Error::kSuccess, TestCreateProfile(&manager, kMachineProfile1));
743
744 // Should be able to push a machine profile.
745 EXPECT_EQ(Error::kSuccess, TestPushProfile(&manager, kMachineProfile0));
746
747 // Should be able to push a user profile atop a machine profile.
748 EXPECT_EQ(Error::kSuccess, TestPushProfile(&manager, kProfile0));
749
750 // Pushing a system-wide profile on top of a user profile should fail.
751 EXPECT_EQ(Error::kInvalidArguments,
752 TestPushProfile(&manager, kMachineProfile1));
753
754 // However if we pop the user profile, we should be able stack another
755 // machine profile on.
756 EXPECT_EQ(Error::kSuccess, TestPopAnyProfile(&manager));
757 EXPECT_EQ(Error::kSuccess, TestPushProfile(&manager, kMachineProfile1));
Paul Stewart5dc40aa2011-10-28 19:43:43 -0700758}
759
Paul Stewarte73d05c2012-03-29 16:26:05 -0700760TEST_F(ManagerTest, RemoveProfile) {
761 // It's much easier to use real Glib in creating a Manager for this
762 // test here since we want the storage side-effects.
763 GLib glib;
764 ScopedTempDir temp_dir;
765 ASSERT_TRUE(temp_dir.CreateUniqueTempDir());
766 Manager manager(control_interface(),
767 dispatcher(),
768 metrics(),
769 &glib,
770 run_path(),
771 storage_path(),
772 temp_dir.path().value());
773
774 const char kProfile0[] = "profile0";
775 FilePath profile_path(
776 FilePath(storage_path()).Append(string(kProfile0) + ".profile"));
777
778 ASSERT_EQ(Error::kSuccess, TestCreateProfile(&manager, kProfile0));
779 ASSERT_TRUE(file_util::PathExists(profile_path));
780
781 EXPECT_EQ(Error::kSuccess, TestPushProfile(&manager, kProfile0));
782
783 // Remove should fail since the profile is still on the stack.
784 {
785 Error error;
786 manager.RemoveProfile(kProfile0, &error);
787 EXPECT_EQ(Error::kInvalidArguments, error.type());
788 }
789
790 // Profile path should still exist.
791 EXPECT_TRUE(file_util::PathExists(profile_path));
792
793 EXPECT_EQ(Error::kSuccess, TestPopAnyProfile(&manager));
794
795 // This should succeed now that the profile is off the stack.
796 {
797 Error error;
798 manager.RemoveProfile(kProfile0, &error);
799 EXPECT_EQ(Error::kSuccess, error.type());
800 }
801
802 // Profile path should no longer exist.
803 EXPECT_FALSE(file_util::PathExists(profile_path));
804
805 // Another remove succeeds, due to a foible in file_util::Delete --
806 // it is not an error to delete a file that does not exist.
807 {
808 Error error;
809 manager.RemoveProfile(kProfile0, &error);
810 EXPECT_EQ(Error::kSuccess, error.type());
811 }
812
813 // Let's create an error case that will "work". Create a non-empty
814 // directory in the place of the profile pathname.
815 ASSERT_TRUE(file_util::CreateDirectory(profile_path.Append("foo")));
816 {
817 Error error;
818 manager.RemoveProfile(kProfile0, &error);
819 EXPECT_EQ(Error::kOperationFailed, error.type());
820 }
821}
822
Paul Stewartfc9a1da2012-06-27 15:54:52 -0700823TEST_F(ManagerTest, CreateDuplicateProfileWithMissingKeyfile) {
824 // It's much easier to use real Glib in creating a Manager for this
825 // test here since we want the storage side-effects.
826 GLib glib;
827 ScopedTempDir temp_dir;
828 ASSERT_TRUE(temp_dir.CreateUniqueTempDir());
829 Manager manager(control_interface(),
830 dispatcher(),
831 metrics(),
832 &glib,
833 run_path(),
834 storage_path(),
835 temp_dir.path().value());
836
837 const char kProfile0[] = "profile0";
838 FilePath profile_path(
839 FilePath(storage_path()).Append(string(kProfile0) + ".profile"));
840
841 ASSERT_EQ(Error::kSuccess, TestCreateProfile(&manager, kProfile0));
842 ASSERT_TRUE(file_util::PathExists(profile_path));
843 EXPECT_EQ(Error::kSuccess, TestPushProfile(&manager, kProfile0));
844
845 // Ensure that even if the backing filestore is removed, we still can't
846 // create a profile twice.
847 ASSERT_TRUE(file_util::Delete(profile_path, false));
848 EXPECT_EQ(Error::kAlreadyExists, TestCreateProfile(&manager, kProfile0));
849}
850
Paul Stewart75225512012-01-26 22:51:33 -0800851// Use this matcher instead of passing RefPtrs directly into the arguments
852// of EXPECT_CALL() because otherwise we may create un-cleaned-up references at
853// system teardown.
854MATCHER_P(IsRefPtrTo, ref_address, "") {
855 return arg.get() == ref_address;
856}
857
858TEST_F(ManagerTest, HandleProfileEntryDeletion) {
859 MockServiceRefPtr s_not_in_profile(
860 new NiceMock<MockService>(control_interface(),
861 dispatcher(),
862 metrics(),
863 manager()));
864 MockServiceRefPtr s_not_in_group(
865 new NiceMock<MockService>(control_interface(),
866 dispatcher(),
867 metrics(),
868 manager()));
869 MockServiceRefPtr s_configure_fail(
870 new NiceMock<MockService>(control_interface(),
871 dispatcher(),
872 metrics(),
873 manager()));
874 MockServiceRefPtr s_configure_succeed(
875 new NiceMock<MockService>(control_interface(),
876 dispatcher(),
877 metrics(),
878 manager()));
879
880 string entry_name("entry_name");
881 EXPECT_CALL(*s_not_in_profile.get(), GetStorageIdentifier()).Times(0);
882 EXPECT_CALL(*s_not_in_group.get(), GetStorageIdentifier())
883 .WillRepeatedly(Return("not_entry_name"));
884 EXPECT_CALL(*s_configure_fail.get(), GetStorageIdentifier())
885 .WillRepeatedly(Return(entry_name));
886 EXPECT_CALL(*s_configure_succeed.get(), GetStorageIdentifier())
887 .WillRepeatedly(Return(entry_name));
888
889 manager()->RegisterService(s_not_in_profile);
890 manager()->RegisterService(s_not_in_group);
891 manager()->RegisterService(s_configure_fail);
892 manager()->RegisterService(s_configure_succeed);
893
894 scoped_refptr<MockProfile> profile0(
895 new StrictMock<MockProfile>(control_interface(), manager(), ""));
896 scoped_refptr<MockProfile> profile1(
897 new StrictMock<MockProfile>(control_interface(), manager(), ""));
898
899 s_not_in_group->set_profile(profile1);
900 s_configure_fail->set_profile(profile1);
901 s_configure_succeed->set_profile(profile1);
902
903 AdoptProfile(manager(), profile0);
904 AdoptProfile(manager(), profile1);
905
906 // No services are a member of this profile.
907 EXPECT_FALSE(manager()->HandleProfileEntryDeletion(profile0, entry_name));
908
909 // No services that are members of this profile have this entry name.
910 EXPECT_FALSE(manager()->HandleProfileEntryDeletion(profile1, ""));
911
912 // Only services that are members of the profile and group will be abandoned.
913 EXPECT_CALL(*profile1.get(),
914 AbandonService(IsRefPtrTo(s_not_in_profile.get()))).Times(0);
915 EXPECT_CALL(*profile1.get(),
916 AbandonService(IsRefPtrTo(s_not_in_group.get()))).Times(0);
917 EXPECT_CALL(*profile1.get(),
918 AbandonService(IsRefPtrTo(s_configure_fail.get())))
919 .WillOnce(Return(true));
920 EXPECT_CALL(*profile1.get(),
921 AbandonService(IsRefPtrTo(s_configure_succeed.get())))
922 .WillOnce(Return(true));
923
924 // Never allow services to re-join profile1.
925 EXPECT_CALL(*profile1.get(), ConfigureService(_))
926 .WillRepeatedly(Return(false));
927
928 // Only allow one of the members of the profile and group to successfully
929 // join profile0.
930 EXPECT_CALL(*profile0.get(),
931 ConfigureService(IsRefPtrTo(s_not_in_profile.get()))).Times(0);
932 EXPECT_CALL(*profile0.get(),
933 ConfigureService(IsRefPtrTo(s_not_in_group.get()))).Times(0);
934 EXPECT_CALL(*profile0.get(),
935 ConfigureService(IsRefPtrTo(s_configure_fail.get())))
936 .WillOnce(Return(false));
937 EXPECT_CALL(*profile0.get(),
938 ConfigureService(IsRefPtrTo(s_configure_succeed.get())))
939 .WillOnce(Return(true));
940
941 // Expect the failed-to-configure service to have Unload() called on it.
942 EXPECT_CALL(*s_not_in_profile.get(), Unload()).Times(0);
943 EXPECT_CALL(*s_not_in_group.get(), Unload()).Times(0);
944 EXPECT_CALL(*s_configure_fail.get(), Unload()).Times(1);
945 EXPECT_CALL(*s_configure_succeed.get(), Unload()).Times(0);
946
947 EXPECT_TRUE(manager()->HandleProfileEntryDeletion(profile1, entry_name));
948
949 EXPECT_EQ(GetEphemeralProfile(manager()), s_not_in_profile->profile().get());
950 EXPECT_EQ(profile1, s_not_in_group->profile());
951 EXPECT_EQ(GetEphemeralProfile(manager()), s_configure_fail->profile());
952
953 // Since we are using a MockProfile, the profile does not actually change,
954 // since ConfigureService was not actually called on the service.
955 EXPECT_EQ(profile1, s_configure_succeed->profile());
956}
957
Paul Stewart65512e12012-03-26 18:01:08 -0700958TEST_F(ManagerTest, HandleProfileEntryDeletionWithUnload) {
959 MockServiceRefPtr s_will_remove0(
960 new NiceMock<MockService>(control_interface(),
961 dispatcher(),
962 metrics(),
963 manager()));
964 MockServiceRefPtr s_will_remove1(
965 new NiceMock<MockService>(control_interface(),
966 dispatcher(),
967 metrics(),
968 manager()));
969 MockServiceRefPtr s_will_not_remove0(
970 new NiceMock<MockService>(control_interface(),
971 dispatcher(),
972 metrics(),
973 manager()));
974 MockServiceRefPtr s_will_not_remove1(
975 new NiceMock<MockService>(control_interface(),
976 dispatcher(),
977 metrics(),
978 manager()));
979
980 EXPECT_CALL(*metrics(), NotifyDefaultServiceChanged(NULL))
981 .Times(4); // Once for each registration.
982
983 string entry_name("entry_name");
984 EXPECT_CALL(*s_will_remove0.get(), GetStorageIdentifier())
985 .WillRepeatedly(Return(entry_name));
986 EXPECT_CALL(*s_will_remove1.get(), GetStorageIdentifier())
987 .WillRepeatedly(Return(entry_name));
988 EXPECT_CALL(*s_will_not_remove0.get(), GetStorageIdentifier())
989 .WillRepeatedly(Return(entry_name));
990 EXPECT_CALL(*s_will_not_remove1.get(), GetStorageIdentifier())
991 .WillRepeatedly(Return(entry_name));
992
993 manager()->RegisterService(s_will_remove0);
Paul Stewartdfa46052012-06-26 09:44:14 -0700994 CompleteServiceSort();
Paul Stewart65512e12012-03-26 18:01:08 -0700995 manager()->RegisterService(s_will_not_remove0);
Paul Stewartdfa46052012-06-26 09:44:14 -0700996 CompleteServiceSort();
Paul Stewart65512e12012-03-26 18:01:08 -0700997 manager()->RegisterService(s_will_remove1);
Paul Stewartdfa46052012-06-26 09:44:14 -0700998 CompleteServiceSort();
Paul Stewart65512e12012-03-26 18:01:08 -0700999 manager()->RegisterService(s_will_not_remove1);
Paul Stewartdfa46052012-06-26 09:44:14 -07001000 CompleteServiceSort();
Paul Stewart65512e12012-03-26 18:01:08 -07001001
1002 // One for each service added above.
1003 ASSERT_EQ(4, manager()->services_.size());
1004
1005 scoped_refptr<MockProfile> profile(
1006 new StrictMock<MockProfile>(control_interface(), manager(), ""));
1007
1008 s_will_remove0->set_profile(profile);
1009 s_will_remove1->set_profile(profile);
1010 s_will_not_remove0->set_profile(profile);
1011 s_will_not_remove1->set_profile(profile);
1012
1013 AdoptProfile(manager(), profile);
1014
1015 // Deny any of the services re-entry to the profile.
1016 EXPECT_CALL(*profile, ConfigureService(_))
1017 .WillRepeatedly(Return(false));
1018
1019 EXPECT_CALL(*profile, AbandonService(ServiceRefPtr(s_will_remove0)))
1020 .WillOnce(Return(true));
1021 EXPECT_CALL(*profile, AbandonService(ServiceRefPtr(s_will_remove1)))
1022 .WillOnce(Return(true));
1023 EXPECT_CALL(*profile, AbandonService(ServiceRefPtr(s_will_not_remove0)))
1024 .WillOnce(Return(true));
1025 EXPECT_CALL(*profile, AbandonService(ServiceRefPtr(s_will_not_remove1)))
1026 .WillOnce(Return(true));
1027
1028 EXPECT_CALL(*s_will_remove0, Unload())
1029 .WillOnce(Return(true));
1030 EXPECT_CALL(*s_will_remove1, Unload())
1031 .WillOnce(Return(true));
1032 EXPECT_CALL(*s_will_not_remove0, Unload())
1033 .WillOnce(Return(false));
1034 EXPECT_CALL(*s_will_not_remove1, Unload())
1035 .WillOnce(Return(false));
1036
1037
1038 // This will cause all the profiles to be unloaded.
1039 EXPECT_TRUE(manager()->HandleProfileEntryDeletion(profile, entry_name));
1040
1041 // 2 of the 4 services added above should have been unregistered and
1042 // removed, leaving 2.
1043 EXPECT_EQ(2, manager()->services_.size());
1044 EXPECT_EQ(s_will_not_remove0.get(), manager()->services_[0].get());
1045 EXPECT_EQ(s_will_not_remove1.get(), manager()->services_[1].get());
1046}
1047
1048TEST_F(ManagerTest, PopProfileWithUnload) {
1049 MockServiceRefPtr s_will_remove0(
1050 new NiceMock<MockService>(control_interface(),
1051 dispatcher(),
1052 metrics(),
1053 manager()));
1054 MockServiceRefPtr s_will_remove1(
1055 new NiceMock<MockService>(control_interface(),
1056 dispatcher(),
1057 metrics(),
1058 manager()));
1059 MockServiceRefPtr s_will_not_remove0(
1060 new NiceMock<MockService>(control_interface(),
1061 dispatcher(),
1062 metrics(),
1063 manager()));
1064 MockServiceRefPtr s_will_not_remove1(
1065 new NiceMock<MockService>(control_interface(),
1066 dispatcher(),
1067 metrics(),
1068 manager()));
1069
1070 EXPECT_CALL(*metrics(), NotifyDefaultServiceChanged(NULL))
1071 .Times(5); // Once for each registration, and one after profile pop.
1072
1073 manager()->RegisterService(s_will_remove0);
Paul Stewartdfa46052012-06-26 09:44:14 -07001074 CompleteServiceSort();
Paul Stewart65512e12012-03-26 18:01:08 -07001075 manager()->RegisterService(s_will_not_remove0);
Paul Stewartdfa46052012-06-26 09:44:14 -07001076 CompleteServiceSort();
Paul Stewart65512e12012-03-26 18:01:08 -07001077 manager()->RegisterService(s_will_remove1);
Paul Stewartdfa46052012-06-26 09:44:14 -07001078 CompleteServiceSort();
Paul Stewart65512e12012-03-26 18:01:08 -07001079 manager()->RegisterService(s_will_not_remove1);
Paul Stewartdfa46052012-06-26 09:44:14 -07001080 CompleteServiceSort();
Paul Stewart65512e12012-03-26 18:01:08 -07001081
1082 // One for each service added above.
1083 ASSERT_EQ(4, manager()->services_.size());
1084
1085 scoped_refptr<MockProfile> profile0(
1086 new StrictMock<MockProfile>(control_interface(), manager(), ""));
1087 scoped_refptr<MockProfile> profile1(
1088 new StrictMock<MockProfile>(control_interface(), manager(), ""));
1089
1090 s_will_remove0->set_profile(profile1);
1091 s_will_remove1->set_profile(profile1);
1092 s_will_not_remove0->set_profile(profile1);
1093 s_will_not_remove1->set_profile(profile1);
1094
1095 AdoptProfile(manager(), profile0);
1096 AdoptProfile(manager(), profile1);
1097
1098 // Deny any of the services entry to profile0, so they will all be unloaded.
1099 EXPECT_CALL(*profile0, ConfigureService(_))
1100 .WillRepeatedly(Return(false));
1101
1102 EXPECT_CALL(*s_will_remove0, Unload())
1103 .WillOnce(Return(true));
1104 EXPECT_CALL(*s_will_remove1, Unload())
1105 .WillOnce(Return(true));
1106 EXPECT_CALL(*s_will_not_remove0, Unload())
Paul Stewartfc9a1da2012-06-27 15:54:52 -07001107 .WillRepeatedly(Return(false));
Paul Stewart65512e12012-03-26 18:01:08 -07001108 EXPECT_CALL(*s_will_not_remove1, Unload())
1109 .WillOnce(Return(false));
1110
1111 // This will pop profile1, which should cause all our profiles to unload.
1112 manager()->PopProfileInternal();
Paul Stewartdfa46052012-06-26 09:44:14 -07001113 CompleteServiceSort();
Paul Stewart65512e12012-03-26 18:01:08 -07001114
1115 // 2 of the 4 services added above should have been unregistered and
1116 // removed, leaving 2.
1117 EXPECT_EQ(2, manager()->services_.size());
1118 EXPECT_EQ(s_will_not_remove0.get(), manager()->services_[0].get());
1119 EXPECT_EQ(s_will_not_remove1.get(), manager()->services_[1].get());
Paul Stewartfc9a1da2012-06-27 15:54:52 -07001120
1121 // Expect the unloaded services to lose their profile reference.
1122 EXPECT_FALSE(s_will_remove0->profile());
1123 EXPECT_FALSE(s_will_remove1->profile());
1124
1125 // If we explicitly deregister a service, the effect should be the same
1126 // with respect to the profile reference.
1127 ASSERT_TRUE(s_will_not_remove0->profile());
1128 manager()->DeregisterService(s_will_not_remove0);
1129 EXPECT_FALSE(s_will_not_remove0->profile());
Paul Stewart65512e12012-03-26 18:01:08 -07001130}
1131
mukesh agrawal6bb9e7c2012-01-30 14:57:54 -08001132TEST_F(ManagerTest, SetProperty) {
Chris Masonea8a2c252011-06-27 22:16:30 -07001133 {
1134 ::DBus::Error error;
mukesh agrawal6bb9e7c2012-01-30 14:57:54 -08001135 EXPECT_TRUE(DBusAdaptor::SetProperty(manager()->mutable_store(),
1136 flimflam::kOfflineModeProperty,
1137 PropertyStoreTest::kBoolV,
1138 &error));
Chris Masonea8a2c252011-06-27 22:16:30 -07001139 }
1140 {
1141 ::DBus::Error error;
mukesh agrawal6bb9e7c2012-01-30 14:57:54 -08001142 EXPECT_TRUE(DBusAdaptor::SetProperty(manager()->mutable_store(),
1143 flimflam::kCountryProperty,
1144 PropertyStoreTest::kStringV,
1145 &error));
Chris Masonea8a2c252011-06-27 22:16:30 -07001146 }
Chris Masoneb925cc82011-06-22 15:39:57 -07001147 // Attempt to write with value of wrong type should return InvalidArgs.
Chris Masonea8a2c252011-06-27 22:16:30 -07001148 {
1149 ::DBus::Error error;
mukesh agrawal6bb9e7c2012-01-30 14:57:54 -08001150 EXPECT_FALSE(DBusAdaptor::SetProperty(manager()->mutable_store(),
1151 flimflam::kCountryProperty,
1152 PropertyStoreTest::kBoolV,
1153 &error));
Chris Masone9d779932011-08-25 16:33:41 -07001154 EXPECT_EQ(invalid_args(), error.name());
Chris Masonea8a2c252011-06-27 22:16:30 -07001155 }
1156 {
1157 ::DBus::Error error;
mukesh agrawal6bb9e7c2012-01-30 14:57:54 -08001158 EXPECT_FALSE(DBusAdaptor::SetProperty(manager()->mutable_store(),
1159 flimflam::kOfflineModeProperty,
1160 PropertyStoreTest::kStringV,
1161 &error));
Chris Masone9d779932011-08-25 16:33:41 -07001162 EXPECT_EQ(invalid_args(), error.name());
Chris Masonea8a2c252011-06-27 22:16:30 -07001163 }
Chris Masoneb925cc82011-06-22 15:39:57 -07001164 // Attempt to write R/O property should return InvalidArgs.
Chris Masonea8a2c252011-06-27 22:16:30 -07001165 {
1166 ::DBus::Error error;
mukesh agrawal6bb9e7c2012-01-30 14:57:54 -08001167 EXPECT_FALSE(DBusAdaptor::SetProperty(
mukesh agrawalde29fa82011-09-16 16:16:36 -07001168 manager()->mutable_store(),
Chris Masonea8a2c252011-06-27 22:16:30 -07001169 flimflam::kEnabledTechnologiesProperty,
1170 PropertyStoreTest::kStringsV,
1171 &error));
Chris Masone9d779932011-08-25 16:33:41 -07001172 EXPECT_EQ(invalid_args(), error.name());
Chris Masonea8a2c252011-06-27 22:16:30 -07001173 }
Chris Masone3bd3c8c2011-06-13 08:20:26 -07001174}
1175
mukesh agrawal32399322011-09-01 10:53:43 -07001176TEST_F(ManagerTest, RequestScan) {
1177 {
1178 Error error;
Paul Stewart22aa71b2011-09-16 12:15:11 -07001179 manager()->RegisterDevice(mock_devices_[0].get());
1180 manager()->RegisterDevice(mock_devices_[1].get());
Joshua Krollda798622012-06-05 12:30:48 -07001181 EXPECT_CALL(*mock_devices_[0], technology())
1182 .WillRepeatedly(Return(Technology::kWifi));
Paul Stewart22aa71b2011-09-16 12:15:11 -07001183 EXPECT_CALL(*mock_devices_[0], Scan(_));
Joshua Krollda798622012-06-05 12:30:48 -07001184 EXPECT_CALL(*mock_devices_[1], technology())
1185 .WillRepeatedly(Return(Technology::kUnknown));
Paul Stewart22aa71b2011-09-16 12:15:11 -07001186 EXPECT_CALL(*mock_devices_[1], Scan(_)).Times(0);
Chris Masone9d779932011-08-25 16:33:41 -07001187 manager()->RequestScan(flimflam::kTypeWifi, &error);
mukesh agrawal32399322011-09-01 10:53:43 -07001188 }
1189
1190 {
1191 Error error;
Chris Masone9d779932011-08-25 16:33:41 -07001192 manager()->RequestScan("bogus_device_type", &error);
mukesh agrawal32399322011-09-01 10:53:43 -07001193 EXPECT_EQ(Error::kInvalidArguments, error.type());
1194 }
1195}
1196
Darin Petkovb65c2452012-02-23 15:17:06 +01001197TEST_F(ManagerTest, GetServiceNoType) {
mukesh agrawal7a4e4002011-09-06 11:26:05 -07001198 KeyValueStore args;
1199 Error e;
Darin Petkovb65c2452012-02-23 15:17:06 +01001200 manager()->GetService(args, &e);
1201 EXPECT_EQ(Error::kInvalidArguments, e.type());
1202 EXPECT_EQ("must specify service type", e.message());
1203}
1204
1205TEST_F(ManagerTest, GetServiceUnknownType) {
1206 KeyValueStore args;
1207 Error e;
1208 args.SetString(flimflam::kTypeProperty, flimflam::kTypeEthernet);
1209 manager()->GetService(args, &e);
1210 EXPECT_EQ(Error::kNotSupported, e.type());
1211 EXPECT_EQ("service type is unsupported", e.message());
1212}
1213
1214TEST_F(ManagerTest, GetServiceNoWifiDevice) {
1215 KeyValueStore args;
1216 Error e;
1217 args.SetString(flimflam::kTypeProperty, flimflam::kTypeWifi);
1218 manager()->GetService(args, &e);
mukesh agrawal7a4e4002011-09-06 11:26:05 -07001219 EXPECT_EQ(Error::kInvalidArguments, e.type());
1220 EXPECT_EQ("no wifi devices available", e.message());
1221}
1222
Darin Petkovb65c2452012-02-23 15:17:06 +01001223TEST_F(ManagerTest, GetServiceWifi) {
mukesh agrawal7a4e4002011-09-06 11:26:05 -07001224 KeyValueStore args;
1225 Error e;
1226 WiFiServiceRefPtr wifi_service;
Darin Petkovb65c2452012-02-23 15:17:06 +01001227 args.SetString(flimflam::kTypeProperty, flimflam::kTypeWifi);
mukesh agrawal7a4e4002011-09-06 11:26:05 -07001228 manager()->RegisterDevice(mock_wifi_);
1229 EXPECT_CALL(*mock_wifi_, GetService(_, _))
1230 .WillRepeatedly(Return(wifi_service));
Darin Petkovb65c2452012-02-23 15:17:06 +01001231 manager()->GetService(args, &e);
1232 EXPECT_TRUE(e.IsSuccess());
1233}
1234
Darin Petkov33af05c2012-02-28 10:10:30 +01001235TEST_F(ManagerTest, GetServiceVPNUnknownType) {
1236 KeyValueStore args;
1237 Error e;
1238 args.SetString(flimflam::kTypeProperty, flimflam::kTypeVPN);
Paul Stewart7f5ad572012-06-04 15:18:54 -07001239 scoped_refptr<MockProfile> profile(
1240 new StrictMock<MockProfile>(control_interface(), manager(), ""));
1241 AdoptProfile(manager(), profile);
Darin Petkov33af05c2012-02-28 10:10:30 +01001242 ServiceRefPtr service = manager()->GetService(args, &e);
1243 EXPECT_EQ(Error::kNotSupported, e.type());
1244 EXPECT_FALSE(service);
1245}
1246
Darin Petkovb65c2452012-02-23 15:17:06 +01001247TEST_F(ManagerTest, GetServiceVPN) {
1248 KeyValueStore args;
1249 Error e;
Darin Petkovb65c2452012-02-23 15:17:06 +01001250 args.SetString(flimflam::kTypeProperty, flimflam::kTypeVPN);
Darin Petkov33af05c2012-02-28 10:10:30 +01001251 args.SetString(flimflam::kProviderTypeProperty, flimflam::kProviderOpenVpn);
Darin Petkov02867712012-03-12 14:25:05 +01001252 args.SetString(flimflam::kProviderHostProperty, "10.8.0.1");
1253 args.SetString(flimflam::kProviderNameProperty, "vpn-name");
Paul Stewart7f5ad572012-06-04 15:18:54 -07001254 scoped_refptr<MockProfile> profile(
1255 new StrictMock<MockProfile>(control_interface(), manager(), ""));
1256 AdoptProfile(manager(), profile);
1257 ServiceRefPtr updated_service;
1258 EXPECT_CALL(*profile, UpdateService(_))
1259 .WillOnce(DoAll(SaveArg<0>(&updated_service), Return(true)));
1260 ServiceRefPtr configured_service;
1261 EXPECT_CALL(*profile, ConfigureService(_))
1262 .WillOnce(DoAll(SaveArg<0>(&configured_service), Return(true)));
Darin Petkov33af05c2012-02-28 10:10:30 +01001263 ServiceRefPtr service = manager()->GetService(args, &e);
1264 EXPECT_TRUE(e.IsSuccess());
1265 EXPECT_TRUE(service);
Paul Stewart7f5ad572012-06-04 15:18:54 -07001266 EXPECT_EQ(service, updated_service);
1267 EXPECT_EQ(service, configured_service);
mukesh agrawal7a4e4002011-09-06 11:26:05 -07001268}
1269
Darin Petkovc63dcf02012-05-24 11:51:43 +02001270TEST_F(ManagerTest, GetServiceWiMaxNoNetworkId) {
1271 KeyValueStore args;
1272 Error e;
1273 args.SetString(flimflam::kTypeProperty, flimflam::kTypeWimax);
1274 ServiceRefPtr service = manager()->GetService(args, &e);
1275 EXPECT_EQ(Error::kInvalidArguments, e.type());
1276 EXPECT_EQ("Missing WiMAX network id.", e.message());
1277 EXPECT_FALSE(service);
1278}
1279
Darin Petkovd1cd7972012-05-22 15:26:15 +02001280TEST_F(ManagerTest, GetServiceWiMax) {
1281 KeyValueStore args;
1282 Error e;
1283 args.SetString(flimflam::kTypeProperty, flimflam::kTypeWimax);
Darin Petkovc63dcf02012-05-24 11:51:43 +02001284 args.SetString(WiMaxService::kNetworkIdProperty, "01234567");
1285 args.SetString(flimflam::kNameProperty, "WiMAX Network");
1286 ServiceRefPtr service = manager()->GetService(args, &e);
1287 EXPECT_TRUE(e.IsSuccess());
1288 EXPECT_TRUE(service);
Darin Petkovd1cd7972012-05-22 15:26:15 +02001289}
1290
Paul Stewart7f61e522012-03-22 11:13:45 -07001291TEST_F(ManagerTest, ConfigureServiceWithInvalidProfile) {
1292 // Manager calls ActiveProfile() so we need at least one profile installed.
1293 scoped_refptr<MockProfile> profile(
1294 new NiceMock<MockProfile>(control_interface(), manager(), ""));
1295 AdoptProfile(manager(), profile);
1296
1297 KeyValueStore args;
1298 args.SetString(flimflam::kProfileProperty, "xxx");
1299 Error error;
1300 manager()->ConfigureService(args, &error);
1301 EXPECT_EQ(Error::kInvalidArguments, error.type());
1302 EXPECT_EQ("Invalid profile name xxx", error.message());
1303}
1304
1305TEST_F(ManagerTest, ConfigureServiceWithGetServiceFailure) {
1306 // Manager calls ActiveProfile() so we need at least one profile installed.
1307 scoped_refptr<MockProfile> profile(
1308 new NiceMock<MockProfile>(control_interface(), manager(), ""));
1309 AdoptProfile(manager(), profile);
1310
1311 KeyValueStore args;
1312 Error error;
1313 manager()->ConfigureService(args, &error);
1314 EXPECT_EQ(Error::kInvalidArguments, error.type());
1315 EXPECT_EQ("must specify service type", error.message());
1316}
1317
1318// A registered service in the ephemeral profile should be moved to the
1319// active profile as a part of configuration if no profile was explicitly
1320// specified.
1321TEST_F(ManagerTest, ConfigureRegisteredServiceWithoutProfile) {
1322 scoped_refptr<MockProfile> profile(
1323 new NiceMock<MockProfile>(control_interface(), manager(), ""));
1324
1325 AdoptProfile(manager(), profile); // This is now the active profile.
1326
1327 const std::vector<uint8_t> ssid;
1328 scoped_refptr<MockWiFiService> service(
1329 new NiceMock<MockWiFiService>(control_interface(),
1330 dispatcher(),
1331 metrics(),
1332 manager(),
1333 mock_wifi_,
1334 ssid,
1335 "",
1336 "",
1337 false));
1338
1339 manager()->RegisterService(service);
1340 service->set_profile(GetEphemeralProfile(manager()));
1341
1342 // A separate MockWiFi from mock_wifi_ is used in the Manager since using
1343 // the same device as that used above causes a refcounting loop.
1344 scoped_refptr<MockWiFi> wifi(new NiceMock<MockWiFi>(control_interface(),
1345 dispatcher(),
1346 metrics(),
1347 manager(),
1348 "wifi1",
1349 "addr5",
1350 5));
1351 manager()->RegisterDevice(wifi);
1352 EXPECT_CALL(*wifi, GetService(_, _))
1353 .WillOnce(Return(service));
1354 EXPECT_CALL(*profile, UpdateService(ServiceRefPtr(service.get())))
1355 .WillOnce(Return(true));
1356 EXPECT_CALL(*profile, AdoptService(ServiceRefPtr(service.get())))
1357 .WillOnce(Return(true));
1358
1359 KeyValueStore args;
1360 args.SetString(flimflam::kTypeProperty, flimflam::kTypeWifi);
1361 Error error;
1362 manager()->ConfigureService(args, &error);
1363 EXPECT_TRUE(error.IsSuccess());
1364}
1365
1366// If were configure a service that was already registered and explicitly
1367// specify a profile, it should be moved from the profile it was previously
1368// in to the specified profile if one was requested.
1369TEST_F(ManagerTest, ConfigureRegisteredServiceWithProfile) {
1370 scoped_refptr<MockProfile> profile0(
1371 new NiceMock<MockProfile>(control_interface(), manager(), ""));
1372 scoped_refptr<MockProfile> profile1(
1373 new NiceMock<MockProfile>(control_interface(), manager(), ""));
1374
1375 const string kProfileName0 = "profile0";
1376 const string kProfileName1 = "profile1";
1377
1378 EXPECT_CALL(*profile0, GetRpcIdentifier())
1379 .WillRepeatedly(Return(kProfileName0));
1380 EXPECT_CALL(*profile1, GetRpcIdentifier())
1381 .WillRepeatedly(Return(kProfileName1));
1382
1383 AdoptProfile(manager(), profile0);
1384 AdoptProfile(manager(), profile1); // profile1 is now the ActiveProfile.
1385
1386 const std::vector<uint8_t> ssid;
1387 scoped_refptr<MockWiFiService> service(
1388 new NiceMock<MockWiFiService>(control_interface(),
1389 dispatcher(),
1390 metrics(),
1391 manager(),
1392 mock_wifi_,
1393 ssid,
1394 "",
1395 "",
1396 false));
1397
1398 manager()->RegisterService(service);
1399 service->set_profile(profile1);
1400
1401 // A separate MockWiFi from mock_wifi_ is used in the Manager since using
1402 // the same device as that used above causes a refcounting loop.
1403 scoped_refptr<MockWiFi> wifi(new NiceMock<MockWiFi>(control_interface(),
1404 dispatcher(),
1405 metrics(),
1406 manager(),
1407 "wifi1",
1408 "addr5",
1409 5));
1410 manager()->RegisterDevice(wifi);
1411 EXPECT_CALL(*wifi, GetService(_, _))
1412 .WillOnce(Return(service));
1413 EXPECT_CALL(*profile0, UpdateService(ServiceRefPtr(service.get())))
1414 .WillOnce(Return(true));
1415 EXPECT_CALL(*profile0, AdoptService(ServiceRefPtr(service.get())))
1416 .WillOnce(Return(true));
1417 EXPECT_CALL(*profile1, AbandonService(ServiceRefPtr(service.get())))
1418 .WillOnce(Return(true));
1419
1420 KeyValueStore args;
1421 args.SetString(flimflam::kTypeProperty, flimflam::kTypeWifi);
1422 args.SetString(flimflam::kProfileProperty, kProfileName0);
1423 Error error;
1424 manager()->ConfigureService(args, &error);
1425 EXPECT_TRUE(error.IsSuccess());
1426 service->set_profile(NULL); // Breaks refcounting loop.
1427}
1428
1429// An unregistered service should remain unregistered, but its contents should
1430// be saved to the specified profile nonetheless.
1431TEST_F(ManagerTest, ConfigureUnregisteredServiceWithProfile) {
1432 scoped_refptr<MockProfile> profile0(
1433 new NiceMock<MockProfile>(control_interface(), manager(), ""));
1434 scoped_refptr<MockProfile> profile1(
1435 new NiceMock<MockProfile>(control_interface(), manager(), ""));
1436
1437 const string kProfileName0 = "profile0";
1438 const string kProfileName1 = "profile1";
1439
1440 EXPECT_CALL(*profile0, GetRpcIdentifier())
1441 .WillRepeatedly(Return(kProfileName0));
1442 EXPECT_CALL(*profile1, GetRpcIdentifier())
1443 .WillRepeatedly(Return(kProfileName1));
1444
1445 AdoptProfile(manager(), profile0);
1446 AdoptProfile(manager(), profile1); // profile1 is now the ActiveProfile.
1447
1448 const std::vector<uint8_t> ssid;
1449 scoped_refptr<MockWiFiService> service(
1450 new NiceMock<MockWiFiService>(control_interface(),
1451 dispatcher(),
1452 metrics(),
1453 manager(),
1454 mock_wifi_,
1455 ssid,
1456 "",
1457 "",
1458 false));
1459
1460 service->set_profile(profile1);
1461
1462 // A separate MockWiFi from mock_wifi_ is used in the Manager since using
1463 // the same device as that used above causes a refcounting loop.
1464 scoped_refptr<MockWiFi> wifi(new NiceMock<MockWiFi>(control_interface(),
1465 dispatcher(),
1466 metrics(),
1467 manager(),
1468 "wifi1",
1469 "addr5",
1470 5));
1471 manager()->RegisterDevice(wifi);
1472 EXPECT_CALL(*wifi, GetService(_, _))
1473 .WillOnce(Return(service));
1474 EXPECT_CALL(*profile0, UpdateService(ServiceRefPtr(service.get())))
1475 .WillOnce(Return(true));
1476 EXPECT_CALL(*profile0, AdoptService(_))
1477 .Times(0);
1478 EXPECT_CALL(*profile1, AdoptService(_))
1479 .Times(0);
1480
1481 KeyValueStore args;
1482 args.SetString(flimflam::kTypeProperty, flimflam::kTypeWifi);
1483 args.SetString(flimflam::kProfileProperty, kProfileName0);
1484 Error error;
1485 manager()->ConfigureService(args, &error);
1486 EXPECT_TRUE(error.IsSuccess());
1487}
1488
Paul Stewart22aa71b2011-09-16 12:15:11 -07001489TEST_F(ManagerTest, TechnologyOrder) {
1490 Error error;
1491 manager()->SetTechnologyOrder(string(flimflam::kTypeEthernet) + "," +
1492 string(flimflam::kTypeWifi), &error);
1493 ASSERT_TRUE(error.IsSuccess());
1494 EXPECT_EQ(manager()->GetTechnologyOrder(),
1495 string(flimflam::kTypeEthernet) + "," +
1496 string(flimflam::kTypeWifi));
1497
1498 manager()->SetTechnologyOrder(string(flimflam::kTypeEthernet) + "x," +
1499 string(flimflam::kTypeWifi), &error);
1500 ASSERT_FALSE(error.IsSuccess());
1501 EXPECT_EQ(Error::kInvalidArguments, error.type());
1502 EXPECT_EQ(string(flimflam::kTypeEthernet) + "," +
1503 string(flimflam::kTypeWifi),
1504 manager()->GetTechnologyOrder());
1505}
1506
1507TEST_F(ManagerTest, SortServices) {
mukesh agrawal00917ce2011-11-22 23:56:55 +00001508 // TODO(quiche): Some of these tests would probably fit better in
1509 // service_unittest, since the actual comparison of Services is
1510 // implemented in Service. (crosbug.com/23370)
1511
Paul Stewart22aa71b2011-09-16 12:15:11 -07001512 scoped_refptr<MockService> mock_service0(
1513 new NiceMock<MockService>(control_interface(),
1514 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -08001515 metrics(),
Paul Stewart22aa71b2011-09-16 12:15:11 -07001516 manager()));
1517 scoped_refptr<MockService> mock_service1(
1518 new NiceMock<MockService>(control_interface(),
1519 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -08001520 metrics(),
Paul Stewart22aa71b2011-09-16 12:15:11 -07001521 manager()));
Paul Stewart22aa71b2011-09-16 12:15:11 -07001522
1523 manager()->RegisterService(mock_service0);
1524 manager()->RegisterService(mock_service1);
1525
1526 // Services should already be sorted by UniqueName
1527 EXPECT_TRUE(ServiceOrderIs(mock_service0, mock_service1));
1528
1529 // Asking explictly to sort services should not change anything
Paul Stewartdfa46052012-06-26 09:44:14 -07001530 manager()->SortServicesTask();
Paul Stewart22aa71b2011-09-16 12:15:11 -07001531 EXPECT_TRUE(ServiceOrderIs(mock_service0, mock_service1));
1532
1533 // Two otherwise equal services should be reordered by strength
Darin Petkovd78ee7e2012-01-12 11:21:10 +01001534 mock_service1->SetStrength(1);
Paul Stewart22aa71b2011-09-16 12:15:11 -07001535 manager()->UpdateService(mock_service1);
1536 EXPECT_TRUE(ServiceOrderIs(mock_service1, mock_service0));
1537
1538 // Security
Paul Stewart1ca3e852011-11-04 07:50:49 -07001539 mock_service0->set_security_level(1);
Paul Stewart22aa71b2011-09-16 12:15:11 -07001540 manager()->UpdateService(mock_service0);
1541 EXPECT_TRUE(ServiceOrderIs(mock_service0, mock_service1));
1542
1543 // Technology
Joshua Kroll053fa822012-06-05 09:50:43 -07001544 EXPECT_CALL(*mock_service0.get(), technology())
1545 .WillRepeatedly(Return((Technology::kWifi)));
1546 EXPECT_CALL(*mock_service1.get(), technology())
1547 .WillRepeatedly(Return(Technology::kEthernet));
Paul Stewart22aa71b2011-09-16 12:15:11 -07001548
1549 Error error;
mukesh agrawal84de5d22012-02-17 19:29:15 -08001550 // Default technology ordering should favor Ethernet over WiFi.
Paul Stewartdfa46052012-06-26 09:44:14 -07001551 manager()->SortServicesTask();
Paul Stewart22aa71b2011-09-16 12:15:11 -07001552 EXPECT_TRUE(ServiceOrderIs(mock_service1, mock_service0));
1553
1554 manager()->SetTechnologyOrder(string(flimflam::kTypeWifi) + "," +
1555 string(flimflam::kTypeEthernet), &error);
1556 EXPECT_TRUE(error.IsSuccess());
1557 EXPECT_TRUE(ServiceOrderIs(mock_service0, mock_service1));
1558
Gaurav Shah435de2c2011-11-17 19:01:07 -08001559 // Priority.
Paul Stewart22aa71b2011-09-16 12:15:11 -07001560 mock_service0->set_priority(1);
1561 manager()->UpdateService(mock_service0);
1562 EXPECT_TRUE(ServiceOrderIs(mock_service0, mock_service1));
1563
mukesh agrawal8a3188d2011-12-01 20:56:44 +00001564 // Favorite.
mukesh agrawal00917ce2011-11-22 23:56:55 +00001565 mock_service1->MakeFavorite();
Paul Stewart22aa71b2011-09-16 12:15:11 -07001566 manager()->UpdateService(mock_service1);
1567 EXPECT_TRUE(ServiceOrderIs(mock_service1, mock_service0));
1568
mukesh agrawal8a3188d2011-12-01 20:56:44 +00001569 // Auto-connect.
1570 mock_service0->set_auto_connect(true);
Paul Stewart22aa71b2011-09-16 12:15:11 -07001571 manager()->UpdateService(mock_service0);
mukesh agrawal8a3188d2011-12-01 20:56:44 +00001572 mock_service1->set_auto_connect(false);
1573 manager()->UpdateService(mock_service1);
Paul Stewart22aa71b2011-09-16 12:15:11 -07001574 EXPECT_TRUE(ServiceOrderIs(mock_service0, mock_service1));
1575
mukesh agrawal8a3188d2011-12-01 20:56:44 +00001576 // Connectable.
1577 mock_service1->set_connectable(true);
1578 manager()->UpdateService(mock_service1);
1579 mock_service0->set_connectable(false);
1580 manager()->UpdateService(mock_service0);
1581 EXPECT_TRUE(ServiceOrderIs(mock_service1, mock_service0));
1582
1583 // IsFailed.
1584 EXPECT_CALL(*mock_service0.get(), state())
1585 .WillRepeatedly(Return(Service::kStateIdle));
1586 EXPECT_CALL(*mock_service0.get(), IsFailed())
1587 .WillRepeatedly(Return(false));
1588 manager()->UpdateService(mock_service0);
1589 EXPECT_CALL(*mock_service0.get(), state())
1590 .WillRepeatedly(Return(Service::kStateFailure));
1591 EXPECT_CALL(*mock_service1.get(), IsFailed())
1592 .WillRepeatedly(Return(true));
1593 manager()->UpdateService(mock_service1);
1594 EXPECT_TRUE(ServiceOrderIs(mock_service0, mock_service1));
1595
1596 // Connecting.
Paul Stewart22aa71b2011-09-16 12:15:11 -07001597 EXPECT_CALL(*mock_service1.get(), state())
mukesh agrawal8a3188d2011-12-01 20:56:44 +00001598 .WillRepeatedly(Return(Service::kStateAssociating));
1599 EXPECT_CALL(*mock_service1.get(), IsConnecting())
Gaurav Shah435de2c2011-11-17 19:01:07 -08001600 .WillRepeatedly(Return(true));
Paul Stewart22aa71b2011-09-16 12:15:11 -07001601 manager()->UpdateService(mock_service1);
1602 EXPECT_TRUE(ServiceOrderIs(mock_service1, mock_service0));
1603
mukesh agrawal8a3188d2011-12-01 20:56:44 +00001604 // Connected.
1605 EXPECT_CALL(*mock_service0.get(), state())
Paul Stewarta121c442012-06-09 14:12:58 -07001606 .WillRepeatedly(Return(Service::kStatePortal));
mukesh agrawal8a3188d2011-12-01 20:56:44 +00001607 EXPECT_CALL(*mock_service0.get(), IsConnected())
1608 .WillRepeatedly(Return(true));
1609 manager()->UpdateService(mock_service0);
1610 EXPECT_TRUE(ServiceOrderIs(mock_service0, mock_service1));
1611
Paul Stewarta121c442012-06-09 14:12:58 -07001612 // Portal.
1613 EXPECT_CALL(*mock_service1.get(), state())
1614 .WillRepeatedly(Return(Service::kStateConnected));
1615 EXPECT_CALL(*mock_service1.get(), IsConnected())
1616 .WillRepeatedly(Return(true));
1617 manager()->UpdateService(mock_service1);
1618 EXPECT_TRUE(ServiceOrderIs(mock_service1, mock_service0));
1619
Paul Stewart22aa71b2011-09-16 12:15:11 -07001620 manager()->DeregisterService(mock_service0);
1621 manager()->DeregisterService(mock_service1);
1622}
1623
Paul Stewartc1dec4d2011-12-08 15:25:28 -08001624TEST_F(ManagerTest, SortServicesWithConnection) {
Thieu Lea20cbc22012-01-09 22:01:43 +00001625 MockMetrics mock_metrics;
1626 manager()->set_metrics(&mock_metrics);
1627
Paul Stewartc1dec4d2011-12-08 15:25:28 -08001628 scoped_refptr<MockService> mock_service0(
1629 new NiceMock<MockService>(control_interface(),
1630 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -08001631 metrics(),
Paul Stewartc1dec4d2011-12-08 15:25:28 -08001632 manager()));
1633 scoped_refptr<MockService> mock_service1(
1634 new NiceMock<MockService>(control_interface(),
1635 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -08001636 metrics(),
Paul Stewartc1dec4d2011-12-08 15:25:28 -08001637 manager()));
1638
1639 scoped_refptr<MockConnection> mock_connection0(
1640 new NiceMock<MockConnection>(device_info_.get()));
1641 scoped_refptr<MockConnection> mock_connection1(
1642 new NiceMock<MockConnection>(device_info_.get()));
1643
Paul Stewarte2bad7c2012-03-14 08:55:33 -07001644 EXPECT_CALL(mock_metrics, NotifyDefaultServiceChanged(NULL));
Paul Stewartc1dec4d2011-12-08 15:25:28 -08001645 manager()->RegisterService(mock_service0);
Paul Stewartdfa46052012-06-26 09:44:14 -07001646 CompleteServiceSort();
Paul Stewarte2bad7c2012-03-14 08:55:33 -07001647 EXPECT_CALL(mock_metrics, NotifyDefaultServiceChanged(NULL));
Paul Stewartc1dec4d2011-12-08 15:25:28 -08001648 manager()->RegisterService(mock_service1);
Paul Stewartdfa46052012-06-26 09:44:14 -07001649 CompleteServiceSort();
Paul Stewartc1dec4d2011-12-08 15:25:28 -08001650
Paul Stewarte2bad7c2012-03-14 08:55:33 -07001651 EXPECT_CALL(mock_metrics, NotifyDefaultServiceChanged(NULL));
Paul Stewartdfa46052012-06-26 09:44:14 -07001652 manager()->SortServicesTask();
Paul Stewarte2bad7c2012-03-14 08:55:33 -07001653
1654 mock_service1->set_priority(1);
1655 EXPECT_CALL(mock_metrics, NotifyDefaultServiceChanged(NULL));
Paul Stewartdfa46052012-06-26 09:44:14 -07001656 manager()->SortServicesTask();
Paul Stewarte2bad7c2012-03-14 08:55:33 -07001657
1658 mock_service1->set_priority(0);
1659 EXPECT_CALL(mock_metrics, NotifyDefaultServiceChanged(NULL));
Paul Stewartdfa46052012-06-26 09:44:14 -07001660 manager()->SortServicesTask();
Paul Stewarte2bad7c2012-03-14 08:55:33 -07001661
Paul Stewartce4ec192012-03-14 12:53:46 -07001662 mock_service0->set_mock_connection(mock_connection0);
1663 mock_service1->set_mock_connection(mock_connection1);
Paul Stewartc1dec4d2011-12-08 15:25:28 -08001664
1665 EXPECT_CALL(*mock_connection0.get(), SetIsDefault(true));
Thieu Lea20cbc22012-01-09 22:01:43 +00001666 EXPECT_CALL(mock_metrics, NotifyDefaultServiceChanged(mock_service0.get()));
Paul Stewartdfa46052012-06-26 09:44:14 -07001667 manager()->SortServicesTask();
Paul Stewartc1dec4d2011-12-08 15:25:28 -08001668
1669 mock_service1->set_priority(1);
1670 EXPECT_CALL(*mock_connection0.get(), SetIsDefault(false));
1671 EXPECT_CALL(*mock_connection1.get(), SetIsDefault(true));
Thieu Lea20cbc22012-01-09 22:01:43 +00001672 EXPECT_CALL(mock_metrics, NotifyDefaultServiceChanged(mock_service1.get()));
Paul Stewartdfa46052012-06-26 09:44:14 -07001673 manager()->SortServicesTask();
Paul Stewartc1dec4d2011-12-08 15:25:28 -08001674
1675 EXPECT_CALL(*mock_connection0.get(), SetIsDefault(true));
Thieu Lea20cbc22012-01-09 22:01:43 +00001676 EXPECT_CALL(mock_metrics, NotifyDefaultServiceChanged(mock_service0.get()));
Paul Stewartce4ec192012-03-14 12:53:46 -07001677 mock_service1->set_mock_connection(NULL);
Paul Stewartc1dec4d2011-12-08 15:25:28 -08001678 manager()->DeregisterService(mock_service1);
Paul Stewartdfa46052012-06-26 09:44:14 -07001679 CompleteServiceSort();
Paul Stewartc1dec4d2011-12-08 15:25:28 -08001680
Paul Stewartce4ec192012-03-14 12:53:46 -07001681 mock_service0->set_mock_connection(NULL);
Paul Stewarte2bad7c2012-03-14 08:55:33 -07001682 EXPECT_CALL(mock_metrics, NotifyDefaultServiceChanged(NULL));
Paul Stewartc1dec4d2011-12-08 15:25:28 -08001683 manager()->DeregisterService(mock_service0);
Paul Stewartdfa46052012-06-26 09:44:14 -07001684 CompleteServiceSort();
Paul Stewarte2bad7c2012-03-14 08:55:33 -07001685
1686 EXPECT_CALL(mock_metrics, NotifyDefaultServiceChanged(NULL));
Paul Stewartdfa46052012-06-26 09:44:14 -07001687 manager()->SortServicesTask();
Paul Stewartc1dec4d2011-12-08 15:25:28 -08001688}
1689
Gaurav Shah435de2c2011-11-17 19:01:07 -08001690TEST_F(ManagerTest, AvailableTechnologies) {
1691 mock_devices_.push_back(new NiceMock<MockDevice>(control_interface(),
1692 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -08001693 metrics(),
Gaurav Shah435de2c2011-11-17 19:01:07 -08001694 manager(),
1695 "null4",
1696 "addr4",
1697 0));
1698 manager()->RegisterDevice(mock_devices_[0]);
1699 manager()->RegisterDevice(mock_devices_[1]);
1700 manager()->RegisterDevice(mock_devices_[2]);
1701 manager()->RegisterDevice(mock_devices_[3]);
1702
1703 ON_CALL(*mock_devices_[0].get(), technology())
1704 .WillByDefault(Return(Technology::kEthernet));
1705 ON_CALL(*mock_devices_[1].get(), technology())
1706 .WillByDefault(Return(Technology::kWifi));
1707 ON_CALL(*mock_devices_[2].get(), technology())
1708 .WillByDefault(Return(Technology::kCellular));
1709 ON_CALL(*mock_devices_[3].get(), technology())
1710 .WillByDefault(Return(Technology::kWifi));
1711
1712 set<string> expected_technologies;
1713 expected_technologies.insert(Technology::NameFromIdentifier(
1714 Technology::kEthernet));
1715 expected_technologies.insert(Technology::NameFromIdentifier(
1716 Technology::kWifi));
1717 expected_technologies.insert(Technology::NameFromIdentifier(
1718 Technology::kCellular));
1719 Error error;
1720 vector<string> technologies = manager()->AvailableTechnologies(&error);
1721
1722 EXPECT_THAT(set<string>(technologies.begin(), technologies.end()),
1723 ContainerEq(expected_technologies));
1724}
1725
1726TEST_F(ManagerTest, ConnectedTechnologies) {
1727 scoped_refptr<MockService> connected_service1(
1728 new NiceMock<MockService>(control_interface(),
1729 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -08001730 metrics(),
Gaurav Shah435de2c2011-11-17 19:01:07 -08001731 manager()));
1732 scoped_refptr<MockService> connected_service2(
1733 new NiceMock<MockService>(control_interface(),
1734 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -08001735 metrics(),
Gaurav Shah435de2c2011-11-17 19:01:07 -08001736 manager()));
1737 scoped_refptr<MockService> disconnected_service1(
1738 new NiceMock<MockService>(control_interface(),
1739 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -08001740 metrics(),
Gaurav Shah435de2c2011-11-17 19:01:07 -08001741 manager()));
1742 scoped_refptr<MockService> disconnected_service2(
1743 new NiceMock<MockService>(control_interface(),
1744 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -08001745 metrics(),
Gaurav Shah435de2c2011-11-17 19:01:07 -08001746 manager()));
1747
1748 ON_CALL(*connected_service1.get(), IsConnected())
1749 .WillByDefault(Return(true));
1750 ON_CALL(*connected_service2.get(), IsConnected())
1751 .WillByDefault(Return(true));
1752
1753 manager()->RegisterService(connected_service1);
1754 manager()->RegisterService(connected_service2);
1755 manager()->RegisterService(disconnected_service1);
1756 manager()->RegisterService(disconnected_service2);
1757
1758 manager()->RegisterDevice(mock_devices_[0]);
1759 manager()->RegisterDevice(mock_devices_[1]);
1760 manager()->RegisterDevice(mock_devices_[2]);
1761 manager()->RegisterDevice(mock_devices_[3]);
1762
1763 ON_CALL(*mock_devices_[0].get(), technology())
1764 .WillByDefault(Return(Technology::kEthernet));
1765 ON_CALL(*mock_devices_[1].get(), technology())
1766 .WillByDefault(Return(Technology::kWifi));
1767 ON_CALL(*mock_devices_[2].get(), technology())
1768 .WillByDefault(Return(Technology::kCellular));
1769 ON_CALL(*mock_devices_[3].get(), technology())
1770 .WillByDefault(Return(Technology::kWifi));
1771
1772 mock_devices_[0]->SelectService(connected_service1);
1773 mock_devices_[1]->SelectService(disconnected_service1);
1774 mock_devices_[2]->SelectService(disconnected_service2);
1775 mock_devices_[3]->SelectService(connected_service2);
1776
1777 set<string> expected_technologies;
1778 expected_technologies.insert(Technology::NameFromIdentifier(
1779 Technology::kEthernet));
1780 expected_technologies.insert(Technology::NameFromIdentifier(
1781 Technology::kWifi));
1782 Error error;
1783
1784 vector<string> technologies = manager()->ConnectedTechnologies(&error);
1785 EXPECT_THAT(set<string>(technologies.begin(), technologies.end()),
1786 ContainerEq(expected_technologies));
1787}
1788
1789TEST_F(ManagerTest, DefaultTechnology) {
1790 scoped_refptr<MockService> connected_service(
1791 new NiceMock<MockService>(control_interface(),
1792 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -08001793 metrics(),
Gaurav Shah435de2c2011-11-17 19:01:07 -08001794 manager()));
1795 scoped_refptr<MockService> disconnected_service(
1796 new NiceMock<MockService>(control_interface(),
1797 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -08001798 metrics(),
Gaurav Shah435de2c2011-11-17 19:01:07 -08001799 manager()));
1800
1801 // Connected. WiFi.
1802 ON_CALL(*connected_service.get(), IsConnected())
1803 .WillByDefault(Return(true));
1804 ON_CALL(*connected_service.get(), state())
1805 .WillByDefault(Return(Service::kStateConnected));
1806 ON_CALL(*connected_service.get(), technology())
1807 .WillByDefault(Return(Technology::kWifi));
1808
1809 // Disconnected. Ethernet.
1810 ON_CALL(*disconnected_service.get(), technology())
1811 .WillByDefault(Return(Technology::kEthernet));
1812
1813 manager()->RegisterService(disconnected_service);
Paul Stewartdfa46052012-06-26 09:44:14 -07001814 CompleteServiceSort();
Gaurav Shah435de2c2011-11-17 19:01:07 -08001815 Error error;
1816 EXPECT_THAT(manager()->DefaultTechnology(&error), StrEq(""));
1817
1818
1819 manager()->RegisterService(connected_service);
Paul Stewartdfa46052012-06-26 09:44:14 -07001820 CompleteServiceSort();
Gaurav Shah435de2c2011-11-17 19:01:07 -08001821 // Connected service should be brought to the front now.
1822 string expected_technology =
1823 Technology::NameFromIdentifier(Technology::kWifi);
1824 EXPECT_THAT(manager()->DefaultTechnology(&error), StrEq(expected_technology));
1825}
1826
Thieu Le1271d682011-11-02 22:48:19 +00001827TEST_F(ManagerTest, DisconnectServicesOnStop) {
1828 scoped_refptr<MockService> mock_service(
1829 new NiceMock<MockService>(control_interface(),
1830 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -08001831 metrics(),
Thieu Le1271d682011-11-02 22:48:19 +00001832 manager()));
1833 manager()->RegisterService(mock_service);
mukesh agrawal0ed0f2e2011-12-05 20:36:17 +00001834 EXPECT_CALL(*mock_service.get(), Disconnect(_)).Times(1);
Thieu Le1271d682011-11-02 22:48:19 +00001835 manager()->Stop();
1836}
1837
mukesh agrawal00917ce2011-11-22 23:56:55 +00001838TEST_F(ManagerTest, UpdateServiceConnected) {
1839 scoped_refptr<MockService> mock_service(
1840 new NiceMock<MockService>(control_interface(),
1841 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -08001842 metrics(),
mukesh agrawal00917ce2011-11-22 23:56:55 +00001843 manager()));
1844 manager()->RegisterService(mock_service);
1845 EXPECT_FALSE(mock_service->favorite());
1846 EXPECT_FALSE(mock_service->auto_connect());
1847
Gaurav Shah435de2c2011-11-17 19:01:07 -08001848 EXPECT_CALL(*mock_service.get(), IsConnected())
1849 .WillRepeatedly(Return(true));
mukesh agrawal00917ce2011-11-22 23:56:55 +00001850 manager()->UpdateService(mock_service);
1851 // We can't EXPECT_CALL(..., MakeFavorite), because that requires us
1852 // to mock out MakeFavorite. And mocking that out would break the
1853 // SortServices test. (crosbug.com/23370)
1854 EXPECT_TRUE(mock_service->favorite());
1855 EXPECT_TRUE(mock_service->auto_connect());
1856}
1857
Thieu Led4e9e552012-02-16 16:26:07 -08001858TEST_F(ManagerTest, UpdateServiceConnectedPersistFavorite) {
1859 // This tests the case where the user connects to a service that is
1860 // currently associated with a profile. We want to make sure that the
1861 // favorite flag is set and that the flag is saved to the current
1862 // profile.
1863 scoped_refptr<MockService> mock_service(
1864 new NiceMock<MockService>(control_interface(),
1865 dispatcher(),
1866 metrics(),
1867 manager()));
1868 manager()->RegisterService(mock_service);
1869 EXPECT_FALSE(mock_service->favorite());
1870 EXPECT_FALSE(mock_service->auto_connect());
1871
Gary Moraind93615e2012-04-27 11:50:03 -07001872 scoped_refptr<MockProfile> profile(
1873 new MockProfile(control_interface(), manager(), ""));
Thieu Led4e9e552012-02-16 16:26:07 -08001874
Gary Moraind93615e2012-04-27 11:50:03 -07001875 mock_service->set_profile(profile);
1876 EXPECT_CALL(*mock_service, IsConnected())
Thieu Led4e9e552012-02-16 16:26:07 -08001877 .WillRepeatedly(Return(true));
Gary Moraind93615e2012-04-27 11:50:03 -07001878 EXPECT_CALL(*profile,
1879 UpdateService(static_cast<ServiceRefPtr>(mock_service)));
Thieu Led4e9e552012-02-16 16:26:07 -08001880 manager()->UpdateService(mock_service);
1881 // We can't EXPECT_CALL(..., MakeFavorite), because that requires us
1882 // to mock out MakeFavorite. And mocking that out would break the
1883 // SortServices test. (crosbug.com/23370)
1884 EXPECT_TRUE(mock_service->favorite());
1885 EXPECT_TRUE(mock_service->auto_connect());
Gary Moraind93615e2012-04-27 11:50:03 -07001886 // This releases the ref on the mock profile.
1887 mock_service->set_profile(NULL);
Thieu Led4e9e552012-02-16 16:26:07 -08001888}
1889
Paul Stewart3d9bcf52011-12-12 15:02:22 -08001890TEST_F(ManagerTest, SaveSuccessfulService) {
1891 scoped_refptr<MockProfile> profile(
1892 new StrictMock<MockProfile>(control_interface(), manager(), ""));
1893 AdoptProfile(manager(), profile);
1894 scoped_refptr<MockService> service(
1895 new NiceMock<MockService>(control_interface(),
1896 dispatcher(),
Thieu Le3426c8f2012-01-11 17:35:11 -08001897 metrics(),
Paul Stewart3d9bcf52011-12-12 15:02:22 -08001898 manager()));
1899
1900 // Re-cast this back to a ServiceRefPtr, so EXPECT arguments work correctly.
1901 ServiceRefPtr expect_service(service.get());
1902
1903 EXPECT_CALL(*profile.get(), ConfigureService(expect_service))
1904 .WillOnce(Return(false));
1905 manager()->RegisterService(service);
1906
1907 EXPECT_CALL(*service.get(), state())
1908 .WillRepeatedly(Return(Service::kStateConnected));
1909 EXPECT_CALL(*service.get(), IsConnected())
1910 .WillRepeatedly(Return(true));
1911 EXPECT_CALL(*profile.get(), AdoptService(expect_service))
1912 .WillOnce(Return(true));
1913 manager()->UpdateService(service);
1914}
1915
Darin Petkove7c6ad32012-06-29 10:22:09 +02001916TEST_F(ManagerTest, UpdateDevice) {
1917 MockProfile *profile0 = new MockProfile(control_interface(), manager(), "");
1918 MockProfile *profile1 = new MockProfile(control_interface(), manager(), "");
1919 MockProfile *profile2 = new MockProfile(control_interface(), manager(), "");
1920 AdoptProfile(manager(), profile0); // Passes ownership.
1921 AdoptProfile(manager(), profile1); // Passes ownership.
1922 AdoptProfile(manager(), profile2); // Passes ownership.
1923 DeviceRefPtr device_ref(mock_devices_[0].get());
1924 EXPECT_CALL(*profile0, UpdateDevice(device_ref)).Times(0);
1925 EXPECT_CALL(*profile1, UpdateDevice(device_ref)).WillOnce(Return(true));
1926 EXPECT_CALL(*profile2, UpdateDevice(device_ref)).WillOnce(Return(false));
1927 manager()->UpdateDevice(mock_devices_[0]);
1928}
1929
Paul Stewart1b253142012-01-26 14:05:52 -08001930TEST_F(ManagerTest, EnumerateProfiles) {
1931 vector<string> profile_paths;
1932 for (size_t i = 0; i < 10; i++) {
1933 scoped_refptr<MockProfile> profile(
1934 new StrictMock<MockProfile>(control_interface(), manager(), ""));
Jason Glasgow5d8197b2012-01-27 08:37:32 -05001935 profile_paths.push_back(base::StringPrintf("/profile/%zd", i));
Paul Stewart1b253142012-01-26 14:05:52 -08001936 EXPECT_CALL(*profile.get(), GetRpcIdentifier())
1937 .WillOnce(Return(profile_paths.back()));
1938 AdoptProfile(manager(), profile);
1939 }
1940
1941 Error error;
1942 vector<string> returned_paths = manager()->EnumerateProfiles(&error);
1943 EXPECT_TRUE(error.IsSuccess());
1944 EXPECT_EQ(profile_paths.size(), returned_paths.size());
1945 for (size_t i = 0; i < profile_paths.size(); i++) {
1946 EXPECT_EQ(profile_paths[i], returned_paths[i]);
1947 }
1948}
1949
mukesh agrawal8a3188d2011-12-01 20:56:44 +00001950TEST_F(ManagerTest, AutoConnectOnRegister) {
1951 MockServiceRefPtr service = MakeAutoConnectableService();
1952 EXPECT_CALL(*service.get(), AutoConnect());
1953 manager()->RegisterService(service);
1954 dispatcher()->DispatchPendingEvents();
1955}
1956
1957TEST_F(ManagerTest, AutoConnectOnUpdate) {
1958 MockServiceRefPtr service1 = MakeAutoConnectableService();
1959 service1->set_priority(1);
1960 MockServiceRefPtr service2 = MakeAutoConnectableService();
1961 service2->set_priority(2);
1962 manager()->RegisterService(service1);
1963 manager()->RegisterService(service2);
1964 dispatcher()->DispatchPendingEvents();
1965
1966 EXPECT_CALL(*service1.get(), AutoConnect());
1967 EXPECT_CALL(*service2.get(), state())
1968 .WillRepeatedly(Return(Service::kStateFailure));
1969 EXPECT_CALL(*service2.get(), IsFailed())
1970 .WillRepeatedly(Return(true));
1971 EXPECT_CALL(*service2.get(), IsConnected())
1972 .WillRepeatedly(Return(false));
1973 manager()->UpdateService(service2);
1974 dispatcher()->DispatchPendingEvents();
1975}
1976
1977TEST_F(ManagerTest, AutoConnectOnDeregister) {
1978 MockServiceRefPtr service1 = MakeAutoConnectableService();
1979 service1->set_priority(1);
1980 MockServiceRefPtr service2 = MakeAutoConnectableService();
1981 service2->set_priority(2);
1982 manager()->RegisterService(service1);
1983 manager()->RegisterService(service2);
1984 dispatcher()->DispatchPendingEvents();
1985
1986 EXPECT_CALL(*service1.get(), AutoConnect());
1987 manager()->DeregisterService(service2);
1988 dispatcher()->DispatchPendingEvents();
1989}
1990
Paul Stewartc681fa02012-03-02 19:40:04 -08001991TEST_F(ManagerTest, RecheckPortal) {
1992 EXPECT_CALL(*mock_devices_[0].get(), RequestPortalDetection())
1993 .WillOnce(Return(false));
1994 EXPECT_CALL(*mock_devices_[1].get(), RequestPortalDetection())
1995 .WillOnce(Return(true));
1996 EXPECT_CALL(*mock_devices_[2].get(), RequestPortalDetection())
1997 .Times(0);
1998
1999 manager()->RegisterDevice(mock_devices_[0]);
2000 manager()->RegisterDevice(mock_devices_[1]);
2001 manager()->RegisterDevice(mock_devices_[2]);
2002
2003 manager()->RecheckPortal(NULL);
2004}
2005
Paul Stewartd215af62012-04-24 23:25:50 -07002006TEST_F(ManagerTest, RecheckPortalOnService) {
2007 MockServiceRefPtr service = new NiceMock<MockService>(control_interface(),
2008 dispatcher(),
2009 metrics(),
2010 manager());
2011 EXPECT_CALL(*mock_devices_[0].get(),
2012 IsConnectedToService(IsRefPtrTo(service)))
2013 .WillOnce(Return(false));
2014 EXPECT_CALL(*mock_devices_[1].get(),
2015 IsConnectedToService(IsRefPtrTo(service)))
2016 .WillOnce(Return(true));
2017 EXPECT_CALL(*mock_devices_[1].get(), RestartPortalDetection())
2018 .WillOnce(Return(true));
2019 EXPECT_CALL(*mock_devices_[2].get(), IsConnectedToService(_))
2020 .Times(0);
2021
2022 manager()->RegisterDevice(mock_devices_[0]);
2023 manager()->RegisterDevice(mock_devices_[1]);
2024 manager()->RegisterDevice(mock_devices_[2]);
2025
2026 manager()->RecheckPortalOnService(service);
2027}
2028
Paul Stewarte2bad7c2012-03-14 08:55:33 -07002029TEST_F(ManagerTest, GetDefaultService) {
2030 EXPECT_FALSE(manager()->GetDefaultService().get());
2031
2032 scoped_refptr<MockService> mock_service(
2033 new NiceMock<MockService>(control_interface(),
2034 dispatcher(),
2035 metrics(),
2036 manager()));
2037
2038 manager()->RegisterService(mock_service);
2039 EXPECT_FALSE(manager()->GetDefaultService().get());
2040
2041 scoped_refptr<MockConnection> mock_connection(
2042 new NiceMock<MockConnection>(device_info_.get()));
Paul Stewartce4ec192012-03-14 12:53:46 -07002043 mock_service->set_mock_connection(mock_connection);
Paul Stewarte2bad7c2012-03-14 08:55:33 -07002044 EXPECT_EQ(mock_service.get(), manager()->GetDefaultService().get());
2045
Paul Stewartce4ec192012-03-14 12:53:46 -07002046 mock_service->set_mock_connection(NULL);
Paul Stewarte2bad7c2012-03-14 08:55:33 -07002047 manager()->DeregisterService(mock_service);
2048}
2049
Paul Stewart13ed2252012-03-21 12:52:46 -07002050TEST_F(ManagerTest, GetServiceWithGUID) {
2051 scoped_refptr<MockService> mock_service0(
2052 new NiceMock<MockService>(control_interface(),
2053 dispatcher(),
2054 metrics(),
2055 manager()));
2056
2057 scoped_refptr<MockService> mock_service1(
2058 new NiceMock<MockService>(control_interface(),
2059 dispatcher(),
2060 metrics(),
2061 manager()));
2062
Paul Stewartcb59fed2012-03-21 21:14:46 -07002063 EXPECT_CALL(*mock_service0.get(), Configure(_, _))
2064 .Times(0);
2065 EXPECT_CALL(*mock_service1.get(), Configure(_, _))
2066 .Times(0);
2067
Paul Stewart13ed2252012-03-21 12:52:46 -07002068 manager()->RegisterService(mock_service0);
2069 manager()->RegisterService(mock_service1);
2070
2071 const string kGUID0 = "GUID0";
2072 const string kGUID1 = "GUID1";
2073
2074 {
2075 Error error;
2076 ServiceRefPtr service = manager()->GetServiceWithGUID(kGUID0, &error);
2077 EXPECT_FALSE(error.IsSuccess());
2078 EXPECT_FALSE(service);
2079 }
2080
2081 KeyValueStore args;
2082 args.SetString(flimflam::kGuidProperty, kGUID1);
2083
2084 {
2085 Error error;
2086 ServiceRefPtr service = manager()->GetService(args, &error);
2087 EXPECT_EQ(Error::kInvalidArguments, error.type());
2088 EXPECT_FALSE(service);
2089 }
2090
2091 mock_service0->set_guid(kGUID0);
2092 mock_service1->set_guid(kGUID1);
2093
2094 {
2095 Error error;
2096 ServiceRefPtr service = manager()->GetServiceWithGUID(kGUID0, &error);
2097 EXPECT_TRUE(error.IsSuccess());
2098 EXPECT_EQ(mock_service0.get(), service.get());
2099 }
2100
2101 {
2102 Error error;
Paul Stewartcb59fed2012-03-21 21:14:46 -07002103 EXPECT_CALL(*mock_service1.get(), Configure(_, &error))
2104 .Times(1);
Paul Stewart13ed2252012-03-21 12:52:46 -07002105 ServiceRefPtr service = manager()->GetService(args, &error);
2106 EXPECT_TRUE(error.IsSuccess());
2107 EXPECT_EQ(mock_service1.get(), service.get());
2108 }
2109
2110 manager()->DeregisterService(mock_service0);
2111 manager()->DeregisterService(mock_service1);
2112}
2113
Gary Morain028545d2012-04-07 14:55:52 -07002114
2115TEST_F(ManagerTest, CalculateStateOffline) {
2116 MockMetrics mock_metrics;
2117 manager()->set_metrics(&mock_metrics);
2118 EXPECT_CALL(mock_metrics, NotifyDefaultServiceChanged(_))
2119 .Times(AnyNumber());
2120 scoped_refptr<MockService> mock_service0(
2121 new NiceMock<MockService>(control_interface(),
2122 dispatcher(),
2123 metrics(),
2124 manager()));
2125
2126 scoped_refptr<MockService> mock_service1(
2127 new NiceMock<MockService>(control_interface(),
2128 dispatcher(),
2129 metrics(),
2130 manager()));
2131
2132 EXPECT_CALL(*mock_service0.get(), IsConnected())
2133 .WillRepeatedly(Return(false));
2134 EXPECT_CALL(*mock_service1.get(), IsConnected())
2135 .WillRepeatedly(Return(false));
2136
2137 manager()->RegisterService(mock_service0);
2138 manager()->RegisterService(mock_service1);
2139
2140 EXPECT_EQ("offline", manager()->CalculateState(NULL));
2141
2142 manager()->DeregisterService(mock_service0);
2143 manager()->DeregisterService(mock_service1);
2144}
2145
2146TEST_F(ManagerTest, CalculateStateOnline) {
2147 MockMetrics mock_metrics;
2148 manager()->set_metrics(&mock_metrics);
2149 EXPECT_CALL(mock_metrics, NotifyDefaultServiceChanged(_))
2150 .Times(AnyNumber());
2151 scoped_refptr<MockService> mock_service0(
2152 new NiceMock<MockService>(control_interface(),
2153 dispatcher(),
2154 metrics(),
2155 manager()));
2156
2157 scoped_refptr<MockService> mock_service1(
2158 new NiceMock<MockService>(control_interface(),
2159 dispatcher(),
2160 metrics(),
2161 manager()));
2162
2163 EXPECT_CALL(*mock_service0.get(), IsConnected())
2164 .WillRepeatedly(Return(false));
2165 EXPECT_CALL(*mock_service1.get(), IsConnected())
2166 .WillRepeatedly(Return(true));
2167 EXPECT_CALL(*mock_service0.get(), state())
2168 .WillRepeatedly(Return(Service::kStateIdle));
2169 EXPECT_CALL(*mock_service1.get(), state())
2170 .WillRepeatedly(Return(Service::kStateConnected));
2171
2172 manager()->RegisterService(mock_service0);
2173 manager()->RegisterService(mock_service1);
Paul Stewartdfa46052012-06-26 09:44:14 -07002174 CompleteServiceSort();
Gary Morain028545d2012-04-07 14:55:52 -07002175
2176 EXPECT_EQ("online", manager()->CalculateState(NULL));
2177
2178 manager()->DeregisterService(mock_service0);
2179 manager()->DeregisterService(mock_service1);
2180}
2181
Paul Stewart10e9e4e2012-04-26 19:46:28 -07002182TEST_F(ManagerTest, StartupPortalList) {
2183 // Simulate loading value from the default profile.
2184 const string kProfileValue("wifi,vpn");
2185 manager()->props_.check_portal_list = kProfileValue;
2186
2187 EXPECT_EQ(kProfileValue, manager()->GetCheckPortalList(NULL));
2188 EXPECT_TRUE(manager()->IsPortalDetectionEnabled(Technology::kWifi));
2189 EXPECT_FALSE(manager()->IsPortalDetectionEnabled(Technology::kCellular));
2190
2191 const string kStartupValue("cellular,ethernet");
2192 manager()->SetStartupPortalList(kStartupValue);
2193 // Ensure profile value is not overwritten, so when we save the default
2194 // profile, the correct value will still be written.
2195 EXPECT_EQ(kProfileValue, manager()->props_.check_portal_list);
2196
2197 // However we should read back a different list.
2198 EXPECT_EQ(kStartupValue, manager()->GetCheckPortalList(NULL));
2199 EXPECT_FALSE(manager()->IsPortalDetectionEnabled(Technology::kWifi));
2200 EXPECT_TRUE(manager()->IsPortalDetectionEnabled(Technology::kCellular));
2201
2202 const string kRuntimeValue("ppp");
2203 // Setting a runtime value over the control API should overwrite both
2204 // the profile value and what we read back.
2205 Error error;
2206 manager()->mutable_store()->SetStringProperty(
2207 flimflam::kCheckPortalListProperty,
2208 kRuntimeValue,
2209 &error);
2210 ASSERT_TRUE(error.IsSuccess());
2211 EXPECT_EQ(kRuntimeValue, manager()->GetCheckPortalList(NULL));
2212 EXPECT_EQ(kRuntimeValue, manager()->props_.check_portal_list);
2213 EXPECT_FALSE(manager()->IsPortalDetectionEnabled(Technology::kCellular));
2214 EXPECT_TRUE(manager()->IsPortalDetectionEnabled(Technology::kPPP));
2215}
2216
Jason Glasgowdf7c5532012-05-14 14:41:45 -04002217TEST_F(ManagerTest, EnableTechnology) {
2218 Error error(Error::kOperationInitiated);
2219 ResultCallback callback;
2220 manager()->EnableTechnology(flimflam::kTypeEthernet, &error, callback);
2221 EXPECT_TRUE(error.IsSuccess());
2222
Joshua Krollda798622012-06-05 12:30:48 -07002223 ON_CALL(*mock_devices_[0], technology())
2224 .WillByDefault(Return(Technology::kEthernet));
Jason Glasgowdf7c5532012-05-14 14:41:45 -04002225
2226 manager()->RegisterDevice(mock_devices_[0]);
2227
2228 // Device is enabled, so expect operation is successful.
2229 mock_devices_[0]->enabled_ = true;
2230 error.Populate(Error::kOperationInitiated);
2231 manager()->EnableTechnology(flimflam::kTypeEthernet, &error, callback);
2232 EXPECT_TRUE(error.IsSuccess());
2233
2234 // Device is disabled, so expect operation in progress.
2235 mock_devices_[0]->enabled_ = false;
2236 EXPECT_CALL(*mock_devices_[0], SetEnabledPersistent(true, _, _));
2237 error.Populate(Error::kOperationInitiated);
2238 manager()->EnableTechnology(flimflam::kTypeEthernet, &error, callback);
2239 EXPECT_TRUE(error.IsOngoing());
2240}
2241
2242TEST_F(ManagerTest, DisableTechnology) {
2243 Error error(Error::kOperationInitiated);
2244 ResultCallback callback;
2245 manager()->DisableTechnology(flimflam::kTypeEthernet, &error, callback);
2246 EXPECT_TRUE(error.IsSuccess());
2247
Joshua Krollda798622012-06-05 12:30:48 -07002248 ON_CALL(*mock_devices_[0], technology())
2249 .WillByDefault(Return(Technology::kEthernet));
Jason Glasgowdf7c5532012-05-14 14:41:45 -04002250
2251 manager()->RegisterDevice(mock_devices_[0]);
2252
2253 // Device is disabled, so expect operation is successful.
2254 error.Populate(Error::kOperationInitiated);
2255 manager()->DisableTechnology(flimflam::kTypeEthernet, &error, callback);
2256 EXPECT_TRUE(error.IsSuccess());
2257
2258 // Device is enabled, so expect operation in progress.
2259 EXPECT_CALL(*mock_devices_[0], SetEnabledPersistent(false, _, _));
2260 mock_devices_[0]->enabled_ = true;
2261 error.Populate(Error::kOperationInitiated);
2262 manager()->DisableTechnology(flimflam::kTypeEthernet, &error, callback);
2263 EXPECT_TRUE(error.IsOngoing());
2264}
2265
2266
Chris Masone9be4a9d2011-05-16 15:44:09 -07002267} // namespace shill