chiark / gitweb /
udev: move string copy functions to shared/
[elogind.git] / src / udev / udevd.c
index 23351aebd5685b9c02e51af23e0ad2a34d30036b..9f184621ae45ff683996a2912bbbdbdd082f5d82 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * Copyright (C) 2004-2012 Kay Sievers <kay.sievers@vrfy.org>
+ * Copyright (C) 2004-2012 Kay Sievers <kay@vrfy.org>
  * Copyright (C) 2004 Chris Friesen <chris_friesen@sympatico.ca>
  * Copyright (C) 2009 Canonical Ltd.
  * Copyright (C) 2009 Scott James Remnant <scott@netsplit.com>
@@ -95,8 +95,9 @@ struct event {
         size_t devpath_len;
         const char *devpath_old;
         dev_t devnum;
-        bool is_block;
         int ifindex;
+        bool is_block;
+        bool nodelay;
 };
 
 static inline struct event *node_to_event(struct udev_list_node *node)
@@ -121,7 +122,7 @@ struct worker {
         struct udev_monitor *monitor;
         enum worker_state state;
         struct event *event;
-        unsigned long long event_start_usec;
+        usec_t event_start_usec;
 };
 
 /* passed from worker to main process */
@@ -377,7 +378,7 @@ out:
                 worker->monitor = worker_monitor;
                 worker->pid = pid;
                 worker->state = WORKER_RUNNING;
-                worker->event_start_usec = now_usec();
+                worker->event_start_usec = now(CLOCK_MONOTONIC);
                 worker->event = event;
                 event->state = EVENT_RUNNING;
                 udev_list_node_append(&worker->node, &worker_list);
@@ -408,7 +409,7 @@ static void event_run(struct event *event)
                 worker_ref(worker);
                 worker->event = event;
                 worker->state = WORKER_RUNNING;
-                worker->event_start_usec = now_usec();
+                worker->event_start_usec = now(CLOCK_MONOTONIC);
                 event->state = EVENT_RUNNING;
                 return;
         }
@@ -438,8 +439,10 @@ static int event_queue_insert(struct udev_device *dev)
         event->devpath_len = strlen(event->devpath);
         event->devpath_old = udev_device_get_devpath_old(dev);
         event->devnum = udev_device_get_devnum(dev);
-        event->is_block = (strcmp("block", udev_device_get_subsystem(dev)) == 0);
+        event->is_block = streq("block", udev_device_get_subsystem(dev));
         event->ifindex = udev_device_get_ifindex(dev);
+        if (streq(udev_device_get_subsystem(dev), "firmware"))
+                event->nodelay = true;
 
         udev_queue_export_device_queued(udev_queue_export, dev);
         log_debug("seq %llu queued, '%s' '%s'\n", udev_device_get_seqnum(dev),
@@ -519,6 +522,10 @@ static bool is_devpath_busy(struct event *event)
                         return true;
                 }
 
