+static void udev_log_fn(struct udev __attribute__((unused)) *udev,
+ int __attribute__((unused)) priority, const char *file, int line,
+ const char *fn, const char *format, va_list args)
+{
+ pb_log("libudev: %s %s:%d: ", fn, file, line);
+ vfprintf(pb_log_get_stream(), format, args);
+}
+
+struct pb_udev *udev_init(struct waitset *waitset,
+ struct device_handler *handler)
+{
+ int result;
+ struct pb_udev *udev = talloc(NULL, struct pb_udev);
+
+ talloc_set_destructor(udev, udev_destructor);
+ udev->handler = handler;
+
+ udev->udev = udev_new();
+
+ if (!udev->udev) {
+ pb_log("udev_new failed\n");
+ goto fail_new;
+ }
+
+ udev_set_userdata(udev->udev, udev);
+
+ udev_set_log_fn(udev->udev, udev_log_fn);
+
+ result = udev_enumerate(udev->udev);
+
+ if (result)
+ goto fail_enumerate;
+
+ result = udev_setup_monitor(udev->udev, &udev->monitor);
+
+ if (result)
+ goto fail_monitor;
+
+ waiter_register_io(waitset, udev_monitor_get_fd(udev->monitor), WAIT_IN,
+ udev_process, udev->monitor);
+
+ pb_debug("%s: waiting on udev\n", __func__);
+
+ return udev;
+
+fail_monitor:
+fail_enumerate:
+ udev_unref(udev->udev);
+fail_new:
+ talloc_free(udev);
+ return NULL;