summaryrefslogtreecommitdiff
path: root/src/core
diff options
context:
space:
mode:
authorLennart Poettering <lennart@poettering.net>2020-01-07 11:48:57 +0100
committerLennart Poettering <lennart@poettering.net>2020-01-09 11:03:53 +0100
commitc80a9a33d04fb4381327a69ce929c94a9f1d0e6c (patch)
tree5d127d9c883beceafdba11d1346fecad9f6dc72e /src/core
parent125c7814fa50d1459b515180bc6a698b0e56bc61 (diff)
downloadsystemd-c80a9a33d04fb4381327a69ce929c94a9f1d0e6c.tar.gz
core: clearly refuse OnFailure= deps on units that can't fail
Similar, refuse triggering deps on units that cannot trigger. And rework how we ignore After= dependencies on device units, to work the same way. See: #14142
Diffstat (limited to 'src/core')
-rw-r--r--src/core/automount.c6
-rw-r--r--src/core/device.c1
-rw-r--r--src/core/mount.c5
-rw-r--r--src/core/path.c2
-rw-r--r--src/core/scope.c1
-rw-r--r--src/core/service.c1
-rw-r--r--src/core/socket.c2
-rw-r--r--src/core/swap.c2
-rw-r--r--src/core/timer.c6
-rw-r--r--src/core/unit.c22
-rw-r--r--src/core/unit.h9
11 files changed, 48 insertions, 9 deletions
diff --git a/src/core/automount.c b/src/core/automount.c
index 091b59fe78..0b3f498bfc 100644
--- a/src/core/automount.c
+++ b/src/core/automount.c
@@ -1106,6 +1106,10 @@ const UnitVTable automount_vtable = {
"Automount\0"
"Install\0",
+ .can_transient = true,
+ .can_fail = true,
+ .can_trigger = true,
+
.init = automount_init,
.load = automount_load,
.done = automount_done,
@@ -1132,8 +1136,6 @@ const UnitVTable automount_vtable = {
.bus_vtable = bus_automount_vtable,
.bus_set_property = bus_automount_set_property,
- .can_transient = true,
-
.shutdown = automount_shutdown,
.supported = automount_supported,
diff --git a/src/core/device.c b/src/core/device.c
index 45149e7555..06bbbf8d2c 100644
--- a/src/core/device.c
+++ b/src/core/device.c
@@ -1064,6 +1064,7 @@ const UnitVTable device_vtable = {
"Device\0"
"Install\0",
+ .refuse_after = true,
.gc_jobs = true,
.init = device_init,
diff --git a/src/core/mount.c b/src/core/mount.c
index dfed691c43..8ae76dd03a 100644
--- a/src/core/mount.c
+++ b/src/core/mount.c
@@ -2065,6 +2065,9 @@ const UnitVTable mount_vtable = {
"Install\0",
.private_section = "Mount",
+ .can_transient = true,
+ .can_fail = true,
+
.init = mount_init,
.load = mount_load,
.done = mount_done,
@@ -2103,8 +2106,6 @@ const UnitVTable mount_vtable = {
.get_timeout = mount_get_timeout,
- .can_transient = true,
-
.enumerate_perpetual = mount_enumerate_perpetual,
.enumerate = mount_enumerate,
.shutdown = mount_shutdown,
diff --git a/src/core/path.c b/src/core/path.c
index ca15ca884e..cb75d778af 100644
--- a/src/core/path.c
+++ b/src/core/path.c
@@ -806,6 +806,8 @@ const UnitVTable path_vtable = {
.private_section = "Path",
.can_transient = true,
+ .can_fail = true,
+ .can_trigger = true,
.init = path_init,
.done = path_done,
diff --git a/src/core/scope.c b/src/core/scope.c
index e8cfedb0d4..76358c416a 100644
--- a/src/core/scope.c
+++ b/src/core/scope.c
@@ -619,6 +619,7 @@ const UnitVTable scope_vtable = {
.can_transient = true,
.can_delegate = true,
+ .can_fail = true,
.once_only = true,
.init = scope_init,
diff --git a/src/core/service.c b/src/core/service.c
index 49ad166c26..d355618e38 100644
--- a/src/core/service.c
+++ b/src/core/service.c
@@ -4391,6 +4391,7 @@ const UnitVTable service_vtable = {
.can_transient = true,
.can_delegate = true,
+ .can_fail = true,
.init = service_init,
.done = service_done,
diff --git a/src/core/socket.c b/src/core/socket.c
index fc5ee69c9c..b5f297e510 100644
--- a/src/core/socket.c
+++ b/src/core/socket.c
@@ -3417,6 +3417,8 @@ const UnitVTable socket_vtable = {
.private_section = "Socket",
.can_transient = true,
+ .can_trigger = true,
+ .can_fail = true,
.init = socket_init,
.done = socket_done,
diff --git a/src/core/swap.c b/src/core/swap.c
index 03f443daec..b9879ba1ea 100644
--- a/src/core/swap.c
+++ b/src/core/swap.c
@@ -1593,6 +1593,8 @@ const UnitVTable swap_vtable = {
"Install\0",
.private_section = "Swap",
+ .can_fail = true,
+
.init = swap_init,
.load = swap_load,
.done = swap_done,
diff --git a/src/core/timer.c b/src/core/timer.c
index 051ca76273..57d979d52d 100644
--- a/src/core/timer.c
+++ b/src/core/timer.c
@@ -895,6 +895,10 @@ const UnitVTable timer_vtable = {
"Install\0",
.private_section = "Timer",
+ .can_transient = true,
+ .can_fail = true,
+ .can_trigger = true,
+
.init = timer_init,
.done = timer_done,
.load = timer_load,
@@ -923,6 +927,4 @@ const UnitVTable timer_vtable = {
.bus_vtable = bus_timer_vtable,
.bus_set_property = bus_timer_set_property,
-
- .can_transient = true,
};
diff --git a/src/core/unit.c b/src/core/unit.c
index 399a8cf655..b6b03ac4f4 100644
--- a/src/core/unit.c
+++ b/src/core/unit.c
@@ -2937,12 +2937,28 @@ int unit_add_dependency(
return 0;
}
- if ((d == UNIT_BEFORE && other->type == UNIT_DEVICE) ||
- (d == UNIT_AFTER && u->type == UNIT_DEVICE)) {
- log_unit_warning(u, "Dependency Before=%s ignored (.device units cannot be delayed)", other->id);
+ if (d == UNIT_AFTER && UNIT_VTABLE(u)->refuse_after) {
+ log_unit_warning(u, "Requested dependency After=%s ignored (%s units cannot be delayed).", other->id, unit_type_to_string(u->type));
return 0;
}
+ if (d == UNIT_BEFORE && UNIT_VTABLE(other)->refuse_after) {
+ log_unit_warning(u, "Requested dependency Before=%s ignored (%s units cannot be delayed).", other->id, unit_type_to_string(other->type));
+ return 0;
+ }
+
+ if (d == UNIT_ON_FAILURE && !UNIT_VTABLE(u)->can_fail) {
+ log_unit_warning(u, "Requested dependency OnFailure=%s ignored (%s units cannot fail).", other->id, unit_type_to_string(u->type));
+ return 0;
+ }
+
+ if (d == UNIT_TRIGGERS && !UNIT_VTABLE(u)->can_trigger)
+ return log_unit_error_errno(u, SYNTHETIC_ERRNO(EINVAL),
+ "Requested dependency Triggers=%s refused (%s units cannot trigger other units).", other->id, unit_type_to_string(u->type));
+ if (d == UNIT_TRIGGERED_BY && !UNIT_VTABLE(other)->can_trigger)
+ return log_unit_error_errno(u, SYNTHETIC_ERRNO(EINVAL),
+ "Requested dependency TriggeredBy=%s refused (%s units cannot trigger other units).", other->id, unit_type_to_string(other->type));
+
r = unit_add_dependency_hashmap(u->dependencies + d, other, mask, 0);
if (r < 0)
return r;
diff --git a/src/core/unit.h b/src/core/unit.h
index c5d8170c92..21f34a3ad9 100644
--- a/src/core/unit.h
+++ b/src/core/unit.h
@@ -600,6 +600,15 @@ typedef struct UnitVTable {
/* True if cgroup delegation is permissible */
bool can_delegate:1;
+ /* True if the unit type triggers other units, i.e. can have a UNIT_TRIGGERS dependency */
+ bool can_trigger:1;
+
+ /* True if the unit type knows a failure state, and thus can be source of an OnFailure= dependency */
+ bool can_fail:1;
+
+ /* True if After= dependencies should be refused */
+ bool refuse_after:1;
+
/* True if units of this type shall be startable only once and then never again */
bool once_only:1;