spawn: add optional reaper callback, return pid_t

This will allow spawn() callers to do things when the spawned process
has terminated.
This commit is contained in:
Daniel Eklöf 2024-07-23 06:57:30 +02:00
parent 57af75f988
commit a42f990818
No known key found for this signature in database
GPG key ID: 5BBD4992C116573F
6 changed files with 26 additions and 19 deletions

View file

@ -306,8 +306,8 @@ execute_binding(struct seat *seat, struct terminal *term,
} }
} }
if (!spawn(term->reaper, term->cwd, binding->aux->pipe.args, if (spawn(term->reaper, term->cwd, binding->aux->pipe.args,
pipe_fd[0], stdout_fd, stderr_fd, NULL)) pipe_fd[0], stdout_fd, stderr_fd, NULL, NULL, NULL) < 0)
goto pipe_err; goto pipe_err;
/* Close read end */ /* Close read end */

View file

@ -59,7 +59,11 @@ notify_notify(const struct terminal *term, const char *title, const char *body,
/* Redirect stdin to /dev/null, but ignore failure to open */ /* Redirect stdin to /dev/null, but ignore failure to open */
int devnull = open("/dev/null", O_RDONLY); int devnull = open("/dev/null", O_RDONLY);
spawn(term->reaper, NULL, argv, devnull, -1, -1, NULL); pid_t pid = spawn(
term->reaper, NULL, argv, devnull, stdout_fds[1], -1,
&notif_done, (void *)term, NULL);
if (stdout_fds[1] >= 0) {
if (devnull >= 0) if (devnull >= 0)
close(devnull); close(devnull);

14
spawn.c
View file

@ -15,9 +15,9 @@
#include "debug.h" #include "debug.h"
#include "xmalloc.h" #include "xmalloc.h"
bool pid_t
spawn(struct reaper *reaper, const char *cwd, char *const argv[], spawn(struct reaper *reaper, const char *cwd, char *const argv[],
int stdin_fd, int stdout_fd, int stderr_fd, int stdin_fd, int stdout_fd, int stderr_fd, reaper_cb cb, void *cb_data,
const char *xdg_activation_token) const char *xdg_activation_token)
{ {
int pipe_fds[2] = {-1, -1}; int pipe_fds[2] = {-1, -1};
@ -104,16 +104,16 @@ spawn(struct reaper *reaper, const char *cwd, char *const argv[],
close(pipe_fds[0]); close(pipe_fds[0]);
if (ret == 0) { if (ret == 0) {
reaper_add(reaper, pid, NULL, NULL); reaper_add(reaper, pid, cb, cb_data);
return true; return pid;
} else if (ret < 0) { } else if (ret < 0) {
LOG_ERRNO("failed to read from pipe"); LOG_ERRNO("failed to read from pipe");
return false; return -1;
} else { } else {
LOG_ERRNO_P(errno_copy, "%s: failed to spawn", argv[0]); LOG_ERRNO_P(errno_copy, "%s: failed to spawn", argv[0]);
errno = errno_copy; errno = errno_copy;
waitpid(pid, NULL, 0); waitpid(pid, NULL, 0);
return false; return -1;
} }
err: err:
@ -121,7 +121,7 @@ err:
close(pipe_fds[0]); close(pipe_fds[0]);
if (pipe_fds[1] != -1) if (pipe_fds[1] != -1)
close(pipe_fds[1]); close(pipe_fds[1]);
return false; return -1;
} }
bool bool

View file

@ -1,12 +1,14 @@
#pragma once #pragma once
#include <stdbool.h> #include <stdbool.h>
#include <unistd.h>
#include "config.h" #include "config.h"
#include "reaper.h" #include "reaper.h"
bool spawn(struct reaper *reaper, const char *cwd, char *const argv[], pid_t spawn(struct reaper *reaper, const char *cwd, char *const argv[],
int stdin_fd, int stdout_fd, int stderr_fd, int stdin_fd, int stdout_fd, int stderr_fd,
const char *xdg_activation_token); reaper_cb cb, void *cb_data, const char *xdg_activation_token);
bool spawn_expand_template( bool spawn_expand_template(
const struct config_spawn_template *template, const struct config_spawn_template *template,

View file

@ -198,7 +198,7 @@ add_utmp_record(const struct config *conf, struct reaper *reaper, int ptmx)
return true; return true;
char *const argv[] = {conf->utmp_helper_path, UTMP_ADD, getenv("WAYLAND_DISPLAY"), NULL}; char *const argv[] = {conf->utmp_helper_path, UTMP_ADD, getenv("WAYLAND_DISPLAY"), NULL};
return spawn(reaper, NULL, argv, ptmx, ptmx, -1, NULL); return spawn(reaper, NULL, argv, ptmx, ptmx, -1, NULL, NULL, NULL) >= 0;
#else #else
return true; return true;
#endif #endif
@ -222,7 +222,7 @@ del_utmp_record(const struct config *conf, struct reaper *reaper, int ptmx)
; ;
char *const argv[] = {conf->utmp_helper_path, UTMP_DEL, del_argument, NULL}; char *const argv[] = {conf->utmp_helper_path, UTMP_DEL, del_argument, NULL};
return spawn(reaper, NULL, argv, ptmx, ptmx, -1, NULL); return spawn(reaper, NULL, argv, ptmx, ptmx, -1, NULL, NULL, NULL) >= 0;
#else #else
return true; return true;
#endif #endif
@ -3594,7 +3594,7 @@ term_bell(struct terminal *term)
{ {
int devnull = open("/dev/null", O_RDONLY); int devnull = open("/dev/null", O_RDONLY);
spawn(term->reaper, NULL, term->conf->bell.command.argv.args, spawn(term->reaper, NULL, term->conf->bell.command.argv.args,
devnull, -1, -1, NULL); devnull, -1, -1, NULL, NULL, NULL);
if (devnull >= 0) if (devnull >= 0)
close(devnull); close(devnull);
@ -3606,7 +3606,7 @@ term_spawn_new(const struct terminal *term)
{ {
return spawn( return spawn(
term->reaper, term->cwd, (char *const []){term->foot_exe, NULL}, term->reaper, term->cwd, (char *const []){term->foot_exe, NULL},
-1, -1, -1, NULL); -1, -1, -1, NULL, NULL, NULL) >= 0;
} }
void void

View file

@ -74,8 +74,9 @@ spawn_url_launcher_with_token(struct terminal *term,
(const char *[]){url}, (const char *[]){url},
&argc, &argv)) &argc, &argv))
{ {
ret = spawn(term->reaper, term->cwd, argv, ret = spawn(
dev_null, dev_null, dev_null, xdg_activation_token); term->reaper, term->cwd, argv,
dev_null, dev_null, dev_null, NULL, NULL, xdg_activation_token) >= 0;
for (size_t i = 0; i < argc; i++) for (size_t i = 0; i < argc; i++)
free(argv[i]); free(argv[i]);