mirror of
https://github.com/vale981/spectrwm
synced 2025-03-05 09:51:38 -05:00
rework how spawning processes works. this prevents programs that flush to
stderr splode
This commit is contained in:
parent
5e9607bf68
commit
29b5153d1a
1 changed files with 47 additions and 29 deletions
76
scrotwm.c
76
scrotwm.c
|
@ -66,6 +66,7 @@ static const char *cvstag = "$scrotwm$";
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
#include <util.h>
|
#include <util.h>
|
||||||
#include <pwd.h>
|
#include <pwd.h>
|
||||||
|
#include <paths.h>
|
||||||
#include <ctype.h>
|
#include <ctype.h>
|
||||||
|
|
||||||
#include <sys/types.h>
|
#include <sys/types.h>
|
||||||
|
@ -1251,39 +1252,56 @@ find_window(Window id)
|
||||||
void
|
void
|
||||||
spawn(struct swm_region *r, union arg *args)
|
spawn(struct swm_region *r, union arg *args)
|
||||||
{
|
{
|
||||||
char *ret;
|
int fd;
|
||||||
int si;
|
char *ret = NULL;
|
||||||
|
|
||||||
DNPRINTF(SWM_D_MISC, "spawn: %s\n", args->argv[0]);
|
DNPRINTF(SWM_D_MISC, "spawn: %s\n", args->argv[0]);
|
||||||
/*
|
|
||||||
* The double-fork construct avoids zombie processes and keeps the code
|
|
||||||
* clean from stupid signal handlers.
|
|
||||||
*/
|
|
||||||
if (fork() == 0) {
|
if (fork() == 0) {
|
||||||
if (fork() == 0) {
|
if (display)
|
||||||
if (display)
|
close(ConnectionNumber(display));
|
||||||
close(ConnectionNumber(display));
|
|
||||||
setenv("LD_PRELOAD", SWM_LIB, 1);
|
setenv("LD_PRELOAD", SWM_LIB, 1);
|
||||||
if (asprintf(&ret, "%d", r->ws->idx)) {
|
|
||||||
setenv("_SWM_WS", ret, 1);
|
if (asprintf(&ret, "%d", r->ws->idx) == -1) {
|
||||||
free(ret);
|
perror("_SWM_WS");
|
||||||
}
|
_exit(1);
|
||||||
if (asprintf(&ret, "%d", getpid())) {
|
|
||||||
setenv("_SWM_PID", ret, 1);
|
|
||||||
free(ret);
|
|
||||||
}
|
|
||||||
setsid();
|
|
||||||
/* kill stdin, mplayer, ssh-add etc. need that */
|
|
||||||
si = open("/dev/null", O_RDONLY, 0);
|
|
||||||
if (si == -1)
|
|
||||||
err(1, "open /dev/null");
|
|
||||||
if (dup2(si, 0) == -1)
|
|
||||||
err(1, "dup2 /dev/null");
|
|
||||||
execvp(args->argv[0], args->argv);
|
|
||||||
fprintf(stderr, "execvp failed\n");
|
|
||||||
perror(" failed");
|
|
||||||
}
|
}
|
||||||
exit(0);
|
setenv("_SWM_WS", ret, 1);
|
||||||
|
free(ret);
|
||||||
|
ret = NULL;
|
||||||
|
|
||||||
|
if (asprintf(&ret, "%d", getpid()) == -1) {
|
||||||
|
perror("_SWM_PID");
|
||||||
|
_exit(1);
|
||||||
|
}
|
||||||
|
setenv("_SWM_PID", ret, 1);
|
||||||
|
free(ret);
|
||||||
|
ret = NULL;
|
||||||
|
|
||||||
|
if (setsid() == -1) {
|
||||||
|
perror("setsid");
|
||||||
|
_exit(1);
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* close stdin and stdout to prevent interaction between apps
|
||||||
|
* and the baraction script
|
||||||
|
* leave stderr open to record errors
|
||||||
|
*/
|
||||||
|
if ((fd = open(_PATH_DEVNULL, O_RDWR, 0)) == -1) {
|
||||||
|
perror("open");
|
||||||
|
_exit(1);
|
||||||
|
}
|
||||||
|
dup2(fd, STDIN_FILENO);
|
||||||
|
dup2(fd, STDOUT_FILENO);
|
||||||
|
if (fd > 2)
|
||||||
|
close(fd);
|
||||||
|
|
||||||
|
execvp(args->argv[0], args->argv);
|
||||||
|
|
||||||
|
perror("execvp");
|
||||||
|
_exit(1);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Add table
Reference in a new issue