+                /* allow to bypass the dependency tracking */
+                if (event->nodelay)
+                        continue;
+
                 /* parent device event found */
                 if (event->devpath[common] == '/') {
                         event->delaying_seqnum = loop_event->seqnum;
@@ -719,7 +726,7 @@ static int handle_inotify(struct udev *udev)
                                 int fd;
 
                                 log_debug("device %s closed, synthesising 'change'\n", udev_device_get_devnode(dev));
-                                util_strscpyl(filename, sizeof(filename), udev_device_get_syspath(dev), "/uevent", NULL);
+                                strscpyl(filename, sizeof(filename), udev_device_get_syspath(dev), "/uevent", NULL);
                                 fd = open(filename, O_WRONLY);
                                 if (fd >= 0) {
                                         if (write(fd, "change", 6) < 0)
@@ -806,7 +813,7 @@ static void static_dev_create_from_modules(struct udev *udev)
         FILE *f;
 
         uname(&kernel);
-        util_strscpyl(modules, sizeof(modules), ROOTPREFIX "/lib/modules/", kernel.release, "/modules.devname", NULL);
+        strscpyl(modules, sizeof(modules), ROOTPREFIX "/lib/modules/", kernel.release, "/modules.devname", NULL);
         f = fopen(modules, "re");
         if (f == NULL)
                 return;
@@ -853,7 +860,7 @@ static void static_dev_create_from_modules(struct udev *udev)
                 else
                         continue;
 
-                util_strscpyl(filename, sizeof(filename), "/dev/", devname, NULL);
+                strscpyl(filename, sizeof(filename), "/dev/", devname, NULL);
                 mkdir_parents_label(filename, 0755);
                 label_context_set(filename, mode);
                 log_debug("mknod '%s' %c%u:%u\n", filename, type, maj, min);
@@ -902,7 +909,7 @@ static int convert_db(struct udev *udev)
         mkdir_p("/run/udev/data", 0755);
 
         /* old database */
-        util_strscpyl(filename, sizeof(filename), "/dev/.udev/db", NULL);
+        strscpyl(filename, sizeof(filename), "/dev/.udev/db", NULL);
         if (access(filename, F_OK) < 0)
                 return 0;
 
@@ -931,7 +938,7 @@ static int convert_db(struct udev *udev)
 
                         /* find database in old location */
                         id = udev_device_get_id_filename(device);
-                        util_strscpyl(from, sizeof(from), "/dev/.udev/db/", id, NULL);
+                        strscpyl(from, sizeof(from), "/dev/.udev/db/", id, NULL);
                         if (lstat(from, &stats) == 0) {
                                 if (!have_db) {
                                         udev_device_read_db(device, from);
@@ -941,7 +948,7 @@ static int convert_db(struct udev *udev)
                         }
 
                         /* find old database with $subsys:$sysname name */
-                        util_strscpyl(from, sizeof(from), "/dev/.udev/db/",
+                        strscpyl(from, sizeof(from), "/dev/.udev/db/",
                                       udev_device_get_subsystem(device), ":", udev_device_get_sysname(device), NULL);
                         if (lstat(from, &stats) == 0) {
                                 if (!have_db) {
@@ -953,7 +960,7 @@ static int convert_db(struct udev *udev)
 
                         /* find old database with the encoded devpath name */
                         util_path_encode(udev_device_get_devpath(device), devpath, sizeof(devpath));
-                        util_strscpyl(from, sizeof(from), "/dev/.udev/db/", devpath, NULL);
+                        strscpyl(from, sizeof(from), "/dev/.udev/db/", devpath, NULL);
                         if (lstat(from, &stats) == 0) {
                                 if (!have_db) {
                                         udev_device_read_db(device, from);
@@ -1090,7 +1097,7 @@ int main(int argc, char *argv[])
         for (;;) {
                 int option;
 
-                option = getopt_long(argc, argv, "c:deDtN:hV", options, NULL);
+                option = getopt_long(argc, argv, "c:de:DtN:hV", options, NULL);
                 if (option == -1)
                         break;
 
@@ -1155,7 +1162,7 @@ int main(int argc, char *argv[])
 
         mkdir("/run/udev", 0755);
 
-        dev_setup();
+        dev_setup(NULL);
         static_dev_create_from_modules(udev);
 
         /* before opening new files, make sure std{in,out,err} fds are in a sane state */
@@ -1177,7 +1184,7 @@ int main(int argc, char *argv[])
         }
 
         if (systemd_fds(udev, &fd_ctrl, &fd_netlink) >= 0) {
-                /* get control and netlink socket from from systemd */
+                /* get control and netlink socket from systemd */
                 udev_ctrl = udev_ctrl_new_from_fd(udev, fd_ctrl);
                 if (udev_ctrl == NULL) {
                         log_error("error taking over udev control socket");
@@ -1367,7 +1374,7 @@ int main(int argc, char *argv[])
         udev_list_node_init(&worker_list);
 
         for (;;) {
-                static unsigned long long last_usec;
+                static usec_t last_usec;
                 struct epoll_event ev[8];
                 int fdcount;
                 int timeout;
@@ -1438,7 +1445,7 @@ int main(int argc, char *argv[])
                                 if (worker->state != WORKER_RUNNING)
                                         continue;
 
-                                if ((now_usec() - worker->event_start_usec) > 30 * 1000 * 1000) {
+                                if ((now(CLOCK_MONOTONIC) - worker->event_start_usec) > 30 * 1000 * 1000) {
                                         log_error("worker [%u] %s timeout; kill it\n", worker->pid,
                                             worker->event ? worker->event->devpath : "<idle>");
                                         kill(worker->pid, SIGKILL);
@@ -1472,13 +1479,13 @@ int main(int argc, char *argv[])
                 }
 
                 /* check for changed config, every 3 seconds at most */
-                if ((now_usec() - last_usec) > 3 * 1000 * 1000) {
+                if ((now(CLOCK_MONOTONIC) - last_usec) > 3 * 1000 * 1000) {
                         if (udev_rules_check_timestamp(rules))
                                 reload = true;
                         if (udev_builtin_validate(udev))
                                 reload = true;
 
-                        last_usec = now_usec();
+                        last_usec = now(CLOCK_MONOTONIC);
                 }
 
                 /* reload requested, HUP signal received, rules changed, builtin changed */
@@ -1498,7 +1505,7 @@ int main(int argc, char *argv[])
 
                         dev = udev_monitor_receive_device(monitor);
                         if (dev != NULL) {
-                                udev_device_set_usec_initialized(dev, now_usec());
+                                udev_device_set_usec_initialized(dev, now(CLOCK_MONOTONIC));
                                 if (event_queue_insert(dev) < 0)
                                         udev_device_unref(dev);
                         }