[package] uhttpd: block SIGCHLD until it is expected (#6957)
authorJo-Philipp Wich <jow@openwrt.org>
Sat, 27 Mar 2010 14:31:35 +0000 (14:31 +0000)
committerJo-Philipp Wich <jow@openwrt.org>
Sat, 27 Mar 2010 14:31:35 +0000 (14:31 +0000)
SVN-Revision: 20513

package/uhttpd/Makefile
package/uhttpd/src/uhttpd-cgi.c
package/uhttpd/src/uhttpd-lua.c
package/uhttpd/src/uhttpd-utils.c
package/uhttpd/src/uhttpd-utils.h
package/uhttpd/src/uhttpd.c

index d5c4aa6..2b7714d 100644 (file)
@@ -8,7 +8,7 @@
 include $(TOPDIR)/rules.mk
 
 PKG_NAME:=uhttpd
-PKG_RELEASE:=3
+PKG_RELEASE:=4
 
 PKG_BUILD_DIR := $(BUILD_DIR)/$(PKG_NAME)
 
index 8bd2250..28686b4 100644 (file)
@@ -376,7 +376,7 @@ void uh_cgi_request(struct client *cl, struct http_request *req, struct path_inf
                                FD_SET(wfd[1], &writer);
 
                                /* wait until we can read or write or both */
-                               if( select(fd_max, &reader,
+                               if( select_intr(fd_max, &reader,
                                        (content_length > -1) ? &writer : NULL, NULL,
                                        (header_sent < 1) ? &timeout : NULL) > 0
                                ) {
index fcbdc64..b3f3cb4 100644 (file)
@@ -452,7 +452,7 @@ void uh_lua_request(struct client *cl, struct http_request *req, lua_State *L)
                                FD_SET(wfd[1], &writer);
 
                                /* wait until we can read or write or both */
-                               if( select(fd_max, &reader,
+                               if( select_intr(fd_max, &reader,
                                    (content_length > -1) ? &writer : NULL, NULL,
                                        (data_sent < 1) ? &timeout : NULL) > 0
                                ) {
index c1e08b0..55b2c41 100644 (file)
@@ -88,6 +88,25 @@ char *strfind(char *haystack, int hslen, const char *needle, int ndlen)
        return NULL;
 }
 
+/* interruptable select() */
+int select_intr(int n, fd_set *r, fd_set *w, fd_set *e, struct timeval *t)
+{
+       int rv;
+       sigset_t ssn, sso;
+
+       /* unblock SIGCHLD */
+       sigemptyset(&ssn);
+       sigaddset(&ssn, SIGCHLD);
+       sigprocmask(SIG_UNBLOCK, &ssn, &sso);
+
+       rv = select(n, r, w, e, t);
+
+       /* restore signal mask */
+       sigprocmask(SIG_SETMASK, &sso, NULL);
+
+       return rv;
+}
+
 
 int uh_tcp_send(struct client *cl, const char *buf, int len)
 {
index 43a74e5..a6448b6 100644 (file)
@@ -52,6 +52,8 @@ int sa_port(void *sa);
 
 char *strfind(char *haystack, int hslen, const char *needle, int ndlen);
 
+int select_intr(int n, fd_set *r, fd_set *w, fd_set *e, struct timeval *t);
+
 int uh_tcp_send(struct client *cl, const char *buf, int len);
 int uh_tcp_peek(struct client *cl, char *buf, int len);
 int uh_tcp_recv(struct client *cl, char *buf, int len);
index 97c4f83..be13b53 100644 (file)
@@ -410,6 +410,9 @@ int main (int argc, char **argv)
        struct sigaction sa;
        struct config conf;
 
+       /* signal mask */
+       sigset_t ss;
+
        /* maximum file descriptor number */
        int new_fd, cur_fd, max_fd = 0;
 
@@ -432,7 +435,7 @@ int main (int argc, char **argv)
        FD_ZERO(&serv_fds);
        FD_ZERO(&read_fds);
 
-       /* handle SIGPIPE, SIGCHILD */
+       /* handle SIGPIPE, SIGINT, SIGTERM, SIGCHLD */
        sa.sa_flags = 0;
        sigemptyset(&sa.sa_mask);
 
@@ -446,6 +449,11 @@ int main (int argc, char **argv)
        sigaction(SIGINT,  &sa, NULL);
        sigaction(SIGTERM, &sa, NULL);
 
+       /* defer SIGCHLD */
+       sigemptyset(&ss);
+       sigaddset(&ss, SIGCHLD);
+       sigprocmask(SIG_BLOCK, &ss, NULL);
+
        /* prepare addrinfo hints */
        memset(&hints, 0, sizeof(hints));
        hints.ai_family   = AF_UNSPEC;