summaryrefslogtreecommitdiffstats
path: root/src/core/device.h
diff options
context:
space:
mode:
authorLennart Poettering <lennart@poettering.net>2018-06-05 17:28:32 +0200
committerLennart Poettering <lennart@poettering.net>2018-06-07 15:29:17 +0200
commit66f3fdbb073d8263b34bd65982a7e59d09086b23 (patch)
tree62155e9df194a39e1c87baeaab5dcd4072363dbf /src/core/device.h
parentdevice: simplify device_found_to_string_many() a tiny bit (diff)
downloadsystemd-66f3fdbb073d8263b34bd65982a7e59d09086b23.tar.xz
systemd-66f3fdbb073d8263b34bd65982a7e59d09086b23.zip
core: rework how device units get set up
This reworks how device units are "powered on". This makes sure that any device changes that might have happened while we were restarting/reloading will be noticed properly. For that we'll now properly serialize/deserialize both the device unit state and the device "found" flags, and restore these initially in the "coldplug" phase of the manager deserialization. While enumerating the udev devices during startup we'll put together a new "found" flags mask, which we'll the switch to in the "catchup" phase of the manager deserialization, which follows the "coldplug" phase. Note that during the "coldplug" phase no unit state change events are generated, which is different for the "catchall" phase which will do that. Thus we correctly make sure that the deserialized state won't pull in new deps, but any device's change while we were reloading would. Fixes: #8832 Replaces: #8675
Diffstat (limited to 'src/core/device.h')
-rw-r--r--src/core/device.h21
1 files changed, 12 insertions, 9 deletions
diff --git a/src/core/device.h b/src/core/device.h
index ab534ca24e..51b27e71b5 100644
--- a/src/core/device.h
+++ b/src/core/device.h
@@ -11,26 +11,29 @@
typedef struct Device Device;
+/* A mask specifying where we have seen the device currently. This is a bitmask because the device might show up
+ * asynchronously from each other at various places. For example, in very common case a device might already be mounted
+ * before udev finished probing it (think: a script setting up a loopback block device, formatting it and mounting it
+ * in quick succession). Hence we need to track precisely where it is already visible and where not. */
typedef enum DeviceFound {
- DEVICE_NOT_FOUND = 0,
- DEVICE_FOUND_UDEV = 1 << 1,
- DEVICE_FOUND_UDEV_DB = 1 << 2,
- DEVICE_FOUND_MOUNT = 1 << 3,
- DEVICE_FOUND_SWAP = 1 << 4,
+ DEVICE_NOT_FOUND = 0,
+ DEVICE_FOUND_UDEV = 1U << 1, /* The device has shown up in the udev database */
+ DEVICE_FOUND_MOUNT = 1U << 2, /* The device has shown up in /proc/self/mountinfo */
+ DEVICE_FOUND_SWAP = 1U << 3, /* The device has shown up in /proc/swaps */
+ DEVICE_FOUND_MASK = DEVICE_FOUND_UDEV|DEVICE_FOUND_MOUNT|DEVICE_FOUND_SWAP,
} DeviceFound;
struct Device {
Unit meta;
char *sysfs;
- DeviceFound found;
- /* In order to be able to distinguish dependencies on
- different device nodes we might end up creating multiple
- devices for the same sysfs path. We chain them up here. */
+ /* In order to be able to distinguish dependencies on different device nodes we might end up creating multiple
+ * devices for the same sysfs path. We chain them up here. */
LIST_FIELDS(struct Device, same_sysfs);
DeviceState state, deserialized_state;
+ DeviceFound found, deserialized_found, enumerated_found;
bool bind_mounts;
};