summaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
authorrofl0r <rofl0r@users.noreply.github.com>2020-09-17 21:13:28 +0100
committerrofl0r <rofl0r@users.noreply.github.com>2020-09-17 21:24:45 +0100
commitd4ef2cfa625d4a9011d61dcc7537963906ff3105 (patch)
tree4f465d811b669336768fe426f30d6faab8df9b07
parentda1bc1425d954ab5f3cb518fac10286ba958c3bc (diff)
child_kill_children(): use method that actually works
it turned out that close()ing an fd behind the back of a thread doesn't actually cause blocking operations to get a read/write event, because the fd will stay valid to in-progress operations.
-rw-r--r--src/child.c18
1 files changed, 11 insertions, 7 deletions
diff --git a/src/child.c b/src/child.c
index a4a90f6..985357d 100644
--- a/src/child.c
+++ b/src/child.c
@@ -222,21 +222,25 @@ oom:
*/
void child_kill_children (int sig)
{
- size_t i;
+ size_t i, tries = 0;
if (sig != SIGTERM) return;
+ log_message (LOG_INFO,
+ "trying to bring down %zu threads...",
+ sblist_getsize(childs)
+ );
+
+again:
for (i = 0; i < sblist_getsize(childs); i++) {
struct child *c = *((struct child**)sblist_get(childs, i));
- if (!c->done) {
- /* interrupt blocking operations.
- this should cause the threads to shutdown orderly. */
- close(c->conn.client_fd);
- }
+ if (!c->done) pthread_kill(c->thread, SIGCHLD);
}
- usleep(16);
+ usleep(8192);
collect_threads();
if (sblist_getsize(childs) != 0)
+ if(tries++ < 8) goto again;
+ if (sblist_getsize(childs) != 0)
log_message (LOG_CRIT,
"child_kill_children: %zu threads still alive!",
sblist_getsize(childs)