blob: 443210c98e21f6b5f5bcb60def13942952a62dba [file] [log] [blame]
[email protected]9cc40cb2013-03-25 18:20:081// Copyright (c) 2013 The Chromium Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5#include "dbus/object_manager.h"
6
avi22437c692015-12-22 18:12:457#include <stddef.h>
8#include <stdint.h>
9
[email protected]9cc40cb2013-03-25 18:20:0810#include <string>
11#include <vector>
12
[email protected]9cc40cb2013-03-25 18:20:0813#include "base/bind.h"
[email protected]2a9ec0e2013-07-17 23:00:3014#include "base/message_loop/message_loop.h"
earthdok9562caf2014-09-03 10:32:3615#include "base/run_loop.h"
[email protected]9cc40cb2013-03-25 18:20:0816#include "base/threading/thread.h"
17#include "base/threading/thread_restrictions.h"
18#include "dbus/bus.h"
19#include "dbus/object_path.h"
20#include "dbus/object_proxy.h"
21#include "dbus/property.h"
22#include "dbus/test_service.h"
23#include "testing/gtest/include/gtest/gtest.h"
24
[email protected]2a57ca642013-06-13 06:37:1925namespace dbus {
26
[email protected]9cc40cb2013-03-25 18:20:0827// The object manager test exercises the asynchronous APIs in ObjectManager,
28// and by extension PropertySet and Property<>.
29class ObjectManagerTest
30 : public testing::Test,
[email protected]2a57ca642013-06-13 06:37:1931 public ObjectManager::Interface {
[email protected]9cc40cb2013-03-25 18:20:0832 public:
armansitoebff093d2014-09-05 17:49:3433 ObjectManagerTest() : timeout_expired_(false) {
[email protected]9cc40cb2013-03-25 18:20:0834 }
35
[email protected]2a57ca642013-06-13 06:37:1936 struct Properties : public PropertySet {
37 Property<std::string> name;
avi22437c692015-12-22 18:12:4538 Property<int16_t> version;
[email protected]2a57ca642013-06-13 06:37:1939 Property<std::vector<std::string> > methods;
40 Property<std::vector<ObjectPath> > objects;
[email protected]9cc40cb2013-03-25 18:20:0841
[email protected]2a57ca642013-06-13 06:37:1942 Properties(ObjectProxy* object_proxy,
[email protected]9cc40cb2013-03-25 18:20:0843 const std::string& interface_name,
44 PropertyChangedCallback property_changed_callback)
[email protected]2a57ca642013-06-13 06:37:1945 : PropertySet(object_proxy, interface_name, property_changed_callback) {
[email protected]9cc40cb2013-03-25 18:20:0846 RegisterProperty("Name", &name);
47 RegisterProperty("Version", &version);
48 RegisterProperty("Methods", &methods);
49 RegisterProperty("Objects", &objects);
50 }
51 };
52
dcheng3bb7119c2014-12-29 18:30:1753 PropertySet* CreateProperties(ObjectProxy* object_proxy,
54 const ObjectPath& object_path,
55 const std::string& interface_name) override {
[email protected]9cc40cb2013-03-25 18:20:0856 Properties* properties = new Properties(
57 object_proxy, interface_name,
58 base::Bind(&ObjectManagerTest::OnPropertyChanged,
59 base::Unretained(this), object_path));
[email protected]2a57ca642013-06-13 06:37:1960 return static_cast<PropertySet*>(properties);
[email protected]9cc40cb2013-03-25 18:20:0861 }
62
dcheng3bb7119c2014-12-29 18:30:1763 void SetUp() override {
[email protected]9cc40cb2013-03-25 18:20:0864 // Make the main thread not to allow IO.
65 base::ThreadRestrictions::SetIOAllowed(false);
66
67 // Start the D-Bus thread.
68 dbus_thread_.reset(new base::Thread("D-Bus Thread"));
69 base::Thread::Options thread_options;
[email protected]ff33b18e2013-05-01 16:10:3070 thread_options.message_loop_type = base::MessageLoop::TYPE_IO;
[email protected]9cc40cb2013-03-25 18:20:0871 ASSERT_TRUE(dbus_thread_->StartWithOptions(thread_options));
72
73 // Start the test service, using the D-Bus thread.
[email protected]2a57ca642013-06-13 06:37:1974 TestService::Options options;
skyostil8a033aa2015-06-17 15:46:0475 options.dbus_task_runner = dbus_thread_->task_runner();
[email protected]2a57ca642013-06-13 06:37:1976 test_service_.reset(new TestService(options));
[email protected]9cc40cb2013-03-25 18:20:0877 ASSERT_TRUE(test_service_->StartService());
78 ASSERT_TRUE(test_service_->WaitUntilServiceIsStarted());
79 ASSERT_TRUE(test_service_->HasDBusThread());
80
81 // Create the client, using the D-Bus thread.
[email protected]2a57ca642013-06-13 06:37:1982 Bus::Options bus_options;
83 bus_options.bus_type = Bus::SESSION;
84 bus_options.connection_type = Bus::PRIVATE;
skyostil8a033aa2015-06-17 15:46:0485 bus_options.dbus_task_runner = dbus_thread_->task_runner();
[email protected]2a57ca642013-06-13 06:37:1986 bus_ = new Bus(bus_options);
[email protected]9cc40cb2013-03-25 18:20:0887 ASSERT_TRUE(bus_->HasDBusThread());
88
89 object_manager_ = bus_->GetObjectManager(
hashimoto067d84f522016-01-05 08:48:0390 test_service_->service_name(),
[email protected]2a57ca642013-06-13 06:37:1991 ObjectPath("/org/chromium/TestService"));
[email protected]9cc40cb2013-03-25 18:20:0892 object_manager_->RegisterInterface("org.chromium.TestInterface", this);
93
[email protected]9cc40cb2013-03-25 18:20:0894 WaitForObject();
95 }
96
dcheng3bb7119c2014-12-29 18:30:1797 void TearDown() override {
[email protected]9cc40cb2013-03-25 18:20:0898 bus_->ShutdownOnDBusThreadAndBlock();
99
100 // Shut down the service.
101 test_service_->ShutdownAndBlock();
102
103 // Reset to the default.
104 base::ThreadRestrictions::SetIOAllowed(true);
105
106 // Stopping a thread is considered an IO operation, so do this after
107 // allowing IO.
108 test_service_->Stop();
earthdok9562caf2014-09-03 10:32:36109
110 base::RunLoop().RunUntilIdle();
[email protected]9cc40cb2013-03-25 18:20:08111 }
112
[email protected]2a57ca642013-06-13 06:37:19113 void MethodCallback(Response* response) {
[email protected]9cc40cb2013-03-25 18:20:08114 method_callback_called_ = true;
earthdok9562caf2014-09-03 10:32:36115 run_loop_->Quit();
[email protected]9cc40cb2013-03-25 18:20:08116 }
117
armansitoebff093d2014-09-05 17:49:34118 // Called from the PropertiesChangedAsObjectsReceived test case. The test will
119 // not run the message loop if it receives the expected PropertiesChanged
120 // signal before the timeout. This method immediately fails the test.
121 void PropertiesChangedTestTimeout() {
122 timeout_expired_ = true;
123 run_loop_->Quit();
124
125 FAIL() << "Never received PropertiesChanged";
126 }
127
[email protected]2a57ca642013-06-13 06:37:19128 protected:
[email protected]9cc40cb2013-03-25 18:20:08129 // Called when an object is added.
dcheng3bb7119c2014-12-29 18:30:17130 void ObjectAdded(const ObjectPath& object_path,
131 const std::string& interface_name) override {
[email protected]9cc40cb2013-03-25 18:20:08132 added_objects_.push_back(std::make_pair(object_path, interface_name));
earthdok9562caf2014-09-03 10:32:36133 run_loop_->Quit();
[email protected]9cc40cb2013-03-25 18:20:08134 }
135
136 // Called when an object is removed.
dcheng3bb7119c2014-12-29 18:30:17137 void ObjectRemoved(const ObjectPath& object_path,
138 const std::string& interface_name) override {
[email protected]9cc40cb2013-03-25 18:20:08139 removed_objects_.push_back(std::make_pair(object_path, interface_name));
earthdok9562caf2014-09-03 10:32:36140 run_loop_->Quit();
[email protected]9cc40cb2013-03-25 18:20:08141 }
142
143 // Called when a property value is updated.
[email protected]2a57ca642013-06-13 06:37:19144 void OnPropertyChanged(const ObjectPath& object_path,
[email protected]9cc40cb2013-03-25 18:20:08145 const std::string& name) {
armansitoebff093d2014-09-05 17:49:34146 // Store the value of the "Name" property if that's the one that
147 // changed.
148 Properties* properties = static_cast<Properties*>(
149 object_manager_->GetProperties(
150 object_path,
151 "org.chromium.TestInterface"));
152 if (name == properties->name.name())
153 last_name_value_ = properties->name.value();
154
155 // Store the updated property.
[email protected]9cc40cb2013-03-25 18:20:08156 updated_properties_.push_back(name);
earthdok9562caf2014-09-03 10:32:36157 run_loop_->Quit();
[email protected]9cc40cb2013-03-25 18:20:08158 }
159
160 static const size_t kExpectedObjects = 1;
161 static const size_t kExpectedProperties = 4;
162
163 void WaitForObject() {
164 while (added_objects_.size() < kExpectedObjects ||
earthdok9562caf2014-09-03 10:32:36165 updated_properties_.size() < kExpectedProperties) {
166 run_loop_.reset(new base::RunLoop);
167 run_loop_->Run();
168 }
[email protected]9cc40cb2013-03-25 18:20:08169 for (size_t i = 0; i < kExpectedObjects; ++i)
170 added_objects_.erase(added_objects_.begin());
171 for (size_t i = 0; i < kExpectedProperties; ++i)
172 updated_properties_.erase(updated_properties_.begin());
173 }
174
175 void WaitForRemoveObject() {
earthdok9562caf2014-09-03 10:32:36176 while (removed_objects_.size() < kExpectedObjects) {
177 run_loop_.reset(new base::RunLoop);
178 run_loop_->Run();
179 }
[email protected]9cc40cb2013-03-25 18:20:08180 for (size_t i = 0; i < kExpectedObjects; ++i)
181 removed_objects_.erase(removed_objects_.begin());
182 }
183
184 void WaitForMethodCallback() {
earthdok9562caf2014-09-03 10:32:36185 run_loop_.reset(new base::RunLoop);
186 run_loop_->Run();
[email protected]9cc40cb2013-03-25 18:20:08187 method_callback_called_ = false;
188 }
189
[email protected]2a57ca642013-06-13 06:37:19190 void PerformAction(const std::string& action, const ObjectPath& object_path) {
191 ObjectProxy* object_proxy = bus_->GetObjectProxy(
hashimoto067d84f522016-01-05 08:48:03192 test_service_->service_name(),
[email protected]2a57ca642013-06-13 06:37:19193 ObjectPath("/org/chromium/TestObject"));
[email protected]9cc40cb2013-03-25 18:20:08194
[email protected]2a57ca642013-06-13 06:37:19195 MethodCall method_call("org.chromium.TestInterface", "PerformAction");
196 MessageWriter writer(&method_call);
[email protected]9cc40cb2013-03-25 18:20:08197 writer.AppendString(action);
198 writer.AppendObjectPath(object_path);
199
200 object_proxy->CallMethod(&method_call,
[email protected]2a57ca642013-06-13 06:37:19201 ObjectProxy::TIMEOUT_USE_DEFAULT,
[email protected]9cc40cb2013-03-25 18:20:08202 base::Bind(&ObjectManagerTest::MethodCallback,
203 base::Unretained(this)));
204 WaitForMethodCallback();
205 }
206
[email protected]ff33b18e2013-05-01 16:10:30207 base::MessageLoop message_loop_;
earthdok9562caf2014-09-03 10:32:36208 scoped_ptr<base::RunLoop> run_loop_;
[email protected]9cc40cb2013-03-25 18:20:08209 scoped_ptr<base::Thread> dbus_thread_;
[email protected]2a57ca642013-06-13 06:37:19210 scoped_refptr<Bus> bus_;
211 ObjectManager* object_manager_;
212 scoped_ptr<TestService> test_service_;
[email protected]9cc40cb2013-03-25 18:20:08213
armansitoebff093d2014-09-05 17:49:34214 std::string last_name_value_;
215 bool timeout_expired_;
216
[email protected]2a57ca642013-06-13 06:37:19217 std::vector<std::pair<ObjectPath, std::string> > added_objects_;
218 std::vector<std::pair<ObjectPath, std::string> > removed_objects_;
[email protected]9cc40cb2013-03-25 18:20:08219 std::vector<std::string> updated_properties_;
220
221 bool method_callback_called_;
222};
223
224
225TEST_F(ObjectManagerTest, InitialObject) {
[email protected]2a57ca642013-06-13 06:37:19226 ObjectProxy* object_proxy = object_manager_->GetObjectProxy(
227 ObjectPath("/org/chromium/TestObject"));
[email protected]9cc40cb2013-03-25 18:20:08228 EXPECT_TRUE(object_proxy != NULL);
229
230 Properties* properties = static_cast<Properties*>(
[email protected]2a57ca642013-06-13 06:37:19231 object_manager_->GetProperties(ObjectPath("/org/chromium/TestObject"),
232 "org.chromium.TestInterface"));
[email protected]9cc40cb2013-03-25 18:20:08233 EXPECT_TRUE(properties != NULL);
234
235 EXPECT_EQ("TestService", properties->name.value());
236 EXPECT_EQ(10, properties->version.value());
237
238 std::vector<std::string> methods = properties->methods.value();
239 ASSERT_EQ(4U, methods.size());
240 EXPECT_EQ("Echo", methods[0]);
241 EXPECT_EQ("SlowEcho", methods[1]);
242 EXPECT_EQ("AsyncEcho", methods[2]);
243 EXPECT_EQ("BrokenMethod", methods[3]);
244
[email protected]2a57ca642013-06-13 06:37:19245 std::vector<ObjectPath> objects = properties->objects.value();
[email protected]9cc40cb2013-03-25 18:20:08246 ASSERT_EQ(1U, objects.size());
[email protected]2a57ca642013-06-13 06:37:19247 EXPECT_EQ(ObjectPath("/TestObjectPath"), objects[0]);
[email protected]9cc40cb2013-03-25 18:20:08248}
249
250TEST_F(ObjectManagerTest, UnknownObjectProxy) {
[email protected]2a57ca642013-06-13 06:37:19251 ObjectProxy* object_proxy = object_manager_->GetObjectProxy(
252 ObjectPath("/org/chromium/UnknownObject"));
[email protected]9cc40cb2013-03-25 18:20:08253 EXPECT_TRUE(object_proxy == NULL);
254}
255
256TEST_F(ObjectManagerTest, UnknownObjectProperties) {
257 Properties* properties = static_cast<Properties*>(
[email protected]2a57ca642013-06-13 06:37:19258 object_manager_->GetProperties(ObjectPath("/org/chromium/UnknownObject"),
259 "org.chromium.TestInterface"));
[email protected]9cc40cb2013-03-25 18:20:08260 EXPECT_TRUE(properties == NULL);
261}
262
263TEST_F(ObjectManagerTest, UnknownInterfaceProperties) {
264 Properties* properties = static_cast<Properties*>(
[email protected]2a57ca642013-06-13 06:37:19265 object_manager_->GetProperties(ObjectPath("/org/chromium/TestObject"),
266 "org.chromium.UnknownService"));
[email protected]9cc40cb2013-03-25 18:20:08267 EXPECT_TRUE(properties == NULL);
268}
269
270TEST_F(ObjectManagerTest, GetObjects) {
[email protected]2a57ca642013-06-13 06:37:19271 std::vector<ObjectPath> object_paths = object_manager_->GetObjects();
[email protected]9cc40cb2013-03-25 18:20:08272 ASSERT_EQ(1U, object_paths.size());
[email protected]2a57ca642013-06-13 06:37:19273 EXPECT_EQ(ObjectPath("/org/chromium/TestObject"), object_paths[0]);
[email protected]9cc40cb2013-03-25 18:20:08274}
275
276TEST_F(ObjectManagerTest, GetObjectsWithInterface) {
[email protected]2a57ca642013-06-13 06:37:19277 std::vector<ObjectPath> object_paths =
[email protected]9cc40cb2013-03-25 18:20:08278 object_manager_->GetObjectsWithInterface("org.chromium.TestInterface");
279 ASSERT_EQ(1U, object_paths.size());
[email protected]2a57ca642013-06-13 06:37:19280 EXPECT_EQ(ObjectPath("/org/chromium/TestObject"), object_paths[0]);
[email protected]9cc40cb2013-03-25 18:20:08281}
282
283TEST_F(ObjectManagerTest, GetObjectsWithUnknownInterface) {
[email protected]2a57ca642013-06-13 06:37:19284 std::vector<ObjectPath> object_paths =
[email protected]9cc40cb2013-03-25 18:20:08285 object_manager_->GetObjectsWithInterface("org.chromium.UnknownService");
286 EXPECT_EQ(0U, object_paths.size());
287}
288
289TEST_F(ObjectManagerTest, SameObject) {
[email protected]2a57ca642013-06-13 06:37:19290 ObjectManager* object_manager = bus_->GetObjectManager(
hashimoto067d84f522016-01-05 08:48:03291 test_service_->service_name(),
[email protected]2a57ca642013-06-13 06:37:19292 ObjectPath("/org/chromium/TestService"));
[email protected]9cc40cb2013-03-25 18:20:08293 EXPECT_EQ(object_manager_, object_manager);
294}
295
296TEST_F(ObjectManagerTest, DifferentObjectForService) {
[email protected]2a57ca642013-06-13 06:37:19297 ObjectManager* object_manager = bus_->GetObjectManager(
[email protected]9cc40cb2013-03-25 18:20:08298 "org.chromium.DifferentService",
[email protected]2a57ca642013-06-13 06:37:19299 ObjectPath("/org/chromium/TestService"));
[email protected]9cc40cb2013-03-25 18:20:08300 EXPECT_NE(object_manager_, object_manager);
301}
302
303TEST_F(ObjectManagerTest, DifferentObjectForPath) {
[email protected]2a57ca642013-06-13 06:37:19304 ObjectManager* object_manager = bus_->GetObjectManager(
hashimoto067d84f522016-01-05 08:48:03305 test_service_->service_name(),
[email protected]2a57ca642013-06-13 06:37:19306 ObjectPath("/org/chromium/DifferentService"));
[email protected]9cc40cb2013-03-25 18:20:08307 EXPECT_NE(object_manager_, object_manager);
308}
309
310TEST_F(ObjectManagerTest, SecondObject) {
[email protected]2a57ca642013-06-13 06:37:19311 PerformAction("AddObject", ObjectPath("/org/chromium/SecondObject"));
[email protected]9cc40cb2013-03-25 18:20:08312 WaitForObject();
313
[email protected]2a57ca642013-06-13 06:37:19314 ObjectProxy* object_proxy = object_manager_->GetObjectProxy(
315 ObjectPath("/org/chromium/SecondObject"));
[email protected]9cc40cb2013-03-25 18:20:08316 EXPECT_TRUE(object_proxy != NULL);
317
318 Properties* properties = static_cast<Properties*>(
[email protected]2a57ca642013-06-13 06:37:19319 object_manager_->GetProperties(ObjectPath("/org/chromium/SecondObject"),
320 "org.chromium.TestInterface"));
[email protected]9cc40cb2013-03-25 18:20:08321 EXPECT_TRUE(properties != NULL);
322
[email protected]2a57ca642013-06-13 06:37:19323 std::vector<ObjectPath> object_paths = object_manager_->GetObjects();
[email protected]9cc40cb2013-03-25 18:20:08324 ASSERT_EQ(2U, object_paths.size());
325
326 std::sort(object_paths.begin(), object_paths.end());
[email protected]2a57ca642013-06-13 06:37:19327 EXPECT_EQ(ObjectPath("/org/chromium/SecondObject"), object_paths[0]);
328 EXPECT_EQ(ObjectPath("/org/chromium/TestObject"), object_paths[1]);
[email protected]9cc40cb2013-03-25 18:20:08329
330 object_paths =
331 object_manager_->GetObjectsWithInterface("org.chromium.TestInterface");
332 ASSERT_EQ(2U, object_paths.size());
333
334 std::sort(object_paths.begin(), object_paths.end());
[email protected]2a57ca642013-06-13 06:37:19335 EXPECT_EQ(ObjectPath("/org/chromium/SecondObject"), object_paths[0]);
336 EXPECT_EQ(ObjectPath("/org/chromium/TestObject"), object_paths[1]);
[email protected]9cc40cb2013-03-25 18:20:08337}
338
339TEST_F(ObjectManagerTest, RemoveSecondObject) {
[email protected]2a57ca642013-06-13 06:37:19340 PerformAction("AddObject", ObjectPath("/org/chromium/SecondObject"));
[email protected]9cc40cb2013-03-25 18:20:08341 WaitForObject();
342
[email protected]2a57ca642013-06-13 06:37:19343 std::vector<ObjectPath> object_paths = object_manager_->GetObjects();
[email protected]9cc40cb2013-03-25 18:20:08344 ASSERT_EQ(2U, object_paths.size());
345
[email protected]2a57ca642013-06-13 06:37:19346 PerformAction("RemoveObject", ObjectPath("/org/chromium/SecondObject"));
[email protected]9cc40cb2013-03-25 18:20:08347 WaitForRemoveObject();
348
[email protected]2a57ca642013-06-13 06:37:19349 ObjectProxy* object_proxy = object_manager_->GetObjectProxy(
350 ObjectPath("/org/chromium/SecondObject"));
[email protected]9cc40cb2013-03-25 18:20:08351 EXPECT_TRUE(object_proxy == NULL);
352
353 Properties* properties = static_cast<Properties*>(
[email protected]2a57ca642013-06-13 06:37:19354 object_manager_->GetProperties(ObjectPath("/org/chromium/SecondObject"),
355 "org.chromium.TestInterface"));
[email protected]9cc40cb2013-03-25 18:20:08356 EXPECT_TRUE(properties == NULL);
357
358 object_paths = object_manager_->GetObjects();
359 ASSERT_EQ(1U, object_paths.size());
[email protected]2a57ca642013-06-13 06:37:19360 EXPECT_EQ(ObjectPath("/org/chromium/TestObject"), object_paths[0]);
[email protected]9cc40cb2013-03-25 18:20:08361
362 object_paths =
363 object_manager_->GetObjectsWithInterface("org.chromium.TestInterface");
364 ASSERT_EQ(1U, object_paths.size());
[email protected]2a57ca642013-06-13 06:37:19365 EXPECT_EQ(ObjectPath("/org/chromium/TestObject"), object_paths[0]);
[email protected]9cc40cb2013-03-25 18:20:08366}
[email protected]2a57ca642013-06-13 06:37:19367
[email protected]043fb8c2014-03-07 02:24:33368TEST_F(ObjectManagerTest, OwnershipLost) {
369 PerformAction("ReleaseOwnership", ObjectPath("/org/chromium/TestService"));
370 WaitForRemoveObject();
371
372 std::vector<ObjectPath> object_paths = object_manager_->GetObjects();
373 ASSERT_EQ(0U, object_paths.size());
374}
375
376TEST_F(ObjectManagerTest, OwnershipLostAndRegained) {
377 PerformAction("Ownership", ObjectPath("/org/chromium/TestService"));
378 WaitForRemoveObject();
379 WaitForObject();
380
381 std::vector<ObjectPath> object_paths = object_manager_->GetObjects();
382 ASSERT_EQ(1U, object_paths.size());
383}
384
armansitoebff093d2014-09-05 17:49:34385TEST_F(ObjectManagerTest, PropertiesChangedAsObjectsReceived) {
386 // Remove the existing object manager.
387 object_manager_->UnregisterInterface("org.chromium.TestInterface");
388 run_loop_.reset(new base::RunLoop);
389 EXPECT_TRUE(bus_->RemoveObjectManager(
hashimoto067d84f522016-01-05 08:48:03390 test_service_->service_name(),
armansitoebff093d2014-09-05 17:49:34391 ObjectPath("/org/chromium/TestService"),
392 run_loop_->QuitClosure()));
393 run_loop_->Run();
394
395 PerformAction("SetSendImmediatePropertiesChanged",
396 ObjectPath("/org/chromium/TestService"));
397
398 object_manager_ = bus_->GetObjectManager(
hashimoto067d84f522016-01-05 08:48:03399 test_service_->service_name(),
armansitoebff093d2014-09-05 17:49:34400 ObjectPath("/org/chromium/TestService"));
401 object_manager_->RegisterInterface("org.chromium.TestInterface", this);
402
403 // The newly created object manager should call GetManagedObjects immediately
404 // after setting up the match rule for PropertiesChanged. We should process
405 // the PropertiesChanged event right after that. If we don't receive it within
406 // 2 seconds, then fail the test.
407 message_loop_.PostDelayedTask(
408 FROM_HERE,
409 base::Bind(&ObjectManagerTest::PropertiesChangedTestTimeout,
410 base::Unretained(this)),
411 base::TimeDelta::FromSeconds(2));
412
413 while (last_name_value_ != "ChangedTestServiceName" && !timeout_expired_) {
414 run_loop_.reset(new base::RunLoop);
415 run_loop_->Run();
416 }
417}
418
[email protected]2a57ca642013-06-13 06:37:19419} // namespace dbus