blob: c1372a5b97e03e9fedadc3932d9836d4785d29b1 [file] [log] [blame]
[email protected]e3c1fc92012-11-15 00:56:461// Copyright (c) 2012 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
avi6e1a22d2015-12-21 03:43:205#include <stddef.h>
6#include <stdint.h>
7
Ben Chan35c94022017-10-17 02:41:478#include <memory>
Hidehiko Abe06ce6dc2017-12-08 19:32:039#include <string>
10#include <utility>
11#include <vector>
Ben Chan35c94022017-10-17 02:41:4712
[email protected]e3c1fc92012-11-15 00:56:4613#include "base/bind.h"
fdorayf5b47fd12016-09-13 14:12:3614#include "base/run_loop.h"
Avi Drissman5fbef51a2018-12-25 21:30:4315#include "base/stl_util.h"
yamaguchicafadf52016-09-15 09:05:5316#include "base/strings/stringprintf.h"
fdoraye324edd2017-05-08 16:21:4617#include "base/test/scoped_task_environment.h"
zelidrag29fe3382014-08-27 01:44:4818#include "chromeos/dbus/dbus_thread_manager.h"
[email protected]cc70f5012013-05-14 04:58:5619#include "chromeos/dbus/fake_cros_disks_client.h"
Steven Bennetts3330b9f2019-03-15 20:24:1320#include "chromeos/dbus/power/power_manager_client.h"
Anand K. Mistry6039ab02018-08-07 03:21:3421#include "chromeos/disks/disk.h"
[email protected]e3c1fc92012-11-15 00:56:4622#include "chromeos/disks/disk_mount_manager.h"
[email protected]e3c1fc92012-11-15 00:56:4623#include "testing/gtest/include/gtest/gtest.h"
24
yamaguchicafadf52016-09-15 09:05:5325using base::StringPrintf;
Evan Stade523f7fc2019-03-02 19:20:5126
27namespace chromeos {
28
29namespace disks {
[email protected]e3c1fc92012-11-15 00:56:4630
31namespace {
32
yamaguchi934309a2016-10-20 05:07:1233const char kDevice1SourcePath[] = "/device/source_path";
34const char kDevice1MountPath[] = "/device/mount_path";
35const char kDevice2SourcePath[] = "/device/source_path2";
yamaguchi934309a2016-10-20 05:07:1236const char kReadOnlyDeviceMountPath[] = "/device/read_only_mount_path";
37const char kReadOnlyDeviceSourcePath[] = "/device/read_only_source_path";
Klemen Kozjek46f1c6192017-08-25 19:20:5438const char kFileSystemType1[] = "ntfs";
39const char kFileSystemType2[] = "exfat";
Austin Tankiang15af57a2019-07-19 04:32:5940const FormatFileSystemType kFormatFileSystemType1 = FormatFileSystemType::kVfat;
41const FormatFileSystemType kFormatFileSystemType2 =
42 FormatFileSystemType::kExfat;
Austin Tankiang2608bf72019-07-19 04:52:5343const char kFormatFileSystemType1String[] = "vfat";
44const char kFormatFileSystemType2String[] = "exfat";
Austin Tankianga4b6a3f2019-06-28 06:51:3845const char kFormatLabel1[] = "UNTITLED";
46const char kFormatLabel2[] = "TESTUSB";
yamaguchibffc32eb2016-08-17 06:35:3947
Anand K. Mistry6039ab02018-08-07 03:21:3448// Holds information needed to create a Disk instance.
[email protected]e3c1fc92012-11-15 00:56:4649struct TestDiskInfo {
50 const char* source_path;
51 const char* mount_path;
[email protected]e3c1fc92012-11-15 00:56:4652 const char* file_path;
53 const char* device_label;
54 const char* drive_label;
55 const char* vendor_id;
56 const char* vendor_name;
57 const char* product_id;
58 const char* product_name;
59 const char* fs_uuid;
Austin Tankiangdd25b512019-05-09 01:36:4760 const char* storage_device_path;
[email protected]e3c1fc92012-11-15 00:56:4661 chromeos::DeviceType device_type;
avi6e1a22d2015-12-21 03:43:2062 uint64_t size_in_bytes;
[email protected]e3c1fc92012-11-15 00:56:4663 bool is_read_only;
Klemen Kozjek46f1c6192017-08-25 19:20:5464 const char* file_system_type;
Anand K. Mistryedf46792018-08-28 00:22:3465 bool is_mounted;
[email protected]e3c1fc92012-11-15 00:56:4666};
67
68// Holds information to create a DiskMOuntManager::MountPointInfo instance.
69struct TestMountPointInfo {
70 const char* source_path;
71 const char* mount_path;
72 chromeos::MountType mount_type;
73 chromeos::disks::MountCondition mount_condition;
74};
75
Anand K. Mistry6a162e12018-08-21 06:33:1076// List of disks held in DiskMountManager at the beginning of the test.
[email protected]e3c1fc92012-11-15 00:56:4677const TestDiskInfo kTestDisks[] = {
Klemen Kozjekbf5610f2017-08-25 20:20:0978 {
79 kDevice1SourcePath,
80 kDevice1MountPath,
Klemen Kozjekbf5610f2017-08-25 20:20:0981 "/device/file_path",
82 "/device/device_label",
83 "/device/drive_label",
84 "/device/vendor_id",
85 "/device/vendor_name",
86 "/device/product_id",
87 "/device/product_name",
88 "/device/fs_uuid",
89 "/device/prefix",
90 chromeos::DEVICE_TYPE_USB,
91 1073741824, // size in bytes
Klemen Kozjekbf5610f2017-08-25 20:20:0992 false, // is read only
Klemen Kozjekbf5610f2017-08-25 20:20:0993 kFileSystemType1,
Anand K. Mistryedf46792018-08-28 00:22:3494 true, // is_mounted
Klemen Kozjekbf5610f2017-08-25 20:20:0995 },
96 {
97 kDevice2SourcePath,
98 "", // not mounted initially
Klemen Kozjekbf5610f2017-08-25 20:20:0999 "/device/file_path2",
100 "/device/device_label2",
101 "/device/drive_label2",
102 "/device/vendor_id2",
103 "/device/vendor_name2",
104 "/device/product_id2",
105 "/device/product_name2",
106 "/device/fs_uuid2",
107 "/device/prefix2",
108 chromeos::DEVICE_TYPE_SD,
109 1073741824, // size in bytes
Klemen Kozjekbf5610f2017-08-25 20:20:09110 false, // is read only
Klemen Kozjekbf5610f2017-08-25 20:20:09111 kFileSystemType2,
Anand K. Mistryedf46792018-08-28 00:22:34112 false, // is_mounted
Klemen Kozjekbf5610f2017-08-25 20:20:09113 },
114 {
115 kReadOnlyDeviceSourcePath,
116 kReadOnlyDeviceMountPath,
Klemen Kozjekbf5610f2017-08-25 20:20:09117 "/device/file_path_3",
118 "/device/device_label_3",
119 "/device/drive_label_3",
120 "/device/vendor_id_3",
121 "/device/vendor_name_3",
122 "/device/product_id_3",
123 "/device/product_name_3",
124 "/device/fs_uuid_3",
125 "/device/prefix",
126 chromeos::DEVICE_TYPE_USB,
127 1073741824, // size in bytes
Klemen Kozjekbf5610f2017-08-25 20:20:09128 true, // is read only
Klemen Kozjekbf5610f2017-08-25 20:20:09129 kFileSystemType2,
Anand K. Mistryedf46792018-08-28 00:22:34130 true, // is_mounted
Klemen Kozjekbf5610f2017-08-25 20:20:09131 },
[email protected]e3c1fc92012-11-15 00:56:46132};
133
Anand K. Mistry6a162e12018-08-21 06:33:10134// List of mount points held in DiskMountManager at the beginning of the test.
[email protected]e3c1fc92012-11-15 00:56:46135const TestMountPointInfo kTestMountPoints[] = {
136 {
137 "/archive/source_path",
138 "/archive/mount_path",
139 chromeos::MOUNT_TYPE_ARCHIVE,
140 chromeos::disks::MOUNT_CONDITION_NONE
141 },
142 {
yamaguchi934309a2016-10-20 05:07:12143 kDevice1SourcePath,
144 kDevice1MountPath,
[email protected]e3c1fc92012-11-15 00:56:46145 chromeos::MOUNT_TYPE_DEVICE,
146 chromeos::disks::MOUNT_CONDITION_NONE
147 },
yamaguchibffc32eb2016-08-17 06:35:39148 {
yamaguchi934309a2016-10-20 05:07:12149 kReadOnlyDeviceSourcePath,
150 kReadOnlyDeviceMountPath,
yamaguchibffc32eb2016-08-17 06:35:39151 chromeos::MOUNT_TYPE_DEVICE,
152 chromeos::disks::MOUNT_CONDITION_NONE
153 },
[email protected]e3c1fc92012-11-15 00:56:46154};
155
yamaguchicafadf52016-09-15 09:05:53156// Represents which function in |DiskMountManager::Observer| was invoked.
157enum ObserverEventType {
Aga Wronskaddc1a752017-12-01 19:44:02158 DEVICE_EVENT, // OnDeviceEvent()
159 AUTO_MOUNTABLE_DISK_EVENT, // OnAutoMountableDiskEvent()
160 BOOT_DEVICE_DISK_EVENT, // OnBootDeviceDiskEvent()
161 FORMAT_EVENT, // OnFormatEvent()
162 MOUNT_EVENT, // OnMountEvent()
163 RENAME_EVENT // OnRenameEvent()
yamaguchia07c4fb2016-09-14 03:58:03164};
165
yamaguchicafadf52016-09-15 09:05:53166// Represents every event notified to |DiskMountManager::Observer|.
167struct ObserverEvent {
168 public:
169 virtual ObserverEventType type() const = 0;
Chris Watkins2c529d62017-11-29 02:14:41170 virtual ~ObserverEvent() = default;
yamaguchicafadf52016-09-15 09:05:53171};
172
173// Represents an invocation of |DiskMountManager::Observer::OnDeviceEvent()|.
174struct DeviceEvent : public ObserverEvent {
175 DiskMountManager::DeviceEvent event;
176 std::string device_path;
177
Chris Watkins2c529d62017-11-29 02:14:41178 DeviceEvent() = default;
yamaguchicafadf52016-09-15 09:05:53179
180 DeviceEvent(DiskMountManager::DeviceEvent event,
181 const std::string& device_path)
182 : event(event), device_path(device_path) {}
183
184 ObserverEventType type() const override { return DEVICE_EVENT; }
185
186 bool operator==(const DeviceEvent& other) const {
187 return event == other.event && device_path == other.device_path;
188 }
189
190 std::string DebugString() const {
191 return StringPrintf("OnDeviceEvent(%d, %s)", event, device_path.c_str());
192 }
193};
194
Aga Wronskaddc1a752017-12-01 19:44:02195// Represents an invocation of
196// DiskMountManager::Observer::OnAutoMountableDiskEvent().
197struct AutoMountableDiskEvent : public ObserverEvent {
yamaguchicafadf52016-09-15 09:05:53198 DiskMountManager::DiskEvent event;
Anand K. Mistry6039ab02018-08-07 03:21:34199 std::unique_ptr<Disk> disk;
yamaguchicafadf52016-09-15 09:05:53200
Anand K. Mistry6039ab02018-08-07 03:21:34201 AutoMountableDiskEvent(DiskMountManager::DiskEvent event, const Disk& disk)
202 : event(event), disk(std::make_unique<Disk>(disk)) {}
yamaguchicafadf52016-09-15 09:05:53203
Aga Wronskaddc1a752017-12-01 19:44:02204 AutoMountableDiskEvent(AutoMountableDiskEvent&& other)
yamaguchicafadf52016-09-15 09:05:53205 : event(other.event), disk(std::move(other.disk)) {}
206
Aga Wronskaddc1a752017-12-01 19:44:02207 ObserverEventType type() const override { return AUTO_MOUNTABLE_DISK_EVENT; }
yamaguchicafadf52016-09-15 09:05:53208
Aga Wronskaddc1a752017-12-01 19:44:02209 bool operator==(const AutoMountableDiskEvent& other) const {
yamaguchicafadf52016-09-15 09:05:53210 return event == other.event && disk == other.disk;
211 }
212
213 std::string DebugString() const {
Aga Wronskaddc1a752017-12-01 19:44:02214 return StringPrintf(
215 "OnAutoMountableDiskEvent(event=%d, device_path=%s, mount_path=%s",
216 event, disk->device_path().c_str(), disk->mount_path().c_str());
217 }
218};
219
220// Represents an invocation of
221// DiskMountManager::Observer::OnBootDeviceDiskEvent().
222// TODO(agawronska): Add tests for disks events.
223struct BootDeviceDiskEvent : public ObserverEvent {
224 DiskMountManager::DiskEvent event;
Anand K. Mistry6039ab02018-08-07 03:21:34225 std::unique_ptr<Disk> disk;
Aga Wronskaddc1a752017-12-01 19:44:02226
Anand K. Mistry6039ab02018-08-07 03:21:34227 BootDeviceDiskEvent(DiskMountManager::DiskEvent event, const Disk& disk)
228 : event(event), disk(std::make_unique<Disk>(disk)) {}
Aga Wronskaddc1a752017-12-01 19:44:02229
230 BootDeviceDiskEvent(BootDeviceDiskEvent&& other)
231 : event(other.event), disk(std::move(other.disk)) {}
232
233 ObserverEventType type() const override { return BOOT_DEVICE_DISK_EVENT; }
234
235 bool operator==(const BootDeviceDiskEvent& other) const {
236 return event == other.event && disk == other.disk;
237 }
238
239 std::string DebugString() const {
240 return StringPrintf(
241 "OnBootDeviceDiskEvent(event=%d, device_path=%s, mount_path=%s", event,
242 disk->device_path().c_str(), disk->mount_path().c_str());
yamaguchicafadf52016-09-15 09:05:53243 }
244};
245
246// Represents an invocation of |DiskMountManager::Observer::OnFormatEvent()|.
247struct FormatEvent : public ObserverEvent {
248 DiskMountManager::FormatEvent event;
249 chromeos::FormatError error_code;
250 std::string device_path;
251
Chris Watkins2c529d62017-11-29 02:14:41252 FormatEvent() = default;
yamaguchicafadf52016-09-15 09:05:53253 FormatEvent(DiskMountManager::FormatEvent event,
254 chromeos::FormatError error_code,
255 const std::string& device_path)
256 : event(event), error_code(error_code), device_path(device_path) {}
257
258 ObserverEventType type() const override { return FORMAT_EVENT; }
259
260 bool operator==(const FormatEvent& other) const {
261 return event == other.event && error_code == other.error_code &&
262 device_path == other.device_path;
263 }
264
265 std::string DebugString() const {
266 return StringPrintf("OnFormatEvent(%d, %d, %s)", event, error_code,
267 device_path.c_str());
268 }
269};
270
Klemen Kozjekdb1d04e2017-08-25 22:01:50271// Represents an invocation of |DiskMountManager::Observer::OnRenameEvent()|.
272struct RenameEvent : public ObserverEvent {
273 DiskMountManager::RenameEvent event;
274 chromeos::RenameError error_code;
275 std::string device_path;
276
277 RenameEvent(DiskMountManager::RenameEvent event,
278 chromeos::RenameError error_code,
279 const std::string& device_path)
280 : event(event), error_code(error_code), device_path(device_path) {}
281
282 ObserverEventType type() const override { return RENAME_EVENT; }
283
284 bool operator==(const RenameEvent& other) const {
285 return event == other.event && error_code == other.error_code &&
286 device_path == other.device_path;
287 }
288
289 std::string DebugString() const {
290 return StringPrintf("OnRenameEvent(%d, %d, %s)", event, error_code,
291 device_path.c_str());
292 }
293};
294
yamaguchicafadf52016-09-15 09:05:53295// Represents an invocation of |DiskMountManager::Observer::OnMountEvent()|.
296struct MountEvent : public ObserverEvent {
297 DiskMountManager::MountEvent event;
298 chromeos::MountError error_code;
299 DiskMountManager::MountPointInfo mount_point;
300
301 // Not passed to callback, but read by handlers. So it's captured upon
302 // callback.
Anand K. Mistry6039ab02018-08-07 03:21:34303 std::unique_ptr<Disk> disk;
yamaguchicafadf52016-09-15 09:05:53304
305 MountEvent(MountEvent&& other)
306 : event(other.event),
307 error_code(other.error_code),
308 mount_point(other.mount_point),
309 disk(std::move(other.disk)) {}
310 MountEvent(DiskMountManager::MountEvent event,
311 chromeos::MountError error_code,
312 const DiskMountManager::MountPointInfo& mount_point,
Anand K. Mistry6039ab02018-08-07 03:21:34313 const Disk& disk)
yamaguchicafadf52016-09-15 09:05:53314 : event(event),
315 error_code(error_code),
316 mount_point(mount_point),
Anand K. Mistry6039ab02018-08-07 03:21:34317 disk(std::make_unique<Disk>(disk)) {}
yamaguchicafadf52016-09-15 09:05:53318
319 ObserverEventType type() const override { return MOUNT_EVENT; }
320
321 bool operator==(const MountEvent& other) const;
322
323 std::string DebugString() const {
324 return StringPrintf("OnMountEvent(%d, %d, %s, %s, %d, %d)", event,
325 error_code, mount_point.source_path.c_str(),
326 mount_point.mount_path.c_str(), mount_point.mount_type,
327 mount_point.mount_condition);
328 }
329};
330
331// A mock |Observer| class which records all invocation of the methods invoked
332// from DiskMountManager and all the arguments passed to them.
333class MockDiskMountManagerObserver : public DiskMountManager::Observer {
334 public:
avi8194ad62016-09-20 16:58:36335 explicit MockDiskMountManagerObserver(const DiskMountManager* manager)
yamaguchicafadf52016-09-15 09:05:53336 : manager_(manager) {}
Chris Watkins2c529d62017-11-29 02:14:41337 ~MockDiskMountManagerObserver() override = default;
yamaguchicafadf52016-09-15 09:05:53338
339 // Mock notify methods.
340 void OnDeviceEvent(DiskMountManager::DeviceEvent event,
341 const std::string& device_path) override {
Ben Chan35c94022017-10-17 02:41:47342 events_.push_back(std::make_unique<DeviceEvent>(event, device_path));
yamaguchicafadf52016-09-15 09:05:53343 }
344
Aga Wronskaddc1a752017-12-01 19:44:02345 void OnBootDeviceDiskEvent(DiskMountManager::DiskEvent event,
Anand K. Mistry6039ab02018-08-07 03:21:34346 const Disk& disk) override {
yamaguchicafadf52016-09-15 09:05:53347 // Take a snapshot (copy) of the Disk object at the time of invocation for
348 // later verification.
Aga Wronskaddc1a752017-12-01 19:44:02349 events_.push_back(std::make_unique<BootDeviceDiskEvent>(event, disk));
350 }
351
352 void OnAutoMountableDiskEvent(DiskMountManager::DiskEvent event,
Anand K. Mistry6039ab02018-08-07 03:21:34353 const Disk& disk) override {
Aga Wronskaddc1a752017-12-01 19:44:02354 // Take a snapshot (copy) of the Disk object at the time of invocation for
355 // later verification.
356 events_.push_back(std::make_unique<AutoMountableDiskEvent>(event, disk));
yamaguchicafadf52016-09-15 09:05:53357 }
358
359 void OnFormatEvent(DiskMountManager::FormatEvent event,
360 chromeos::FormatError error_code,
361 const std::string& device_path) override {
Ben Chan35c94022017-10-17 02:41:47362 events_.push_back(
363 std::make_unique<FormatEvent>(event, error_code, device_path));
yamaguchicafadf52016-09-15 09:05:53364 }
365
Klemen Kozjekbf5610f2017-08-25 20:20:09366 void OnRenameEvent(DiskMountManager::RenameEvent event,
367 chromeos::RenameError error_code,
368 const std::string& device_path) override {
Ben Chan35c94022017-10-17 02:41:47369 events_.push_back(
370 std::make_unique<RenameEvent>(event, error_code, device_path));
Klemen Kozjekbf5610f2017-08-25 20:20:09371 }
372
yamaguchicafadf52016-09-15 09:05:53373 void OnMountEvent(
374 DiskMountManager::MountEvent event,
375 chromeos::MountError error_code,
376 const DiskMountManager::MountPointInfo& mount_point) override {
377 // Take a snapshot (copy) of a Disk object at the time of invocation.
378 // It can be verified later besides the arguments.
Ben Chan35c94022017-10-17 02:41:47379 events_.push_back(std::make_unique<MountEvent>(
yamaguchicafadf52016-09-15 09:05:53380 event, error_code, mount_point,
381 *manager_->disks().find(mount_point.source_path)->second));
382 }
383
384 // Gets invocation history to be verified by testcases.
385 // Verifies if the |index|th invocation is OnDeviceEvent() and returns
386 // details.
387 const DeviceEvent& GetDeviceEvent(size_t index) {
388 DCHECK_GT(events_.size(), index);
389 DCHECK_EQ(DEVICE_EVENT, events_[index]->type());
390 return static_cast<const DeviceEvent&>(*events_[index]);
391 }
392
Aga Wronskaddc1a752017-12-01 19:44:02393 // Verifies if the |index|th invocation is OnAutoMountableDiskEvent() and
394 // returns details.
395 const AutoMountableDiskEvent& GetAutoMountableDiskEvent(size_t index) {
yamaguchicafadf52016-09-15 09:05:53396 DCHECK_GT(events_.size(), index);
Aga Wronskaddc1a752017-12-01 19:44:02397 DCHECK_EQ(AUTO_MOUNTABLE_DISK_EVENT, events_[index]->type());
398 return static_cast<const AutoMountableDiskEvent&>(*events_[index]);
399 }
400
401 // Verifies if the |index|th invocation is OnBootDeviceDiskEvent() and returns
402 // details.
403 const BootDeviceDiskEvent& GetBootDeviceDiskEvent(size_t index) {
404 DCHECK_GT(events_.size(), index);
405 DCHECK_EQ(BOOT_DEVICE_DISK_EVENT, events_[index]->type());
406 return static_cast<const BootDeviceDiskEvent&>(*events_[index]);
yamaguchicafadf52016-09-15 09:05:53407 }
408
409 // Verifies if the |index|th invocation is OnFormatEvent() and returns
410 // details.
411 const FormatEvent& GetFormatEvent(size_t index) {
412 DCHECK_GT(events_.size(), index);
413 DCHECK_EQ(FORMAT_EVENT, events_[index]->type());
414 return static_cast<const FormatEvent&>(*events_[index]);
415 }
416
Klemen Kozjekdb1d04e2017-08-25 22:01:50417 // Verifies if the |index|th invocation is OnRenameEvent() and returns
418 // details.
419 const RenameEvent& GetRenameEvent(size_t index) {
420 DCHECK_GT(events_.size(), index);
421 DCHECK_EQ(RENAME_EVENT, events_[index]->type());
422 return static_cast<const RenameEvent&>(*events_[index]);
423 }
424
yamaguchicafadf52016-09-15 09:05:53425 // Verifies if the |index|th invocation is OnMountEvent() and returns details.
426 const MountEvent& GetMountEvent(size_t index) {
427 DCHECK_GT(events_.size(), index);
428 DCHECK_EQ(MOUNT_EVENT, events_[index]->type());
429 return static_cast<const MountEvent&>(*events_[index]);
430 }
431
432 // Returns number of callback invocations happened so far.
433 size_t GetEventCount() { return events_.size(); }
434
435 // Counts the number of |MountEvent| recorded so far that matches the given
436 // condition.
437 size_t CountMountEvents(DiskMountManager::MountEvent mount_event_type,
438 chromeos::MountError error_code,
439 const std::string& mount_path) {
440 size_t num_matched = 0;
441 for (const auto& it : events_) {
442 if (it->type() != MOUNT_EVENT)
443 continue;
444 const MountEvent& mount_event = static_cast<const MountEvent&>(*it);
445 if (mount_event.event == mount_event_type &&
446 mount_event.error_code == error_code &&
447 mount_event.mount_point.mount_path == mount_path)
448 num_matched++;
449 }
450 return num_matched;
451 }
452
453 // Counts the number of |FormatEvent| recorded so far that matches with
454 // |format_event|.
455 size_t CountFormatEvents(const FormatEvent& exptected_format_event) {
456 size_t num_matched = 0;
457 for (const auto& it : events_) {
458 if (it->type() != FORMAT_EVENT)
459 continue;
460 if (static_cast<const FormatEvent&>(*it) == exptected_format_event)
461 num_matched++;
462 }
463 return num_matched;
464 }
465
Klemen Kozjekdb1d04e2017-08-25 22:01:50466 // Counts the number of |RenameEvent| recorded so far that matches with
467 // |rename_event|.
468 size_t CountRenameEvents(const RenameEvent& exptected_rename_event) {
469 size_t num_matched = 0;
470 for (const auto& event : events_) {
471 if (event->type() != RENAME_EVENT)
472 continue;
473 if (static_cast<const RenameEvent&>(*event) == exptected_rename_event)
474 num_matched++;
475 }
476 return num_matched;
477 }
478
yamaguchicafadf52016-09-15 09:05:53479 private:
480 // Pointer to the manager object to which this |Observer| is registered.
481 const DiskMountManager* manager_;
482
483 // Records all invocations.
484 std::vector<std::unique_ptr<ObserverEvent>> events_;
485};
486
487// Shift operators of ostream.
488// Needed to print values in case of EXPECT_* failure in gtest.
489std::ostream& operator<<(std::ostream& stream,
yamaguchicafadf52016-09-15 09:05:53490 const FormatEvent& format_event) {
491 return stream << format_event.DebugString();
492}
493
[email protected]e3c1fc92012-11-15 00:56:46494class DiskMountManagerTest : public testing::Test {
495 public:
fdoraye324edd2017-05-08 16:21:46496 DiskMountManagerTest()
497 : scoped_task_environment_(
498 base::test::ScopedTaskEnvironment::MainThreadType::UI) {}
Chris Watkins2c529d62017-11-29 02:14:41499 ~DiskMountManagerTest() override = default;
[email protected]e3c1fc92012-11-15 00:56:46500
Anand K. Mistry6a162e12018-08-21 06:33:10501 // Sets up test dbus thread manager and disks mount manager.
[email protected]e3c1fc92012-11-15 00:56:46502 // Initializes disk mount manager disks and mount points.
503 // Adds a test observer to the disk mount manager.
dchengae98daa2015-01-21 20:30:49504 void SetUp() override {
[email protected]54652d82013-11-10 16:02:49505 fake_cros_disks_client_ = new FakeCrosDisksClient;
zelidrag29fe3382014-08-27 01:44:48506 DBusThreadManager::GetSetterForTesting()->SetCrosDisksClient(
dcheng0a6e80c2016-04-08 18:37:38507 std::unique_ptr<CrosDisksClient>(fake_cros_disks_client_));
Steven Bennettsb95d2d42019-03-19 17:03:49508 PowerManagerClient::InitializeFake();
[email protected]e3c1fc92012-11-15 00:56:46509
[email protected]e3c1fc92012-11-15 00:56:46510 DiskMountManager::Initialize();
511
512 InitDisksAndMountPoints();
513
yamaguchicafadf52016-09-15 09:05:53514 observer_.reset(
515 new MockDiskMountManagerObserver(DiskMountManager::GetInstance()));
516 DiskMountManager::GetInstance()->AddObserver(observer_.get());
[email protected]e3c1fc92012-11-15 00:56:46517 }
518
Anand K. Mistry6a162e12018-08-21 06:33:10519 // Shuts down dbus thread manager and disk mount manager used in the test.
dchengae98daa2015-01-21 20:30:49520 void TearDown() override {
yamaguchicafadf52016-09-15 09:05:53521 DiskMountManager::GetInstance()->RemoveObserver(observer_.get());
[email protected]e3c1fc92012-11-15 00:56:46522 DiskMountManager::Shutdown();
Evan Stade523f7fc2019-03-02 19:20:51523 PowerManagerClient::Shutdown();
[email protected]e3c1fc92012-11-15 00:56:46524 DBusThreadManager::Shutdown();
525 }
526
527 protected:
Anand K. Mistry6a162e12018-08-21 06:33:10528 // Checks if disk mount manager contains a mount point with specified mount
[email protected]e3c1fc92012-11-15 00:56:46529 // path.
530 bool HasMountPoint(const std::string& mount_path) {
531 const DiskMountManager::MountPointMap& mount_points =
532 DiskMountManager::GetInstance()->mount_points();
533 return mount_points.find(mount_path) != mount_points.end();
534 }
535
536 private:
537 // Adds a new disk to the disk mount manager.
538 void AddTestDisk(const TestDiskInfo& disk) {
Anand K. Mistry6283c342018-08-08 02:41:39539 std::unique_ptr<Disk> test_disk =
540 Disk::Builder()
541 .SetDevicePath(disk.source_path)
542 .SetMountPath(disk.mount_path)
Anand K. Mistry6283c342018-08-08 02:41:39543 .SetFilePath(disk.file_path)
544 .SetDeviceLabel(disk.device_label)
545 .SetDriveLabel(disk.drive_label)
546 .SetVendorId(disk.vendor_id)
547 .SetVendorName(disk.vendor_name)
548 .SetProductId(disk.product_id)
549 .SetProductName(disk.product_name)
550 .SetFileSystemUUID(disk.fs_uuid)
Austin Tankiangdd25b512019-05-09 01:36:47551 .SetStorageDevicePath(disk.storage_device_path)
Anand K. Mistry6283c342018-08-08 02:41:39552 .SetDeviceType(disk.device_type)
553 .SetSizeInBytes(disk.size_in_bytes)
554 .SetIsReadOnlyHardware(disk.is_read_only)
555 .SetHasMedia(true)
556 .SetOnRemovableDevice(true)
557 .SetFileSystemType(disk.file_system_type)
Anand K. Mistryedf46792018-08-28 00:22:34558 .SetIsMounted(disk.is_mounted)
Anand K. Mistry6283c342018-08-08 02:41:39559 .Build();
Anand K. Mistry6039ab02018-08-07 03:21:34560 EXPECT_TRUE(
Anand K. Mistry6283c342018-08-08 02:41:39561 DiskMountManager::GetInstance()->AddDiskForTest(std::move(test_disk)));
[email protected]e3c1fc92012-11-15 00:56:46562 }
563
564 // Adds a new mount point to the disk mount manager.
Anand K. Mistry620679652018-08-21 03:18:22565 // If the mount point is a device mount point, disk with its source path
[email protected]e3c1fc92012-11-15 00:56:46566 // should already be added to the disk mount manager.
567 void AddTestMountPoint(const TestMountPointInfo& mount_point) {
568 EXPECT_TRUE(DiskMountManager::GetInstance()->AddMountPointForTest(
569 DiskMountManager::MountPointInfo(mount_point.source_path,
570 mount_point.mount_path,
571 mount_point.mount_type,
572 mount_point.mount_condition)));
573 }
574
575 // Adds disks and mount points to disk mount manager.
576 void InitDisksAndMountPoints() {
577 // Disks should be added first (when adding device mount points it is
578 // expected that the corresponding disk is already added).
Avi Drissman5fbef51a2018-12-25 21:30:43579 for (size_t i = 0; i < base::size(kTestDisks); i++)
[email protected]e3c1fc92012-11-15 00:56:46580 AddTestDisk(kTestDisks[i]);
581
Avi Drissman5fbef51a2018-12-25 21:30:43582 for (size_t i = 0; i < base::size(kTestMountPoints); i++)
[email protected]e3c1fc92012-11-15 00:56:46583 AddTestMountPoint(kTestMountPoints[i]);
584 }
585
586 protected:
[email protected]cc70f5012013-05-14 04:58:56587 chromeos::FakeCrosDisksClient* fake_cros_disks_client_;
yamaguchicafadf52016-09-15 09:05:53588 std::unique_ptr<MockDiskMountManagerObserver> observer_;
fdorayb5206192017-01-06 22:30:36589
590 private:
fdoraye324edd2017-05-08 16:21:46591 base::test::ScopedTaskEnvironment scoped_task_environment_;
[email protected]e3c1fc92012-11-15 00:56:46592};
593
594// Tests that the observer gets notified on attempt to format non existent mount
595// point.
596TEST_F(DiskMountManagerTest, Format_NotMounted) {
Austin Tankianga4b6a3f2019-06-28 06:51:38597 DiskMountManager::GetInstance()->FormatMountedDevice(
598 "/mount/non_existent", kFormatFileSystemType1, kFormatLabel1);
yamaguchicafadf52016-09-15 09:05:53599 ASSERT_EQ(1U, observer_->GetEventCount());
600 EXPECT_EQ(FormatEvent(DiskMountManager::FORMAT_COMPLETED,
601 chromeos::FORMAT_ERROR_UNKNOWN, "/mount/non_existent"),
602 observer_->GetFormatEvent(0));
[email protected]e3c1fc92012-11-15 00:56:46603}
604
yamaguchibffc32eb2016-08-17 06:35:39605// Tests that the observer gets notified on attempt to format read-only mount
606// point.
607TEST_F(DiskMountManagerTest, Format_ReadOnly) {
yamaguchi934309a2016-10-20 05:07:12608 DiskMountManager::GetInstance()->FormatMountedDevice(
Austin Tankianga4b6a3f2019-06-28 06:51:38609 kReadOnlyDeviceMountPath, kFormatFileSystemType1, kFormatLabel1);
yamaguchicafadf52016-09-15 09:05:53610 ASSERT_EQ(1U, observer_->GetEventCount());
611 EXPECT_EQ(FormatEvent(DiskMountManager::FORMAT_COMPLETED,
612 chromeos::FORMAT_ERROR_DEVICE_NOT_ALLOWED,
yamaguchi934309a2016-10-20 05:07:12613 kReadOnlyDeviceMountPath),
yamaguchicafadf52016-09-15 09:05:53614 observer_->GetFormatEvent(0));
yamaguchibffc32eb2016-08-17 06:35:39615}
616
[email protected]e3c1fc92012-11-15 00:56:46617// Tests that it is not possible to format archive mount point.
618TEST_F(DiskMountManagerTest, Format_Archive) {
Austin Tankianga4b6a3f2019-06-28 06:51:38619 DiskMountManager::GetInstance()->FormatMountedDevice(
620 "/archive/mount_path", kFormatFileSystemType1, kFormatLabel1);
yamaguchicafadf52016-09-15 09:05:53621 ASSERT_EQ(1U, observer_->GetEventCount());
622 EXPECT_EQ(FormatEvent(DiskMountManager::FORMAT_COMPLETED,
623 chromeos::FORMAT_ERROR_UNKNOWN, "/archive/source_path"),
624 observer_->GetFormatEvent(0));
[email protected]e3c1fc92012-11-15 00:56:46625}
626
627// Tests that format fails if the device cannot be unmounted.
628TEST_F(DiskMountManagerTest, Format_FailToUnmount) {
[email protected]e3c1fc92012-11-15 00:56:46629 // Before formatting mounted device, the device should be unmounted.
630 // In this test unmount will fail, and there should be no attempt to
631 // format the device.
[email protected]e3c1fc92012-11-15 00:56:46632
Anand K. Mistry9647a6e2018-08-20 00:33:10633 fake_cros_disks_client_->MakeUnmountFail(
Sergei Datsenko89391e92019-06-26 01:15:25634 chromeos::MOUNT_ERROR_INSUFFICIENT_PERMISSIONS);
[email protected]e3c1fc92012-11-15 00:56:46635 // Start test.
Austin Tankianga4b6a3f2019-06-28 06:51:38636 DiskMountManager::GetInstance()->FormatMountedDevice(
637 kDevice1MountPath, kFormatFileSystemType1, kFormatLabel1);
[email protected]e3c1fc92012-11-15 00:56:46638
639 // Cros disks will respond asynchronoulsy, so let's drain the message loop.
fdorayf5b47fd12016-09-13 14:12:36640 base::RunLoop().RunUntilIdle();
[email protected]e3c1fc92012-11-15 00:56:46641
yamaguchicafadf52016-09-15 09:05:53642 // Observer should be notified that unmount attempt fails and format task
643 // failed to start.
644 ASSERT_EQ(2U, observer_->GetEventCount());
645 const MountEvent& mount_event = observer_->GetMountEvent(0);
646 EXPECT_EQ(DiskMountManager::UNMOUNTING, mount_event.event);
Sergei Datsenko89391e92019-06-26 01:15:25647 EXPECT_EQ(chromeos::MOUNT_ERROR_INSUFFICIENT_PERMISSIONS,
648 mount_event.error_code);
yamaguchi934309a2016-10-20 05:07:12649 EXPECT_EQ(kDevice1MountPath, mount_event.mount_point.mount_path);
yamaguchicafadf52016-09-15 09:05:53650
651 EXPECT_EQ(FormatEvent(DiskMountManager::FORMAT_COMPLETED,
yamaguchi934309a2016-10-20 05:07:12652 chromeos::FORMAT_ERROR_UNKNOWN, kDevice1SourcePath),
yamaguchicafadf52016-09-15 09:05:53653 observer_->GetFormatEvent(1));
[email protected]cc70f5012013-05-14 04:58:56654 EXPECT_EQ(1, fake_cros_disks_client_->unmount_call_count());
yamaguchi934309a2016-10-20 05:07:12655 EXPECT_EQ(kDevice1MountPath,
[email protected]cc70f5012013-05-14 04:58:56656 fake_cros_disks_client_->last_unmount_device_path());
657 EXPECT_EQ(chromeos::UNMOUNT_OPTIONS_NONE,
658 fake_cros_disks_client_->last_unmount_options());
[email protected]f026c0f2014-05-06 21:52:35659 EXPECT_EQ(0, fake_cros_disks_client_->format_call_count());
[email protected]cc70f5012013-05-14 04:58:56660
[email protected]e3c1fc92012-11-15 00:56:46661 // The device mount should still be here.
yamaguchi934309a2016-10-20 05:07:12662 EXPECT_TRUE(HasMountPoint(kDevice1MountPath));
[email protected]e3c1fc92012-11-15 00:56:46663}
664
665// Tests that observer is notified when cros disks fails to start format
666// process.
667TEST_F(DiskMountManagerTest, Format_FormatFailsToStart) {
[email protected]e3c1fc92012-11-15 00:56:46668 // Before formatting mounted device, the device should be unmounted.
[email protected]f026c0f2014-05-06 21:52:35669 // In this test, unmount will succeed, but call to Format method will
[email protected]e3c1fc92012-11-15 00:56:46670 // fail.
[email protected]e3c1fc92012-11-15 00:56:46671
[email protected]f026c0f2014-05-06 21:52:35672 fake_cros_disks_client_->MakeFormatFail();
[email protected]e3c1fc92012-11-15 00:56:46673 // Start the test.
Austin Tankianga4b6a3f2019-06-28 06:51:38674 DiskMountManager::GetInstance()->FormatMountedDevice(
675 kDevice1MountPath, kFormatFileSystemType1, kFormatLabel1);
[email protected]e3c1fc92012-11-15 00:56:46676
677 // Cros disks will respond asynchronoulsy, so let's drain the message loop.
fdorayf5b47fd12016-09-13 14:12:36678 base::RunLoop().RunUntilIdle();
[email protected]e3c1fc92012-11-15 00:56:46679
yamaguchicafadf52016-09-15 09:05:53680 // Observer should be notified that the device was unmounted and format task
681 // failed to start.
682 ASSERT_EQ(2U, observer_->GetEventCount());
683 const MountEvent& mount_event = observer_->GetMountEvent(0);
684 EXPECT_EQ(DiskMountManager::UNMOUNTING, mount_event.event);
685 EXPECT_EQ(chromeos::MOUNT_ERROR_NONE, mount_event.error_code);
yamaguchi934309a2016-10-20 05:07:12686 EXPECT_EQ(kDevice1MountPath, mount_event.mount_point.mount_path);
yamaguchicafadf52016-09-15 09:05:53687
688 EXPECT_EQ(FormatEvent(DiskMountManager::FORMAT_COMPLETED,
yamaguchi934309a2016-10-20 05:07:12689 chromeos::FORMAT_ERROR_UNKNOWN, kDevice1SourcePath),
yamaguchicafadf52016-09-15 09:05:53690 observer_->GetFormatEvent(1));
691
[email protected]cc70f5012013-05-14 04:58:56692 EXPECT_EQ(1, fake_cros_disks_client_->unmount_call_count());
yamaguchi934309a2016-10-20 05:07:12693 EXPECT_EQ(kDevice1MountPath,
[email protected]cc70f5012013-05-14 04:58:56694 fake_cros_disks_client_->last_unmount_device_path());
695 EXPECT_EQ(chromeos::UNMOUNT_OPTIONS_NONE,
696 fake_cros_disks_client_->last_unmount_options());
[email protected]f026c0f2014-05-06 21:52:35697 EXPECT_EQ(1, fake_cros_disks_client_->format_call_count());
yamaguchi934309a2016-10-20 05:07:12698 EXPECT_EQ(kDevice1SourcePath,
[email protected]f026c0f2014-05-06 21:52:35699 fake_cros_disks_client_->last_format_device_path());
Austin Tankiang2608bf72019-07-19 04:52:53700 EXPECT_EQ(kFormatFileSystemType1String,
Austin Tankianga4b6a3f2019-06-28 06:51:38701 fake_cros_disks_client_->last_format_filesystem());
702 EXPECT_EQ(kFormatLabel1, fake_cros_disks_client_->last_format_label());
[email protected]cc70f5012013-05-14 04:58:56703
[email protected]e3c1fc92012-11-15 00:56:46704 // The device mount should be gone.
yamaguchi934309a2016-10-20 05:07:12705 EXPECT_FALSE(HasMountPoint(kDevice1MountPath));
[email protected]e3c1fc92012-11-15 00:56:46706}
707
708// Tests the case where there are two format requests for the same device.
709TEST_F(DiskMountManagerTest, Format_ConcurrentFormatCalls) {
[email protected]8f919ee2013-03-14 19:53:29710 // Only the first format request should be processed (the second unmount
711 // request fails because the device is already unmounted at that point).
[email protected]e3c1fc92012-11-15 00:56:46712 // CrosDisksClient will report that the format process for the first request
713 // is successfully started.
[email protected]e3c1fc92012-11-15 00:56:46714
yamaguchi48ec0aa2016-09-14 10:00:45715 fake_cros_disks_client_->set_unmount_listener(
Anand K. Mistryc10d4c192018-08-28 00:17:38716 base::BindRepeating(&FakeCrosDisksClient::MakeUnmountFail,
717 base::Unretained(fake_cros_disks_client_),
718 chromeos::MOUNT_ERROR_INVALID_UNMOUNT_OPTIONS));
yamaguchi48ec0aa2016-09-14 10:00:45719 // Start the test.
Austin Tankianga4b6a3f2019-06-28 06:51:38720 DiskMountManager::GetInstance()->FormatMountedDevice(
721 kDevice1MountPath, kFormatFileSystemType1, kFormatLabel1);
722 DiskMountManager::GetInstance()->FormatMountedDevice(
723 kDevice1MountPath, kFormatFileSystemType2, kFormatLabel2);
yamaguchi48ec0aa2016-09-14 10:00:45724
725 // Cros disks will respond asynchronoulsy, so let's drain the message loop.
726 base::RunLoop().RunUntilIdle();
yamaguchia07c4fb2016-09-14 03:58:03727
yamaguchicafadf52016-09-15 09:05:53728 // The observer should get a FORMAT_STARTED event for one format request and a
729 // FORMAT_COMPLETED with an error code for the other format request. The
730 // formatting will be started only for the first request.
731 // There should be only one UNMOUNTING event. The result of the second one
732 // should not be reported as the mount point will go away after the first
733 // request.
734 //
735 // Note that in this test the format completion signal will not be simulated,
736 // so the observer should not get FORMAT_COMPLETED signal.
737
738 ASSERT_EQ(3U, observer_->GetEventCount());
739 const MountEvent& mount_event = observer_->GetMountEvent(0);
740 EXPECT_EQ(DiskMountManager::UNMOUNTING, mount_event.event);
741 EXPECT_EQ(chromeos::MOUNT_ERROR_NONE, mount_event.error_code);
yamaguchi934309a2016-10-20 05:07:12742 EXPECT_EQ(kDevice1MountPath, mount_event.mount_point.mount_path);
yamaguchicafadf52016-09-15 09:05:53743 EXPECT_EQ(FormatEvent(DiskMountManager::FORMAT_COMPLETED,
yamaguchi934309a2016-10-20 05:07:12744 chromeos::FORMAT_ERROR_UNKNOWN, kDevice1SourcePath),
yamaguchicafadf52016-09-15 09:05:53745 observer_->GetFormatEvent(1));
746 EXPECT_EQ(FormatEvent(DiskMountManager::FORMAT_STARTED,
yamaguchi934309a2016-10-20 05:07:12747 chromeos::FORMAT_ERROR_NONE, kDevice1SourcePath),
yamaguchicafadf52016-09-15 09:05:53748 observer_->GetFormatEvent(2));
749
[email protected]cc70f5012013-05-14 04:58:56750 EXPECT_EQ(2, fake_cros_disks_client_->unmount_call_count());
yamaguchi934309a2016-10-20 05:07:12751 EXPECT_EQ(kDevice1MountPath,
[email protected]cc70f5012013-05-14 04:58:56752 fake_cros_disks_client_->last_unmount_device_path());
753 EXPECT_EQ(chromeos::UNMOUNT_OPTIONS_NONE,
754 fake_cros_disks_client_->last_unmount_options());
[email protected]f026c0f2014-05-06 21:52:35755 EXPECT_EQ(1, fake_cros_disks_client_->format_call_count());
yamaguchi934309a2016-10-20 05:07:12756 EXPECT_EQ(kDevice1SourcePath,
[email protected]f026c0f2014-05-06 21:52:35757 fake_cros_disks_client_->last_format_device_path());
Austin Tankiang2608bf72019-07-19 04:52:53758 EXPECT_EQ(kFormatFileSystemType1String,
[email protected]f026c0f2014-05-06 21:52:35759 fake_cros_disks_client_->last_format_filesystem());
Austin Tankianga4b6a3f2019-06-28 06:51:38760 EXPECT_EQ(kFormatLabel1, fake_cros_disks_client_->last_format_label());
[email protected]cc70f5012013-05-14 04:58:56761
[email protected]e3c1fc92012-11-15 00:56:46762 // The device mount should be gone.
yamaguchi934309a2016-10-20 05:07:12763 EXPECT_FALSE(HasMountPoint(kDevice1MountPath));
[email protected]e3c1fc92012-11-15 00:56:46764}
765
yamaguchicafadf52016-09-15 09:05:53766// Verifies a |MountEvent| with the given condition. This function only checks
767// the |mount_path| in |MountPointInfo| to make sure to match the event with
768// preceding mount invocations.
769void VerifyMountEvent(const MountEvent& mount_event,
770 DiskMountManager::MountEvent mount_event_type,
771 chromeos::MountError error_code,
772 const std::string& mount_path) {
773 EXPECT_EQ(mount_event_type, mount_event.event);
774 EXPECT_EQ(error_code, mount_event.error_code);
775 EXPECT_EQ(mount_path, mount_event.mount_point.mount_path);
776}
777
[email protected]e3c1fc92012-11-15 00:56:46778// Tests the case when the format process actually starts and fails.
779TEST_F(DiskMountManagerTest, Format_FormatFails) {
[email protected]f026c0f2014-05-06 21:52:35780 // Both unmount and format device cals are successful in this test.
[email protected]e3c1fc92012-11-15 00:56:46781
[email protected]e3c1fc92012-11-15 00:56:46782 // Start the test.
Austin Tankianga4b6a3f2019-06-28 06:51:38783 DiskMountManager::GetInstance()->FormatMountedDevice(
784 kDevice1MountPath, kFormatFileSystemType1, kFormatLabel1);
[email protected]e3c1fc92012-11-15 00:56:46785
[email protected]f026c0f2014-05-06 21:52:35786 // Wait for Unmount and Format calls to end.
fdorayf5b47fd12016-09-13 14:12:36787 base::RunLoop().RunUntilIdle();
[email protected]e3c1fc92012-11-15 00:56:46788
[email protected]cc70f5012013-05-14 04:58:56789 EXPECT_EQ(1, fake_cros_disks_client_->unmount_call_count());
yamaguchi934309a2016-10-20 05:07:12790 EXPECT_EQ(kDevice1MountPath,
[email protected]cc70f5012013-05-14 04:58:56791 fake_cros_disks_client_->last_unmount_device_path());
792 EXPECT_EQ(chromeos::UNMOUNT_OPTIONS_NONE,
793 fake_cros_disks_client_->last_unmount_options());
[email protected]f026c0f2014-05-06 21:52:35794 EXPECT_EQ(1, fake_cros_disks_client_->format_call_count());
yamaguchi934309a2016-10-20 05:07:12795 EXPECT_EQ(kDevice1SourcePath,
[email protected]f026c0f2014-05-06 21:52:35796 fake_cros_disks_client_->last_format_device_path());
Austin Tankiang2608bf72019-07-19 04:52:53797 EXPECT_EQ(kFormatFileSystemType1String,
Austin Tankianga4b6a3f2019-06-28 06:51:38798 fake_cros_disks_client_->last_format_filesystem());
799 EXPECT_EQ(kFormatLabel1, fake_cros_disks_client_->last_format_label());
[email protected]cc70f5012013-05-14 04:58:56800
[email protected]e3c1fc92012-11-15 00:56:46801 // The device should be unmounted by now.
yamaguchi934309a2016-10-20 05:07:12802 EXPECT_FALSE(HasMountPoint(kDevice1MountPath));
[email protected]e3c1fc92012-11-15 00:56:46803
[email protected]a0278d52014-05-06 03:36:15804 // Send failing FORMAT_COMPLETED signal.
[email protected]e3c1fc92012-11-15 00:56:46805 // The failure is marked by ! in fromt of the path (but this should change
806 // soon).
Hidehiko Abe06ce6dc2017-12-08 19:32:03807 fake_cros_disks_client_->NotifyFormatCompleted(chromeos::FORMAT_ERROR_UNKNOWN,
808 kDevice1SourcePath);
yamaguchicafadf52016-09-15 09:05:53809
810 // The observer should get notified that the device was unmounted and that
811 // formatting has started.
812 // After the formatting starts, the test will simulate failing
813 // FORMAT_COMPLETED signal, so the observer should also be notified the
814 // formatting has failed (FORMAT_COMPLETED event).
815 ASSERT_EQ(3U, observer_->GetEventCount());
816 VerifyMountEvent(observer_->GetMountEvent(0), DiskMountManager::UNMOUNTING,
yamaguchi934309a2016-10-20 05:07:12817 chromeos::MOUNT_ERROR_NONE, kDevice1MountPath);
yamaguchicafadf52016-09-15 09:05:53818 EXPECT_EQ(FormatEvent(DiskMountManager::FORMAT_STARTED,
yamaguchi934309a2016-10-20 05:07:12819 chromeos::FORMAT_ERROR_NONE, kDevice1SourcePath),
yamaguchicafadf52016-09-15 09:05:53820 observer_->GetFormatEvent(1));
821 EXPECT_EQ(FormatEvent(DiskMountManager::FORMAT_COMPLETED,
yamaguchi934309a2016-10-20 05:07:12822 chromeos::FORMAT_ERROR_UNKNOWN, kDevice1SourcePath),
yamaguchicafadf52016-09-15 09:05:53823 observer_->GetFormatEvent(2));
[email protected]e3c1fc92012-11-15 00:56:46824}
825
[email protected]e3c1fc92012-11-15 00:56:46826// Tests the case when formatting completes successfully.
827TEST_F(DiskMountManagerTest, Format_FormatSuccess) {
Klemen Kozjek46f1c6192017-08-25 19:20:54828 DiskMountManager* manager = DiskMountManager::GetInstance();
829 const DiskMountManager::DiskMap& disks = manager->disks();
830
[email protected]e3c1fc92012-11-15 00:56:46831 // Set up cros disks client mocks.
[email protected]f026c0f2014-05-06 21:52:35832 // Both unmount and format device cals are successful in this test.
[email protected]e3c1fc92012-11-15 00:56:46833
[email protected]e3c1fc92012-11-15 00:56:46834 // Start the test.
Austin Tankianga4b6a3f2019-06-28 06:51:38835 DiskMountManager::GetInstance()->FormatMountedDevice(
836 kDevice1MountPath, kFormatFileSystemType1, kFormatLabel1);
[email protected]e3c1fc92012-11-15 00:56:46837
[email protected]f026c0f2014-05-06 21:52:35838 // Wait for Unmount and Format calls to end.
fdorayf5b47fd12016-09-13 14:12:36839 base::RunLoop().RunUntilIdle();
[email protected]e3c1fc92012-11-15 00:56:46840
[email protected]cc70f5012013-05-14 04:58:56841 EXPECT_EQ(1, fake_cros_disks_client_->unmount_call_count());
yamaguchi934309a2016-10-20 05:07:12842 EXPECT_EQ(kDevice1MountPath,
[email protected]cc70f5012013-05-14 04:58:56843 fake_cros_disks_client_->last_unmount_device_path());
844 EXPECT_EQ(chromeos::UNMOUNT_OPTIONS_NONE,
845 fake_cros_disks_client_->last_unmount_options());
[email protected]f026c0f2014-05-06 21:52:35846 EXPECT_EQ(1, fake_cros_disks_client_->format_call_count());
yamaguchi934309a2016-10-20 05:07:12847 EXPECT_EQ(kDevice1SourcePath,
[email protected]f026c0f2014-05-06 21:52:35848 fake_cros_disks_client_->last_format_device_path());
Austin Tankiang2608bf72019-07-19 04:52:53849 EXPECT_EQ(kFormatFileSystemType1String,
Austin Tankianga4b6a3f2019-06-28 06:51:38850 fake_cros_disks_client_->last_format_filesystem());
851 EXPECT_EQ(kFormatLabel1, fake_cros_disks_client_->last_format_label());
[email protected]cc70f5012013-05-14 04:58:56852
[email protected]e3c1fc92012-11-15 00:56:46853 // The device should be unmounted by now.
yamaguchi934309a2016-10-20 05:07:12854 EXPECT_FALSE(HasMountPoint(kDevice1MountPath));
[email protected]e3c1fc92012-11-15 00:56:46855
856 // Simulate cros_disks reporting success.
Hidehiko Abe06ce6dc2017-12-08 19:32:03857 fake_cros_disks_client_->NotifyFormatCompleted(chromeos::FORMAT_ERROR_NONE,
858 kDevice1SourcePath);
yamaguchicafadf52016-09-15 09:05:53859
860 // The observer should receive UNMOUNTING, FORMAT_STARTED and FORMAT_COMPLETED
861 // events (all of them without an error set).
862 ASSERT_EQ(3U, observer_->GetEventCount());
863 VerifyMountEvent(observer_->GetMountEvent(0), DiskMountManager::UNMOUNTING,
yamaguchi934309a2016-10-20 05:07:12864 chromeos::MOUNT_ERROR_NONE, kDevice1MountPath);
yamaguchicafadf52016-09-15 09:05:53865 EXPECT_EQ(FormatEvent(DiskMountManager::FORMAT_STARTED,
yamaguchi934309a2016-10-20 05:07:12866 chromeos::FORMAT_ERROR_NONE, kDevice1SourcePath),
yamaguchicafadf52016-09-15 09:05:53867 observer_->GetFormatEvent(1));
868 EXPECT_EQ(FormatEvent(DiskMountManager::FORMAT_COMPLETED,
yamaguchi934309a2016-10-20 05:07:12869 chromeos::FORMAT_ERROR_NONE, kDevice1SourcePath),
yamaguchicafadf52016-09-15 09:05:53870 observer_->GetFormatEvent(2));
Klemen Kozjek46f1c6192017-08-25 19:20:54871
872 // Disk should have new values for file system type and device label name
Austin Tankiang2608bf72019-07-19 04:52:53873 EXPECT_EQ(kFormatFileSystemType1String,
Austin Tankianga4b6a3f2019-06-28 06:51:38874 disks.find(kDevice1SourcePath)->second->file_system_type());
875 EXPECT_EQ(kFormatLabel1,
876 disks.find(kDevice1SourcePath)->second->device_label());
[email protected]e3c1fc92012-11-15 00:56:46877}
878
879// Tests that it's possible to format the device twice in a row (this may not be
880// true if the list of pending formats is not properly cleared).
881TEST_F(DiskMountManagerTest, Format_ConsecutiveFormatCalls) {
[email protected]f026c0f2014-05-06 21:52:35882 // All unmount and format device cals are successful in this test.
[email protected]e3c1fc92012-11-15 00:56:46883 // Each of the should be made twice (once for each formatting task).
[email protected]e3c1fc92012-11-15 00:56:46884
[email protected]e3c1fc92012-11-15 00:56:46885 // Start the test.
Austin Tankianga4b6a3f2019-06-28 06:51:38886 DiskMountManager::GetInstance()->FormatMountedDevice(
887 kDevice1MountPath, kFormatFileSystemType1, kFormatLabel1);
[email protected]e3c1fc92012-11-15 00:56:46888
[email protected]f026c0f2014-05-06 21:52:35889 // Wait for Unmount and Format calls to end.
fdorayf5b47fd12016-09-13 14:12:36890 base::RunLoop().RunUntilIdle();
[email protected]e3c1fc92012-11-15 00:56:46891
[email protected]cc70f5012013-05-14 04:58:56892 EXPECT_EQ(1, fake_cros_disks_client_->unmount_call_count());
yamaguchi934309a2016-10-20 05:07:12893 EXPECT_EQ(kDevice1MountPath,
[email protected]cc70f5012013-05-14 04:58:56894 fake_cros_disks_client_->last_unmount_device_path());
895 EXPECT_EQ(chromeos::UNMOUNT_OPTIONS_NONE,
896 fake_cros_disks_client_->last_unmount_options());
[email protected]f026c0f2014-05-06 21:52:35897 EXPECT_EQ(1, fake_cros_disks_client_->format_call_count());
yamaguchi934309a2016-10-20 05:07:12898 EXPECT_EQ(kDevice1SourcePath,
[email protected]f026c0f2014-05-06 21:52:35899 fake_cros_disks_client_->last_format_device_path());
Austin Tankiang2608bf72019-07-19 04:52:53900 EXPECT_EQ(kFormatFileSystemType1String,
Austin Tankianga4b6a3f2019-06-28 06:51:38901 fake_cros_disks_client_->last_format_filesystem());
902 EXPECT_EQ(kFormatLabel1, fake_cros_disks_client_->last_format_label());
[email protected]cc70f5012013-05-14 04:58:56903
[email protected]e3c1fc92012-11-15 00:56:46904 // The device should be unmounted by now.
yamaguchi934309a2016-10-20 05:07:12905 EXPECT_FALSE(HasMountPoint(kDevice1MountPath));
[email protected]e3c1fc92012-11-15 00:56:46906
907 // Simulate cros_disks reporting success.
Hidehiko Abe06ce6dc2017-12-08 19:32:03908 fake_cros_disks_client_->NotifyFormatCompleted(chromeos::FORMAT_ERROR_NONE,
909 kDevice1SourcePath);
[email protected]e3c1fc92012-11-15 00:56:46910
911 // Simulate the device remounting.
Hidehiko Abe06ce6dc2017-12-08 19:32:03912 fake_cros_disks_client_->NotifyMountCompleted(
yamaguchi934309a2016-10-20 05:07:12913 chromeos::MOUNT_ERROR_NONE, kDevice1SourcePath,
914 chromeos::MOUNT_TYPE_DEVICE, kDevice1MountPath);
[email protected]e3c1fc92012-11-15 00:56:46915
yamaguchi934309a2016-10-20 05:07:12916 EXPECT_TRUE(HasMountPoint(kDevice1MountPath));
[email protected]e3c1fc92012-11-15 00:56:46917
918 // Try formatting again.
Austin Tankianga4b6a3f2019-06-28 06:51:38919 DiskMountManager::GetInstance()->FormatMountedDevice(
920 kDevice1MountPath, kFormatFileSystemType2, kFormatLabel2);
[email protected]e3c1fc92012-11-15 00:56:46921
[email protected]f026c0f2014-05-06 21:52:35922 // Wait for Unmount and Format calls to end.
fdorayf5b47fd12016-09-13 14:12:36923 base::RunLoop().RunUntilIdle();
[email protected]e3c1fc92012-11-15 00:56:46924
[email protected]cc70f5012013-05-14 04:58:56925 EXPECT_EQ(2, fake_cros_disks_client_->unmount_call_count());
yamaguchi934309a2016-10-20 05:07:12926 EXPECT_EQ(kDevice1MountPath,
[email protected]cc70f5012013-05-14 04:58:56927 fake_cros_disks_client_->last_unmount_device_path());
928 EXPECT_EQ(chromeos::UNMOUNT_OPTIONS_NONE,
929 fake_cros_disks_client_->last_unmount_options());
[email protected]f026c0f2014-05-06 21:52:35930 EXPECT_EQ(2, fake_cros_disks_client_->format_call_count());
yamaguchi934309a2016-10-20 05:07:12931 EXPECT_EQ(kDevice1SourcePath,
[email protected]f026c0f2014-05-06 21:52:35932 fake_cros_disks_client_->last_format_device_path());
Austin Tankiang2608bf72019-07-19 04:52:53933 EXPECT_EQ(kFormatFileSystemType2String,
Austin Tankianga4b6a3f2019-06-28 06:51:38934 fake_cros_disks_client_->last_format_filesystem());
935 EXPECT_EQ(kFormatLabel2, fake_cros_disks_client_->last_format_label());
[email protected]cc70f5012013-05-14 04:58:56936
[email protected]e3c1fc92012-11-15 00:56:46937 // Simulate cros_disks reporting success.
Hidehiko Abe06ce6dc2017-12-08 19:32:03938 fake_cros_disks_client_->NotifyFormatCompleted(chromeos::FORMAT_ERROR_NONE,
939 kDevice1SourcePath);
yamaguchicafadf52016-09-15 09:05:53940
941 // The observer should receive UNMOUNTING, FORMAT_STARTED and FORMAT_COMPLETED
942 // events (all of them without an error set) twice (once for each formatting
943 // task).
944 // Also, there should be a MOUNTING event when the device remounting is
945 // simulated.
946 EXPECT_EQ(7U, observer_->GetEventCount());
947
948 EXPECT_EQ(2U, observer_->CountFormatEvents(FormatEvent(
949 DiskMountManager::FORMAT_COMPLETED,
yamaguchi934309a2016-10-20 05:07:12950 chromeos::FORMAT_ERROR_NONE, kDevice1SourcePath)));
yamaguchicafadf52016-09-15 09:05:53951
952 EXPECT_EQ(2U, observer_->CountFormatEvents(FormatEvent(
953 DiskMountManager::FORMAT_STARTED,
yamaguchi934309a2016-10-20 05:07:12954 chromeos::FORMAT_ERROR_NONE, kDevice1SourcePath)));
yamaguchicafadf52016-09-15 09:05:53955
956 EXPECT_EQ(2U, observer_->CountMountEvents(DiskMountManager::UNMOUNTING,
957 chromeos::MOUNT_ERROR_NONE,
yamaguchi934309a2016-10-20 05:07:12958 kDevice1MountPath));
yamaguchicafadf52016-09-15 09:05:53959
960 EXPECT_EQ(1U, observer_->CountMountEvents(DiskMountManager::MOUNTING,
961 chromeos::MOUNT_ERROR_NONE,
yamaguchi934309a2016-10-20 05:07:12962 kDevice1MountPath));
[email protected]e3c1fc92012-11-15 00:56:46963}
964
yamaguchi6594bf7e12016-08-24 22:16:11965TEST_F(DiskMountManagerTest, MountPath_RecordAccessMode) {
966 DiskMountManager* manager = DiskMountManager::GetInstance();
yamaguchi934309a2016-10-20 05:07:12967 const std::string kSourcePath1 = kDevice1SourcePath;
968 const std::string kSourcePath2 = kDevice2SourcePath;
yamaguchi6594bf7e12016-08-24 22:16:11969 const std::string kSourceFormat = std::string();
970 const std::string kMountLabel = std::string(); // N/A for MOUNT_TYPE_DEVICE
971 // For MountCompleted. Must be non-empty strings.
972 const std::string kMountPath1 = "/media/foo";
973 const std::string kMountPath2 = "/media/bar";
974
Sergei Datsenkod19248182018-05-11 01:52:56975 manager->MountPath(kSourcePath1, kSourceFormat, std::string(), {},
yamaguchi6594bf7e12016-08-24 22:16:11976 chromeos::MOUNT_TYPE_DEVICE,
977 chromeos::MOUNT_ACCESS_MODE_READ_WRITE);
Sergei Datsenkod19248182018-05-11 01:52:56978 manager->MountPath(kSourcePath2, kSourceFormat, std::string(), {},
yamaguchi6594bf7e12016-08-24 22:16:11979 chromeos::MOUNT_TYPE_DEVICE,
980 chromeos::MOUNT_ACCESS_MODE_READ_ONLY);
981 // Simulate cros_disks reporting mount completed.
Hidehiko Abe06ce6dc2017-12-08 19:32:03982 fake_cros_disks_client_->NotifyMountCompleted(
yamaguchi6594bf7e12016-08-24 22:16:11983 chromeos::MOUNT_ERROR_NONE, kSourcePath1, chromeos::MOUNT_TYPE_DEVICE,
984 kMountPath1);
Hidehiko Abe06ce6dc2017-12-08 19:32:03985 fake_cros_disks_client_->NotifyMountCompleted(
yamaguchi6594bf7e12016-08-24 22:16:11986 chromeos::MOUNT_ERROR_NONE, kSourcePath2, chromeos::MOUNT_TYPE_DEVICE,
987 kMountPath2);
988
yamaguchicafadf52016-09-15 09:05:53989 // Event handlers of observers should be called.
990 ASSERT_EQ(2U, observer_->GetEventCount());
991 VerifyMountEvent(observer_->GetMountEvent(0), DiskMountManager::MOUNTING,
992 chromeos::MOUNT_ERROR_NONE, kMountPath1);
993 // For the 2nd source, the disk (block device) is not read-only but the
994 // test will mount it in read-only mode.
995 // Observers query |disks_| from |DiskMountManager| in its event handler for
996 // a mount completion event. Therefore |disks_| must be updated with correct
997 // |read_only| value before notifying to observers.
998 const MountEvent& secondMountEvent = observer_->GetMountEvent(1);
999 EXPECT_EQ(DiskMountManager::MOUNTING, secondMountEvent.event);
1000 EXPECT_EQ(chromeos::MOUNT_ERROR_NONE, secondMountEvent.error_code);
1001 EXPECT_EQ(kMountPath2, secondMountEvent.mount_point.mount_path);
1002 // Verify if the disk appears read-only at the time of notification to
1003 // observers.
1004 EXPECT_TRUE(secondMountEvent.disk->is_read_only());
1005
1006 // Verify the final state of manager->disks.
yamaguchi6594bf7e12016-08-24 22:16:111007 const DiskMountManager::DiskMap& disks = manager->disks();
1008 ASSERT_GT(disks.count(kSourcePath1), 0U);
1009 EXPECT_FALSE(disks.find(kSourcePath1)->second->is_read_only());
1010 ASSERT_GT(disks.count(kSourcePath2), 0U);
1011 EXPECT_TRUE(disks.find(kSourcePath2)->second->is_read_only());
1012}
1013
yamaguchi21448d5b2016-09-06 02:04:561014TEST_F(DiskMountManagerTest, MountPath_ReadOnlyDevice) {
1015 DiskMountManager* manager = DiskMountManager::GetInstance();
1016 const std::string kSourceFormat = std::string();
1017 const std::string kMountLabel = std::string(); // N/A for MOUNT_TYPE_DEVICE
1018
yamaguchi21448d5b2016-09-06 02:04:561019 // Attempt to mount a read-only device in read-write mode.
yamaguchi934309a2016-10-20 05:07:121020 manager->MountPath(kReadOnlyDeviceSourcePath, kSourceFormat, std::string(),
Sergei Datsenkod19248182018-05-11 01:52:561021 {}, chromeos::MOUNT_TYPE_DEVICE,
yamaguchi21448d5b2016-09-06 02:04:561022 chromeos::MOUNT_ACCESS_MODE_READ_WRITE);
1023 // Simulate cros_disks reporting mount completed.
Hidehiko Abe06ce6dc2017-12-08 19:32:031024 fake_cros_disks_client_->NotifyMountCompleted(
yamaguchi934309a2016-10-20 05:07:121025 chromeos::MOUNT_ERROR_NONE, kReadOnlyDeviceSourcePath,
1026 chromeos::MOUNT_TYPE_DEVICE, kReadOnlyDeviceMountPath);
yamaguchi21448d5b2016-09-06 02:04:561027
yamaguchicafadf52016-09-15 09:05:531028 // Event handlers of observers should be called.
1029 ASSERT_EQ(1U, observer_->GetEventCount());
1030 VerifyMountEvent(observer_->GetMountEvent(0), DiskMountManager::MOUNTING,
yamaguchi934309a2016-10-20 05:07:121031 chromeos::MOUNT_ERROR_NONE, kReadOnlyDeviceMountPath);
yamaguchi21448d5b2016-09-06 02:04:561032 const DiskMountManager::DiskMap& disks = manager->disks();
yamaguchi934309a2016-10-20 05:07:121033 ASSERT_GT(disks.count(kReadOnlyDeviceSourcePath), 0U);
yamaguchi21448d5b2016-09-06 02:04:561034 // The mounted disk should preserve the read-only flag of the block device.
yamaguchi934309a2016-10-20 05:07:121035 EXPECT_TRUE(disks.find(kReadOnlyDeviceSourcePath)->second->is_read_only());
yamaguchi21448d5b2016-09-06 02:04:561036}
1037
yamaguchide59ed62016-11-08 10:07:101038TEST_F(DiskMountManagerTest, RemountRemovableDrives) {
1039 DiskMountManager* manager = DiskMountManager::GetInstance();
1040 // Initially we have 2 mounted devices.
1041 // kDevice1MountPath --- read-write device, mounted in read-write mode.
1042 // kReadOnlyDeviceMountPath --- read-only device, mounted in read-only mode.
1043
1044 manager->RemountAllRemovableDrives(chromeos::MOUNT_ACCESS_MODE_READ_ONLY);
1045
1046 // Simulate cros_disks reporting mount completed.
Hidehiko Abe06ce6dc2017-12-08 19:32:031047 fake_cros_disks_client_->NotifyMountCompleted(
yamaguchide59ed62016-11-08 10:07:101048 chromeos::MOUNT_ERROR_NONE, kDevice1SourcePath,
1049 chromeos::MOUNT_TYPE_DEVICE, kDevice1MountPath);
1050
1051 // Should remount disks that are not read-only by its hardware device.
1052 ASSERT_EQ(1U, observer_->GetEventCount());
1053 VerifyMountEvent(observer_->GetMountEvent(0), DiskMountManager::MOUNTING,
1054 chromeos::MOUNT_ERROR_NONE, kDevice1MountPath);
1055 // The disk is remounted in read-only mode.
1056 EXPECT_TRUE(
1057 manager->FindDiskBySourcePath(kDevice1SourcePath)->is_read_only());
1058 // Remounted disk should also appear as read-only to observers.
1059 EXPECT_TRUE(observer_->GetMountEvent(0).disk->is_read_only());
1060
1061 // Remount in read-write mode again.
1062 manager->RemountAllRemovableDrives(chromeos::MOUNT_ACCESS_MODE_READ_WRITE);
1063
1064 // Simulate cros_disks reporting mount completed.
Hidehiko Abe06ce6dc2017-12-08 19:32:031065 fake_cros_disks_client_->NotifyMountCompleted(
yamaguchide59ed62016-11-08 10:07:101066 chromeos::MOUNT_ERROR_NONE, kDevice1SourcePath,
1067 chromeos::MOUNT_TYPE_DEVICE, kDevice1MountPath);
1068 // Event handlers of observers should be called.
1069 ASSERT_EQ(2U, observer_->GetEventCount());
1070 VerifyMountEvent(observer_->GetMountEvent(1), DiskMountManager::MOUNTING,
1071 chromeos::MOUNT_ERROR_NONE, kDevice1MountPath);
1072 // The read-write device should be remounted in read-write mode.
1073 EXPECT_FALSE(
1074 manager->FindDiskBySourcePath(kDevice1SourcePath)->is_read_only());
1075 // Remounted disk should also appear as writable to observers.
1076 EXPECT_FALSE(observer_->GetMountEvent(1).disk->is_read_only());
1077}
1078
Klemen Kozjekdb1d04e2017-08-25 22:01:501079// Tests that the observer gets notified on attempt to rename non existent mount
1080// point.
1081TEST_F(DiskMountManagerTest, Rename_NotMounted) {
1082 DiskMountManager::GetInstance()->RenameMountedDevice("/mount/non_existent",
1083 "MYUSB");
1084 ASSERT_EQ(1U, observer_->GetEventCount());
1085 EXPECT_EQ(RenameEvent(DiskMountManager::RENAME_COMPLETED,
1086 chromeos::RENAME_ERROR_UNKNOWN, "/mount/non_existent"),
1087 observer_->GetRenameEvent(0));
1088}
1089
1090// Tests that the observer gets notified on attempt to rename read-only mount
1091// point.
1092TEST_F(DiskMountManagerTest, Rename_ReadOnly) {
1093 DiskMountManager::GetInstance()->RenameMountedDevice(kReadOnlyDeviceMountPath,
1094 "MYUSB");
1095 ASSERT_EQ(1U, observer_->GetEventCount());
1096 EXPECT_EQ(RenameEvent(DiskMountManager::RENAME_COMPLETED,
1097 chromeos::RENAME_ERROR_DEVICE_NOT_ALLOWED,
1098 kReadOnlyDeviceMountPath),
1099 observer_->GetRenameEvent(0));
1100}
1101
1102// Tests that it is not possible to rename archive mount point.
1103TEST_F(DiskMountManagerTest, Rename_Archive) {
1104 DiskMountManager::GetInstance()->RenameMountedDevice("/archive/mount_path",
1105 "MYUSB");
1106 ASSERT_EQ(1U, observer_->GetEventCount());
1107 EXPECT_EQ(RenameEvent(DiskMountManager::RENAME_COMPLETED,
1108 chromeos::RENAME_ERROR_UNKNOWN, "/archive/source_path"),
1109 observer_->GetRenameEvent(0));
1110}
1111
1112// Tests that rename fails if the device cannot be unmounted.
1113TEST_F(DiskMountManagerTest, Rename_FailToUnmount) {
1114 // Before renaming mounted device, the device should be unmounted.
1115 // In this test unmount will fail, and there should be no attempt to
1116 // rename the device.
1117
Anand K. Mistry9647a6e2018-08-20 00:33:101118 fake_cros_disks_client_->MakeUnmountFail(chromeos::MOUNT_ERROR_UNKNOWN);
Klemen Kozjekdb1d04e2017-08-25 22:01:501119 // Start test.
1120 DiskMountManager::GetInstance()->RenameMountedDevice(kDevice1MountPath,
1121 "MYUSB");
1122
1123 // Cros disks will respond asynchronoulsy, so let's drain the message loop.
1124 base::RunLoop().RunUntilIdle();
1125
1126 // Observer should be notified that unmount attempt fails and rename task
1127 // failed to start.
1128 ASSERT_EQ(2U, observer_->GetEventCount());
1129 const MountEvent& mount_event = observer_->GetMountEvent(0);
1130 EXPECT_EQ(DiskMountManager::UNMOUNTING, mount_event.event);
Anand K. Mistry9647a6e2018-08-20 00:33:101131 EXPECT_EQ(chromeos::MOUNT_ERROR_UNKNOWN, mount_event.error_code);
Klemen Kozjekdb1d04e2017-08-25 22:01:501132 EXPECT_EQ(kDevice1MountPath, mount_event.mount_point.mount_path);
1133
1134 EXPECT_EQ(RenameEvent(DiskMountManager::RENAME_COMPLETED,
1135 chromeos::RENAME_ERROR_UNKNOWN, kDevice1SourcePath),
1136 observer_->GetRenameEvent(1));
1137 EXPECT_EQ(1, fake_cros_disks_client_->unmount_call_count());
1138 EXPECT_EQ(kDevice1MountPath,
1139 fake_cros_disks_client_->last_unmount_device_path());
1140 EXPECT_EQ(chromeos::UNMOUNT_OPTIONS_NONE,
1141 fake_cros_disks_client_->last_unmount_options());
1142 EXPECT_EQ(0, fake_cros_disks_client_->rename_call_count());
1143
1144 // The device mount should still be here.
1145 EXPECT_TRUE(HasMountPoint(kDevice1MountPath));
1146}
1147
1148// Tests that observer is notified when cros disks fails to start rename
1149// process.
1150TEST_F(DiskMountManagerTest, Rename_RenameFailsToStart) {
1151 // Before renaming mounted device, the device should be unmounted.
1152 // In this test, unmount will succeed, but call to Rename method will
1153 // fail.
1154
1155 fake_cros_disks_client_->MakeRenameFail();
1156 // Start the test.
1157 DiskMountManager::GetInstance()->RenameMountedDevice(kDevice1MountPath,
1158 "MYUSB");
1159
1160 // Cros disks will respond asynchronoulsy, so let's drain the message loop.
1161 base::RunLoop().RunUntilIdle();
1162
1163 // Observer should be notified that the device was unmounted and rename task
1164 // failed to start.
1165 ASSERT_EQ(2U, observer_->GetEventCount());
1166 const MountEvent& mount_event = observer_->GetMountEvent(0);
1167 EXPECT_EQ(DiskMountManager::UNMOUNTING, mount_event.event);
1168 EXPECT_EQ(chromeos::MOUNT_ERROR_NONE, mount_event.error_code);
1169 EXPECT_EQ(kDevice1MountPath, mount_event.mount_point.mount_path);
1170
1171 EXPECT_EQ(RenameEvent(DiskMountManager::RENAME_COMPLETED,
1172 chromeos::RENAME_ERROR_UNKNOWN, kDevice1SourcePath),
1173 observer_->GetRenameEvent(1));
1174
1175 EXPECT_EQ(1, fake_cros_disks_client_->unmount_call_count());
1176 EXPECT_EQ(kDevice1MountPath,
1177 fake_cros_disks_client_->last_unmount_device_path());
1178 EXPECT_EQ(chromeos::UNMOUNT_OPTIONS_NONE,
1179 fake_cros_disks_client_->last_unmount_options());
1180 EXPECT_EQ(1, fake_cros_disks_client_->rename_call_count());
1181 EXPECT_EQ(kDevice1SourcePath,
1182 fake_cros_disks_client_->last_rename_device_path());
1183 EXPECT_EQ("MYUSB", fake_cros_disks_client_->last_rename_volume_name());
1184
1185 // The device mount should be gone.
1186 EXPECT_FALSE(HasMountPoint(kDevice1MountPath));
1187}
1188
1189// Tests the case where there are two rename requests for the same device.
1190TEST_F(DiskMountManagerTest, Rename_ConcurrentRenameCalls) {
1191 // Only the first rename request should be processed (the second unmount
1192 // request fails because the device is already unmounted at that point).
1193 // CrosDisksClient will report that the rename process for the first request
1194 // is successfully started.
1195
1196 fake_cros_disks_client_->set_unmount_listener(
Anand K. Mistryc10d4c192018-08-28 00:17:381197 base::BindRepeating(&FakeCrosDisksClient::MakeUnmountFail,
1198 base::Unretained(fake_cros_disks_client_),
1199 chromeos::MOUNT_ERROR_INTERNAL));
Klemen Kozjekdb1d04e2017-08-25 22:01:501200 // Start the test.
1201 DiskMountManager::GetInstance()->RenameMountedDevice(kDevice1MountPath,
1202 "MYUSB1");
1203 DiskMountManager::GetInstance()->RenameMountedDevice(kDevice1MountPath,
1204 "MYUSB2");
1205
1206 // Cros disks will respond asynchronoulsy, so let's drain the message loop.
1207 base::RunLoop().RunUntilIdle();
1208
1209 // The observer should get a RENAME_STARTED event for one rename request and a
1210 // RENAME_COMPLETED with an error code for the other rename request. The
1211 // renaming will be started only for the first request.
1212 // There should be only one UNMOUNTING event. The result of the second one
1213 // should not be reported as the mount point will go away after the first
1214 // request.
1215 //
1216 // Note that in this test the rename completion signal will not be simulated,
1217 // so the observer should not get RENAME_COMPLETED signal.
1218
1219 ASSERT_EQ(3U, observer_->GetEventCount());
1220 const MountEvent& mount_event = observer_->GetMountEvent(0);
1221 EXPECT_EQ(DiskMountManager::UNMOUNTING, mount_event.event);
1222 EXPECT_EQ(chromeos::MOUNT_ERROR_NONE, mount_event.error_code);
1223 EXPECT_EQ(kDevice1MountPath, mount_event.mount_point.mount_path);
1224 EXPECT_EQ(RenameEvent(DiskMountManager::RENAME_COMPLETED,
1225 chromeos::RENAME_ERROR_UNKNOWN, kDevice1SourcePath),
1226 observer_->GetRenameEvent(1));
1227 EXPECT_EQ(RenameEvent(DiskMountManager::RENAME_STARTED,
1228 chromeos::RENAME_ERROR_NONE, kDevice1SourcePath),
1229 observer_->GetRenameEvent(2));
1230
1231 EXPECT_EQ(2, fake_cros_disks_client_->unmount_call_count());
1232 EXPECT_EQ(kDevice1MountPath,
1233 fake_cros_disks_client_->last_unmount_device_path());
1234 EXPECT_EQ(chromeos::UNMOUNT_OPTIONS_NONE,
1235 fake_cros_disks_client_->last_unmount_options());
1236 EXPECT_EQ(1, fake_cros_disks_client_->rename_call_count());
1237 EXPECT_EQ(kDevice1SourcePath,
1238 fake_cros_disks_client_->last_rename_device_path());
1239 EXPECT_EQ("MYUSB1", fake_cros_disks_client_->last_rename_volume_name());
1240
1241 // The device mount should be gone.
1242 EXPECT_FALSE(HasMountPoint(kDevice1MountPath));
1243}
1244
1245// Tests the case when the rename process actually starts and fails.
1246TEST_F(DiskMountManagerTest, Rename_RenameFails) {
1247 // Both unmount and rename device calls are successful in this test.
1248
1249 // Start the test.
1250 DiskMountManager::GetInstance()->RenameMountedDevice(kDevice1MountPath,
1251 "MYUSB");
1252
1253 // Wait for Unmount and Rename calls to end.
1254 base::RunLoop().RunUntilIdle();
1255
1256 EXPECT_EQ(1, fake_cros_disks_client_->unmount_call_count());
1257 EXPECT_EQ(kDevice1MountPath,
1258 fake_cros_disks_client_->last_unmount_device_path());
1259 EXPECT_EQ(chromeos::UNMOUNT_OPTIONS_NONE,
1260 fake_cros_disks_client_->last_unmount_options());
1261 EXPECT_EQ(1, fake_cros_disks_client_->rename_call_count());
1262 EXPECT_EQ(kDevice1SourcePath,
1263 fake_cros_disks_client_->last_rename_device_path());
1264 EXPECT_EQ("MYUSB", fake_cros_disks_client_->last_rename_volume_name());
1265
1266 // The device should be unmounted by now.
1267 EXPECT_FALSE(HasMountPoint(kDevice1MountPath));
1268
1269 // Send failing RENAME_COMPLETED signal.
1270 // The failure is marked by ! in fromt of the path (but this should change
1271 // soon).
Hidehiko Abe06ce6dc2017-12-08 19:32:031272 fake_cros_disks_client_->NotifyRenameCompleted(chromeos::RENAME_ERROR_UNKNOWN,
1273 kDevice1SourcePath);
Klemen Kozjekdb1d04e2017-08-25 22:01:501274
1275 // The observer should get notified that the device was unmounted and that
1276 // renaming has started.
1277 // After the renaming starts, the test will simulate failing
1278 // RENAME_COMPLETED signal, so the observer should also be notified the
1279 // renaming has failed (RENAME_COMPLETED event).
1280 ASSERT_EQ(3U, observer_->GetEventCount());
1281 VerifyMountEvent(observer_->GetMountEvent(0), DiskMountManager::UNMOUNTING,
1282 chromeos::MOUNT_ERROR_NONE, kDevice1MountPath);
1283 EXPECT_EQ(RenameEvent(DiskMountManager::RENAME_STARTED,
1284 chromeos::RENAME_ERROR_NONE, kDevice1SourcePath),
1285 observer_->GetRenameEvent(1));
1286 EXPECT_EQ(RenameEvent(DiskMountManager::RENAME_COMPLETED,
1287 chromeos::RENAME_ERROR_UNKNOWN, kDevice1SourcePath),
1288 observer_->GetRenameEvent(2));
1289}
1290
1291// Tests the case when renaming completes successfully.
1292TEST_F(DiskMountManagerTest, Rename_RenameSuccess) {
1293 DiskMountManager* manager = DiskMountManager::GetInstance();
1294 const DiskMountManager::DiskMap& disks = manager->disks();
1295 // Set up cros disks client mocks.
1296 // Both unmount and rename device calls are successful in this test.
1297
1298 // Start the test.
1299 DiskMountManager::GetInstance()->RenameMountedDevice(kDevice1MountPath,
1300 "MYUSB1");
1301
1302 // Wait for Unmount and Rename calls to end.
1303 base::RunLoop().RunUntilIdle();
1304
1305 EXPECT_EQ(1, fake_cros_disks_client_->unmount_call_count());
1306 EXPECT_EQ(kDevice1MountPath,
1307 fake_cros_disks_client_->last_unmount_device_path());
1308 EXPECT_EQ(chromeos::UNMOUNT_OPTIONS_NONE,
1309 fake_cros_disks_client_->last_unmount_options());
1310 EXPECT_EQ(1, fake_cros_disks_client_->rename_call_count());
1311 EXPECT_EQ(kDevice1SourcePath,
1312 fake_cros_disks_client_->last_rename_device_path());
1313 EXPECT_EQ("MYUSB1", fake_cros_disks_client_->last_rename_volume_name());
1314
1315 // The device should be unmounted by now.
1316 EXPECT_FALSE(HasMountPoint(kDevice1MountPath));
1317
1318 // Simulate cros_disks reporting success.
Hidehiko Abe06ce6dc2017-12-08 19:32:031319 fake_cros_disks_client_->NotifyRenameCompleted(chromeos::RENAME_ERROR_NONE,
1320 kDevice1SourcePath);
Klemen Kozjekdb1d04e2017-08-25 22:01:501321
1322 // The observer should receive UNMOUNTING, RENAME_STARTED and RENAME_COMPLETED
1323 // events (all of them without an error set).
1324 ASSERT_EQ(3U, observer_->GetEventCount());
1325 VerifyMountEvent(observer_->GetMountEvent(0), DiskMountManager::UNMOUNTING,
1326 chromeos::MOUNT_ERROR_NONE, kDevice1MountPath);
1327 EXPECT_EQ(RenameEvent(DiskMountManager::RENAME_STARTED,
1328 chromeos::RENAME_ERROR_NONE, kDevice1SourcePath),
1329 observer_->GetRenameEvent(1));
1330 EXPECT_EQ(RenameEvent(DiskMountManager::RENAME_COMPLETED,
1331 chromeos::RENAME_ERROR_NONE, kDevice1SourcePath),
1332 observer_->GetRenameEvent(2));
1333
1334 // Disk should have new value for device label name
1335 EXPECT_EQ("MYUSB1", disks.find(kDevice1SourcePath)->second->device_label());
1336}
1337
1338// Tests that it's possible to rename the device twice in a row (this may not be
1339// true if the list of pending renames is not properly cleared).
1340TEST_F(DiskMountManagerTest, Rename_ConsecutiveRenameCalls) {
1341 DiskMountManager* manager = DiskMountManager::GetInstance();
1342 const DiskMountManager::DiskMap& disks = manager->disks();
1343 // All unmount and rename device calls are successful in this test.
1344 // Each of the should be made twice (once for each renaming task).
1345
1346 // Start the test.
1347 DiskMountManager::GetInstance()->RenameMountedDevice(kDevice1MountPath,
1348 "MYUSB");
1349
1350 // Wait for Unmount and Rename calls to end.
1351 base::RunLoop().RunUntilIdle();
1352
1353 EXPECT_EQ(1, fake_cros_disks_client_->unmount_call_count());
1354 EXPECT_EQ(kDevice1MountPath,
1355 fake_cros_disks_client_->last_unmount_device_path());
1356 EXPECT_EQ(chromeos::UNMOUNT_OPTIONS_NONE,
1357 fake_cros_disks_client_->last_unmount_options());
1358 EXPECT_EQ(1, fake_cros_disks_client_->rename_call_count());
1359 EXPECT_EQ(kDevice1SourcePath,
1360 fake_cros_disks_client_->last_rename_device_path());
1361 EXPECT_EQ("MYUSB", fake_cros_disks_client_->last_rename_volume_name());
1362 EXPECT_EQ("", disks.find(kDevice1SourcePath)->second->base_mount_path());
1363
1364 // The device should be unmounted by now.
1365 EXPECT_FALSE(HasMountPoint(kDevice1MountPath));
1366
1367 // Simulate cros_disks reporting success.
Hidehiko Abe06ce6dc2017-12-08 19:32:031368 fake_cros_disks_client_->NotifyRenameCompleted(chromeos::RENAME_ERROR_NONE,
1369 kDevice1SourcePath);
Klemen Kozjekdb1d04e2017-08-25 22:01:501370
1371 // Simulate the device remounting.
Hidehiko Abe06ce6dc2017-12-08 19:32:031372 fake_cros_disks_client_->NotifyMountCompleted(
Klemen Kozjekdb1d04e2017-08-25 22:01:501373 chromeos::MOUNT_ERROR_NONE, kDevice1SourcePath,
1374 chromeos::MOUNT_TYPE_DEVICE, kDevice1MountPath);
1375
1376 EXPECT_TRUE(HasMountPoint(kDevice1MountPath));
1377
1378 auto previousMountPath = disks.find(kDevice1SourcePath)->second->mount_path();
1379 // Try renaming again.
1380 DiskMountManager::GetInstance()->RenameMountedDevice(kDevice1MountPath,
1381 "MYUSB2");
1382
1383 // Wait for Unmount and Rename calls to end.
1384 base::RunLoop().RunUntilIdle();
1385
1386 EXPECT_EQ(2, fake_cros_disks_client_->unmount_call_count());
1387 EXPECT_EQ(kDevice1MountPath,
1388 fake_cros_disks_client_->last_unmount_device_path());
1389 EXPECT_EQ(chromeos::UNMOUNT_OPTIONS_NONE,
1390 fake_cros_disks_client_->last_unmount_options());
1391 EXPECT_EQ(2, fake_cros_disks_client_->rename_call_count());
1392 EXPECT_EQ(kDevice1SourcePath,
1393 fake_cros_disks_client_->last_rename_device_path());
1394 EXPECT_EQ("MYUSB2", fake_cros_disks_client_->last_rename_volume_name());
1395 // Base mount path should be set to previous mount path.
1396 EXPECT_EQ(previousMountPath,
1397 disks.find(kDevice1SourcePath)->second->base_mount_path());
1398
1399 // Simulate cros_disks reporting success.
Hidehiko Abe06ce6dc2017-12-08 19:32:031400 fake_cros_disks_client_->NotifyRenameCompleted(chromeos::RENAME_ERROR_NONE,
1401 kDevice1SourcePath);
Klemen Kozjekdb1d04e2017-08-25 22:01:501402
1403 // The observer should receive UNMOUNTING, RENAME_STARTED and RENAME_COMPLETED
1404 // events (all of them without an error set) twice (once for each renaming
1405 // task).
1406 // Also, there should be a MOUNTING event when the device remounting is
1407 // simulated.
1408 EXPECT_EQ(7U, observer_->GetEventCount());
1409
1410 EXPECT_EQ(2U, observer_->CountRenameEvents(RenameEvent(
1411 DiskMountManager::RENAME_COMPLETED,
1412 chromeos::RENAME_ERROR_NONE, kDevice1SourcePath)));
1413
1414 EXPECT_EQ(2U, observer_->CountRenameEvents(RenameEvent(
1415 DiskMountManager::RENAME_STARTED,
1416 chromeos::RENAME_ERROR_NONE, kDevice1SourcePath)));
1417
1418 EXPECT_EQ(2U, observer_->CountMountEvents(DiskMountManager::UNMOUNTING,
1419 chromeos::MOUNT_ERROR_NONE,
1420 kDevice1MountPath));
1421
1422 EXPECT_EQ(1U, observer_->CountMountEvents(DiskMountManager::MOUNTING,
1423 chromeos::MOUNT_ERROR_NONE,
1424 kDevice1MountPath));
1425}
1426
Anand K. Mistry620679652018-08-21 03:18:221427void SaveUnmountResult(MountError* save_error,
1428 base::OnceClosure done_callback,
1429 MountError error_code) {
1430 *save_error = error_code;
1431 std::move(done_callback).Run();
1432}
1433
1434TEST_F(DiskMountManagerTest, UnmountDeviceRecursively) {
1435 base::RunLoop run_loop;
1436
1437 auto disk_sda =
1438 Disk::Builder().SetDevicePath("/dev/sda").SetIsParent(true).Build();
1439 EXPECT_TRUE(
1440 DiskMountManager::GetInstance()->AddDiskForTest(std::move(disk_sda)));
1441
1442 auto disk_sda1 = Disk::Builder()
1443 .SetDevicePath("/dev/sda1")
1444 .SetMountPath("/mount/path1")
1445 .Build();
1446 EXPECT_TRUE(
1447 DiskMountManager::GetInstance()->AddDiskForTest(std::move(disk_sda1)));
1448
1449 auto disk_sda2 = Disk::Builder()
1450 .SetDevicePath("/dev/sda2")
1451 .SetMountPath("/mount/path2")
1452 .Build();
1453 EXPECT_TRUE(
1454 DiskMountManager::GetInstance()->AddDiskForTest(std::move(disk_sda2)));
1455
1456 MountError error_code = chromeos::MOUNT_ERROR_UNKNOWN;
1457 DiskMountManager::GetInstance()->UnmountDeviceRecursively(
1458 "/dev/sda",
1459 base::BindOnce(&SaveUnmountResult, base::Unretained(&error_code),
1460 run_loop.QuitClosure()));
1461 run_loop.Run();
1462
1463 EXPECT_EQ(2, fake_cros_disks_client_->unmount_call_count());
1464 EXPECT_EQ(chromeos::UNMOUNT_OPTIONS_NONE,
1465 fake_cros_disks_client_->last_unmount_options());
1466 EXPECT_EQ(chromeos::MOUNT_ERROR_NONE, error_code);
1467}
1468
1469TEST_F(DiskMountManagerTest, UnmountDeviceRecursively_NoMounted) {
1470 base::RunLoop run_loop;
1471
1472 auto disk_sda =
1473 Disk::Builder().SetDevicePath("/dev/sda").SetIsParent(true).Build();
1474 EXPECT_TRUE(
1475 DiskMountManager::GetInstance()->AddDiskForTest(std::move(disk_sda)));
1476
1477 auto disk_sda1 = Disk::Builder().SetDevicePath("/dev/sda1").Build();
1478 EXPECT_TRUE(
1479 DiskMountManager::GetInstance()->AddDiskForTest(std::move(disk_sda1)));
1480
1481 MountError error_code = chromeos::MOUNT_ERROR_UNKNOWN;
1482 DiskMountManager::GetInstance()->UnmountDeviceRecursively(
1483 "/dev/sda",
1484 base::BindOnce(&SaveUnmountResult, base::Unretained(&error_code),
1485 run_loop.QuitClosure()));
1486 run_loop.Run();
1487
1488 EXPECT_EQ(0, fake_cros_disks_client_->unmount_call_count());
1489 EXPECT_EQ(chromeos::MOUNT_ERROR_NONE, error_code);
1490}
1491
1492TEST_F(DiskMountManagerTest, UnmountDeviceRecursively_NoDisk) {
1493 base::RunLoop run_loop;
1494
1495 auto disk_sda =
1496 Disk::Builder().SetDevicePath("/dev/sda").SetIsParent(true).Build();
1497 EXPECT_TRUE(
1498 DiskMountManager::GetInstance()->AddDiskForTest(std::move(disk_sda)));
1499
1500 auto disk_sda1 = Disk::Builder().SetDevicePath("/dev/sda1").Build();
1501 EXPECT_TRUE(
1502 DiskMountManager::GetInstance()->AddDiskForTest(std::move(disk_sda1)));
1503
1504 MountError error_code = chromeos::MOUNT_ERROR_UNKNOWN;
1505 // Unmount sdB instead of sdA.
1506 DiskMountManager::GetInstance()->UnmountDeviceRecursively(
1507 "/dev/sdb",
1508 base::BindOnce(&SaveUnmountResult, base::Unretained(&error_code),
1509 run_loop.QuitClosure()));
1510 run_loop.Run();
1511
1512 EXPECT_EQ(0, fake_cros_disks_client_->unmount_call_count());
1513 EXPECT_EQ(chromeos::MOUNT_ERROR_INVALID_DEVICE_PATH, error_code);
1514}
1515
1516void SetUnmountError(FakeCrosDisksClient* client, MountError error_code) {
1517 client->MakeUnmountFail(error_code);
1518}
1519
1520TEST_F(DiskMountManagerTest, UnmountDeviceRecursively_FailFirst) {
1521 base::RunLoop run_loop;
1522
1523 auto disk_sda =
1524 Disk::Builder().SetDevicePath("/dev/sda").SetIsParent(true).Build();
1525 EXPECT_TRUE(
1526 DiskMountManager::GetInstance()->AddDiskForTest(std::move(disk_sda)));
1527
1528 auto disk_sda1 = Disk::Builder()
1529 .SetDevicePath("/dev/sda1")
1530 .SetMountPath("/mount/path1")
1531 .Build();
1532 EXPECT_TRUE(
1533 DiskMountManager::GetInstance()->AddDiskForTest(std::move(disk_sda1)));
1534
1535 auto disk_sda2 = Disk::Builder()
1536 .SetDevicePath("/dev/sda2")
1537 .SetMountPath("/mount/path2")
1538 .Build();
1539 EXPECT_TRUE(
1540 DiskMountManager::GetInstance()->AddDiskForTest(std::move(disk_sda2)));
1541
1542 // Fail the first unmount, but make the second succeed.
1543 fake_cros_disks_client_->MakeUnmountFail(
1544 chromeos::MOUNT_ERROR_INVALID_UNMOUNT_OPTIONS);
Anand K. Mistryc10d4c192018-08-28 00:17:381545 fake_cros_disks_client_->set_unmount_listener(base::BindRepeating(
1546 &SetUnmountError, base::Unretained(fake_cros_disks_client_),
1547 chromeos::MOUNT_ERROR_NONE));
Anand K. Mistry620679652018-08-21 03:18:221548
1549 MountError error_code = chromeos::MOUNT_ERROR_UNKNOWN;
1550 DiskMountManager::GetInstance()->UnmountDeviceRecursively(
1551 "/dev/sda",
1552 base::BindOnce(&SaveUnmountResult, base::Unretained(&error_code),
1553 run_loop.QuitClosure()));
1554 run_loop.Run();
1555
1556 EXPECT_EQ(2, fake_cros_disks_client_->unmount_call_count());
1557 EXPECT_EQ(chromeos::UNMOUNT_OPTIONS_NONE,
1558 fake_cros_disks_client_->last_unmount_options());
1559 EXPECT_EQ(chromeos::MOUNT_ERROR_INVALID_UNMOUNT_OPTIONS, error_code);
1560}
1561
Sergei Datsenko89391e92019-06-26 01:15:251562TEST_F(DiskMountManagerTest, UnmountDeviceRecursively_AlreadyUnmounted) {
1563 base::RunLoop run_loop;
1564
1565 auto disk_sda =
1566 Disk::Builder().SetDevicePath("/dev/sda").SetIsParent(true).Build();
1567 EXPECT_TRUE(
1568 DiskMountManager::GetInstance()->AddDiskForTest(std::move(disk_sda)));
1569
1570 auto disk_sda1 = Disk::Builder()
1571 .SetDevicePath("/dev/sda1")
1572 .SetMountPath("/mount/path1")
1573 .Build();
1574 EXPECT_TRUE(
1575 DiskMountManager::GetInstance()->AddDiskForTest(std::move(disk_sda1)));
1576
1577 // Fail the unmount with "not mounted".
1578 fake_cros_disks_client_->MakeUnmountFail(
1579 chromeos::MOUNT_ERROR_PATH_NOT_MOUNTED);
1580
1581 MountError error_code = chromeos::MOUNT_ERROR_UNKNOWN;
1582 DiskMountManager::GetInstance()->UnmountDeviceRecursively(
1583 "/dev/sda",
1584 base::BindOnce(&SaveUnmountResult, base::Unretained(&error_code),
1585 run_loop.QuitClosure()));
1586 run_loop.Run();
1587
1588 EXPECT_EQ(1, fake_cros_disks_client_->unmount_call_count());
1589 EXPECT_EQ(chromeos::MOUNT_ERROR_NONE, error_code);
1590}
1591
Austin Tankiang41a118e2019-07-12 01:48:271592TEST_F(DiskMountManagerTest, Mount_MountUnsetsFirstMount) {
1593 DiskMountManager* manager = DiskMountManager::GetInstance();
1594 const Disk* device1 = manager->FindDiskBySourcePath(kDevice1SourcePath);
1595 EXPECT_TRUE(device1->is_first_mount());
1596
1597 fake_cros_disks_client_->NotifyMountCompleted(
1598 chromeos::MOUNT_ERROR_NONE, kDevice1SourcePath,
1599 chromeos::MOUNT_TYPE_DEVICE, kDevice1MountPath);
1600
1601 EXPECT_FALSE(device1->is_first_mount());
1602}
1603
[email protected]e3c1fc92012-11-15 00:56:461604} // namespace
Evan Stade523f7fc2019-03-02 19:20:511605
1606} // namespace disks
1607} // namespace chromeos