aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--include/sway/server.h3
-rw-r--r--meson.build2
-rw-r--r--sway/commands/exec_always.c2
-rw-r--r--sway/config/bar.c2
-rw-r--r--sway/config/output.c2
-rw-r--r--sway/main.c38
-rw-r--r--sway/swaynag.c2
7 files changed, 23 insertions, 28 deletions
diff --git a/include/sway/server.h b/include/sway/server.h
index 66f0967c..e7d7094f 100644
--- a/include/sway/server.h
+++ b/include/sway/server.h
@@ -164,9 +164,6 @@ void server_fini(struct sway_server *server);
bool server_start(struct sway_server *server);
void server_run(struct sway_server *server);
-void restore_nofile_limit(void);
-void restore_signals(void);
-
void handle_new_output(struct wl_listener *listener, void *data);
void handle_idle_inhibitor_v1(struct wl_listener *listener, void *data);
diff --git a/meson.build b/meson.build
index 2d406dec..9e8e798e 100644
--- a/meson.build
+++ b/meson.build
@@ -79,7 +79,7 @@ libudev = wlroots_features['libinput_backend'] ? dependency('libudev') : null_de
math = cc.find_library('m')
rt = cc.find_library('rt')
xcb_icccm = wlroots_features['xwayland'] ? dependency('xcb-icccm') : null_dep
-threads = dependency('threads') # for pthread_setschedparam
+threads = dependency('threads') # for pthread_setschedparam and pthread_atfork
if get_option('sd-bus-provider') == 'auto'
if not get_option('tray').disabled()
diff --git a/sway/commands/exec_always.c b/sway/commands/exec_always.c
index 8f02bbdc..a966696c 100644
--- a/sway/commands/exec_always.c
+++ b/sway/commands/exec_always.c
@@ -51,8 +51,6 @@ struct cmd_results *cmd_exec_process(int argc, char **argv) {
// Fork process
pid_t child = fork();
if (child == 0) {
- restore_nofile_limit();
- restore_signals();
setsid();
if (ctx) {
diff --git a/sway/config/bar.c b/sway/config/bar.c
index 6cace0da..f4efb276 100644
--- a/sway/config/bar.c
+++ b/sway/config/bar.c
@@ -213,8 +213,6 @@ static void invoke_swaybar(struct bar_config *bar) {
sway_log(SWAY_ERROR, "Failed to create fork for swaybar");
return;
} else if (pid == 0) {
- restore_nofile_limit();
- restore_signals();
if (!sway_set_cloexec(sockets[1], false)) {
_exit(EXIT_FAILURE);
}
diff --git a/sway/config/output.c b/sway/config/output.c
index b8a613cc..5ed518bf 100644
--- a/sway/config/output.c
+++ b/sway/config/output.c
@@ -1060,8 +1060,6 @@ static bool _spawn_swaybg(char **command) {
sway_log_errno(SWAY_ERROR, "fork failed");
return false;
} else if (pid == 0) {
- restore_nofile_limit();
- restore_signals();
if (!sway_set_cloexec(sockets[1], false)) {
_exit(EXIT_FAILURE);
}
diff --git a/sway/main.c b/sway/main.c
index bebb5e1b..56f09b7e 100644
--- a/sway/main.c
+++ b/sway/main.c
@@ -1,5 +1,6 @@
#include <getopt.h>
#include <pango/pangocairo.h>
+#include <pthread.h>
#include <signal.h>
#include <stdbool.h>
#include <stdio.h>
@@ -121,6 +122,16 @@ static bool detect_suid(void) {
return true;
}
+static void restore_nofile_limit(void) {
+ if (original_nofile_rlimit.rlim_cur == 0) {
+ return;
+ }
+ if (setrlimit(RLIMIT_NOFILE, &original_nofile_rlimit) != 0) {
+ sway_log_errno(SWAY_ERROR, "Failed to restore max open files limit: "
+ "setrlimit(NOFILE) failed");
+ }
+}
+
static void increase_nofile_limit(void) {
if (getrlimit(RLIMIT_NOFILE, &original_nofile_rlimit) != 0) {
sway_log_errno(SWAY_ERROR, "Failed to bump max open files limit: "
@@ -135,17 +146,10 @@ static void increase_nofile_limit(void) {
"setrlimit(NOFILE) failed");
sway_log(SWAY_INFO, "Running with %d max open files",
(int)original_nofile_rlimit.rlim_cur);
- }
-}
-
-void restore_nofile_limit(void) {
- if (original_nofile_rlimit.rlim_cur == 0) {
return;
}
- if (setrlimit(RLIMIT_NOFILE, &original_nofile_rlimit) != 0) {
- sway_log_errno(SWAY_ERROR, "Failed to restore max open files limit: "
- "setrlimit(NOFILE) failed");
- }
+
+ pthread_atfork(NULL, NULL, restore_nofile_limit);
}
static int term_signal(int signal, void *data) {
@@ -153,6 +157,14 @@ static int term_signal(int signal, void *data) {
return 0;
}
+static void restore_signals(void) {
+ sigset_t set;
+ sigemptyset(&set);
+ sigprocmask(SIG_SETMASK, &set, NULL);
+ signal(SIGCHLD, SIG_DFL);
+ signal(SIGPIPE, SIG_DFL);
+}
+
static void init_signals(void) {
wl_event_loop_add_signal(server.wl_event_loop, SIGTERM, term_signal, NULL);
wl_event_loop_add_signal(server.wl_event_loop, SIGINT, term_signal, NULL);
@@ -162,14 +174,8 @@ static void init_signals(void) {
// prevent ipc write errors from crashing sway
signal(SIGPIPE, SIG_IGN);
-}
-void restore_signals(void) {
- sigset_t set;
- sigemptyset(&set);
- sigprocmask(SIG_SETMASK, &set, NULL);
- signal(SIGCHLD, SIG_DFL);
- signal(SIGPIPE, SIG_DFL);
+ pthread_atfork(NULL, NULL, restore_signals);
}
void enable_debug_flag(const char *flag) {
diff --git a/sway/swaynag.c b/sway/swaynag.c
index f0a31218..204a5791 100644
--- a/sway/swaynag.c
+++ b/sway/swaynag.c
@@ -63,7 +63,6 @@ bool swaynag_spawn(const char *swaynag_command,
sway_log(SWAY_ERROR, "Failed to create fork for swaynag");
goto failed;
} else if (pid == 0) {
- restore_nofile_limit();
if (!sway_set_cloexec(sockets[1], false)) {
_exit(EXIT_FAILURE);
}
@@ -148,4 +147,3 @@ void swaynag_show(struct swaynag_instance *swaynag) {
close(swaynag->fd[1]);
}
}
-