diff --git a/src/Makefile.am b/src/Makefile.am index c1e31499..ffda1e05 100644 --- a/src/Makefile.am +++ b/src/Makefile.am @@ -12,7 +12,9 @@ libinput_la_SOURCES = \ evdev.h \ evdev-touchpad.c \ filter.c \ - filter.h + filter.h \ + udev-seat.c \ + udev-seat.h libinput_la_LIBADD = $(MTDEV_LIBS) libinput_la_CFLAGS = $(MTDEV_CFLAGS) \ diff --git a/src/evdev-touchpad.c b/src/evdev-touchpad.c index a673a7b7..778dcf9b 100644 --- a/src/evdev-touchpad.c +++ b/src/evdev-touchpad.c @@ -709,7 +709,7 @@ touchpad_destroy(struct evdev_dispatch *dispatch) { struct touchpad_dispatch *touchpad = (struct touchpad_dispatch *) dispatch; - struct libinput *libinput = touchpad->device->base.libinput; + struct libinput *libinput = touchpad->device->base.seat->libinput; touchpad->filter->interface->destroy(touchpad->filter); libinput_remove_source(libinput, touchpad->fsm.timer.source); @@ -798,7 +798,7 @@ touchpad_init(struct touchpad_dispatch *touchpad, touchpad->fsm.timer.fd = timerfd_create(CLOCK_MONOTONIC, TFD_CLOEXEC); touchpad->fsm.timer.source = - libinput_add_fd(touchpad->device->base.libinput, + libinput_add_fd(touchpad->device->base.seat->libinput, touchpad->fsm.timer.fd, fsm_timeout_handler, touchpad); diff --git a/src/evdev.c b/src/evdev.c index 55d8a155..81539c84 100644 --- a/src/evdev.c +++ b/src/evdev.c @@ -227,7 +227,7 @@ evdev_process_touch(struct evdev_device *device, struct input_event *e, uint32_t time) { - struct libinput *libinput = device->base.libinput; + struct libinput *libinput = device->base.seat->libinput; int screen_width; int screen_height; @@ -272,7 +272,7 @@ static inline void evdev_process_absolute_motion(struct evdev_device *device, struct input_event *e) { - struct libinput *libinput = device->base.libinput; + struct libinput *libinput = device->base.seat->libinput; int screen_width; int screen_height; @@ -434,6 +434,7 @@ static void evdev_device_dispatch(void *data) { struct evdev_device *device = data; + struct libinput *libinput = device->base.seat->libinput; int fd = device->fd; struct input_event ev[32]; int len; @@ -451,7 +452,7 @@ evdev_device_dispatch(void *data) if (len < 0 || len % sizeof ev[0] != 0) { if (len < 0 && errno != EAGAIN && errno != EINTR) { - libinput_remove_source(device->base.libinput, + libinput_remove_source(libinput, device->source); device->source = NULL; } @@ -584,36 +585,41 @@ evdev_handle_device(struct evdev_device *device) return 1; } -static int +static void evdev_configure_device(struct evdev_device *device) { if ((device->caps & (EVDEV_MOTION_ABS | EVDEV_MOTION_REL)) && - (device->caps & EVDEV_BUTTON)) { - device_register_capability(&device->base, - LIBINPUT_DEVICE_CAP_POINTER); + (device->caps & EVDEV_BUTTON)) device->seat_caps |= EVDEV_DEVICE_POINTER; - } - if ((device->caps & EVDEV_KEYBOARD)) { - device_register_capability(&device->base, - LIBINPUT_DEVICE_CAP_KEYBOARD); + if ((device->caps & EVDEV_KEYBOARD)) device->seat_caps |= EVDEV_DEVICE_KEYBOARD; - } - if ((device->caps & EVDEV_TOUCH)) { - device_register_capability(&device->base, - LIBINPUT_DEVICE_CAP_TOUCH); + if ((device->caps & EVDEV_TOUCH)) device->seat_caps |= EVDEV_DEVICE_TOUCH; - } - - return 0; } -LIBINPUT_EXPORT struct libinput_device * -libinput_device_create_evdev( - struct libinput *libinput, - const char *devnode, - int fd, - void *user_data) +static void +register_device_capabilities(struct evdev_device *device) { + if (device->seat_caps & EVDEV_DEVICE_POINTER) { + device_register_capability(&device->base, + LIBINPUT_DEVICE_CAP_POINTER); + } + if (device->seat_caps & EVDEV_DEVICE_KEYBOARD) { + device_register_capability(&device->base, + LIBINPUT_DEVICE_CAP_KEYBOARD); + } + if (device->seat_caps & EVDEV_DEVICE_TOUCH) { + device_register_capability(&device->base, + LIBINPUT_DEVICE_CAP_TOUCH); + } +} + +struct evdev_device * +evdev_device_create(struct libinput_seat *seat, + const char *devnode, + int fd) +{ + struct libinput *libinput = seat->libinput; struct evdev_device *device; char devname[256] = "unknown"; @@ -621,8 +627,7 @@ libinput_device_create_evdev( if (device == NULL) return NULL; - device->base.libinput = libinput; - device->base.user_data = user_data; + libinput_device_init(&device->base, seat); device->seat_caps = 0; device->is_mt = 0; @@ -644,8 +649,7 @@ libinput_device_create_evdev( return NULL; } - if (evdev_configure_device(device) == -1) - goto err; + evdev_configure_device(device); /* If the dispatch was not set up use the fallback. */ if (device->dispatch == NULL) @@ -658,7 +662,11 @@ libinput_device_create_evdev( if (!device->source) goto err; - return &device->base; + list_insert(seat->devices_list.prev, &device->base.link); + notify_added_device(&device->base); + register_device_capabilities(device); + + return device; err: evdev_device_destroy(device); @@ -672,6 +680,12 @@ evdev_device_get_keys(struct evdev_device *device, char *keys, size_t size) return ioctl(device->fd, EVIOCGKEY(size), keys); } +const char * +evdev_device_get_output(struct evdev_device *device) +{ + return device->output_name; +} + void evdev_device_calibrate(struct evdev_device *device, float calibration[6]) { @@ -680,7 +694,7 @@ evdev_device_calibrate(struct evdev_device *device, float calibration[6]) } void -evdev_device_terminate(struct evdev_device *device) +evdev_device_remove(struct evdev_device *device) { if (device->seat_caps & EVDEV_DEVICE_POINTER) { device_unregister_capability(&device->base, @@ -694,6 +708,18 @@ evdev_device_terminate(struct evdev_device *device) device_unregister_capability(&device->base, LIBINPUT_DEVICE_CAP_TOUCH); } + + if (device->source) + libinput_remove_source(device->base.seat->libinput, + device->source); + + if (device->mtdev) + mtdev_close_delete(device->mtdev); + close(device->fd); + list_remove(&device->base.link); + + notify_removed_device(&device->base); + libinput_device_unref(&device->base); } void @@ -705,9 +731,6 @@ evdev_device_destroy(struct evdev_device *device) if (dispatch) dispatch->interface->destroy(dispatch); - if (device->mtdev) - mtdev_close_delete(device->mtdev); - close(device->fd); free(device->devname); free(device->devnode); free(device); diff --git a/src/evdev.h b/src/evdev.h index c8cb4054..9b904aae 100644 --- a/src/evdev.h +++ b/src/evdev.h @@ -70,6 +70,7 @@ struct evdev_device { struct libinput_source *source; struct evdev_dispatch *dispatch; + char *output_name; char *devnode; char *devname; int fd; @@ -129,6 +130,11 @@ struct evdev_dispatch { struct evdev_dispatch_interface *interface; }; +struct evdev_device * +evdev_device_create(struct libinput_seat *seat, + const char *devnode, + int fd); + struct evdev_dispatch * evdev_touchpad_create(struct evdev_device *device); @@ -141,11 +147,14 @@ evdev_device_led_update(struct evdev_device *device, enum libinput_led leds); int evdev_device_get_keys(struct evdev_device *device, char *keys, size_t size); +const char * +evdev_device_get_output(struct evdev_device *device); + void evdev_device_calibrate(struct evdev_device *device, float calibration[6]); void -evdev_device_terminate(struct evdev_device *terminate); +evdev_device_remove(struct evdev_device *device); void evdev_device_destroy(struct evdev_device *device); diff --git a/src/libinput-private.h b/src/libinput-private.h index f49badce..529e0020 100644 --- a/src/libinput-private.h +++ b/src/libinput-private.h @@ -30,6 +30,8 @@ struct libinput { int epoll_fd; struct list source_destroy_list; + struct list seat_list; + struct libinput_event **events; size_t events_count; size_t events_len; @@ -40,16 +42,32 @@ struct libinput { void *user_data; }; -struct libinput_device { +struct libinput_seat { struct libinput *libinput; + struct list link; + struct list devices_list; + void *user_data; + int refcount; + char *name; +}; + +struct libinput_device { + struct libinput_seat *seat; + struct list link; void *user_data; int terminated; + int refcount; }; typedef void (*libinput_source_dispatch_t)(void *data); struct libinput_source; +int +libinput_init(struct libinput *libinput, + const struct libinput_interface *interface, + void *user_data); + struct libinput_source * libinput_add_fd(struct libinput *libinput, int fd, @@ -60,9 +78,33 @@ void libinput_remove_source(struct libinput *libinput, struct libinput_source *source); +int +open_restricted(struct libinput *libinput, + const char *path, int flags); + void -libinput_post_event(struct libinput *libinput, - struct libinput_event *event); +close_restricted(struct libinput *libinput, int fd); + +void +libinput_seat_init(struct libinput_seat *seat, + struct libinput *libinput, + const char *name); + +void +libinput_device_init(struct libinput_device *device, + struct libinput_seat *seat); + +void +notify_added_seat(struct libinput_seat *seat); + +void +notify_removed_seat(struct libinput_seat *seat); + +void +notify_added_device(struct libinput_device *device); + +void +notify_removed_device(struct libinput_device *device); void device_register_capability(struct libinput_device *device, diff --git a/src/libinput.c b/src/libinput.c index 10d6fc13..b7dc30b8 100644 --- a/src/libinput.c +++ b/src/libinput.c @@ -30,8 +30,9 @@ #include #include "libinput.h" -#include "evdev.h" #include "libinput-private.h" +#include "evdev.h" +#include "udev-seat.h" struct libinput_source { libinput_source_dispatch_t dispatch; @@ -40,6 +41,10 @@ struct libinput_source { struct list link; }; +static void +libinput_post_event(struct libinput *libinput, + struct libinput_event *event); + struct libinput_source * libinput_add_fd(struct libinput *libinput, int fd, @@ -80,25 +85,21 @@ libinput_remove_source(struct libinput *libinput, list_insert(&libinput->source_destroy_list, &source->link); } -LIBINPUT_EXPORT struct libinput * -libinput_create(const struct libinput_interface *interface, void *user_data) +int +libinput_init(struct libinput *libinput, + const struct libinput_interface *interface, + void *user_data) { - struct libinput *libinput; - - libinput = zalloc(sizeof *libinput); - if (!libinput) - return NULL; - - list_init(&libinput->source_destroy_list); + libinput->epoll_fd = epoll_create1(EPOLL_CLOEXEC);; + if (libinput->epoll_fd < 0) + return -1; libinput->interface = interface; libinput->user_data = user_data; + list_init(&libinput->source_destroy_list); + list_init(&libinput->seat_list); - libinput->epoll_fd = epoll_create1(EPOLL_CLOEXEC);; - if (libinput->epoll_fd < 0) - return NULL; - - return libinput; + return 0; } LIBINPUT_EXPORT void @@ -114,6 +115,88 @@ libinput_destroy(struct libinput *libinput) free(libinput); } +int +open_restricted(struct libinput *libinput, + const char *path, int flags) +{ + return libinput->interface->open_restricted(path, + flags, + libinput->user_data); +} + +void +close_restricted(struct libinput *libinput, int fd) +{ + return libinput->interface->close_restricted(fd, libinput->user_data); +} + +void +libinput_seat_init(struct libinput_seat *seat, + struct libinput *libinput, + const char *name) +{ + seat->refcount = 1; + seat->libinput = libinput; + seat->name = strdup(name); + list_init(&seat->devices_list); +} + +LIBINPUT_EXPORT void +libinput_seat_ref(struct libinput_seat *seat) +{ + seat->refcount++; +} + +LIBINPUT_EXPORT void +libinput_seat_unref(struct libinput_seat *seat) +{ + seat->refcount--; + if (seat->refcount == 0) { + free(seat->name); + udev_seat_destroy((struct udev_seat *) seat); + } +} + +LIBINPUT_EXPORT void +libinput_seat_set_user_data(struct libinput_seat *seat, void *user_data) +{ + seat->user_data = user_data; +} + +LIBINPUT_EXPORT void * +libinput_seat_get_user_data(struct libinput_seat *seat) +{ + return seat->user_data; +} + +LIBINPUT_EXPORT const char * +libinput_seat_get_name(struct libinput_seat *seat) +{ + return seat->name; +} + +void +libinput_device_init(struct libinput_device *device, + struct libinput_seat *seat) +{ + device->seat = seat; + device->refcount = 1; +} + +LIBINPUT_EXPORT void +libinput_device_ref(struct libinput_device *device) +{ + device->refcount++; +} + +LIBINPUT_EXPORT void +libinput_device_unref(struct libinput_device *device) +{ + device->refcount--; + if (device->refcount == 0) + evdev_device_destroy((struct evdev_device *) device); +} + LIBINPUT_EXPORT int libinput_get_fd(struct libinput *libinput) { @@ -149,19 +232,114 @@ libinput_dispatch(struct libinput *libinput) static void init_event_base(struct libinput_event *event, enum libinput_event_type type, - struct libinput_device *device) + union libinput_event_target target) { event->type = type; - event->device = device; + event->target = target; } +static void +post_base_event(struct libinput *libinput, + enum libinput_event_type type, + struct libinput_event *event) +{ + init_event_base(event, type, + (union libinput_event_target) { .libinput = libinput }); + libinput_post_event(libinput, event); +} + +#if 0 +static void +post_seat_event(struct libinput_seat *seat, + enum libinput_event_type type, + struct libinput_event *event) +{ + init_event_base(event, type, + (union libinput_event_target) { .seat = seat }); + libinput_post_event(seat->libinput, event); +} +#endif + static void post_device_event(struct libinput_device *device, enum libinput_event_type type, struct libinput_event *event) { - init_event_base(event, type, device); - libinput_post_event(device->libinput, event); + init_event_base(event, type, + (union libinput_event_target) { .device = device }); + libinput_post_event(device->seat->libinput, event); +} + +void +notify_added_seat(struct libinput_seat *seat) +{ + struct libinput_event_added_seat *added_seat_event; + + added_seat_event = malloc(sizeof *added_seat_event); + if (!added_seat_event) + return; + + *added_seat_event = (struct libinput_event_added_seat) { + .seat = seat, + }; + + post_base_event(seat->libinput, + LIBINPUT_EVENT_ADDED_SEAT, + &added_seat_event->base); +} + +void +notify_removed_seat(struct libinput_seat *seat) +{ + struct libinput_event_removed_seat *removed_seat_event; + + removed_seat_event = malloc(sizeof *removed_seat_event); + if (!removed_seat_event) + return; + + *removed_seat_event = (struct libinput_event_removed_seat) { + .seat = seat, + }; + + post_base_event(seat->libinput, + LIBINPUT_EVENT_REMOVED_SEAT, + &removed_seat_event->base); +} + +void +notify_added_device(struct libinput_device *device) +{ + struct libinput_event_added_device *added_device_event; + + added_device_event = malloc(sizeof *added_device_event); + if (!added_device_event) + return; + + *added_device_event = (struct libinput_event_added_device) { + .device = device, + }; + + post_base_event(device->seat->libinput, + LIBINPUT_EVENT_ADDED_DEVICE, + &added_device_event->base); +} + +void +notify_removed_device(struct libinput_device *device) +{ + struct libinput_event_removed_device *removed_device_event; + + removed_device_event = malloc(sizeof *removed_device_event); + if (!removed_device_event) + return; + + *removed_device_event = (struct libinput_event_removed_device) { + .device = device, + }; + + post_base_event(device->seat->libinput, + LIBINPUT_EVENT_REMOVED_DEVICE, + &removed_device_event->base); } void @@ -340,7 +518,7 @@ touch_notify_touch(struct libinput_device *device, &touch_event->base); } -void +static void libinput_post_event(struct libinput *libinput, struct libinput_event *event) { @@ -400,18 +578,28 @@ libinput_get_event(struct libinput *libinput) return event; } -LIBINPUT_EXPORT void -libinput_device_terminate(struct libinput_device *device) +LIBINPUT_EXPORT void * +libinput_get_user_data(struct libinput *libinput) { - evdev_device_terminate((struct evdev_device *) device); - device->terminated = 1; + return libinput->user_data; +} + +LIBINPUT_EXPORT int +libinput_resume(struct libinput *libinput) +{ + return udev_input_enable((struct udev_input *) libinput); } LIBINPUT_EXPORT void -libinput_device_destroy(struct libinput_device *device) +libinput_suspend(struct libinput *libinput) { - assert(device->terminated); - evdev_device_destroy((struct evdev_device *) device); + udev_input_disable((struct udev_input *) libinput); +} + +LIBINPUT_EXPORT void +libinput_device_set_user_data(struct libinput_device *device, void *user_data) +{ + device->user_data = user_data; } LIBINPUT_EXPORT void * @@ -420,6 +608,18 @@ libinput_device_get_user_data(struct libinput_device *device) return device->user_data; } +LIBINPUT_EXPORT const char * +libinput_device_get_output_name(struct libinput_device *device) +{ + return evdev_device_get_output((struct evdev_device *) device); +} + +LIBINPUT_EXPORT struct libinput_seat * +libinput_device_get_seat(struct libinput_device *device) +{ + return device->seat; +} + LIBINPUT_EXPORT void libinput_device_led_update(struct libinput_device *device, enum libinput_led leds) diff --git a/src/libinput.h b/src/libinput.h index a051e4ac..e9be9a41 100644 --- a/src/libinput.h +++ b/src/libinput.h @@ -25,6 +25,7 @@ #include #include +#include typedef int32_t li_fixed_t; @@ -64,6 +65,11 @@ enum libinput_touch_type { }; enum libinput_event_type { + LIBINPUT_EVENT_ADDED_SEAT = 0, + LIBINPUT_EVENT_REMOVED_SEAT, + LIBINPUT_EVENT_ADDED_DEVICE, + LIBINPUT_EVENT_REMOVED_DEVICE, + LIBINPUT_EVENT_DEVICE_REGISTER_CAPABILITY = 200, LIBINPUT_EVENT_DEVICE_UNREGISTER_CAPABILITY, @@ -77,8 +83,34 @@ enum libinput_event_type { LIBINPUT_EVENT_TOUCH_TOUCH = 500, }; +union libinput_event_target { + struct libinput *libinput; + struct libinput_seat *seat; + struct libinput_device *device; +}; + struct libinput_event { enum libinput_event_type type; + union libinput_event_target target; +}; + +struct libinput_event_added_seat { + struct libinput_event base; + struct libinput_seat *seat; +}; + +struct libinput_event_removed_seat { + struct libinput_event base; + struct libinput_seat *seat; +}; + +struct libinput_event_added_device { + struct libinput_event base; + struct libinput_device *device; +}; + +struct libinput_event_removed_device { + struct libinput_event base; struct libinput_device *device; }; @@ -141,6 +173,9 @@ struct libinput_fd_handle; typedef void (*libinput_fd_callback)(int fd, void *data); struct libinput_interface { + int (*open_restricted)(const char *path, int flags, void *user_data); + void (*close_restricted)(int fd, void *user_data); + void (*get_current_screen_dimensions)(struct libinput_device *device, int *width, int *height, @@ -150,8 +185,15 @@ struct libinput_interface { struct libinput; struct libinput_device; +/* + * Base + */ + struct libinput * -libinput_create(const struct libinput_interface *interface, void *user_data); +libinput_create_udev(const struct libinput_interface *interface, + void *user_data, + struct udev *udev, + const char *seat_id); int libinput_get_fd(struct libinput *libinput); @@ -162,24 +204,59 @@ libinput_dispatch(struct libinput *libinput); struct libinput_event * libinput_get_event(struct libinput *libinput); +void * +libinput_get_user_data(struct libinput *libinput); + +int +libinput_resume(struct libinput *libinput); + +void +libinput_suspend(struct libinput *libinput); + void libinput_destroy(struct libinput *libinput); -struct libinput_device * -libinput_device_create_evdev(struct libinput *libinput, - const char *devnode, - int fd, - void *user_data); +/* + * Seat + */ void -libinput_device_terminate(struct libinput_device *device); +libinput_seat_ref(struct libinput_seat *seat); void -libinput_device_destroy(struct libinput_device *device); +libinput_seat_unref(struct libinput_seat *seat); + +void +libinput_seat_set_user_data(struct libinput_seat *seat, void *user_data); + +void * +libinput_seat_get_user_data(struct libinput_seat *seat); + +const char * +libinput_seat_get_name(struct libinput_seat *seat); + +/* + * Device + */ + +void +libinput_device_ref(struct libinput_device *device); + +void +libinput_device_unref(struct libinput_device *device); + +void +libinput_device_set_user_data(struct libinput_device *device, void *user_data); void * libinput_device_get_user_data(struct libinput_device *device); +const char * +libinput_device_get_output_name(struct libinput_device *device); + +struct libinput_seat * +libinput_device_get_seat(struct libinput_device *device); + void libinput_device_led_update(struct libinput_device *device, enum libinput_led leds); diff --git a/src/udev-seat.c b/src/udev-seat.c index deceb50c..9a1ce7aa 100644 --- a/src/udev-seat.c +++ b/src/udev-seat.c @@ -23,12 +23,11 @@ #include "config.h" #include +#include #include #include #include -#include "compositor.h" -#include "launcher-util.h" #include "evdev.h" #include "udev-seat.h" @@ -36,16 +35,15 @@ static const char default_seat[] = "seat0"; static const char default_seat_name[] = "default"; static struct udev_seat * -udev_seat_create(struct weston_compositor *c, const char *seat_name); -static void -udev_seat_destroy(struct udev_seat *seat); +udev_seat_create(struct udev_input *input, const char *seat_name); +static struct udev_seat * +udev_seat_get_named(struct udev_input *input, const char *seat_name); static int device_added(struct udev_device *udev_device, struct udev_input *input) { - struct weston_compositor *c; + struct libinput *libinput = &input->base; struct evdev_device *device; - struct weston_output *output; const char *devnode; const char *device_seat, *seat_name, *output_name; const char *calibration_values; @@ -59,7 +57,6 @@ device_added(struct udev_device *udev_device, struct udev_input *input) if (strcmp(device_seat, input->seat_id)) return 0; - c = input->compositor; devnode = udev_device_get_devnode(udev_device); /* Search for matching logical seat */ @@ -67,7 +64,7 @@ device_added(struct udev_device *udev_device, struct udev_input *input) if (!seat_name) seat_name = default_seat_name; - seat = udev_seat_get_named(c, seat_name); + seat = udev_seat_get_named(input, seat_name); if (seat == NULL) return -1; @@ -75,20 +72,20 @@ device_added(struct udev_device *udev_device, struct udev_input *input) /* Use non-blocking mode so that we can loop on read on * evdev_device_data() until all events on the fd are * read. mtdev_get() also expects this. */ - fd = weston_launcher_open(c->launcher, devnode, O_RDWR | O_NONBLOCK); + fd = open_restricted(libinput, devnode, O_RDWR | O_NONBLOCK); if (fd < 0) { - weston_log("opening input device '%s' failed.\n", devnode); + log_info("opening input device '%s' failed.\n", devnode); return 0; } device = evdev_device_create(&seat->base, devnode, fd); if (device == EVDEV_UNHANDLED_DEVICE) { - weston_launcher_close(c->launcher, fd); - weston_log("not using input device '%s'.\n", devnode); + close_restricted(libinput, fd); + log_info("not using input device '%s'.\n", devnode); return 0; } else if (device == NULL) { - weston_launcher_close(c->launcher, fd); - weston_log("failed to create input device '%s'.\n", devnode); + close_restricted(libinput, fd); + log_info("failed to create input device '%s'.\n", devnode); return 0; } @@ -105,31 +102,18 @@ device_added(struct udev_device *udev_device, struct udev_input *input) &device->abs.calibration[4], &device->abs.calibration[5]) == 6) { device->abs.apply_calibration = 1; - weston_log ("Applying calibration: %f %f %f %f %f %f\n", - device->abs.calibration[0], - device->abs.calibration[1], - device->abs.calibration[2], - device->abs.calibration[3], - device->abs.calibration[4], - device->abs.calibration[5]); + log_info("Applying calibration: %f %f %f %f %f %f\n", + device->abs.calibration[0], + device->abs.calibration[1], + device->abs.calibration[2], + device->abs.calibration[3], + device->abs.calibration[4], + device->abs.calibration[5]); } - wl_list_insert(seat->devices_list.prev, &device->link); - - if (seat->base.output && seat->base.pointer) - weston_pointer_clamp(seat->base.pointer, - &seat->base.pointer->x, - &seat->base.pointer->y); - output_name = udev_device_get_property_value(udev_device, "WL_OUTPUT"); - if (output_name) { - wl_list_for_each(output, &c->output_list, link) - if (strcmp(output->name, output_name) == 0) - device->output = output; - } - - if (input->enabled == 1) - weston_seat_repick(&seat->base); + if (output_name) + device->output_name = strdup(output_name); return 0; } @@ -141,8 +125,6 @@ udev_input_add_devices(struct udev_input *input, struct udev *udev) struct udev_list_entry *entry; struct udev_device *device; const char *path, *sysname; - struct udev_seat *seat; - int devices_found = 0; e = udev_enumerate_new(udev); udev_enumerate_add_match_subsystem(e, "input"); @@ -167,31 +149,14 @@ udev_input_add_devices(struct udev_input *input, struct udev *udev) } udev_enumerate_unref(e); - wl_list_for_each(seat, &input->compositor->seat_list, base.link) { - evdev_notify_keyboard_focus(&seat->base, &seat->devices_list); - - if (!wl_list_empty(&seat->devices_list)) - devices_found = 1; - } - - if (devices_found == 0) { - weston_log( - "warning: no input devices on entering Weston. " - "Possible causes:\n" - "\t- no permissions to read /dev/input/event*\n" - "\t- seats misconfigured " - "(Weston backend option 'seat', " - "udev device property ID_SEAT)\n"); - return -1; - } - return 0; } -static int -evdev_udev_handler(int fd, uint32_t mask, void *data) +static void +evdev_udev_handler(void *data) { struct udev_input *input = data; + struct libinput *libinput = &input->base; struct udev_device *udev_device; struct evdev_device *device, *next; const char *action; @@ -200,7 +165,7 @@ evdev_udev_handler(int fd, uint32_t mask, void *data) udev_device = udev_monitor_receive_device(input->udev_monitor); if (!udev_device) - return 1; + return; action = udev_device_get_action(udev_device); if (!action) @@ -214,14 +179,14 @@ evdev_udev_handler(int fd, uint32_t mask, void *data) } else if (!strcmp(action, "remove")) { devnode = udev_device_get_devnode(udev_device); - wl_list_for_each(seat, &input->compositor->seat_list, base.link) { - wl_list_for_each_safe(device, next, &seat->devices_list, link) + list_for_each(seat, &input->base.seat_list, base.link) { + list_for_each_safe(device, next, + &seat->base.devices_list, base.link) if (!strcmp(device->devnode, devnode)) { - weston_log("input device %s, %s removed\n", - device->devname, device->devnode); - weston_launcher_close(input->compositor->launcher, - device->fd); - evdev_device_destroy(device); + log_info("input device %s, %s removed\n", + device->devname, device->devnode); + close_restricted(libinput, device->fd); + evdev_device_remove(device); break; } } @@ -229,20 +194,17 @@ evdev_udev_handler(int fd, uint32_t mask, void *data) out: udev_device_unref(udev_device); - - return 0; } int -udev_input_enable(struct udev_input *input, struct udev *udev) +udev_input_enable(struct udev_input *input) { - struct wl_event_loop *loop; - struct weston_compositor *c = input->compositor; + struct udev *udev = input->udev; int fd; input->udev_monitor = udev_monitor_new_from_netlink(udev, "udev"); if (!input->udev_monitor) { - weston_log("udev: failed to create the udev monitor\n"); + log_info("udev: failed to create the udev monitor\n"); return -1; } @@ -250,16 +212,16 @@ udev_input_enable(struct udev_input *input, struct udev *udev) "input", NULL); if (udev_monitor_enable_receiving(input->udev_monitor)) { - weston_log("udev: failed to bind the udev monitor\n"); + log_info("udev: failed to bind the udev monitor\n"); udev_monitor_unref(input->udev_monitor); return -1; } - loop = wl_display_get_event_loop(c->wl_display); fd = udev_monitor_get_fd(input->udev_monitor); - input->udev_monitor_source = - wl_event_loop_add_fd(loop, fd, WL_EVENT_READABLE, - evdev_udev_handler, input); + input->udev_monitor_source = libinput_add_fd(&input->base, + fd, + evdev_udev_handler, + input); if (!input->udev_monitor_source) { udev_monitor_unref(input->udev_monitor); return -1; @@ -268,8 +230,6 @@ udev_input_enable(struct udev_input *input, struct udev *udev) if (udev_input_add_devices(input, udev) < 0) return -1; - input->enabled = 1; - return 0; } @@ -279,15 +239,12 @@ udev_input_remove_devices(struct udev_input *input) struct evdev_device *device, *next; struct udev_seat *seat; - wl_list_for_each(seat, &input->compositor->seat_list, base.link) { - wl_list_for_each_safe(device, next, &seat->devices_list, link) { - weston_launcher_close(input->compositor->launcher, - device->fd); - evdev_device_destroy(device); + list_for_each(seat, &input->base.seat_list, base.link) { + list_for_each_safe(device, next, + &seat->base.devices_list, base.link) { + close_restricted(&input->base, device->fd); + evdev_device_remove(device); } - - if (seat->base.keyboard) - notify_keyboard_focus_out(&seat->base); } } @@ -299,87 +256,92 @@ udev_input_disable(struct udev_input *input) udev_monitor_unref(input->udev_monitor); input->udev_monitor = NULL; - wl_event_source_remove(input->udev_monitor_source); + libinput_remove_source(&input->base, input->udev_monitor_source); input->udev_monitor_source = NULL; udev_input_remove_devices(input); } - -int -udev_input_init(struct udev_input *input, struct weston_compositor *c, struct udev *udev, - const char *seat_id) -{ - memset(input, 0, sizeof *input); - input->seat_id = strdup(seat_id); - input->compositor = c; - if (udev_input_enable(input, udev) < 0) - goto err; - - return 0; - - err: - free(input->seat_id); - return -1; -} - void udev_input_destroy(struct udev_input *input) { - struct udev_seat *seat, *next; + struct libinput_seat *seat, *next; udev_input_disable(input); - wl_list_for_each_safe(seat, next, &input->compositor->seat_list, base.link) - udev_seat_destroy(seat); + list_for_each_safe(seat, next, &input->base.seat_list, link) { + notify_removed_seat(seat); + libinput_seat_unref(seat); + } + udev_unref(input->udev); free(input->seat_id); } -static void -drm_led_update(struct weston_seat *seat_base, enum weston_led leds) -{ - struct udev_seat *seat = (struct udev_seat *) seat_base; - struct evdev_device *device; - - wl_list_for_each(device, &seat->devices_list, link) - evdev_led_update(device, leds); -} - static struct udev_seat * -udev_seat_create(struct weston_compositor *c, const char *seat_name) +udev_seat_create(struct udev_input *input, const char *seat_name) { struct udev_seat *seat; seat = zalloc(sizeof *seat); - if (!seat) return NULL; - weston_seat_init(&seat->base, c, seat_name); - seat->base.led_update = drm_led_update; - wl_list_init(&seat->devices_list); + libinput_seat_init(&seat->base, &input->base, seat_name); + list_insert(&input->base.seat_list, &seat->base.link); + notify_added_seat(&seat->base); + return seat; } -static void +void udev_seat_destroy(struct udev_seat *seat) { - weston_seat_release(&seat->base); + list_remove(&seat->base.link); free(seat); } -struct udev_seat * -udev_seat_get_named(struct weston_compositor *c, const char *seat_name) +static struct udev_seat * +udev_seat_get_named(struct udev_input *input, const char *seat_name) { struct udev_seat *seat; - wl_list_for_each(seat, &c->seat_list, base.link) { - if (strcmp(seat->base.seat_name, seat_name) == 0) + list_for_each(seat, &input->base.seat_list, base.link) { + if (strcmp(seat->base.name, seat_name) == 0) return seat; } - seat = udev_seat_create(c, seat_name); + seat = udev_seat_create(input, seat_name); if (!seat) return NULL; return seat; } + +LIBINPUT_EXPORT struct libinput * +libinput_create_udev(const struct libinput_interface *interface, + void *user_data, + struct udev *udev, + const char *seat_id) +{ + struct udev_input *input; + + input = zalloc(sizeof *input); + if (!input) + return NULL; + + if (libinput_init(&input->base, interface, user_data) != 0) { + free(input); + return NULL; + } + + input->udev = udev_ref(udev); + input->seat_id = strdup(seat_id); + + if (udev_input_enable(input) < 0) { + udev_unref(udev); + libinput_destroy(&input->base); + free(input); + return NULL; + } + + return &input->base; +} diff --git a/src/udev-seat.h b/src/udev-seat.h index 4cb6f071..6ac18bcf 100644 --- a/src/udev-seat.h +++ b/src/udev-seat.h @@ -27,30 +27,24 @@ #include -#include "compositor.h" - struct udev_seat { - struct weston_seat base; - struct wl_list devices_list; + struct libinput_seat base; + char *seat_name; }; struct udev_input { + struct libinput base; + struct udev *udev; struct udev_monitor *udev_monitor; - struct wl_event_source *udev_monitor_source; + struct libinput_source *udev_monitor_source; char *seat_id; - struct weston_compositor *compositor; - int enabled; }; - -int udev_input_enable(struct udev_input *input, struct udev *udev); +int udev_input_process_event(struct libinput_event); +int udev_input_enable(struct udev_input *input); void udev_input_disable(struct udev_input *input); -int udev_input_init(struct udev_input *input, - struct weston_compositor *c, - struct udev *udev, - const char *seat_id); void udev_input_destroy(struct udev_input *input); -struct udev_seat *udev_seat_get_named(struct weston_compositor *c, - const char *seat_name); +void udev_seat_destroy(struct udev_seat *seat); + #endif