tlsgate

TLS proxy
git clone git://git.akobets.xyz/tlsgate
Log | Files | Refs | README | LICENSE

commit 3df85795c09aa87e25e0ffd88f374459dd839e96
parent a7c0362f8349dfe33b849bf6238b73b617e67113
Author: Artem Kobets <artem@akobets.xyz>
Date:   Sun,  8 Nov 2020 20:38:08 +0200

remove double fork

removes killing all children on parent kill

Diffstat:
Mmain.c | 86+++++++++++++++++++++++++++++--------------------------------------------------
Msock.c | 4++--
2 files changed, 33 insertions(+), 57 deletions(-)

diff --git a/main.c b/main.c @@ -31,7 +31,6 @@ struct settings { static void serve(const struct settings *s, int cfd, const struct sockaddr_storage *addr); static void cleanup(void); -static void sigchld(int unused); static void sigcleanup(int sig); static void handle_termsignals(void (*func)(int)); static void usage(void); @@ -231,12 +230,6 @@ cleanup: } static void -sigchld(int unused) -{ - while (waitpid(-1, NULL, WNOHANG) > 0); -} - -static void cleanup(void) { if (proxy_udsfile != NULL) @@ -249,12 +242,13 @@ sigcleanup(int sig) struct sigaction act; cleanup(); - kill(0, sig); act.sa_handler = SIG_DFL; sigemptyset(&act.sa_mask); act.sa_flags = 0; sigaction(sig, &act, NULL); + + raise(sig); } static void @@ -404,64 +398,46 @@ main(int argc, char **argv) if (tls_configure(s.tls_ctx, config) == -1) err("tls_configure"); - // set new process group - // so only children will be killed with kill(0, sig) - setpgid(0, 0); - handle_termsignals(sigcleanup); + // reap children + act.sa_handler = SIG_IGN; + sigemptyset(&act.sa_mask); + act.sa_flags = 0; + sigaction(SIGCHLD, &act, NULL); + // setup proxy socket fd = proxy_udsfile ? sock_proxy_uds(proxy_udsfile) : sock_proxy_ips(proxy_host, proxy_port); - switch (fork()) { - case 0: - // signal handlers were copied with fork - // restore default signal handlers - // so that only parent process performs cleanup - handle_termsignals(SIG_DFL); - - // reap children - act.sa_handler = sigchld; - sigemptyset(&act.sa_mask); - act.sa_flags = 0; - sigaction(SIGCHLD, &act, NULL); + addr_len = sizeof(addr); + while (1) { + if ((cfd = accept(fd, (struct sockaddr *) &addr, &addr_len)) == -1) { + warn("accept"); + continue; + } - addr_len = sizeof(addr); - while (1) { - if ((cfd = accept(fd, (struct sockaddr *)&addr, &addr_len)) == -1) { - // can be interrupted with SIGCHLD - if (errno != EINTR) - warn("accept"); - continue; - } + switch (fork()) { + case 0: + // signal handlers were copied with fork + // restore default signal handlers + // so that only parent process performs cleanup + handle_termsignals(SIG_DFL); - switch (fork()) { - case 0: - serve(&s, cfd, &addr); - exit(0); - break; - case -1: - warn("fork"); - close(cfd); - break; - default: - close(cfd); - break; - } + serve(&s, cfd, &addr); + exit(0); + break; + case -1: + warn("fork"); + close(cfd); + break; + default: + close(cfd); + break; } - // unreachable - exit(1); - break; - case -1: - warn("fork:"); - break; - default: - while (wait(NULL) != -1); - break; } - cleanup(); + // unreachable return 1; } diff --git a/sock.c b/sock.c @@ -180,13 +180,13 @@ int sock_get_addr_str(const struct sockaddr_storage *addr, char *str, size_t len) { switch (addr->ss_family) { case AF_INET: - if (!inet_ntop(AF_INET, &(((struct sockaddr_in *)addr)->sin_addr), str, len)) { + if (!inet_ntop(AF_INET, &(((struct sockaddr_in *) addr)->sin_addr), str, len)) { warn("inet_ntop:"); return -1; } break; case AF_INET6: - if (!inet_ntop(AF_INET6, &(((struct sockaddr_in6 *)addr)->sin6_addr), str, len)) { + if (!inet_ntop(AF_INET6, &(((struct sockaddr_in6 *) addr)->sin6_addr), str, len)) { warn("inet_ntop:"); return -1; }