if (script->result.sig > 0) {
ret = -EINTR;
} else if (script->result.err > 0) {
- if (script->result.err == EACCES) {
- /* Map EACCESS to ENOEXEC */
+ if (script->result.err == EACCES ||
+ script->result.err == ENOENT) {
+ /*
+ * Map EACCESS/ENOENT to ENOEXEC
+ *
+ * ENOENT: Disabling a standard event script
+ * by removing its symlink can result in
+ * ENOENT. This happens when the script list
+ * is built while the link exists, but the
+ * link is removed before the attempt to run
+ * it. Map it to ENOEXEC (which causes a
+ * script to be shown as DISABLED). This
+ * makes it impossible to distinguish a
+ * removed symlink from a dangling
+ * symlink... but the latter can just be
+ * defined as disabled. It should be rare
+ * because it shouldn't happen if event
+ * scripts are properly managed. If someone
+ * is doing weird things then they can easily
+ * debug such issues by looking at the link.
+ */
ret = -ENOEXEC;
} else {
ret = -script->result.err;
* 03.notalink
EOF
simple_test script list data
+
+#
+# Test disabling of scripts after the script list has been
+# built. Normally this would be an admin racing with eventd instead of
+# one script disabling subsequent ones.
+#
+
+# First enable all scripts - this might repeat some previous stuff
+ok_null
+simple_test script enable data 01.dummy
+ok_null
+simple_test script enable data 02.disabled
+ok_null
+simple_test script enable data 03.notalink
+
+# Confirm expected state
+ok <<EOF
+* 01.dummy
+* 02.disabled
+
+* 03.notalink
+EOF
+simple_test script list data
+
+# Now run the event that disables the subsequent scripts:
+# - 02.disabled has its link removed
+# - 03.notalink effectively has "chmod -x" applied
+ok_null
+simple_test run 10 data disablehack
+
+# Confirm that both subsequent
+ok <<EOF
+01.dummy OK DURATION DATETIME
+02.disabled DISABLED
+03.notalink DISABLED
+EOF
+simple_test status data disablehack