Ignore all virtual block devices except loop devices.
This CL modifies DiskManager to ignore all virtual block devices, except
loop devices, when enumerating devices and processing udev events.
BUG=chromium:265683
TEST=Tested the following:
1. Build and run unit tests.
2. Run the following tests:
- platform_CrosDisksDBus
- platform_CrosDisksFilesystem
3. Verify that no virtual block devices, except loop devices, are
reported when running the following command on lumpy:
dbus-send --system --print-reply --dest=org.chromium.CrosDisks \
/org/chromium/CrosDisks org.chromium.CrosDisks.EnumerateDevices
Change-Id: I8315af19de914c75db350dfca5dc27faf713af73
Reviewed-on: https://gerrit.chromium.org/gerrit/63666
Tested-by: Ben Chan <benchan@chromium.org>
Reviewed-by: Luigi Semenzato <semenzato@chromium.org>
Commit-Queue: Ben Chan <benchan@chromium.org>
diff --git a/disk-manager.cc b/disk-manager.cc
index 49a9406..0b24e92 100644
--- a/disk-manager.cc
+++ b/disk-manager.cc
@@ -122,7 +122,10 @@
LOG(INFO) << " " << key << " = " << value;
}
- disks.push_back(UdevDevice(dev).ToDisk());
+ UdevDevice device(dev);
+ if (!device.IsIgnored()) {
+ disks.push_back(device.ToDisk());
+ }
udev_device_unref(dev);
}
@@ -134,6 +137,8 @@
void DiskManager::ProcessBlockDeviceEvents(
struct udev_device* dev, const char* action, DeviceEventList* events) {
UdevDevice device(dev);
+ if (device.IsIgnored())
+ return;
bool disk_added = false;
bool disk_removed = false;
diff --git a/udev-device.cc b/udev-device.cc
index d71cef1..3cd01fe 100644
--- a/udev-device.cc
+++ b/udev-device.cc
@@ -53,6 +53,7 @@
const char kPropertySerial[] = "ID_SERIAL";
const char kSubsystemUsb[] = "usb";
const char kVirtualDevicePathPrefix[] = "/sys/devices/virtual/";
+const char kLoopDevicePathPrefix[] = "/sys/devices/virtual/block/loop";
const char kUSBDeviceInfoFile[] = "/opt/google/cros-disks/usb-device-info";
const char kUSBIdentifierDatabase[] = "/usr/share/misc/usb.ids";
const char* kNonAutoMountableFilesystemLabels[] = {
@@ -317,6 +318,10 @@
return false;
}
+bool UdevDevice::IsIgnored() const {
+ return IsVirtual() && !IsLoopDevice();
+}
+
bool UdevDevice::IsOnBootDevice() const {
// Obtain the boot device path, e.g. /dev/sda
char boot_device_path[PATH_MAX];
@@ -371,6 +376,14 @@
return true;
}
+bool UdevDevice::IsLoopDevice() const {
+ const char *sys_path = udev_device_get_syspath(dev_);
+ if (sys_path) {
+ return StartsWithASCII(sys_path, kLoopDevicePathPrefix, true);
+ }
+ return false;
+}
+
string UdevDevice::NativePath() const {
const char *sys_path = udev_device_get_syspath(dev_);
return sys_path ? sys_path : "";
diff --git a/udev-device.h b/udev-device.h
index 64122f2..456e3f0 100644
--- a/udev-device.h
+++ b/udev-device.h
@@ -69,6 +69,14 @@
// Checks if a device should be hidden from the file browser.
bool IsHidden();
+ // Checks if the device is completely ignored by cros-disks. Unlike
+ // IsAutoMountable() or IsHidden(), IsIgnored() prevents a device from being
+ // reported by cros-disks during device enumeration and udev events, such that
+ // the system does not even gather properties of the device. Currently, all
+ // virtual devices, except loop devices, are ignored. Loop devices are used
+ // by automated tests to simulate removable devices and thus not ignored.
+ bool IsIgnored() const;
+
// Checks if any media is available in the device.
bool IsMediaAvailable() const;
@@ -84,6 +92,9 @@
// Checks if the device is a virtual device.
bool IsVirtual() const;
+ // Checks if the device is a loop device.
+ bool IsLoopDevice() const;
+
// Gets the native sysfs path of the device.
std::string NativePath() const;
diff --git a/udev-device_unittest.cc b/udev-device_unittest.cc
index 3ee69ea..6b3ff1c 100644
--- a/udev-device_unittest.cc
+++ b/udev-device_unittest.cc
@@ -16,6 +16,8 @@
namespace {
const char kLoopDeviceFile[] = "/dev/loop0";
+const char kRamDeviceFile[] = "/dev/ram0";
+const char kZRamDeviceFile[] = "/dev/zram0";
} // namespace
@@ -64,6 +66,13 @@
loop_device_ = device;
}
+ if (!ram_device_ &&
+ (strcmp(device_file, kRamDeviceFile) == 0 ||
+ strcmp(device_file, kZRamDeviceFile) == 0)) {
+ udev_device_ref(device);
+ ram_device_ = device;
+ }
+
udev_device_unref(device);
}
udev_enumerate_unref(enumerate);
@@ -78,6 +87,10 @@
udev_device_unref(loop_device_);
loop_device_ = NULL;
}
+ if (ram_device_) {
+ udev_device_unref(ram_device_);
+ ram_device_ = NULL;
+ }
if (mounted_device_) {
udev_device_unref(mounted_device_);
mounted_device_ = NULL;
@@ -98,12 +111,14 @@
static struct udev* udev_;
static struct udev_device* boot_device_;
static struct udev_device* loop_device_;
+ static struct udev_device* ram_device_;
static struct udev_device* mounted_device_;
};
struct udev* UdevDeviceTest::udev_ = NULL;
struct udev_device* UdevDeviceTest::boot_device_ = NULL;
struct udev_device* UdevDeviceTest::loop_device_ = NULL;
+struct udev_device* UdevDeviceTest::ram_device_ = NULL;
struct udev_device* UdevDeviceTest::mounted_device_ = NULL;
TEST_F(UdevDeviceTest, EnsureUTF8String) {
@@ -219,6 +234,21 @@
}
}
+TEST_F(UdevDeviceTest, IsIgnored) {
+ if (boot_device_) {
+ UdevDevice device(boot_device_);
+ EXPECT_FALSE(device.IsIgnored());
+ }
+ if (loop_device_) {
+ UdevDevice device(loop_device_);
+ EXPECT_FALSE(device.IsIgnored());
+ }
+ if (ram_device_) {
+ UdevDevice device(ram_device_);
+ EXPECT_TRUE(device.IsIgnored());
+ }
+}
+
TEST_F(UdevDeviceTest, IsOnBootDevice) {
if (boot_device_) {
UdevDevice device(boot_device_);
@@ -260,6 +290,21 @@
UdevDevice device(loop_device_);
EXPECT_TRUE(device.IsVirtual());
}
+ if (ram_device_) {
+ UdevDevice device(ram_device_);
+ EXPECT_TRUE(device.IsVirtual());
+ }
+}
+
+TEST_F(UdevDeviceTest, IsLoopDevice) {
+ if (loop_device_) {
+ UdevDevice device(loop_device_);
+ EXPECT_TRUE(device.IsLoopDevice());
+ }
+ if (ram_device_) {
+ UdevDevice device(ram_device_);
+ EXPECT_FALSE(device.IsLoopDevice());
+ }
}
TEST_F(UdevDeviceTest, GetSizeInfo) {