From f7dc3983bd12bafc5534beb1315b6aa6daedfe71 Mon Sep 17 00:00:00 2001 From: patacongo Date: Sun, 16 Aug 2009 15:26:52 +0000 Subject: Modify THTTPD to avoid poll() for write ready git-svn-id: svn://svn.code.sf.net/p/nuttx/code/trunk@2026 42af7a65-404d-4744-a932-0658087f49c3 --- nuttx/netutils/thttpd/fdwatch.c | 41 +++------ nuttx/netutils/thttpd/fdwatch.h | 24 ++---- nuttx/netutils/thttpd/libhttpd.c | 61 +++++++------- nuttx/netutils/thttpd/thttpd.c | 174 ++++++++++++++++++++++----------------- 4 files changed, 149 insertions(+), 151 deletions(-) (limited to 'nuttx/netutils/thttpd') diff --git a/nuttx/netutils/thttpd/fdwatch.c b/nuttx/netutils/thttpd/fdwatch.c index a402b8f71..5e5d9d9a7 100644 --- a/nuttx/netutils/thttpd/fdwatch.c +++ b/nuttx/netutils/thttpd/fdwatch.c @@ -124,7 +124,7 @@ struct fdwatch_s *fdwatch_initialize(int nfds) fw->nfds = nfds; - fw->client = (struct fw_fd_s*)malloc(sizeof(struct fw_fd_s) * nfds); + fw->client = (void**)malloc(sizeof(void*) * nfds); if (!fw->client) { goto errout_with_allocations; @@ -175,7 +175,7 @@ void fdwatch_uninitialize(struct fdwatch_s *fw) /* Add a descriptor to the watch list. rw is either FDW_READ or FDW_WRITE. */ -void fdwatch_add_fd(struct fdwatch_s *fw, int fd, void *client_data, int rw) +void fdwatch_add_fd(struct fdwatch_s *fw, int fd, void *client_data) { nvdbg("fd: %d client_data: %p\n", fd, client_data); @@ -196,18 +196,9 @@ void fdwatch_add_fd(struct fdwatch_s *fw, int fd, void *client_data, int rw) /* Save the new fd at the end of the list */ - fw->pollfds[fw->nwatched].fd = fd; - fw->client[fw->nwatched].rw = rw; - fw->client[fw->nwatched].data = client_data; - - if (rw == FDW_READ) - { - fw->pollfds[fw->nwatched].events = POLLIN; - } - else - { - fw->pollfds[fw->nwatched].events = POLLOUT; - } + fw->pollfds[fw->nwatched].fd = fd; + fw->pollfds[fw->nwatched].events = POLLIN; + fw->client[fw->nwatched] = client_data; /* Increment the count of watched descriptors */ @@ -246,9 +237,8 @@ void fdwatch_del_fd(struct fdwatch_s *fw, int fd) if (pollndx != fw->nwatched) { - fw->pollfds[pollndx] = fw->pollfds[fw->nwatched]; - fw->client[pollndx].rw = fw->client[fw->nwatched].rw; - fw->client[pollndx].data = fw->client[fw->nwatched].data; + fw->pollfds[pollndx] = fw->pollfds[fw->nwatched]; + fw->client[pollndx] = fw->client[fw->nwatched]; } } } @@ -328,17 +318,10 @@ int fdwatch_check_fd(struct fdwatch_s *fw, int fd) /* Get the index associated with the fd */ - pollndx = fdwatch_pollndx(fw, fd); - if (pollndx >= 0 && (fw->pollfds[pollndx].revents & POLLERR) == 0) + pollndx = fdwatch_pollndx(fw, fd); + if (pollndx >= 0 && (fw->pollfds[pollndx].revents & POLLERR) == 0) { - if (fw->client[pollndx].rw == FDW_READ) - { - return fw->pollfds[pollndx].revents & (POLLIN | POLLHUP | POLLNVAL); - } - else - { - return fw->pollfds[pollndx].revents & (POLLOUT | POLLHUP | POLLNVAL); - } + return fw->pollfds[pollndx].revents & (POLLIN | POLLHUP | POLLNVAL); } nvdbg("POLLERR fd: %d\n", fd); @@ -353,8 +336,8 @@ void *fdwatch_get_next_client_data(struct fdwatch_s *fw) return (void*)-1; } - nvdbg("client_data[%d]: %p\n", fw->next, fw->client[fw->next].data); - return fw->client[fw->next++].data; + nvdbg("client_data[%d]: %p\n", fw->next, fw->client[fw->next]); + return fw->client[fw->next++]; } /* Generate debugging statistics ndbg message. */ diff --git a/nuttx/netutils/thttpd/fdwatch.h b/nuttx/netutils/thttpd/fdwatch.h index 4f960b56c..4a87c3280 100644 --- a/nuttx/netutils/thttpd/fdwatch.h +++ b/nuttx/netutils/thttpd/fdwatch.h @@ -58,21 +58,15 @@ * Private Types ****************************************************************************/ -struct fw_fd_s -{ - uint8 rw; /* Read or write fd */ - void *data; /* Retained client data */ -}; - struct fdwatch_s { - struct pollfd *pollfds; /* Poll data */ - struct fw_fd_s *client; /* Client data */ - uint8 *ready; /* The list of fds with activity */ - uint8 nfds; /* The configured maximum number of fds */ - uint8 nwatched; /* The number of fds currently watched */ - uint8 nactive; /* The number of fds with activity */ - uint8 next; /* The index to the next client data */ + struct pollfd *pollfds; /* Poll data */ + void **client; /* Client data */ + uint8 *ready; /* The list of fds with activity */ + uint8 nfds; /* The configured maximum number of fds */ + uint8 nwatched; /* The number of fds currently watched */ + uint8 nactive; /* The number of fds with activity */ + uint8 next; /* The index to the next client data */ }; /**************************************************************************** @@ -87,9 +81,9 @@ extern struct fdwatch_s *fdwatch_initialize(int nfds); extern void fdwatch_uninitialize(struct fdwatch_s *fw); -/* Add a descriptor to the watch list. rw is either FDW_READ or FDW_WRITE. */ +/* Add a descriptor to the watch list */ -extern void fdwatch_add_fd(struct fdwatch_s *fw, int fd, void *client_data, int rw); +extern void fdwatch_add_fd(struct fdwatch_s *fw, int fd, void *client_data); /* Delete a descriptor from the watch list. */ diff --git a/nuttx/netutils/thttpd/libhttpd.c b/nuttx/netutils/thttpd/libhttpd.c index 19b0599c6..8a048d897 100644 --- a/nuttx/netutils/thttpd/libhttpd.c +++ b/nuttx/netutils/thttpd/libhttpd.c @@ -430,7 +430,7 @@ static void send_mime(httpd_conn *hc, int status, const char *title, const char } gettimeofday(&now, NULL); - if (mod == (time_t) 0) + if (mod == (time_t)0) { mod = now.tv_sec; } @@ -508,7 +508,7 @@ static void send_response(httpd_conn *hc, int status, const char *title, const c nvdbg("title: \"%s\" form: \"%s\"\n", title, form); - send_mime(hc, status, title, "", extraheads, "text/html; charset=%s", (off_t) - 1, (time_t) 0); + send_mime(hc, status, title, "", extraheads, "text/html; charset=%s", (off_t)-1, (time_t)0); add_response(hc, html_html); add_response(hc, html_hdtitle); (void)snprintf(buf, sizeof(buf), "%d %s", status, title); @@ -586,10 +586,13 @@ static int send_err_file(httpd_conn *hc, int status, char *title, char *extrahea size_t nread; fp = fopen(filename, "r"); - if (fp == (FILE *) 0) - return 0; + if (fp == NULL) + { + return 0; + } + send_mime(hc, status, title, "", extraheads, "text/html; charset=%s", - (off_t) - 1, (time_t) 0); + (off_t)-1, (time_t)0); for (;;) { nread = fread(buf, 1, sizeof(buf) - 1, fp); @@ -856,7 +859,7 @@ static int auth_check2(httpd_conn *hc, char *dirname) /* Open the password file. */ fp = fopen(authpath, "r"); - if (fp == (FILE *) 0) + if (fp == NULL) { /* The file exists but we can't open it? Disallow access. */ @@ -1240,7 +1243,7 @@ static int vhost_map(httpd_conn *hc) #endif /* Expands filename, deleting ..'s and leading /'s. - * Returns the expanded path (pointer to static string), or (char*) 0 on + * Returns the expanded path (pointer to static string), or NULL on * errors. Also returns, in the string pointed to by restP, any trailing * parts of the path that don't exist. */ @@ -1466,7 +1469,7 @@ static char *bufgets(httpd_conn *hc) return &(hc->read_buf[i]); } } - return (char *)0; + return NULL; } static void de_dotdot(char *file) @@ -1697,7 +1700,7 @@ static void cgi_kill(ClientData client_data, struct timeval *nowP) /* In case this isn't enough, schedule an uncatchable kill. */ - if (tmr_create(nowP, cgi_kill2, client_data, 5 * 1000L, 0) == (Timer *) 0) + if (tmr_create(nowP, cgi_kill2, client_data, 5 * 1000L, 0) == NULL) { ndbg("tmr_create(cgi_kill2) failed\n"); exit(1); @@ -1754,7 +1757,7 @@ static void ls_child(int argc, char **argv) */ fp = fdopen(hc->conn_fd, "w"); - if (fp == (FILE *) 0) + if (fp == NULL) { ndbg("fdopen: %d\n", errno); INTERNALERROR("fdopen"); @@ -1905,7 +1908,7 @@ static void ls_child(int argc, char **argv) /* Get time string. */ - now = time((time_t *) 0); + now = time(NULL); timestr = ctime(&lsb.st_mtime); timestr[0] = timestr[4]; timestr[1] = timestr[5]; @@ -2001,7 +2004,7 @@ static int ls(httpd_conn *hc) #endif dirp = opendir(hc->expnfilename); - if (dirp == (DIR *) 0) + if (dirp == NULL) { ndbg("opendir %s: %d\n", hc->expnfilename, errno); httpd_send_err(hc, 404, err404title, "", err404form, hc->encodedurl); @@ -2056,7 +2059,7 @@ static int ls(httpd_conn *hc) #if CONFIG_THTTPD_CGI_TIMELIMIT > 0 client_data.i = child; - if (tmr_create((struct timeval *)0, cgi_kill, client_data, CONFIG_THTTPD_CGI_TIMELIMIT * 1000L, 0) == (Timer *) 0) + if (tmr_create(NULL, cgi_kill, client_data, CONFIG_THTTPD_CGI_TIMELIMIT * 1000L, 0) == NULL) { ndbg("tmr_create(cgi_kill ls) failed\n"); exit(1); @@ -2233,7 +2236,7 @@ static FAR char **make_argp(httpd_conn *hc) argp = NEW(char *, strlen(hc->query) + 2); if (!argp) { - return (char **)0; + return NULL; } argp[0] = strrchr(hc->expnfilename, '/'); @@ -2273,7 +2276,7 @@ static FAR char **make_argp(httpd_conn *hc) } } - argp[argn] = (char *)0; + argp[argn] = NULL; return argp; } #endif @@ -2360,7 +2363,7 @@ static inline int cgi_interpose_output(httpd_conn *hc, int rfd, char *inbuffer, struct cgi_outbuffer_s *hdr) { ssize_t nbytes_read; - char *br; + char *br = NULL; int status; const char *title; char *cp; @@ -2462,7 +2465,7 @@ static inline int cgi_interpose_output(httpd_conn *hc, int rfd, char *inbuffer, status = atoi(cp); } - if ((cp = strstr(hdr->buffer, "Status:")) != (char *)0 && + if ((cp = strstr(hdr->buffer, "Status:")) != NULL && cp < br && (cp == hdr->buffer || *(cp - 1) == '\012')) { cp += 7; @@ -2470,7 +2473,7 @@ static inline int cgi_interpose_output(httpd_conn *hc, int rfd, char *inbuffer, status = atoi(cp); } - if ((cp = strstr(hdr->buffer, "Location:")) != (char *)0 && + if ((cp = strstr(hdr->buffer, "Location:")) != NULL && cp < br && (cp == hdr->buffer || *(cp - 1) == '\012')) { status = 302; @@ -2624,8 +2627,8 @@ static int cgi_child(int argc, char **argv) boolean outdone; int child; int pipefd[2]; - int wfd; - int rfd; + int wfd = -1; + int rfd = -1; int fd; int ret; int err = 1; @@ -2782,8 +2785,7 @@ static int cgi_child(int argc, char **argv) #if CONFIG_THTTPD_CGI_TIMELIMIT > 0 client_data.i = child; - if (tmr_create((struct timeval *)0, cgi_kill, client_data, - CONFIG_THTTPD_CGI_TIMELIMIT * 1000L, 0) == (Timer *) 0) + if (tmr_create(NULL, cgi_kill, client_data, CONFIG_THTTPD_CGI_TIMELIMIT * 1000L, 0) == NULL) { ndbg("tmr_create(cgi_kill child) failed\n"); goto errout_with_watch; @@ -2792,8 +2794,8 @@ static int cgi_child(int argc, char **argv) /* Add the read descriptors to the watch */ - fdwatch_add_fd(fw, hc->conn_fd, NULL, FDW_READ); - fdwatch_add_fd(fw, rfd, NULL, FDW_READ); + fdwatch_add_fd(fw, hc->conn_fd, NULL); + fdwatch_add_fd(fw, rfd, NULL); /* Then perform the interposition */ @@ -2964,7 +2966,7 @@ static int really_check_referer(httpd_conn *hc) char *cp1; char *cp2; char *cp3; - static char *refhost = (char *)0; + static char *refhost = NULL; static size_t refhost_size = 0; char *lp; @@ -3824,8 +3826,7 @@ int httpd_parse_request(httpd_conn *hc) *cp = '\0'; } - if (strchr(hc->hdrhost, '/') != (char *)0 || - hc->hdrhost[0] == '.') + if (strchr(hc->hdrhost, '/') != NULL || hc->hdrhost[0] == '.') { BADREQUEST("hdrhost"); httpd_send_err(hc, 400, httpd_err400title, "", httpd_err400form, ""); @@ -3903,7 +3904,7 @@ int httpd_parse_request(httpd_conn *hc) if (cp) { cp_dash = strchr(cp + 1, '-'); - if (cp_dash != (char *)0 && cp_dash != cp + 1) + if (cp_dash != NULL && cp_dash != cp + 1) { *cp_dash = '\0'; hc->got_range = TRUE; @@ -4125,7 +4126,7 @@ int httpd_parse_request(httpd_conn *hc) void httpd_close_conn(httpd_conn *hc, struct timeval *nowP) { - if (hc->file_fd) + if (hc->file_fd >= 0) { (void)close(hc->file_fd); hc->file_fd = -1; @@ -4312,7 +4313,7 @@ int httpd_start_request(httpd_conn *hc, struct timeval *nowP) */ cp = expand_filename(indexname, &pi, hc->tildemapped); - if (cp == (char *)0 || pi[0] != '\0') + if (cp == NULL || pi[0] != '\0') { INTERNALERROR(indexname); httpd_send_err(hc, 500, err500title, "", err500form, hc->encodedurl); diff --git a/nuttx/netutils/thttpd/thttpd.c b/nuttx/netutils/thttpd/thttpd.c index fe109938e..cbdda8a99 100644 --- a/nuttx/netutils/thttpd/thttpd.c +++ b/nuttx/netutils/thttpd/thttpd.c @@ -157,7 +157,7 @@ static void shut_down(void) int cnum; struct timeval tv; - (void)gettimeofday(&tv, (struct timezone *)0); + (void)gettimeofday(&tv, NULL); logstats(&tv); for (cnum = 0; cnum < AVAILABLE_FDS; ++cnum) { @@ -166,19 +166,19 @@ static void shut_down(void) httpd_close_conn(connects[cnum].hc, &tv); } - if (connects[cnum].hc != (httpd_conn *) 0) + if (connects[cnum].hc != NULL) { httpd_destroy_conn(connects[cnum].hc); free((void *)connects[cnum].hc); --httpd_conn_count; - connects[cnum].hc = (httpd_conn *) 0; + connects[cnum].hc = NULL; } } if (hs) { httpd_server *ths = hs; - hs = (httpd_server *) 0; + hs = NULL; if (ths->listen_fd != -1) { fdwatch_del_fd(fw, ths->listen_fd); @@ -233,7 +233,7 @@ static int handle_newconnect(struct timeval *tv, int listen_fd) if (!conn->hc) { conn->hc = NEW(httpd_conn, 1); - if (conn->hc == (httpd_conn *) 0) + if (conn->hc == NULL) { ndbg("out of memory allocating an httpd_conn\n"); exit(1); @@ -282,7 +282,7 @@ static int handle_newconnect(struct timeval *tv, int listen_fd) /* Set the connection file descriptor to no-delay mode */ httpd_set_ndelay(conn->hc->conn_fd); - fdwatch_add_fd(fw, conn->hc->conn_fd, conn, FDW_READ); + fdwatch_add_fd(fw, conn->hc->conn_fd, conn); #if defined(CONFIG_DEBUG) && defined(CONFIG_DEBUG_NET) ++stats_connections; @@ -421,10 +421,8 @@ static void handle_read(struct connect_s *conn, struct timeval *tv) /* We have a valid connection and a file to send to it */ conn->conn_state = CNST_SENDING; - client_data.p = conn; - + client_data.p = conn; fdwatch_del_fd(fw, hc->conn_fd); - fdwatch_add_fd(fw, hc->conn_fd, conn, FDW_WRITE); return; errout_with_400: @@ -466,57 +464,57 @@ static void handle_send(struct connect_s *conn, struct timeval *tv) int nwritten; int nread; - /* Fill the rest of the response buffer with file data */ + /* Read until the entire file is sent -- this could take awhile!! */ - nread = read_buffer(conn); - if (nread < 0) + while (conn->offset < conn->end_offset) { - ndbg("File read error: %d\n", errno); - goto errout_clear_connection; - } - nvdbg("Read %d bytes, buflen %d\n", nread, hc->buflen); + nvdbg("offset: %d end_offset: %d bytes_sent: %d\n", + conn->offset, conn->end_offset, conn->hc->bytes_sent); - /* Send the buffer */ + /* Fill the rest of the response buffer with file data */ - if (hc->buflen > 0) - { - /* httpd_write does not return until all bytes have been sent - * (or an error occurs). - */ - - nwritten = httpd_write(hc->conn_fd, hc->buffer, hc->buflen); - if (nwritten < 0) + nread = read_buffer(conn); + if (nread < 0) { - ndbg("Error sending %s: %d\n", hc->encodedurl, errno); + ndbg("File read error: %d\n", errno); goto errout_clear_connection; } + nvdbg("Read %d bytes, buflen %d\n", nread, hc->buflen); - /* We wrote one full buffer of data (httpd_write does not - * return until the full buffer is written (or an error occurs). - */ + /* Send the buffer */ - conn->active_at = tv->tv_sec; - hc->buflen = 0; + if (hc->buflen > 0) + { + /* httpd_write does not return until all bytes have been sent + * (or an error occurs). + */ + + nwritten = httpd_write(hc->conn_fd, hc->buffer, hc->buflen); + if (nwritten < 0) + { + ndbg("Error sending %s: %d\n", hc->encodedurl, errno); + goto errout_clear_connection; + } - /* And update how much of the file we wrote */ + /* We wrote one full buffer of data (httpd_write does not + * return until the full buffer is written (or an error occurs). + */ - conn->offset += nwritten; - conn->hc->bytes_sent += nwritten; - nvdbg("Wrote %d bytes\n", nwritten); - } + conn->active_at = tv->tv_sec; + hc->buflen = 0; - /* Are we done? */ + /* And update how much of the file we wrote */ - nvdbg("offset: %d end_offset: %d bytes_sent: %d\n", - conn->offset, conn->end_offset, conn->hc->bytes_sent); + conn->offset += nwritten; + conn->hc->bytes_sent += nwritten; + nvdbg("Wrote %d bytes\n", nwritten); + } + } - if (conn->offset >= conn->end_offset) - { - /* This connection is finished! */ + /* The file transfer is complete -- finish the connection */ - nvdbg("Finish connection\n"); - finish_connection(conn, tv); - } + nvdbg("Finish connection\n"); + finish_connection(conn, tv); return; errout_clear_connection: @@ -561,7 +559,7 @@ static void clear_connection(struct connect_s *conn, struct timeval *tv) { ClientData client_data; - if (conn->wakeup_timer != (Timer *) 0) + if (conn->wakeup_timer != NULL) { tmr_cancel(conn->wakeup_timer); conn->wakeup_timer = 0; @@ -584,7 +582,7 @@ static void clear_connection(struct connect_s *conn, struct timeval *tv) /* If we were already lingering, shut down for real */ tmr_cancel(conn->linger_timer); - conn->linger_timer = (Timer *) 0; + conn->linger_timer = NULL; conn->hc->should_linger = FALSE; } @@ -597,17 +595,17 @@ static void clear_connection(struct connect_s *conn, struct timeval *tv) conn->conn_state = CNST_LINGERING; close(conn->hc->conn_fd); - fdwatch_add_fd(fw, conn->hc->conn_fd, conn, FDW_READ); + fdwatch_add_fd(fw, conn->hc->conn_fd, conn); client_data.p = conn; - if (conn->linger_timer != (Timer *) 0) + if (conn->linger_timer != NULL) { ndbg("replacing non-null linger_timer!\n"); } conn->linger_timer = tmr_create(tv, linger_clear_connection, client_data, CONFIG_THTTPD_LINGER_MSEC, 0); - if (conn->linger_timer == (Timer *) 0) + if (conn->linger_timer == NULL) { ndbg("tmr_create(linger_clear_connection) failed\n"); exit(1); @@ -630,7 +628,7 @@ static void really_clear_connection(struct connect_s *conn, struct timeval *tv) } httpd_close_conn(conn->hc, tv); - if (conn->linger_timer != (Timer *) 0) + if (conn->linger_timer != NULL) { tmr_cancel(conn->linger_timer); conn->linger_timer = 0; @@ -679,7 +677,7 @@ static void linger_clear_connection(ClientData client_data, struct timeval *nowP struct connect_s *conn; conn = (struct connect_s *) client_data.p; - conn->linger_timer = (Timer *) 0; + conn->linger_timer = NULL; really_clear_connection(conn, nowP); } @@ -698,9 +696,9 @@ static void logstats(struct timeval *nowP) long up_secs; long stats_secs; - if (nowP == (struct timeval *)0) + if (!nowP) { - (void)gettimeofday(&tv, (struct timezone *)0); + (void)gettimeofday(&tv, NULL); nowP = &tv; } @@ -822,9 +820,7 @@ int thttpd_main(int argc, char **argv) /* Set up the occasional timer */ - if (tmr_create - ((struct timeval *)0, occasional, JunkClientData, CONFIG_THTTPD_OCCASIONAL_MSEC * 1000L, - 1) == (Timer *) 0) + if (tmr_create(NULL, occasional, JunkClientData, CONFIG_THTTPD_OCCASIONAL_MSEC * 1000L, 1) == NULL) { ndbg("tmr_create(occasional) failed\n"); exit(1); @@ -832,8 +828,7 @@ int thttpd_main(int argc, char **argv) /* Set up the idle timer */ - if (tmr_create((struct timeval *)0, idle, JunkClientData, 5 * 1000L, 1) == - (Timer *) 0) + if (tmr_create(NULL, idle, JunkClientData, 5 * 1000L, 1) == NULL) { ndbg("tmr_create(idle) failed\n"); exit(1); @@ -844,10 +839,10 @@ int thttpd_main(int argc, char **argv) { struct timeval ts; gettimeofday(&ts, NULL); - start_time = ts.tv_sec; - stats_time = ts.tv_sec; - stats_connections = 0; - stats_bytes = 0; + start_time = ts.tv_sec; + stats_time = ts.tv_sec; + stats_connections = 0; + stats_bytes = 0; stats_simultaneous = 0; } #endif @@ -855,34 +850,36 @@ int thttpd_main(int argc, char **argv) /* Initialize our connections table */ connects = NEW(struct connect_s, AVAILABLE_FDS); - if (connects == (struct connect_s *) 0) + if (connects == NULL) { - ndbg("out of memory allocating a struct connect_s\n"); + ndbg("Out of memory allocating a struct connect_s\n"); exit(1); } for (cnum = 0; cnum < AVAILABLE_FDS; ++cnum) { - connects[cnum].conn_state = CNST_FREE; + connects[cnum].conn_state = CNST_FREE; connects[cnum].next_free_connect = cnum + 1; - connects[cnum].hc = (httpd_conn *) 0; + connects[cnum].hc = NULL; } connects[AVAILABLE_FDS - 1].next_free_connect = -1; /* end of link list */ first_free_connect = 0; - num_connects = 0; - httpd_conn_count = 0; + num_connects = 0; + httpd_conn_count = 0; - if (hs != (httpd_server *) 0) + if (hs != NULL) { if (hs->listen_fd != -1) - fdwatch_add_fd(fw, hs->listen_fd, (void *)0, FDW_READ); + { + fdwatch_add_fd(fw, hs->listen_fd, NULL); + } } /* Main loop */ nvdbg("Entering the main loop\n"); - (void)gettimeofday(&tv, (struct timezone *)0); + (void)gettimeofday(&tv, NULL); while ((!terminate) || num_connects > 0) { /* Do the fd watch */ @@ -901,7 +898,7 @@ int thttpd_main(int argc, char **argv) exit(1); } - (void)gettimeofday(&tv, (struct timezone *)0); + (void)gettimeofday(&tv, NULL); if (num_ready == 0) { @@ -946,13 +943,36 @@ int thttpd_main(int argc, char **argv) switch (conn->conn_state) { case CNST_READING: - handle_read(conn, &tv); - break; + { + handle_read(conn, &tv); + + /* If a GET request was received and a file is ready to + * be sent, then fall through to send the file. + */ + + if (conn->conn_state != CNST_SENDING) + { + break; + } + } + case CNST_SENDING: - handle_send(conn, &tv); + { + /* Send a file -- this really should be performed on a + * separate thread to keep the serve from locking up during + * the write. + */ + + handle_send(conn, &tv); + } break; + case CNST_LINGERING: - handle_linger(conn, &tv); + { + /* Linger close the connection */ + + handle_linger(conn, &tv); + } break; } } -- cgit v1.2.3