Unify signal handling under wl_event_loop
Merge our signal handlers into a single function and let Wayland deal with all the struct sigaction stuff. ΔSLOC: -3
This commit is contained in:
parent
eda0613cc4
commit
fbd84aca4a
83
dwl.c
83
dwl.c
|
@ -260,6 +260,7 @@ static void focusmon(const Arg *arg);
|
||||||
static void focusstack(const Arg *arg);
|
static void focusstack(const Arg *arg);
|
||||||
static Client *focustop(Monitor *m);
|
static Client *focustop(Monitor *m);
|
||||||
static void fullscreennotify(struct wl_listener *listener, void *data);
|
static void fullscreennotify(struct wl_listener *listener, void *data);
|
||||||
|
static int handlesig(int signo, void *data);
|
||||||
static void incnmaster(const Arg *arg);
|
static void incnmaster(const Arg *arg);
|
||||||
static void inputdevice(struct wl_listener *listener, void *data);
|
static void inputdevice(struct wl_listener *listener, void *data);
|
||||||
static int keybinding(uint32_t mods, xkb_keysym_t sym);
|
static int keybinding(uint32_t mods, xkb_keysym_t sym);
|
||||||
|
@ -283,7 +284,6 @@ static void pointerfocus(Client *c, struct wlr_surface *surface,
|
||||||
double sx, double sy, uint32_t time);
|
double sx, double sy, uint32_t time);
|
||||||
static void printstatus(void);
|
static void printstatus(void);
|
||||||
static void quit(const Arg *arg);
|
static void quit(const Arg *arg);
|
||||||
static void quitsignal(int signo);
|
|
||||||
static void rendermon(struct wl_listener *listener, void *data);
|
static void rendermon(struct wl_listener *listener, void *data);
|
||||||
static void requeststartdrag(struct wl_listener *listener, void *data);
|
static void requeststartdrag(struct wl_listener *listener, void *data);
|
||||||
static void resize(Client *c, struct wlr_box geo, int interact);
|
static void resize(Client *c, struct wlr_box geo, int interact);
|
||||||
|
@ -297,7 +297,6 @@ static void setmon(Client *c, Monitor *m, uint32_t newtags);
|
||||||
static void setpsel(struct wl_listener *listener, void *data);
|
static void setpsel(struct wl_listener *listener, void *data);
|
||||||
static void setsel(struct wl_listener *listener, void *data);
|
static void setsel(struct wl_listener *listener, void *data);
|
||||||
static void setup(void);
|
static void setup(void);
|
||||||
static void sigchld(int unused);
|
|
||||||
static void spawn(const Arg *arg);
|
static void spawn(const Arg *arg);
|
||||||
static void startdrag(struct wl_listener *listener, void *data);
|
static void startdrag(struct wl_listener *listener, void *data);
|
||||||
static void tag(const Arg *arg);
|
static void tag(const Arg *arg);
|
||||||
|
@ -327,6 +326,8 @@ static pid_t child_pid = -1;
|
||||||
static int locked;
|
static int locked;
|
||||||
static void *exclusive_focus;
|
static void *exclusive_focus;
|
||||||
static struct wl_display *dpy;
|
static struct wl_display *dpy;
|
||||||
|
static struct wl_event_loop *eventloop;
|
||||||
|
static struct wl_event_source *sighandler[4];
|
||||||
static struct wlr_backend *backend;
|
static struct wlr_backend *backend;
|
||||||
static struct wlr_scene *scene;
|
static struct wlr_scene *scene;
|
||||||
static struct wlr_scene_tree *layers[NUM_LAYERS];
|
static struct wlr_scene_tree *layers[NUM_LAYERS];
|
||||||
|
@ -652,6 +653,7 @@ checkidleinhibitor(struct wlr_surface *exclude)
|
||||||
void
|
void
|
||||||
cleanup(void)
|
cleanup(void)
|
||||||
{
|
{
|
||||||
|
int i;
|
||||||
#ifdef XWAYLAND
|
#ifdef XWAYLAND
|
||||||
wlr_xwayland_destroy(xwayland);
|
wlr_xwayland_destroy(xwayland);
|
||||||
#endif
|
#endif
|
||||||
|
@ -667,6 +669,8 @@ cleanup(void)
|
||||||
wlr_cursor_destroy(cursor);
|
wlr_cursor_destroy(cursor);
|
||||||
wlr_output_layout_destroy(output_layout);
|
wlr_output_layout_destroy(output_layout);
|
||||||
wlr_seat_destroy(seat);
|
wlr_seat_destroy(seat);
|
||||||
|
for (i = 0; i < LENGTH(sighandler); i++)
|
||||||
|
wl_event_source_remove(sighandler[i]);
|
||||||
wl_display_destroy(dpy);
|
wl_display_destroy(dpy);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -820,8 +824,7 @@ createkeyboard(struct wlr_keyboard *keyboard)
|
||||||
|
|
||||||
wlr_seat_set_keyboard(seat, keyboard);
|
wlr_seat_set_keyboard(seat, keyboard);
|
||||||
|
|
||||||
kb->key_repeat_source = wl_event_loop_add_timer(
|
kb->key_repeat_source = wl_event_loop_add_timer(eventloop, keyrepeat, kb);
|
||||||
wl_display_get_event_loop(dpy), keyrepeat, kb);
|
|
||||||
|
|
||||||
/* And add the keyboard to our list of keyboards */
|
/* And add the keyboard to our list of keyboards */
|
||||||
wl_list_insert(&keyboards, &kb->link);
|
wl_list_insert(&keyboards, &kb->link);
|
||||||
|
@ -1333,6 +1336,28 @@ fullscreennotify(struct wl_listener *listener, void *data)
|
||||||
setfullscreen(c, client_wants_fullscreen(c));
|
setfullscreen(c, client_wants_fullscreen(c));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int
|
||||||
|
handlesig(int signo, void *data)
|
||||||
|
{
|
||||||
|
if (signo == SIGCHLD) {
|
||||||
|
#ifdef XWAYLAND
|
||||||
|
siginfo_t in;
|
||||||
|
/* wlroots expects to reap the XWayland process itself, so we
|
||||||
|
* use WNOWAIT to keep the child waitable until we know it's not
|
||||||
|
* XWayland.
|
||||||
|
*/
|
||||||
|
while (!waitid(P_ALL, 0, &in, WEXITED|WNOHANG|WNOWAIT) && in.si_pid
|
||||||
|
&& (!xwayland || in.si_pid != xwayland->server->pid))
|
||||||
|
waitpid(in.si_pid, NULL, 0);
|
||||||
|
#else
|
||||||
|
while (waitpid(-1, NULL, WNOHANG) > 0);
|
||||||
|
#endif
|
||||||
|
} else if (signo == SIGINT || signo == SIGTERM) {
|
||||||
|
quit(NULL);
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
incnmaster(const Arg *arg)
|
incnmaster(const Arg *arg)
|
||||||
{
|
{
|
||||||
|
@ -1875,12 +1900,6 @@ quit(const Arg *arg)
|
||||||
wl_display_terminate(dpy);
|
wl_display_terminate(dpy);
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
|
||||||
quitsignal(int signo)
|
|
||||||
{
|
|
||||||
quit(NULL);
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
void
|
||||||
rendermon(struct wl_listener *listener, void *data)
|
rendermon(struct wl_listener *listener, void *data)
|
||||||
{
|
{
|
||||||
|
@ -1944,8 +1963,6 @@ run(char *startup_cmd)
|
||||||
{
|
{
|
||||||
/* Add a Unix socket to the Wayland display. */
|
/* Add a Unix socket to the Wayland display. */
|
||||||
const char *socket = wl_display_add_socket_auto(dpy);
|
const char *socket = wl_display_add_socket_auto(dpy);
|
||||||
struct sigaction sa = {.sa_flags = SA_RESTART, .sa_handler = SIG_IGN};
|
|
||||||
sigemptyset(&sa.sa_mask);
|
|
||||||
if (!socket)
|
if (!socket)
|
||||||
die("startup: display_add_socket_auto");
|
die("startup: display_add_socket_auto");
|
||||||
setenv("WAYLAND_DISPLAY", socket, 1);
|
setenv("WAYLAND_DISPLAY", socket, 1);
|
||||||
|
@ -1973,8 +1990,6 @@ run(char *startup_cmd)
|
||||||
close(piperw[1]);
|
close(piperw[1]);
|
||||||
close(piperw[0]);
|
close(piperw[0]);
|
||||||
}
|
}
|
||||||
/* If nobody is reading the status output, don't terminate */
|
|
||||||
sigaction(SIGPIPE, &sa, NULL);
|
|
||||||
printstatus();
|
printstatus();
|
||||||
|
|
||||||
/* At this point the outputs are initialized, choose initial selmon based on
|
/* At this point the outputs are initialized, choose initial selmon based on
|
||||||
|
@ -2127,20 +2142,14 @@ setsel(struct wl_listener *listener, void *data)
|
||||||
void
|
void
|
||||||
setup(void)
|
setup(void)
|
||||||
{
|
{
|
||||||
int layer;
|
int i, sig[] = {SIGCHLD, SIGINT, SIGTERM, SIGPIPE};
|
||||||
|
|
||||||
/* Set up signal handlers */
|
|
||||||
struct sigaction sa = {.sa_flags = SA_RESTART, .sa_handler = sigchld};
|
|
||||||
sigemptyset(&sa.sa_mask);
|
|
||||||
sigaction(SIGCHLD, &sa, NULL);
|
|
||||||
|
|
||||||
sa.sa_handler = quitsignal;
|
|
||||||
sigaction(SIGINT, &sa, NULL);
|
|
||||||
sigaction(SIGTERM, &sa, NULL);
|
|
||||||
|
|
||||||
/* The Wayland display is managed by libwayland. It handles accepting
|
/* The Wayland display is managed by libwayland. It handles accepting
|
||||||
* clients from the Unix socket, manging Wayland globals, and so on. */
|
* clients from the Unix socket, manging Wayland globals, and so on. */
|
||||||
dpy = wl_display_create();
|
dpy = wl_display_create();
|
||||||
|
eventloop = wl_display_get_event_loop(dpy);
|
||||||
|
for (i = 0; i < LENGTH(sighandler); i++)
|
||||||
|
sighandler[i] = wl_event_loop_add_signal(eventloop, sig[i], handlesig, NULL);
|
||||||
|
|
||||||
/* The backend is a wlroots feature which abstracts the underlying input and
|
/* The backend is a wlroots feature which abstracts the underlying input and
|
||||||
* output hardware. The autocreate option will choose the most suitable
|
* output hardware. The autocreate option will choose the most suitable
|
||||||
|
@ -2155,8 +2164,8 @@ setup(void)
|
||||||
|
|
||||||
/* Initialize the scene graph used to lay out windows */
|
/* Initialize the scene graph used to lay out windows */
|
||||||
scene = wlr_scene_create();
|
scene = wlr_scene_create();
|
||||||
for (layer = 0; layer < NUM_LAYERS; layer++)
|
for (i = 0; i < NUM_LAYERS; i++)
|
||||||
layers[layer] = wlr_scene_tree_create(&scene->tree);
|
layers[i] = wlr_scene_tree_create(&scene->tree);
|
||||||
|
|
||||||
/* Create a renderer with the default implementation */
|
/* Create a renderer with the default implementation */
|
||||||
if (!(drw = wlr_renderer_autocreate(backend)))
|
if (!(drw = wlr_renderer_autocreate(backend)))
|
||||||
|
@ -2308,28 +2317,6 @@ setup(void)
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
|
||||||
sigchld(int unused)
|
|
||||||
{
|
|
||||||
#ifdef XWAYLAND
|
|
||||||
siginfo_t in;
|
|
||||||
/* We should be able to remove this function in favor of a simple
|
|
||||||
* struct sigaction sa = {.sa_handler = SIG_IGN};
|
|
||||||
* sigaction(SIGCHLD, &sa, NULL);
|
|
||||||
* but the Xwayland implementation in wlroots currently prevents us from
|
|
||||||
* setting our own disposition for SIGCHLD.
|
|
||||||
*/
|
|
||||||
/* WNOWAIT leaves the child in a waitable state, in case this is the
|
|
||||||
* XWayland process
|
|
||||||
*/
|
|
||||||
while (!waitid(P_ALL, 0, &in, WEXITED|WNOHANG|WNOWAIT) && in.si_pid
|
|
||||||
&& (!xwayland || in.si_pid != xwayland->server->pid))
|
|
||||||
waitpid(in.si_pid, NULL, 0);
|
|
||||||
#else
|
|
||||||
while (waitpid(-1, NULL, WNOHANG) > 0);
|
|
||||||
#endif
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
void
|
||||||
spawn(const Arg *arg)
|
spawn(const Arg *arg)
|
||||||
{
|
{
|
||||||
|
|
Loading…
Reference in a new issue