blob: 426673767b75581023d54e268508b6757757c67d [file] [log] [blame]
Thieu Le3426c8f2012-01-11 17:35:11 -08001// Copyright (c) 2012 The Chromium OS Authors. All rights reserved.
Darin Petkov887f2982011-07-14 16:10:17 -07002// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
Eric Shienbrood3e20a232012-02-16 11:35:56 -05005#include <base/stl_util.h>
Darin Petkov887f2982011-07-14 16:10:17 -07006#include <gtest/gtest.h>
Ben Chan5c853ef2012-10-05 00:05:37 -07007#include <ModemManager/ModemManager.h>
Darin Petkov887f2982011-07-14 16:10:17 -07008
9#include "shill/manager.h"
10#include "shill/mock_control.h"
David Rochberg7cb06f62012-03-05 11:23:44 -050011#include "shill/mock_dbus_objectmanager_proxy.h"
Darin Petkov887f2982011-07-14 16:10:17 -070012#include "shill/mock_glib.h"
Chris Masone2ae797d2011-08-23 20:41:00 -070013#include "shill/mock_manager.h"
Thieu Le3426c8f2012-01-11 17:35:11 -080014#include "shill/mock_metrics.h"
David Rochbergfa1d31d2012-03-20 10:38:07 -040015#include "shill/mock_modem.h"
Darin Petkovc90fe522011-07-15 13:59:47 -070016#include "shill/mock_modem_manager_proxy.h"
Darin Petkove0a312e2011-07-20 13:45:28 -070017#include "shill/modem.h"
Darin Petkov887f2982011-07-14 16:10:17 -070018#include "shill/modem_manager.h"
Darin Petkovc90fe522011-07-15 13:59:47 -070019#include "shill/proxy_factory.h"
Darin Petkov887f2982011-07-14 16:10:17 -070020
Darin Petkovc90fe522011-07-15 13:59:47 -070021using std::string;
David Rochberg7cb06f62012-03-05 11:23:44 -050022using std::tr1::shared_ptr;
Darin Petkov5c97ac52011-07-19 16:30:49 -070023using std::vector;
Darin Petkov887f2982011-07-14 16:10:17 -070024using testing::_;
David Rochberg7cb06f62012-03-05 11:23:44 -050025using testing::Invoke;
David Rochbergb6b6ccb2012-03-16 13:40:36 -040026using testing::Pointee;
Darin Petkov887f2982011-07-14 16:10:17 -070027using testing::Return;
28using testing::StrEq;
29using testing::Test;
30
31namespace shill {
32
David Rochberg7cb06f62012-03-05 11:23:44 -050033// A testing subclass of ModemManager.
34class ModemManagerCore : public ModemManager {
35 public:
36 ModemManagerCore(const string &service,
37 const string &path,
38 ControlInterface *control_interface,
39 EventDispatcher *dispatcher,
40 Metrics *metrics,
41 Manager *manager,
42 GLib *glib,
Ben Chan62028b22012-11-05 11:20:02 -080043 CellularOperatorInfo *cellular_operator_info,
David Rochberg7cb06f62012-03-05 11:23:44 -050044 mobile_provider_db *provider_db)
45 : ModemManager(service,
46 path,
47 control_interface,
48 dispatcher,
49 metrics,
50 manager,
51 glib,
Ben Chan62028b22012-11-05 11:20:02 -080052 cellular_operator_info,
David Rochberg7cb06f62012-03-05 11:23:44 -050053 provider_db) {}
54
55 virtual ~ModemManagerCore() {}
56
57 MOCK_METHOD1(Connect, void(const string &owner));
58 MOCK_METHOD0(Disconnect, void());
David Rochberg7cb06f62012-03-05 11:23:44 -050059};
60
Darin Petkov887f2982011-07-14 16:10:17 -070061class ModemManagerTest : public Test {
62 public:
63 ModemManagerTest()
David Rochberg7cb06f62012-03-05 11:23:44 -050064 : manager_(&control_interface_, &dispatcher_, &metrics_, &glib_) {
Darin Petkovc90fe522011-07-15 13:59:47 -070065 }
David Rochbergfa1d31d2012-03-20 10:38:07 -040066
67 virtual void SetUp() {
68 modem_.reset(new StrictModem(
Jason Glasgowa585fc32012-06-06 11:04:09 -040069 kOwner, kService, kModemPath, &control_interface_, &dispatcher_,
Ben Chan62028b22012-11-05 11:20:02 -080070 &metrics_, &manager_, static_cast<CellularOperatorInfo *>(NULL),
71 static_cast<mobile_provider_db *>(NULL)));
David Rochbergfa1d31d2012-03-20 10:38:07 -040072 }
Ben Chan62028b22012-11-05 11:20:02 -080073
Darin Petkov887f2982011-07-14 16:10:17 -070074 protected:
75 static const char kService[];
76 static const char kPath[];
Darin Petkov5c97ac52011-07-19 16:30:49 -070077 static const char kOwner[];
78 static const char kModemPath[];
Darin Petkov887f2982011-07-14 16:10:17 -070079
David Rochbergfa1d31d2012-03-20 10:38:07 -040080 shared_ptr<StrictModem> modem_;
81
Darin Petkov887f2982011-07-14 16:10:17 -070082 MockGLib glib_;
83 MockControl control_interface_;
84 EventDispatcher dispatcher_;
Thieu Le3426c8f2012-01-11 17:35:11 -080085 MockMetrics metrics_;
Chris Masone2ae797d2011-08-23 20:41:00 -070086 MockManager manager_;
Darin Petkov887f2982011-07-14 16:10:17 -070087};
88
Darin Petkov5c97ac52011-07-19 16:30:49 -070089const char ModemManagerTest::kService[] = "org.chromium.ModemManager";
90const char ModemManagerTest::kPath[] = "/org/chromium/ModemManager";
91const char ModemManagerTest::kOwner[] = ":1.17";
David Rochberg7cb06f62012-03-05 11:23:44 -050092const char ModemManagerTest::kModemPath[] = "/org/blah/Modem/blah/0";
Darin Petkov887f2982011-07-14 16:10:17 -070093
David Rochberg7cb06f62012-03-05 11:23:44 -050094class ModemManagerCoreTest : public ModemManagerTest {
95 public:
96 ModemManagerCoreTest()
97 : ModemManagerTest(),
98 modem_manager_(kService,
99 kPath,
100 &control_interface_,
101 &dispatcher_,
102 &metrics_,
103 &manager_,
104 &glib_,
Ben Chan62028b22012-11-05 11:20:02 -0800105 NULL,
David Rochberg7cb06f62012-03-05 11:23:44 -0500106 NULL) {}
Darin Petkovab565bb2011-10-06 02:55:51 -0700107
David Rochberg7cb06f62012-03-05 11:23:44 -0500108 virtual void TearDown() {
109 modem_manager_.watcher_id_ = 0;
110 }
Darin Petkove0a312e2011-07-20 13:45:28 -0700111
David Rochberg7cb06f62012-03-05 11:23:44 -0500112 protected:
113 ModemManagerCore modem_manager_;
114};
115
David Rochberg7cb06f62012-03-05 11:23:44 -0500116TEST_F(ModemManagerCoreTest, Start) {
Darin Petkov887f2982011-07-14 16:10:17 -0700117 const int kWatcher = 123;
118 EXPECT_CALL(glib_, BusWatchName(G_BUS_TYPE_SYSTEM,
119 StrEq(kService),
120 G_BUS_NAME_WATCHER_FLAGS_NONE,
121 ModemManager::OnAppear,
122 ModemManager::OnVanish,
123 &modem_manager_,
124 NULL))
125 .WillOnce(Return(kWatcher));
126 EXPECT_EQ(0, modem_manager_.watcher_id_);
127 modem_manager_.Start();
128 EXPECT_EQ(kWatcher, modem_manager_.watcher_id_);
129}
130
David Rochberg7cb06f62012-03-05 11:23:44 -0500131TEST_F(ModemManagerCoreTest, Stop) {
Darin Petkov887f2982011-07-14 16:10:17 -0700132 const int kWatcher = 345;
Darin Petkov887f2982011-07-14 16:10:17 -0700133 modem_manager_.watcher_id_ = kWatcher;
134 modem_manager_.owner_ = kOwner;
135 EXPECT_CALL(glib_, BusUnwatchName(kWatcher)).Times(1);
David Rochberg7cb06f62012-03-05 11:23:44 -0500136 EXPECT_CALL(modem_manager_, Disconnect());
Darin Petkov887f2982011-07-14 16:10:17 -0700137 modem_manager_.Stop();
Darin Petkov887f2982011-07-14 16:10:17 -0700138}
139
David Rochberg7cb06f62012-03-05 11:23:44 -0500140TEST_F(ModemManagerCoreTest, OnAppearVanish) {
Darin Petkov887f2982011-07-14 16:10:17 -0700141 EXPECT_EQ("", modem_manager_.owner_);
David Rochberg7cb06f62012-03-05 11:23:44 -0500142 EXPECT_CALL(modem_manager_, Connect(kOwner));
143 EXPECT_CALL(modem_manager_, Disconnect());
Darin Petkov5c97ac52011-07-19 16:30:49 -0700144 ModemManager::OnAppear(NULL, kService, kOwner, &modem_manager_);
David Rochberg7cb06f62012-03-05 11:23:44 -0500145 ModemManager::OnVanish(NULL, kService, &modem_manager_);
146}
147
148TEST_F(ModemManagerCoreTest, Connect) {
149 EXPECT_EQ("", modem_manager_.owner_);
150 modem_manager_.ModemManager::Connect(kOwner);
Darin Petkov887f2982011-07-14 16:10:17 -0700151 EXPECT_EQ(kOwner, modem_manager_.owner_);
152}
153
David Rochberg7cb06f62012-03-05 11:23:44 -0500154TEST_F(ModemManagerCoreTest, Disconnect) {
Darin Petkov887f2982011-07-14 16:10:17 -0700155 modem_manager_.owner_ = kOwner;
David Rochbergfa1d31d2012-03-20 10:38:07 -0400156 modem_manager_.RecordAddedModem(modem_);
David Rochberg7cb06f62012-03-05 11:23:44 -0500157 EXPECT_EQ(1, modem_manager_.modems_.size());
158
159 modem_manager_.ModemManager::Disconnect();
Darin Petkov887f2982011-07-14 16:10:17 -0700160 EXPECT_EQ("", modem_manager_.owner_);
David Rochberg7cb06f62012-03-05 11:23:44 -0500161 EXPECT_EQ(0, modem_manager_.modems_.size());
Darin Petkov887f2982011-07-14 16:10:17 -0700162}
163
David Rochbergfa1d31d2012-03-20 10:38:07 -0400164TEST_F(ModemManagerCoreTest, ModemExists) {
Darin Petkov5c97ac52011-07-19 16:30:49 -0700165 modem_manager_.owner_ = kOwner;
David Rochberg7cb06f62012-03-05 11:23:44 -0500166
David Rochbergfa1d31d2012-03-20 10:38:07 -0400167 EXPECT_FALSE(modem_manager_.ModemExists(kModemPath));
168 modem_manager_.RecordAddedModem(modem_);
169 EXPECT_TRUE(modem_manager_.ModemExists(kModemPath));
Darin Petkov5c97ac52011-07-19 16:30:49 -0700170}
171
David Rochbergb6b6ccb2012-03-16 13:40:36 -0400172class ModemManagerClassicMockInit : public ModemManagerClassic {
173 public:
174 ModemManagerClassicMockInit(const string &service,
175 const string &path,
176 ControlInterface *control_interface,
177 EventDispatcher *dispatcher,
178 Metrics *metrics,
179 Manager *manager,
180 GLib *glib,
Ben Chan62028b22012-11-05 11:20:02 -0800181 CellularOperatorInfo *cellular_operator_info,
David Rochbergb6b6ccb2012-03-16 13:40:36 -0400182 mobile_provider_db *provider_db) :
183 ModemManagerClassic(service,
184 path,
185 control_interface,
186 dispatcher,
187 metrics,
188 manager,
189 glib,
Ben Chan62028b22012-11-05 11:20:02 -0800190 cellular_operator_info,
David Rochbergb6b6ccb2012-03-16 13:40:36 -0400191 provider_db) {}
David Rochbergfa1d31d2012-03-20 10:38:07 -0400192 MOCK_METHOD1(InitModemClassic, void(shared_ptr<ModemClassic>));
David Rochbergb6b6ccb2012-03-16 13:40:36 -0400193};
David Rochberg7cb06f62012-03-05 11:23:44 -0500194
195class ModemManagerClassicTest : public ModemManagerTest {
196 public:
197 ModemManagerClassicTest()
198 : ModemManagerTest(),
199 modem_manager_(kService,
200 kPath,
201 &control_interface_,
202 &dispatcher_,
203 &metrics_,
204 &manager_,
205 &glib_,
Ben Chan62028b22012-11-05 11:20:02 -0800206 NULL,
David Rochberg7cb06f62012-03-05 11:23:44 -0500207 NULL),
208 proxy_(new MockModemManagerProxy()),
209 proxy_factory_(this) {
210 }
211
212 protected:
213 class TestProxyFactory : public ProxyFactory {
214 public:
215 explicit TestProxyFactory(ModemManagerClassicTest *test) : test_(test) {}
216
217 virtual ModemManagerProxyInterface *CreateModemManagerProxy(
218 ModemManagerClassic */*manager*/,
219 const string &/*path*/,
220 const string &/*service*/) {
221 return test_->proxy_.release();
222 }
223
224 private:
225 ModemManagerClassicTest *test_;
226 };
227
228 virtual void SetUp() {
229 modem_manager_.proxy_factory_ = &proxy_factory_;
230 }
231
232 virtual void TearDown() {
233 modem_manager_.proxy_factory_ = NULL;
234 }
235
David Rochbergb6b6ccb2012-03-16 13:40:36 -0400236 ModemManagerClassicMockInit modem_manager_;
David Rochberg7cb06f62012-03-05 11:23:44 -0500237 scoped_ptr<MockModemManagerProxy> proxy_;
238 TestProxyFactory proxy_factory_;
239};
240
241TEST_F(ModemManagerClassicTest, Connect) {
242 EXPECT_EQ("", modem_manager_.owner_);
243
244 EXPECT_CALL(*proxy_, EnumerateDevices())
245 .WillOnce(Return(vector<DBus::Path>(1, kModemPath)));
246
David Rochbergb6b6ccb2012-03-16 13:40:36 -0400247 EXPECT_CALL(modem_manager_,
David Rochbergfa1d31d2012-03-20 10:38:07 -0400248 InitModemClassic(
249 Pointee(Field(&Modem::path_, StrEq(kModemPath)))));
David Rochbergb6b6ccb2012-03-16 13:40:36 -0400250
David Rochberg7cb06f62012-03-05 11:23:44 -0500251 modem_manager_.Connect(kOwner);
252 EXPECT_EQ(kOwner, modem_manager_.owner_);
253 EXPECT_EQ(1, modem_manager_.modems_.size());
254 ASSERT_TRUE(ContainsKey(modem_manager_.modems_, kModemPath));
255}
256
257
David Rochbergfa1d31d2012-03-20 10:38:07 -0400258class ModemManager1MockInit : public ModemManager1 {
259 public:
260 ModemManager1MockInit(const string &service,
261 const string &path,
262 ControlInterface *control_interface,
263 EventDispatcher *dispatcher,
264 Metrics *metrics,
265 Manager *manager,
266 GLib *glib,
Ben Chan62028b22012-11-05 11:20:02 -0800267 CellularOperatorInfo *cellular_operator_info,
David Rochbergfa1d31d2012-03-20 10:38:07 -0400268 mobile_provider_db *provider_db) :
269 ModemManager1(service,
270 path,
271 control_interface,
272 dispatcher,
273 metrics,
274 manager,
275 glib,
Ben Chan62028b22012-11-05 11:20:02 -0800276 cellular_operator_info,
David Rochbergfa1d31d2012-03-20 10:38:07 -0400277 provider_db) {}
278 MOCK_METHOD2(InitModem1, void(shared_ptr<Modem1>,
279 const DBusInterfaceToProperties &));
280};
281
282
David Rochberg7cb06f62012-03-05 11:23:44 -0500283class ModemManager1Test : public ModemManagerTest {
284 public:
285 ModemManager1Test()
286 : ModemManagerTest(),
287 modem_manager_(kService,
288 kPath,
289 &control_interface_,
290 &dispatcher_,
291 &metrics_,
292 &manager_,
293 &glib_,
Ben Chan62028b22012-11-05 11:20:02 -0800294 NULL,
David Rochberg7cb06f62012-03-05 11:23:44 -0500295 NULL),
296 proxy_(new MockDBusObjectManagerProxy()),
297 proxy_factory_(this) {
298 }
299
300 protected:
301 class TestProxyFactory : public ProxyFactory {
302 public:
303 explicit TestProxyFactory(ModemManager1Test *test) : test_(test) {}
304
305 virtual DBusObjectManagerProxyInterface *CreateDBusObjectManagerProxy(
David Rochberg7cb06f62012-03-05 11:23:44 -0500306 const string &/*path*/,
307 const string &/*service*/) {
308 return test_->proxy_.release();
309 }
310
311 private:
312 ModemManager1Test *test_;
313 };
314
315 virtual void SetUp() {
316 modem_manager_.proxy_factory_ = &proxy_factory_;
David Rochbergfa1d31d2012-03-20 10:38:07 -0400317 proxy_->IgnoreSetCallbacks();
David Rochberg7cb06f62012-03-05 11:23:44 -0500318 }
319
320 virtual void TearDown() {
321 modem_manager_.proxy_factory_ = NULL;
322 }
323
324 static DBusObjectsWithProperties GetModemWithProperties() {
325 DBusPropertiesMap o_fd_mm1_modem;
326
Ben Chan876efd32012-09-28 15:25:13 -0700327 DBusInterfaceToProperties properties;
328 properties[MM_DBUS_INTERFACE_MODEM] = o_fd_mm1_modem;
David Rochberg7cb06f62012-03-05 11:23:44 -0500329
330 DBusObjectsWithProperties objects_with_properties;
Ben Chan876efd32012-09-28 15:25:13 -0700331 objects_with_properties[kModemPath] = properties;
David Rochberg7cb06f62012-03-05 11:23:44 -0500332
333 return objects_with_properties;
334 }
335
David Rochbergfa1d31d2012-03-20 10:38:07 -0400336 ModemManager1MockInit modem_manager_;
David Rochberg7cb06f62012-03-05 11:23:44 -0500337 scoped_ptr<MockDBusObjectManagerProxy> proxy_;
338 TestProxyFactory proxy_factory_;
339};
340
341TEST_F(ModemManager1Test, Connect) {
342 Error e;
343
Eric Shienbrood9a245532012-03-07 14:20:39 -0500344 EXPECT_CALL(*proxy_, GetManagedObjects(_, _, _));
David Rochbergfa1d31d2012-03-20 10:38:07 -0400345 EXPECT_CALL(modem_manager_,
346 InitModem1(
347 Pointee(Field(&Modem::path_, StrEq(kModemPath))),
348 _));
David Rochberg7cb06f62012-03-05 11:23:44 -0500349
350 modem_manager_.Connect(kOwner);
Eric Shienbrood9a245532012-03-07 14:20:39 -0500351 modem_manager_.OnGetManagedObjectsReply(GetModemWithProperties(), e);
David Rochberg7cb06f62012-03-05 11:23:44 -0500352 EXPECT_EQ(1, modem_manager_.modems_.size());
353 EXPECT_TRUE(ContainsKey(modem_manager_.modems_, kModemPath));
David Rochberg7cb06f62012-03-05 11:23:44 -0500354}
355
David Rochbergfa1d31d2012-03-20 10:38:07 -0400356
David Rochberg7cb06f62012-03-05 11:23:44 -0500357TEST_F(ModemManager1Test, AddRemoveInterfaces) {
Eric Shienbrood9a245532012-03-07 14:20:39 -0500358 EXPECT_CALL(*proxy_, GetManagedObjects(_, _, _));
David Rochberg7cb06f62012-03-05 11:23:44 -0500359 modem_manager_.Connect(kOwner);
360
361 // Have nothing come back from GetManagedObjects
Eric Shienbrood9a245532012-03-07 14:20:39 -0500362 modem_manager_.OnGetManagedObjectsReply(DBusObjectsWithProperties(), Error());
David Rochberg7cb06f62012-03-05 11:23:44 -0500363 EXPECT_EQ(0, modem_manager_.modems_.size());
364
365 // Add an object that doesn't have a modem interface. Nothing should be added
David Rochbergfa1d31d2012-03-20 10:38:07 -0400366 EXPECT_CALL(modem_manager_, InitModem1(_, _)).Times(0);
Eric Shienbrood9a245532012-03-07 14:20:39 -0500367 modem_manager_.OnInterfacesAddedSignal(kModemPath,
368 DBusInterfaceToProperties());
David Rochberg7cb06f62012-03-05 11:23:44 -0500369 EXPECT_EQ(0, modem_manager_.modems_.size());
370
371 // Actually add a modem
David Rochbergfa1d31d2012-03-20 10:38:07 -0400372 EXPECT_CALL(modem_manager_, InitModem1(_, _)).Times(1);
Eric Shienbrood9a245532012-03-07 14:20:39 -0500373 modem_manager_.OnInterfacesAddedSignal(kModemPath,
374 GetModemWithProperties()[kModemPath]);
David Rochberg7cb06f62012-03-05 11:23:44 -0500375 EXPECT_EQ(1, modem_manager_.modems_.size());
376
377 // Remove an irrelevant interface
378 vector<string> not_including_modem_interface;
379 not_including_modem_interface.push_back("not.a.modem.interface");
Eric Shienbrood9a245532012-03-07 14:20:39 -0500380 modem_manager_.OnInterfacesRemovedSignal(kModemPath,
381 not_including_modem_interface);
David Rochberg7cb06f62012-03-05 11:23:44 -0500382 EXPECT_EQ(1, modem_manager_.modems_.size());
383
384 // Remove the modem
385 vector<string> with_modem_interface;
David Rochbergfa1d31d2012-03-20 10:38:07 -0400386 with_modem_interface.push_back(MM_DBUS_INTERFACE_MODEM);
Eric Shienbrood9a245532012-03-07 14:20:39 -0500387 modem_manager_.OnInterfacesRemovedSignal(kModemPath,
388 with_modem_interface);
David Rochberg7cb06f62012-03-05 11:23:44 -0500389 EXPECT_EQ(0, modem_manager_.modems_.size());
390}
David Rochbergfa1d31d2012-03-20 10:38:07 -0400391
Darin Petkov887f2982011-07-14 16:10:17 -0700392} // namespace shill