From: Yu Watanabe Date: Sat, 6 Mar 2021 11:45:17 +0000 (+0900) Subject: udev: refuse to enable inotify watch on remove event X-Git-Tag: v249-rc1~315^2~10 X-Git-Url: http://git.ipfire.org/gitweb.cgi?a=commitdiff_plain;h=0d77bc4a18efa21022fe90cf8d6051a7b5b039f3;p=thirdparty%2Fsystemd.git udev: refuse to enable inotify watch on remove event Some udev rule may erroneously set inotify watch on remove event. For safety, silently ignore such an inotify watch enablement. This also moves inotify watch enablement code to udev-event.c. --- diff --git a/src/udev/udev-event.c b/src/udev/udev-event.c index 2e82be6fb39..f4dbcef9598 100644 --- a/src/udev/udev-event.c +++ b/src/udev/udev-event.c @@ -1082,3 +1082,34 @@ void udev_event_execute_run(UdevEvent *event, usec_t timeout_usec, int timeout_s } } } + +int udev_event_process_inotify_watch(UdevEvent *event, int inotify_fd) { + sd_device *dev; + int r; + + assert(event); + assert(inotify_fd >= 0); + + dev = event->dev; + + assert(dev); + + if (device_for_action(dev, SD_DEVICE_REMOVE)) + return 0; + + if (sd_device_get_devname(dev, NULL) < 0) + return 0; + + if (!event->inotify_watch) { + (void) udev_watch_end(inotify_fd, dev); + return 0; + } + + (void) udev_watch_begin(inotify_fd, dev); + + r = device_update_db(dev); + if (r < 0) + return log_device_debug_errno(dev, r, "Failed to update database under /run/udev/data/: %m"); + + return 0; +} diff --git a/src/udev/udev-event.h b/src/udev/udev-event.h index d90cc10a2d8..2067909fde4 100644 --- a/src/udev/udev-event.h +++ b/src/udev/udev-event.h @@ -74,6 +74,7 @@ int udev_event_execute_rules( Hashmap *properties_list, UdevRules *rules); void udev_event_execute_run(UdevEvent *event, usec_t timeout_usec, int timeout_signal); +int udev_event_process_inotify_watch(UdevEvent *event, int inotify_fd); static inline usec_t udev_warn_timeout(usec_t timeout_usec) { return DIV_ROUND_UP(timeout_usec, 3); diff --git a/src/udev/udevd.c b/src/udev/udevd.c index 299f89566f5..9689e15b1c4 100644 --- a/src/udev/udevd.c +++ b/src/udev/udevd.c @@ -502,14 +502,9 @@ static int worker_process_device(Manager *manager, sd_device *dev) { /* in case rtnl was initialized */ manager->rtnl = sd_netlink_ref(udev_event->rtnl); - /* apply/restore/end inotify watch */ - if (udev_event->inotify_watch) { - (void) udev_watch_begin(manager->inotify_fd, dev); - r = device_update_db(dev); - if (r < 0) - return log_device_debug_errno(dev, r, "Failed to update database under /run/udev/data/: %m"); - } else - (void) udev_watch_end(manager->inotify_fd, dev); + r = udev_event_process_inotify_watch(udev_event, manager->inotify_fd); + if (r < 0) + return r; log_device_uevent(dev, "Device processed"); return 0;