aboutsummaryrefslogtreecommitdiff
path: root/src/microhttpd/daemon.c
diff options
context:
space:
mode:
authorChristian Grothoff <christian@grothoff.org>2013-10-24 08:41:04 +0000
committerChristian Grothoff <christian@grothoff.org>2013-10-24 08:41:04 +0000
commit8e6b1e789978929efd84aedf44943514dfe1a7e3 (patch)
treebc58d70919f93fdc43ab94d7da17c874aafe367c /src/microhttpd/daemon.c
parenta79c58be3d55fb21d9d47bd6f7a3b5367ad70569 (diff)
downloadlibmicrohttpd-8e6b1e789978929efd84aedf44943514dfe1a7e3.tar.gz
libmicrohttpd-8e6b1e789978929efd84aedf44943514dfe1a7e3.zip
experimental code to support flow control for connections via MHD_suspend_connection and MHD_resume_connection
Diffstat (limited to 'src/microhttpd/daemon.c')
-rw-r--r--src/microhttpd/daemon.c614
1 files changed, 376 insertions, 238 deletions
diff --git a/src/microhttpd/daemon.c b/src/microhttpd/daemon.c
index 70741fba..61416a7b 100644
--- a/src/microhttpd/daemon.c
+++ b/src/microhttpd/daemon.c
@@ -104,7 +104,7 @@
104 * @param line line number with the problem 104 * @param line line number with the problem
105 * @param reason error message with details 105 * @param reason error message with details
106 */ 106 */
107static void 107static void
108mhd_panic_std (void *cls, 108mhd_panic_std (void *cls,
109 const char *file, 109 const char *file,
110 unsigned int line, 110 unsigned int line,
@@ -133,7 +133,7 @@ void *mhd_panic_cls;
133 * Trace up to and return master daemon. If the supplied daemon 133 * Trace up to and return master daemon. If the supplied daemon
134 * is a master, then return the daemon itself. 134 * is a master, then return the daemon itself.
135 * 135 *
136 * @param daemon handle to a daemon 136 * @param daemon handle to a daemon
137 * @return master daemon handle 137 * @return master daemon handle
138 */ 138 */
139static struct MHD_Daemon* 139static struct MHD_Daemon*
@@ -162,12 +162,12 @@ struct MHD_IPCount
162 { 162 {
163 /** 163 /**
164 * IPv4 address. 164 * IPv4 address.
165 */ 165 */
166 struct in_addr ipv4; 166 struct in_addr ipv4;
167#if HAVE_IPV6 167#if HAVE_IPV6
168 /** 168 /**
169 * IPv6 address. 169 * IPv6 address.
170 */ 170 */
171 struct in6_addr ipv6; 171 struct in6_addr ipv6;
172#endif 172#endif
173 } addr; 173 } addr;
@@ -213,7 +213,7 @@ MHD_ip_count_unlock (struct MHD_Daemon *daemon)
213 * Tree comparison function for IP addresses (supplied to tsearch() family). 213 * Tree comparison function for IP addresses (supplied to tsearch() family).
214 * We compare everything in the struct up through the beginning of the 214 * We compare everything in the struct up through the beginning of the
215 * 'count' field. 215 * 'count' field.
216 * 216 *
217 * @param a1 first address to compare 217 * @param a1 first address to compare
218 * @param a2 second address to compare 218 * @param a2 second address to compare
219 * @return -1, 0 or 1 depending on result of compare 219 * @return -1, 0 or 1 depending on result of compare
@@ -234,7 +234,7 @@ MHD_ip_addr_compare (const void *a1, const void *a2)
234 * @return #MHD_YES on success and #MHD_NO otherwise (e.g., invalid address type) 234 * @return #MHD_YES on success and #MHD_NO otherwise (e.g., invalid address type)
235 */ 235 */
236static int 236static int
237MHD_ip_addr_to_key (const struct sockaddr *addr, 237MHD_ip_addr_to_key (const struct sockaddr *addr,
238 socklen_t addrlen, 238 socklen_t addrlen,
239 struct MHD_IPCount *key) 239 struct MHD_IPCount *key)
240{ 240{
@@ -302,14 +302,14 @@ MHD_ip_limit_add (struct MHD_Daemon *daemon,
302 MHD_ip_count_lock (daemon); 302 MHD_ip_count_lock (daemon);
303 303
304 /* Search for the IP address */ 304 /* Search for the IP address */
305 if (NULL == (nodep = TSEARCH (key, 305 if (NULL == (nodep = TSEARCH (key,
306 &daemon->per_ip_connection_count, 306 &daemon->per_ip_connection_count,
307 &MHD_ip_addr_compare))) 307 &MHD_ip_addr_compare)))
308 { 308 {
309#if HAVE_MESSAGES 309#if HAVE_MESSAGES
310 MHD_DLOG (daemon, 310 MHD_DLOG (daemon,
311 "Failed to add IP connection count node\n"); 311 "Failed to add IP connection count node\n");
312#endif 312#endif
313 MHD_ip_count_unlock (daemon); 313 MHD_ip_count_unlock (daemon);
314 free (key); 314 free (key);
315 return MHD_NO; 315 return MHD_NO;
@@ -358,10 +358,10 @@ MHD_ip_limit_del (struct MHD_Daemon *daemon,
358 MHD_ip_count_lock (daemon); 358 MHD_ip_count_lock (daemon);
359 359
360 /* Search for the IP address */ 360 /* Search for the IP address */
361 if (NULL == (nodep = TFIND (&search_key, 361 if (NULL == (nodep = TFIND (&search_key,
362 &daemon->per_ip_connection_count, 362 &daemon->per_ip_connection_count,
363 &MHD_ip_addr_compare))) 363 &MHD_ip_addr_compare)))
364 { 364 {
365 /* Something's wrong if we couldn't find an IP address 365 /* Something's wrong if we couldn't find an IP address
366 * that was previously added */ 366 * that was previously added */
367 MHD_PANIC ("Failed to find previously-added IP address\n"); 367 MHD_PANIC ("Failed to find previously-added IP address\n");
@@ -375,8 +375,8 @@ MHD_ip_limit_del (struct MHD_Daemon *daemon,
375 /* Remove the node entirely if count reduces to 0 */ 375 /* Remove the node entirely if count reduces to 0 */
376 if (0 == --found_key->count) 376 if (0 == --found_key->count)
377 { 377 {
378 TDELETE (found_key, 378 TDELETE (found_key,
379 &daemon->per_ip_connection_count, 379 &daemon->per_ip_connection_count,
380 &MHD_ip_addr_compare); 380 &MHD_ip_addr_compare);
381 free (found_key); 381 free (found_key);
382 } 382 }
@@ -409,7 +409,7 @@ recv_tls_adapter (struct MHD_Connection *connection, void *other, size_t i)
409 (GNUTLS_E_INTERRUPTED == res) ) 409 (GNUTLS_E_INTERRUPTED == res) )
410 { 410 {
411 errno = EINTR; 411 errno = EINTR;
412#if EPOLL_SUPPORT 412#if EPOLL_SUPPORT
413 connection->epoll_state &= ~MHD_EPOLL_STATE_READ_READY; 413 connection->epoll_state &= ~MHD_EPOLL_STATE_READ_READY;
414#endif 414#endif
415 return -1; 415 return -1;
@@ -451,7 +451,7 @@ send_tls_adapter (struct MHD_Connection *connection,
451 { 451 {
452 fprintf (stderr, "WAGAIN!\n"); 452 fprintf (stderr, "WAGAIN!\n");
453 errno = EINTR; 453 errno = EINTR;
454#if EPOLL_SUPPORT 454#if EPOLL_SUPPORT
455 connection->epoll_state &= ~MHD_EPOLL_STATE_WRITE_READY; 455 connection->epoll_state &= ~MHD_EPOLL_STATE_WRITE_READY;
456#endif 456#endif
457 return -1; 457 return -1;
@@ -472,12 +472,12 @@ MHD_init_daemon_certificate (struct MHD_Daemon *daemon)
472 gnutls_datum_t key; 472 gnutls_datum_t key;
473 gnutls_datum_t cert; 473 gnutls_datum_t cert;
474 474
475 if (NULL != daemon->https_mem_trust) 475 if (NULL != daemon->https_mem_trust)
476 { 476 {
477 cert.data = (unsigned char *) daemon->https_mem_trust; 477 cert.data = (unsigned char *) daemon->https_mem_trust;
478 cert.size = strlen (daemon->https_mem_trust); 478 cert.size = strlen (daemon->https_mem_trust);
479 if (gnutls_certificate_set_x509_trust_mem (daemon->x509_cred, &cert, 479 if (gnutls_certificate_set_x509_trust_mem (daemon->x509_cred, &cert,
480 GNUTLS_X509_FMT_PEM) < 0) 480 GNUTLS_X509_FMT_PEM) < 0)
481 { 481 {
482#if HAVE_MESSAGES 482#if HAVE_MESSAGES
483 MHD_DLOG(daemon, 483 MHD_DLOG(daemon,
@@ -486,9 +486,9 @@ MHD_init_daemon_certificate (struct MHD_Daemon *daemon)
486 return -1; 486 return -1;
487 } 487 }
488 } 488 }
489 489
490 /* certificate & key loaded from memory */ 490 /* certificate & key loaded from memory */
491 if ( (NULL != daemon->https_mem_cert) && 491 if ( (NULL != daemon->https_mem_cert) &&
492 (NULL != daemon->https_mem_key) ) 492 (NULL != daemon->https_mem_key) )
493 { 493 {
494 key.data = (unsigned char *) daemon->https_mem_key; 494 key.data = (unsigned char *) daemon->https_mem_key;
@@ -544,8 +544,8 @@ MHD_TLS_init (struct MHD_Daemon *daemon)
544 * @param max_fd maximum value to potentially update 544 * @param max_fd maximum value to potentially update
545 */ 545 */
546static void 546static void
547add_to_fd_set (int fd, 547add_to_fd_set (int fd,
548 fd_set *set, 548 fd_set *set,
549 int *max_fd) 549 int *max_fd)
550{ 550{
551 FD_SET (fd, set); 551 FD_SET (fd, set);
@@ -572,17 +572,17 @@ add_to_fd_set (int fd,
572int 572int
573MHD_get_fdset (struct MHD_Daemon *daemon, 573MHD_get_fdset (struct MHD_Daemon *daemon,
574 fd_set *read_fd_set, 574 fd_set *read_fd_set,
575 fd_set *write_fd_set, 575 fd_set *write_fd_set,
576 fd_set *except_fd_set, 576 fd_set *except_fd_set,
577 int *max_fd) 577 int *max_fd)
578{ 578{
579 struct MHD_Connection *pos; 579 struct MHD_Connection *pos;
580 int fd; 580 int fd;
581 581
582 if ( (NULL == daemon) 582 if ( (NULL == daemon)
583 || (NULL == read_fd_set) 583 || (NULL == read_fd_set)
584 || (NULL == write_fd_set) 584 || (NULL == write_fd_set)
585 || (NULL == except_fd_set) 585 || (NULL == except_fd_set)
586 || (NULL == max_fd) 586 || (NULL == max_fd)
587 || (MHD_YES == daemon->shutdown) 587 || (MHD_YES == daemon->shutdown)
588 || (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) 588 || (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION))
@@ -597,7 +597,7 @@ MHD_get_fdset (struct MHD_Daemon *daemon,
597 if (daemon->epoll_fd >= FD_SETSIZE) 597 if (daemon->epoll_fd >= FD_SETSIZE)
598 return MHD_NO; /* poll fd too big, fail hard */ 598 return MHD_NO; /* poll fd too big, fail hard */
599 FD_SET (daemon->epoll_fd, read_fd_set); 599 FD_SET (daemon->epoll_fd, read_fd_set);
600 if ((*max_fd) < daemon->epoll_fd) 600 if ((*max_fd) < daemon->epoll_fd)
601 *max_fd = daemon->epoll_fd; 601 *max_fd = daemon->epoll_fd;
602 return MHD_YES; 602 return MHD_YES;
603 } 603 }
@@ -607,7 +607,7 @@ MHD_get_fdset (struct MHD_Daemon *daemon,
607 { 607 {
608 FD_SET (fd, read_fd_set); 608 FD_SET (fd, read_fd_set);
609 /* update max file descriptor */ 609 /* update max file descriptor */
610 if ((*max_fd) < fd) 610 if ((*max_fd) < fd)
611 *max_fd = fd; 611 *max_fd = fd;
612 } 612 }
613 for (pos = daemon->connections_head; NULL != pos; pos = pos->next) 613 for (pos = daemon->connections_head; NULL != pos; pos = pos->next)
@@ -643,7 +643,7 @@ MHD_get_fdset (struct MHD_Daemon *daemon,
643/** 643/**
644 * Main function of the thread that handles an individual 644 * Main function of the thread that handles an individual
645 * connection when #MHD_USE_THREAD_PER_CONNECTION is set. 645 * connection when #MHD_USE_THREAD_PER_CONNECTION is set.
646 * 646 *
647 * @param data the 'struct MHD_Connection' this thread will handle 647 * @param data the 'struct MHD_Connection' this thread will handle
648 * @return always NULL 648 * @return always NULL
649 */ 649 */
@@ -664,8 +664,8 @@ MHD_handle_connection (void *data)
664#endif 664#endif
665 665
666 timeout = con->daemon->connection_timeout; 666 timeout = con->daemon->connection_timeout;
667 while ( (MHD_YES != con->daemon->shutdown) && 667 while ( (MHD_YES != con->daemon->shutdown) &&
668 (MHD_CONNECTION_CLOSED != con->state) ) 668 (MHD_CONNECTION_CLOSED != con->state) )
669 { 669 {
670 tvp = NULL; 670 tvp = NULL;
671 if (timeout > 0) 671 if (timeout > 0)
@@ -715,13 +715,13 @@ MHD_handle_connection (void *data)
715 goto exit; 715 goto exit;
716 } 716 }
717 num_ready = SELECT (max + 1, &rs, &ws, NULL, tvp); 717 num_ready = SELECT (max + 1, &rs, &ws, NULL, tvp);
718 if (num_ready < 0) 718 if (num_ready < 0)
719 { 719 {
720 if (EINTR == errno) 720 if (EINTR == errno)
721 continue; 721 continue;
722#if HAVE_MESSAGES 722#if HAVE_MESSAGES
723 MHD_DLOG (con->daemon, 723 MHD_DLOG (con->daemon,
724 "Error during select (%d): `%s'\n", 724 "Error during select (%d): `%s'\n",
725 max, 725 max,
726 STRERROR (errno)); 726 STRERROR (errno));
727#endif 727#endif
@@ -730,7 +730,7 @@ MHD_handle_connection (void *data)
730 /* call appropriate connection handler if necessary */ 730 /* call appropriate connection handler if necessary */
731 if ( (FD_ISSET (con->socket_fd, &rs)) 731 if ( (FD_ISSET (con->socket_fd, &rs))
732#if HTTPS_SUPPORT 732#if HTTPS_SUPPORT
733 || (MHD_YES == con->tls_read_ready) 733 || (MHD_YES == con->tls_read_ready)
734#endif 734#endif
735 ) 735 )
736 con->read_handler (con); 736 con->read_handler (con);
@@ -748,16 +748,16 @@ MHD_handle_connection (void *data)
748 switch (con->event_loop_info) 748 switch (con->event_loop_info)
749 { 749 {
750 case MHD_EVENT_LOOP_INFO_READ: 750 case MHD_EVENT_LOOP_INFO_READ:
751 p[0].events |= POLLIN; 751 p[0].events |= POLLIN;
752 break; 752 break;
753 case MHD_EVENT_LOOP_INFO_WRITE: 753 case MHD_EVENT_LOOP_INFO_WRITE:
754 p[0].events |= POLLOUT; 754 p[0].events |= POLLOUT;
755 if (con->read_buffer_size > con->read_buffer_offset) 755 if (con->read_buffer_size > con->read_buffer_offset)
756 p[0].events |= POLLIN; 756 p[0].events |= POLLIN;
757 break; 757 break;
758 case MHD_EVENT_LOOP_INFO_BLOCK: 758 case MHD_EVENT_LOOP_INFO_BLOCK:
759 if (con->read_buffer_size > con->read_buffer_offset) 759 if (con->read_buffer_size > con->read_buffer_offset)
760 p[0].events |= POLLIN; 760 p[0].events |= POLLIN;
761 tv.tv_sec = 0; 761 tv.tv_sec = 0;
762 tv.tv_usec = 0; 762 tv.tv_usec = 0;
763 tvp = &tv; 763 tvp = &tv;
@@ -766,27 +766,27 @@ MHD_handle_connection (void *data)
766 /* how did we get here!? */ 766 /* how did we get here!? */
767 goto exit; 767 goto exit;
768 } 768 }
769 if (poll (p, 1, 769 if (poll (p, 1,
770 (NULL == tvp) ? -1 : tv.tv_sec * 1000) < 0) 770 (NULL == tvp) ? -1 : tv.tv_sec * 1000) < 0)
771 { 771 {
772 if (EINTR == errno) 772 if (EINTR == errno)
773 continue; 773 continue;
774#if HAVE_MESSAGES 774#if HAVE_MESSAGES
775 MHD_DLOG (con->daemon, "Error during poll: `%s'\n", 775 MHD_DLOG (con->daemon, "Error during poll: `%s'\n",
776 STRERROR (errno)); 776 STRERROR (errno));
777#endif 777#endif
778 break; 778 break;
779 } 779 }
780 if ( (0 != (p[0].revents & POLLIN)) 780 if ( (0 != (p[0].revents & POLLIN))
781#if HTTPS_SUPPORT 781#if HTTPS_SUPPORT
782 || (MHD_YES == con->tls_read_ready) 782 || (MHD_YES == con->tls_read_ready)
783#endif 783#endif
784 ) 784 )
785 con->read_handler (con); 785 con->read_handler (con);
786 if (0 != (p[0].revents & POLLOUT)) 786 if (0 != (p[0].revents & POLLOUT))
787 con->write_handler (con); 787 con->write_handler (con);
788 if (0 != (p[0].revents & (POLLERR | POLLHUP))) 788 if (0 != (p[0].revents & (POLLERR | POLLHUP)))
789 MHD_connection_close (con, MHD_REQUEST_TERMINATED_WITH_ERROR); 789 MHD_connection_close (con, MHD_REQUEST_TERMINATED_WITH_ERROR);
790 if (MHD_NO == con->idle_handler (con)) 790 if (MHD_NO == con->idle_handler (con))
791 goto exit; 791 goto exit;
792 } 792 }
@@ -801,7 +801,7 @@ MHD_handle_connection (void *data)
801#endif 801#endif
802#endif 802#endif
803 if (MHD_CONNECTION_CLOSED != con->state) 803 if (MHD_CONNECTION_CLOSED != con->state)
804 MHD_connection_close (con, 804 MHD_connection_close (con,
805 MHD_REQUEST_TERMINATED_DAEMON_SHUTDOWN); 805 MHD_REQUEST_TERMINATED_DAEMON_SHUTDOWN);
806 con->idle_handler (con); 806 con->idle_handler (con);
807 } 807 }
@@ -825,7 +825,7 @@ exit:
825 */ 825 */
826static ssize_t 826static ssize_t
827recv_param_adapter (struct MHD_Connection *connection, 827recv_param_adapter (struct MHD_Connection *connection,
828 void *other, 828 void *other,
829 size_t i) 829 size_t i)
830{ 830{
831 ssize_t ret; 831 ssize_t ret;
@@ -887,7 +887,7 @@ send_param_adapter (struct MHD_Connection *connection,
887 left = connection->response->total_size - connection->response_write_position; 887 left = connection->response->total_size - connection->response_write_position;
888 if (left > SSIZE_MAX) 888 if (left > SSIZE_MAX)
889 left = SSIZE_MAX; /* cap at return value limit */ 889 left = SSIZE_MAX; /* cap at return value limit */
890 if (-1 != (ret = sendfile (connection->socket_fd, 890 if (-1 != (ret = sendfile (connection->socket_fd,
891 fd, 891 fd,
892 &offset, 892 &offset,
893 (size_t) left))) 893 (size_t) left)))
@@ -904,7 +904,7 @@ send_param_adapter (struct MHD_Connection *connection,
904 if ( (EINTR == errno) || (EAGAIN == errno) ) 904 if ( (EINTR == errno) || (EAGAIN == errno) )
905 return 0; 905 return 0;
906 if ( (EINVAL == errno) || (EBADF == errno) ) 906 if ( (EINVAL == errno) || (EBADF == errno) )
907 return -1; 907 return -1;
908 /* None of the 'usual' sendfile errors occurred, so we should try 908 /* None of the 'usual' sendfile errors occurred, so we should try
909 to fall back to 'SEND'; see also this thread for info on 909 to fall back to 'SEND'; see also this thread for info on
910 odd libc/Linux behavior with sendfile: 910 odd libc/Linux behavior with sendfile:
@@ -934,7 +934,7 @@ typedef void *(*ThreadStartRoutine)(void *cls);
934 934
935/** 935/**
936 * Create a thread and set the attributes according to our options. 936 * Create a thread and set the attributes according to our options.
937 * 937 *
938 * @param thread handle to initialize 938 * @param thread handle to initialize
939 * @param daemon daemon with options 939 * @param daemon daemon with options
940 * @param start_routine main function of thread 940 * @param start_routine main function of thread
@@ -950,10 +950,10 @@ create_thread (pthread_t *thread,
950 pthread_attr_t attr; 950 pthread_attr_t attr;
951 pthread_attr_t *pattr; 951 pthread_attr_t *pattr;
952 int ret; 952 int ret;
953 953
954 if (0 != daemon->thread_stack_size) 954 if (0 != daemon->thread_stack_size)
955 { 955 {
956 if (0 != (ret = pthread_attr_init (&attr))) 956 if (0 != (ret = pthread_attr_init (&attr)))
957 goto ERR; 957 goto ERR;
958 if (0 != (ret = pthread_attr_setstacksize (&attr, daemon->thread_stack_size))) 958 if (0 != (ret = pthread_attr_setstacksize (&attr, daemon->thread_stack_size)))
959 { 959 {
@@ -973,7 +973,7 @@ create_thread (pthread_t *thread,
973 (void) pthread_setname_np (*thread, "libmicrohttpd"); 973 (void) pthread_setname_np (*thread, "libmicrohttpd");
974#endif 974#endif
975#endif 975#endif
976 if (0 != daemon->thread_stack_size) 976 if (0 != daemon->thread_stack_size)
977 pthread_attr_destroy (&attr); 977 pthread_attr_destroy (&attr);
978 return ret; 978 return ret;
979 ERR: 979 ERR:
@@ -987,11 +987,11 @@ create_thread (pthread_t *thread,
987 987
988 988
989/** 989/**
990 * Add another client connection to the set of connections 990 * Add another client connection to the set of connections
991 * managed by MHD. This API is usually not needed (since 991 * managed by MHD. This API is usually not needed (since
992 * MHD will accept inbound connections on the server socket). 992 * MHD will accept inbound connections on the server socket).
993 * Use this API in special cases, for example if your HTTP 993 * Use this API in special cases, for example if your HTTP
994 * server is behind NAT and needs to connect out to the 994 * server is behind NAT and needs to connect out to the
995 * HTTP client. 995 * HTTP client.
996 * 996 *
997 * The given client socket will be managed (and closed!) by MHD after 997 * The given client socket will be managed (and closed!) by MHD after
@@ -1012,8 +1012,8 @@ create_thread (pthread_t *thread,
1012 * The socket will be closed in any case; 'errno' is 1012 * The socket will be closed in any case; 'errno' is
1013 * set to indicate further details about the error. 1013 * set to indicate further details about the error.
1014 */ 1014 */
1015static int 1015static int
1016internal_add_connection (struct MHD_Daemon *daemon, 1016internal_add_connection (struct MHD_Daemon *daemon,
1017 int client_socket, 1017 int client_socket,
1018 const struct sockaddr *addr, 1018 const struct sockaddr *addr,
1019 socklen_t addrlen, 1019 socklen_t addrlen,
@@ -1025,7 +1025,7 @@ internal_add_connection (struct MHD_Daemon *daemon,
1025 int eno; 1025 int eno;
1026#if OSX 1026#if OSX
1027 static int on = 1; 1027 static int on = 1;
1028#endif 1028#endif
1029 1029
1030 if (NULL != daemon->worker_pool) 1030 if (NULL != daemon->worker_pool)
1031 { 1031 {
@@ -1044,7 +1044,7 @@ internal_add_connection (struct MHD_Daemon *daemon,
1044#if ENFILE 1044#if ENFILE
1045 errno = ENFILE; 1045 errno = ENFILE;
1046#endif 1046#endif
1047 return MHD_NO; 1047 return MHD_NO;
1048 } 1048 }
1049 1049
1050#ifndef WINDOWS 1050#ifndef WINDOWS
@@ -1089,8 +1089,8 @@ internal_add_connection (struct MHD_Daemon *daemon,
1089 } 1089 }
1090 1090
1091 /* apply connection acceptance policy if present */ 1091 /* apply connection acceptance policy if present */
1092 if ( (NULL != daemon->apc) && 1092 if ( (NULL != daemon->apc) &&
1093 (MHD_NO == daemon->apc (daemon->apc_cls, 1093 (MHD_NO == daemon->apc (daemon->apc_cls,
1094 addr, addrlen)) ) 1094 addr, addrlen)) )
1095 { 1095 {
1096#if DEBUG_CLOSE 1096#if DEBUG_CLOSE
@@ -1110,8 +1110,8 @@ internal_add_connection (struct MHD_Daemon *daemon,
1110#if OSX 1110#if OSX
1111#ifdef SOL_SOCKET 1111#ifdef SOL_SOCKET
1112#ifdef SO_NOSIGPIPE 1112#ifdef SO_NOSIGPIPE
1113 setsockopt (client_socket, 1113 setsockopt (client_socket,
1114 SOL_SOCKET, SO_NOSIGPIPE, 1114 SOL_SOCKET, SO_NOSIGPIPE,
1115 &on, sizeof (on)); 1115 &on, sizeof (on));
1116#endif 1116#endif
1117#endif 1117#endif
@@ -1121,8 +1121,8 @@ internal_add_connection (struct MHD_Daemon *daemon,
1121 { 1121 {
1122 eno = errno; 1122 eno = errno;
1123#if HAVE_MESSAGES 1123#if HAVE_MESSAGES
1124 MHD_DLOG (daemon, 1124 MHD_DLOG (daemon,
1125 "Error allocating memory: %s\n", 1125 "Error allocating memory: %s\n",
1126 STRERROR (errno)); 1126 STRERROR (errno));
1127#endif 1127#endif
1128 if (0 != CLOSE (client_socket)) 1128 if (0 != CLOSE (client_socket))
@@ -1136,14 +1136,14 @@ internal_add_connection (struct MHD_Daemon *daemon,
1136 if (NULL == connection->pool) 1136 if (NULL == connection->pool)
1137 { 1137 {
1138#if HAVE_MESSAGES 1138#if HAVE_MESSAGES
1139 MHD_DLOG (daemon, 1139 MHD_DLOG (daemon,
1140 "Error allocating memory: %s\n", 1140 "Error allocating memory: %s\n",
1141 STRERROR (errno)); 1141 STRERROR (errno));
1142#endif 1142#endif
1143 if (0 != CLOSE (client_socket)) 1143 if (0 != CLOSE (client_socket))
1144 MHD_PANIC ("close failed\n"); 1144 MHD_PANIC ("close failed\n");
1145 MHD_ip_limit_del (daemon, addr, addrlen); 1145 MHD_ip_limit_del (daemon, addr, addrlen);
1146 free (connection); 1146 free (connection);
1147#if ENOMEM 1147#if ENOMEM
1148 errno = ENOMEM; 1148 errno = ENOMEM;
1149#endif 1149#endif
@@ -1155,8 +1155,8 @@ internal_add_connection (struct MHD_Daemon *daemon,
1155 { 1155 {
1156 eno = errno; 1156 eno = errno;
1157#if HAVE_MESSAGES 1157#if HAVE_MESSAGES
1158 MHD_DLOG (daemon, 1158 MHD_DLOG (daemon,
1159 "Error allocating memory: %s\n", 1159 "Error allocating memory: %s\n",
1160 STRERROR (errno)); 1160 STRERROR (errno));
1161#endif 1161#endif
1162 if (0 != CLOSE (client_socket)) 1162 if (0 != CLOSE (client_socket))
@@ -1172,7 +1172,7 @@ internal_add_connection (struct MHD_Daemon *daemon,
1172 connection->socket_fd = client_socket; 1172 connection->socket_fd = client_socket;
1173 connection->daemon = daemon; 1173 connection->daemon = daemon;
1174 connection->last_activity = MHD_monotonic_time(); 1174 connection->last_activity = MHD_monotonic_time();
1175 1175
1176 /* set default connection handlers */ 1176 /* set default connection handlers */
1177 MHD_set_http_callbacks_ (connection); 1177 MHD_set_http_callbacks_ (connection);
1178 connection->recv_cls = &recv_param_adapter; 1178 connection->recv_cls = &recv_param_adapter;
@@ -1196,7 +1196,7 @@ internal_add_connection (struct MHD_Daemon *daemon,
1196 { 1196 {
1197#if HAVE_MESSAGES 1197#if HAVE_MESSAGES
1198 MHD_DLOG (daemon, 1198 MHD_DLOG (daemon,
1199 "Failed to make socket %d non-blocking: %s\n", 1199 "Failed to make socket %d non-blocking: %s\n",
1200 connection->socket_fd, 1200 connection->socket_fd,
1201 STRERROR (errno)); 1201 STRERROR (errno));
1202#endif 1202#endif
@@ -1206,8 +1206,8 @@ internal_add_connection (struct MHD_Daemon *daemon,
1206 if (0 != ioctlsocket (connection->socket_fd, FIONBIO, &flags)) 1206 if (0 != ioctlsocket (connection->socket_fd, FIONBIO, &flags))
1207 { 1207 {
1208#if HAVE_MESSAGES 1208#if HAVE_MESSAGES
1209 MHD_DLOG (daemon, 1209 MHD_DLOG (daemon,
1210 "Failed to make socket non-blocking: %s\n", 1210 "Failed to make socket non-blocking: %s\n",
1211 STRERROR (errno)); 1211 STRERROR (errno));
1212#endif 1212#endif
1213 } 1213 }
@@ -1258,14 +1258,14 @@ internal_add_connection (struct MHD_Daemon *daemon,
1258 (gnutls_push_func) &send_param_adapter); 1258 (gnutls_push_func) &send_param_adapter);
1259 1259
1260 if (daemon->https_mem_trust) 1260 if (daemon->https_mem_trust)
1261 gnutls_certificate_server_set_request (connection->tls_session, 1261 gnutls_certificate_server_set_request (connection->tls_session,
1262 GNUTLS_CERT_REQUEST); 1262 GNUTLS_CERT_REQUEST);
1263 } 1263 }
1264#endif 1264#endif
1265 1265
1266 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) && 1266 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) &&
1267 (0 != pthread_mutex_lock (&daemon->cleanup_connection_mutex)) ) 1267 (0 != pthread_mutex_lock (&daemon->cleanup_connection_mutex)) )
1268 MHD_PANIC ("Failed to acquire cleanup mutex\n"); 1268 MHD_PANIC ("Failed to acquire cleanup mutex\n");
1269 XDLL_insert (daemon->normal_timeout_head, 1269 XDLL_insert (daemon->normal_timeout_head,
1270 daemon->normal_timeout_tail, 1270 daemon->normal_timeout_tail,
1271 connection); 1271 connection);
@@ -1274,7 +1274,7 @@ internal_add_connection (struct MHD_Daemon *daemon,
1274 connection); 1274 connection);
1275 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) && 1275 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) &&
1276 (0 != pthread_mutex_unlock (&daemon->cleanup_connection_mutex)) ) 1276 (0 != pthread_mutex_unlock (&daemon->cleanup_connection_mutex)) )
1277 MHD_PANIC ("Failed to release cleanup mutex\n"); 1277 MHD_PANIC ("Failed to release cleanup mutex\n");
1278 1278
1279 /* attempt to create handler thread */ 1279 /* attempt to create handler thread */
1280 if (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) 1280 if (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION))
@@ -1307,9 +1307,9 @@ internal_add_connection (struct MHD_Daemon *daemon,
1307 if (0 == (daemon->options & MHD_USE_EPOLL_TURBO)) 1307 if (0 == (daemon->options & MHD_USE_EPOLL_TURBO))
1308 { 1308 {
1309 struct epoll_event event; 1309 struct epoll_event event;
1310 1310
1311 event.events = EPOLLIN | EPOLLOUT | EPOLLET; 1311 event.events = EPOLLIN | EPOLLOUT | EPOLLET;
1312 event.data.ptr = connection; 1312 event.data.ptr = connection;
1313 if (0 != epoll_ctl (daemon->epoll_fd, 1313 if (0 != epoll_ctl (daemon->epoll_fd,
1314 EPOLL_CTL_ADD, 1314 EPOLL_CTL_ADD,
1315 client_socket, 1315 client_socket,
@@ -1317,10 +1317,9 @@ internal_add_connection (struct MHD_Daemon *daemon,
1317 { 1317 {
1318 eno = errno; 1318 eno = errno;
1319#if HAVE_MESSAGES 1319#if HAVE_MESSAGES
1320 if (0 != (daemon->options & MHD_USE_DEBUG)) 1320 MHD_DLOG (daemon,
1321 MHD_DLOG (daemon, 1321 "Call to epoll_ctl failed: %s\n",
1322 "Call to epoll_ctl failed: %s\n", 1322 STRERROR (errno));
1323 STRERROR (errno));
1324#endif 1323#endif
1325 goto cleanup; 1324 goto cleanup;
1326 } 1325 }
@@ -1336,15 +1335,15 @@ internal_add_connection (struct MHD_Daemon *daemon,
1336 } 1335 }
1337 } 1336 }
1338#endif 1337#endif
1339 daemon->max_connections--; 1338 daemon->max_connections--;
1340 return MHD_YES; 1339 return MHD_YES;
1341 cleanup: 1340 cleanup:
1342 if (0 != CLOSE (client_socket)) 1341 if (0 != CLOSE (client_socket))
1343 MHD_PANIC ("close failed\n"); 1342 MHD_PANIC ("close failed\n");
1344 MHD_ip_limit_del (daemon, addr, addrlen); 1343 MHD_ip_limit_del (daemon, addr, addrlen);
1345 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) && 1344 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) &&
1346 (0 != pthread_mutex_lock (&daemon->cleanup_connection_mutex)) ) 1345 (0 != pthread_mutex_lock (&daemon->cleanup_connection_mutex)) )
1347 MHD_PANIC ("Failed to acquire cleanup mutex\n"); 1346 MHD_PANIC ("Failed to acquire cleanup mutex\n");
1348 DLL_remove (daemon->connections_head, 1347 DLL_remove (daemon->connections_head,
1349 daemon->connections_tail, 1348 daemon->connections_tail,
1350 connection); 1349 connection);
@@ -1354,7 +1353,7 @@ internal_add_connection (struct MHD_Daemon *daemon,
1354 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) && 1353 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) &&
1355 (0 != pthread_mutex_unlock (&daemon->cleanup_connection_mutex)) ) 1354 (0 != pthread_mutex_unlock (&daemon->cleanup_connection_mutex)) )
1356 MHD_PANIC ("Failed to release cleanup mutex\n"); 1355 MHD_PANIC ("Failed to release cleanup mutex\n");
1357 MHD_pool_destroy (connection->pool); 1356 MHD_pool_destroy (connection->pool);
1358 free (connection->addr); 1357 free (connection->addr);
1359 free (connection); 1358 free (connection);
1360#if EINVAL 1359#if EINVAL
@@ -1365,11 +1364,150 @@ internal_add_connection (struct MHD_Daemon *daemon,
1365 1364
1366 1365
1367/** 1366/**
1367 * Suspend handling of network data for a given connection. This can
1368 * be used to dequeue a connection from MHD's event loop (external
1369 * select, internal select or thread pool; not applicable to
1370 * thread-per-connection!) for a while.
1371 *
1372 * If you use this API in conjunction with a internal select or a
1373 * thread pool, you must set the option #MHD_USE_PIPE_FOR_SHUTDOWN to
1374 * ensure that a resumed connection is immediately processed by MHD.
1375 *
1376 * Suspended connections continue to count against the total number of
1377 * connections allowed (per daemon, as well as per IP, if such limits
1378 * are set). Suspended connections will NOT time out; timeouts will
1379 * restart when the connection handling is resumed. While a
1380 * connection is suspended, MHD will not detect disconnects by the
1381 * client.
1382 *
1383 * The only safe time to suspend a connection is from the
1384 * #MHD_AccessHandlerCallback.
1385 *
1386 * Finally, it is an API violation to call #MHD_stop_daemon while
1387 * having suspended connections (this will at least create memory and
1388 * socket leaks or lead to undefined behavior). You must explicitly
1389 * resume all connections before stopping the daemon.
1390 *
1391 * @param connection the connection to suspend
1392 */
1393void
1394MHD_suspend_connection (struct MHD_Connection *connection)
1395{
1396 struct MHD_Daemon *daemon;
1397
1398 daemon = connection->daemon;
1399 if (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION))
1400 MHD_PANIC ("Cannot suspend connections in THREAD_PER_CONNECTION mode!\n");
1401 DLL_remove (daemon->connections_head,
1402 daemon->connections_tail,
1403 connection);
1404 if (connection->connection_timeout == daemon->connection_timeout)
1405 XDLL_remove (daemon->normal_timeout_head,
1406 daemon->normal_timeout_tail,
1407 connection);
1408 else
1409 XDLL_remove (daemon->manual_timeout_head,
1410 daemon->manual_timeout_tail,
1411 connection);
1412#if EPOLL_SUPPORT
1413 if (0 != (connection->epoll_state & MHD_EPOLL_STATE_IN_EREADY_EDLL))
1414 {
1415 EDLL_remove (daemon->eready_head,
1416 daemon->eready_tail,
1417 connection);
1418 }
1419 if (0 != (connection->epoll_state & MHD_EPOLL_STATE_IN_EPOLL_SET))
1420 {
1421 if (0 != epoll_ctl (daemon->epoll_fd,
1422 EPOLL_CTL_DEL,
1423 connection->socket_fd,
1424 NULL))
1425 MHD_PANIC ("Failed to remove FD from epoll set\n");
1426 connection->epoll_state &= ~MHD_EPOLL_STATE_IN_EPOLL_SET;
1427 }
1428#endif
1429}
1430
1431
1432/**
1433 * Resume handling of network data for suspended connection. It is
1434 * safe to resume a suspended connection at any time. Calling this function
1435 * on a connection that was not previously suspended will result
1436 * in undefined behavior.
1437 *
1438 * @param connection the connection to resume
1439 */
1440void
1441MHD_resume_connection (struct MHD_Connection *connection)
1442{
1443 struct MHD_Daemon *daemon;
1444
1445 daemon = connection->daemon;
1446 if (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION))
1447 MHD_PANIC ("Cannot resume connections in THREAD_PER_CONNECTION mode!\n");
1448 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) &&
1449 (0 != pthread_mutex_lock (&daemon->cleanup_connection_mutex)) )
1450 MHD_PANIC ("Failed to acquire cleanup mutex\n");
1451 DLL_insert (daemon->connections_head,
1452 daemon->connections_tail,
1453 connection);
1454 if (connection->connection_timeout == daemon->connection_timeout)
1455 XDLL_insert (daemon->normal_timeout_head,
1456 daemon->normal_timeout_tail,
1457 connection);
1458 else
1459 XDLL_insert (daemon->manual_timeout_head,
1460 daemon->manual_timeout_tail,
1461 connection);
1462#if EPOLL_SUPPORT
1463 if (0 != (connection->epoll_state & MHD_EPOLL_STATE_IN_EREADY_EDLL))
1464 {
1465 EDLL_insert (daemon->eready_head,
1466 daemon->eready_tail,
1467 connection);
1468 }
1469 else
1470 {
1471 struct epoll_event event;
1472
1473 event.events = EPOLLIN | EPOLLOUT | EPOLLET;
1474 event.data.ptr = connection;
1475 if (0 != epoll_ctl (daemon->epoll_fd,
1476 EPOLL_CTL_ADD,
1477 connection->socket_fd,
1478 &event))
1479 {
1480#if HAVE_MESSAGES
1481 MHD_DLOG (daemon,
1482 "Call to epoll_ctl failed: %s\n",
1483 STRERROR (errno));
1484#endif
1485 /* and now, good luck with this... */
1486 }
1487 else
1488 connection->epoll_state |= MHD_EPOLL_STATE_IN_EPOLL_SET;
1489 }
1490#endif
1491 if ( (-1 != daemon->wpipe[1]) &&
1492 (1 != WRITE (daemon->wpipe[1], "n", 1)) )
1493 {
1494#if HAVE_MESSAGES
1495 MHD_DLOG (daemon,
1496 "failed to signal resume via pipe");
1497#endif
1498 }
1499 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) &&
1500 (0 != pthread_mutex_unlock (&daemon->cleanup_connection_mutex)) )
1501 MHD_PANIC ("Failed to release cleanup mutex\n");
1502}
1503
1504
1505/**
1368 * Change socket options to be non-blocking, non-inheritable. 1506 * Change socket options to be non-blocking, non-inheritable.
1369 * 1507 *
1370 * @param daemon daemon context 1508 * @param daemon daemon context
1371 * @param sock socket to manipulate 1509 * @param sock socket to manipulate
1372 */ 1510 */
1373static void 1511static void
1374make_nonblocking_noninheritable (struct MHD_Daemon *daemon, 1512make_nonblocking_noninheritable (struct MHD_Daemon *daemon,
1375 int sock) 1513 int sock)
@@ -1389,12 +1527,12 @@ make_nonblocking_noninheritable (struct MHD_Daemon *daemon,
1389#ifdef WINDOWS 1527#ifdef WINDOWS
1390 DWORD dwFlags; 1528 DWORD dwFlags;
1391 unsigned long flags = 1; 1529 unsigned long flags = 1;
1392 1530
1393 if (0 != ioctlsocket (sock, FIONBIO, &flags)) 1531 if (0 != ioctlsocket (sock, FIONBIO, &flags))
1394 { 1532 {
1395#if HAVE_MESSAGES 1533#if HAVE_MESSAGES
1396 MHD_DLOG (daemon, 1534 MHD_DLOG (daemon,
1397 "Failed to make socket non-blocking: %s\n", 1535 "Failed to make socket non-blocking: %s\n",
1398 STRERROR (errno)); 1536 STRERROR (errno));
1399#endif 1537#endif
1400 } 1538 }
@@ -1405,13 +1543,13 @@ make_nonblocking_noninheritable (struct MHD_Daemon *daemon,
1405#if HAVE_MESSAGES 1543#if HAVE_MESSAGES
1406 SetErrnoFromWinError (GetLastError ()); 1544 SetErrnoFromWinError (GetLastError ());
1407 MHD_DLOG (daemon, 1545 MHD_DLOG (daemon,
1408 "Failed to make socket non-inheritable: %s\n", 1546 "Failed to make socket non-inheritable: %s\n",
1409 STRERROR (errno)); 1547 STRERROR (errno));
1410#endif 1548#endif
1411 } 1549 }
1412#else 1550#else
1413 int flags; 1551 int flags;
1414 1552
1415 nonblock = O_NONBLOCK; 1553 nonblock = O_NONBLOCK;
1416#ifdef CYGWIN 1554#ifdef CYGWIN
1417 if (0 == (daemon->options & MHD_USE_SSL)) 1555 if (0 == (daemon->options & MHD_USE_SSL))
@@ -1424,7 +1562,7 @@ make_nonblocking_noninheritable (struct MHD_Daemon *daemon,
1424 { 1562 {
1425#if HAVE_MESSAGES 1563#if HAVE_MESSAGES
1426 MHD_DLOG (daemon, 1564 MHD_DLOG (daemon,
1427 "Failed to make socket non-inheritable: %s\n", 1565 "Failed to make socket non-inheritable: %s\n",
1428 STRERROR (errno)); 1566 STRERROR (errno));
1429#endif 1567#endif
1430 } 1568 }
@@ -1461,13 +1599,13 @@ make_nonblocking_noninheritable (struct MHD_Daemon *daemon,
1461 * set to indicate further details about the error. 1599 * set to indicate further details about the error.
1462 * @ingroup specialized 1600 * @ingroup specialized
1463 */ 1601 */
1464int 1602int
1465MHD_add_connection (struct MHD_Daemon *daemon, 1603MHD_add_connection (struct MHD_Daemon *daemon,
1466 int client_socket, 1604 int client_socket,
1467 const struct sockaddr *addr, 1605 const struct sockaddr *addr,
1468 socklen_t addrlen) 1606 socklen_t addrlen)
1469{ 1607{
1470 make_nonblocking_noninheritable (daemon, 1608 make_nonblocking_noninheritable (daemon,
1471 client_socket); 1609 client_socket);
1472 return internal_add_connection (daemon, 1610 return internal_add_connection (daemon,
1473 client_socket, 1611 client_socket,
@@ -1480,7 +1618,7 @@ MHD_add_connection (struct MHD_Daemon *daemon,
1480 * Accept an incoming connection and create the MHD_Connection object for 1618 * Accept an incoming connection and create the MHD_Connection object for
1481 * it. This function also enforces policy by way of checking with the 1619 * it. This function also enforces policy by way of checking with the
1482 * accept policy callback. 1620 * accept policy callback.
1483 * 1621 *
1484 * @param daemon handle with the listen socket 1622 * @param daemon handle with the listen socket
1485 * @return MHD_YES on success (connections denied by policy or due 1623 * @return MHD_YES on success (connections denied by policy or due
1486 * to 'out of memory' and similar errors) are still considered 1624 * to 'out of memory' and similar errors) are still considered
@@ -1525,8 +1663,8 @@ MHD_accept_connection (struct MHD_Daemon *daemon)
1525#if HAVE_MESSAGES 1663#if HAVE_MESSAGES
1526 /* This could be a common occurance with multiple worker threads */ 1664 /* This could be a common occurance with multiple worker threads */
1527 if ((EAGAIN != errno) && (EWOULDBLOCK != errno)) 1665 if ((EAGAIN != errno) && (EWOULDBLOCK != errno))
1528 MHD_DLOG (daemon, 1666 MHD_DLOG (daemon,
1529 "Error accepting connection: %s\n", 1667 "Error accepting connection: %s\n",
1530 STRERROR (errno)); 1668 STRERROR (errno));
1531#endif 1669#endif
1532 if (-1 != s) 1670 if (-1 != s)
@@ -1567,7 +1705,7 @@ MHD_cleanup_connections (struct MHD_Daemon *daemon)
1567 1705
1568 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) && 1706 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) &&
1569 (0 != pthread_mutex_lock (&daemon->cleanup_connection_mutex)) ) 1707 (0 != pthread_mutex_lock (&daemon->cleanup_connection_mutex)) )
1570 MHD_PANIC ("Failed to acquire cleanup mutex\n"); 1708 MHD_PANIC ("Failed to acquire cleanup mutex\n");
1571 while (NULL != (pos = daemon->cleanup_head)) 1709 while (NULL != (pos = daemon->cleanup_head))
1572 { 1710 {
1573 DLL_remove (daemon->cleanup_head, 1711 DLL_remove (daemon->cleanup_head,
@@ -1575,7 +1713,7 @@ MHD_cleanup_connections (struct MHD_Daemon *daemon)
1575 pos); 1713 pos);
1576 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) && 1714 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) &&
1577 (MHD_NO == pos->thread_joined) ) 1715 (MHD_NO == pos->thread_joined) )
1578 { 1716 {
1579 if (0 != (rc = pthread_join (pos->pid, &unused))) 1717 if (0 != (rc = pthread_join (pos->pid, &unused)))
1580 { 1718 {
1581 MHD_PANIC ("Failed to join a thread\n"); 1719 MHD_PANIC ("Failed to join a thread\n");
@@ -1586,8 +1724,8 @@ MHD_cleanup_connections (struct MHD_Daemon *daemon)
1586 if (pos->tls_session != NULL) 1724 if (pos->tls_session != NULL)
1587 gnutls_deinit (pos->tls_session); 1725 gnutls_deinit (pos->tls_session);
1588#endif 1726#endif
1589 MHD_ip_limit_del (daemon, 1727 MHD_ip_limit_del (daemon,
1590 (struct sockaddr *) pos->addr, 1728 (struct sockaddr *) pos->addr,
1591 pos->addr_len); 1729 pos->addr_len);
1592#if EPOLL_SUPPORT 1730#if EPOLL_SUPPORT
1593 if (0 != (pos->epoll_state & MHD_EPOLL_STATE_IN_EREADY_EDLL)) 1731 if (0 != (pos->epoll_state & MHD_EPOLL_STATE_IN_EREADY_EDLL))
@@ -1633,9 +1771,9 @@ MHD_cleanup_connections (struct MHD_Daemon *daemon)
1633 free (pos); 1771 free (pos);
1634 daemon->max_connections++; 1772 daemon->max_connections++;
1635 } 1773 }
1636 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) && 1774 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) &&
1637 (0 != pthread_mutex_unlock (&daemon->cleanup_connection_mutex)) ) 1775 (0 != pthread_mutex_unlock (&daemon->cleanup_connection_mutex)) )
1638 MHD_PANIC ("Failed to release cleanup mutex\n"); 1776 MHD_PANIC ("Failed to release cleanup mutex\n");
1639} 1777}
1640 1778
1641 1779
@@ -1666,7 +1804,7 @@ MHD_get_timeout (struct MHD_Daemon *daemon,
1666 { 1804 {
1667#if HAVE_MESSAGES 1805#if HAVE_MESSAGES
1668 MHD_DLOG (daemon, "Illegal call to MHD_get_timeout\n"); 1806 MHD_DLOG (daemon, "Illegal call to MHD_get_timeout\n");
1669#endif 1807#endif
1670 return MHD_NO; 1808 return MHD_NO;
1671 } 1809 }
1672 1810
@@ -1683,7 +1821,7 @@ MHD_get_timeout (struct MHD_Daemon *daemon,
1683 have_timeout = MHD_NO; 1821 have_timeout = MHD_NO;
1684 for (pos = daemon->manual_timeout_head; NULL != pos; pos = pos->nextX) 1822 for (pos = daemon->manual_timeout_head; NULL != pos; pos = pos->nextX)
1685 { 1823 {
1686 if (0 != pos->connection_timeout) 1824 if (0 != pos->connection_timeout)
1687 { 1825 {
1688 if ( (! have_timeout) || 1826 if ( (! have_timeout) ||
1689 (earliest_deadline > pos->last_activity + pos->connection_timeout) ) 1827 (earliest_deadline > pos->last_activity + pos->connection_timeout) )
@@ -1743,7 +1881,7 @@ MHD_get_timeout (struct MHD_Daemon *daemon,
1743 * @ingroup event 1881 * @ingroup event
1744 */ 1882 */
1745int 1883int
1746MHD_run_from_select (struct MHD_Daemon *daemon, 1884MHD_run_from_select (struct MHD_Daemon *daemon,
1747 const fd_set *read_fd_set, 1885 const fd_set *read_fd_set,
1748 const fd_set *write_fd_set, 1886 const fd_set *write_fd_set,
1749 const fd_set *except_fd_set) 1887 const fd_set *except_fd_set)
@@ -1790,7 +1928,7 @@ MHD_run_from_select (struct MHD_Daemon *daemon,
1790 case MHD_EVENT_LOOP_INFO_READ: 1928 case MHD_EVENT_LOOP_INFO_READ:
1791 if ( (FD_ISSET (ds, read_fd_set)) 1929 if ( (FD_ISSET (ds, read_fd_set))
1792#if HTTPS_SUPPORT 1930#if HTTPS_SUPPORT
1793 || (MHD_YES == pos->tls_read_ready) 1931 || (MHD_YES == pos->tls_read_ready)
1794#endif 1932#endif
1795 ) 1933 )
1796 pos->read_handler (pos); 1934 pos->read_handler (pos);
@@ -1811,7 +1949,7 @@ MHD_run_from_select (struct MHD_Daemon *daemon,
1811 /* should never happen */ 1949 /* should never happen */
1812 break; 1950 break;
1813 } 1951 }
1814 pos->idle_handler (pos); 1952 pos->idle_handler (pos);
1815 } 1953 }
1816 } 1954 }
1817 MHD_cleanup_connections (daemon); 1955 MHD_cleanup_connections (daemon);
@@ -1828,7 +1966,7 @@ MHD_run_from_select (struct MHD_Daemon *daemon,
1828 * @return #MHD_NO on serious errors, #MHD_YES on success 1966 * @return #MHD_NO on serious errors, #MHD_YES on success
1829 */ 1967 */
1830static int 1968static int
1831MHD_select (struct MHD_Daemon *daemon, 1969MHD_select (struct MHD_Daemon *daemon,
1832 int may_block) 1970 int may_block)
1833{ 1971{
1834 int num_ready; 1972 int num_ready;
@@ -1856,14 +1994,14 @@ MHD_select (struct MHD_Daemon *daemon,
1856 1994
1857 /* If we're at the connection limit, no need to 1995 /* If we're at the connection limit, no need to
1858 accept new connections. */ 1996 accept new connections. */
1859 if ( (0 == daemon->max_connections) && 1997 if ( (0 == daemon->max_connections) &&
1860 (-1 != daemon->socket_fd) ) 1998 (-1 != daemon->socket_fd) )
1861 FD_CLR (daemon->socket_fd, &rs); 1999 FD_CLR (daemon->socket_fd, &rs);
1862 } 2000 }
1863 else 2001 else
1864 { 2002 {
1865 /* accept only, have one thread per connection */ 2003 /* accept only, have one thread per connection */
1866 if (-1 != daemon->socket_fd) 2004 if (-1 != daemon->socket_fd)
1867 { 2005 {
1868 max = daemon->socket_fd; 2006 max = daemon->socket_fd;
1869 FD_SET (daemon->socket_fd, &rs); 2007 FD_SET (daemon->socket_fd, &rs);
@@ -1938,7 +2076,7 @@ MHD_poll_all (struct MHD_Daemon *daemon,
1938 int timeout; 2076 int timeout;
1939 unsigned int poll_server; 2077 unsigned int poll_server;
1940 int poll_listen; 2078 int poll_listen;
1941 2079
1942 memset (p, 0, sizeof (p)); 2080 memset (p, 0, sizeof (p));
1943 poll_server = 0; 2081 poll_server = 0;
1944 poll_listen = -1; 2082 poll_listen = -1;
@@ -1952,7 +2090,7 @@ MHD_poll_all (struct MHD_Daemon *daemon,
1952 poll_listen = (int) poll_server; 2090 poll_listen = (int) poll_server;
1953 poll_server++; 2091 poll_server++;
1954 } 2092 }
1955 if (-1 != daemon->wpipe[0]) 2093 if (-1 != daemon->wpipe[0])
1956 { 2094 {
1957 p[poll_server].fd = daemon->wpipe[0]; 2095 p[poll_server].fd = daemon->wpipe[0];
1958 p[poll_server].events = POLLIN; 2096 p[poll_server].events = POLLIN;
@@ -1966,7 +2104,7 @@ MHD_poll_all (struct MHD_Daemon *daemon,
1966 timeout = -1; 2104 timeout = -1;
1967 else 2105 else
1968 timeout = (ltimeout > INT_MAX) ? INT_MAX : (int) ltimeout; 2106 timeout = (ltimeout > INT_MAX) ? INT_MAX : (int) ltimeout;
1969 2107
1970 i = 0; 2108 i = 0;
1971 for (pos = daemon->connections_head; NULL != pos; pos = pos->next) 2109 for (pos = daemon->connections_head; NULL != pos; pos = pos->next)
1972 { 2110 {
@@ -1974,16 +2112,16 @@ MHD_poll_all (struct MHD_Daemon *daemon,
1974 switch (pos->event_loop_info) 2112 switch (pos->event_loop_info)
1975 { 2113 {
1976 case MHD_EVENT_LOOP_INFO_READ: 2114 case MHD_EVENT_LOOP_INFO_READ:
1977 p[poll_server+i].events |= POLLIN; 2115 p[poll_server+i].events |= POLLIN;
1978 break; 2116 break;
1979 case MHD_EVENT_LOOP_INFO_WRITE: 2117 case MHD_EVENT_LOOP_INFO_WRITE:
1980 p[poll_server+i].events |= POLLOUT; 2118 p[poll_server+i].events |= POLLOUT;
1981 if (pos->read_buffer_size > pos->read_buffer_offset) 2119 if (pos->read_buffer_size > pos->read_buffer_offset)
1982 p[poll_server+i].events |= POLLIN; 2120 p[poll_server+i].events |= POLLIN;
1983 break; 2121 break;
1984 case MHD_EVENT_LOOP_INFO_BLOCK: 2122 case MHD_EVENT_LOOP_INFO_BLOCK:
1985 if (pos->read_buffer_size > pos->read_buffer_offset) 2123 if (pos->read_buffer_size > pos->read_buffer_offset)
1986 p[poll_server+i].events |= POLLIN; 2124 p[poll_server+i].events |= POLLIN;
1987 break; 2125 break;
1988 case MHD_EVENT_LOOP_INFO_CLEANUP: 2126 case MHD_EVENT_LOOP_INFO_CLEANUP:
1989 /* should never happen */ 2127 /* should never happen */
@@ -1993,20 +2131,20 @@ MHD_poll_all (struct MHD_Daemon *daemon,
1993 } 2131 }
1994 if (0 == poll_server + num_connections) 2132 if (0 == poll_server + num_connections)
1995 return MHD_YES; 2133 return MHD_YES;
1996 if (poll (p, poll_server + num_connections, timeout) < 0) 2134 if (poll (p, poll_server + num_connections, timeout) < 0)
1997 { 2135 {
1998 if (EINTR == errno) 2136 if (EINTR == errno)
1999 return MHD_YES; 2137 return MHD_YES;
2000#if HAVE_MESSAGES 2138#if HAVE_MESSAGES
2001 MHD_DLOG (daemon, 2139 MHD_DLOG (daemon,
2002 "poll failed: %s\n", 2140 "poll failed: %s\n",
2003 STRERROR (errno)); 2141 STRERROR (errno));
2004#endif 2142#endif
2005 return MHD_NO; 2143 return MHD_NO;
2006 } 2144 }
2007 /* handle shutdown */ 2145 /* handle shutdown */
2008 if (MHD_YES == daemon->shutdown) 2146 if (MHD_YES == daemon->shutdown)
2009 return MHD_NO; 2147 return MHD_NO;
2010 i = 0; 2148 i = 0;
2011 next = daemon->connections_head; 2149 next = daemon->connections_head;
2012 while (NULL != (pos = next)) 2150 while (NULL != (pos = next))
@@ -2017,11 +2155,11 @@ MHD_poll_all (struct MHD_Daemon *daemon,
2017 case MHD_EVENT_LOOP_INFO_READ: 2155 case MHD_EVENT_LOOP_INFO_READ:
2018 /* first, sanity checks */ 2156 /* first, sanity checks */
2019 if (i >= num_connections) 2157 if (i >= num_connections)
2020 break; /* connection list changed somehow, retry later ... */ 2158 break; /* connection list changed somehow, retry later ... */
2021 if (p[poll_server+i].fd != pos->socket_fd) 2159 if (p[poll_server+i].fd != pos->socket_fd)
2022 break; /* fd mismatch, something else happened, retry later ... */ 2160 break; /* fd mismatch, something else happened, retry later ... */
2023 /* normal handling */ 2161 /* normal handling */
2024 if (0 != (p[poll_server+i].revents & POLLIN)) 2162 if (0 != (p[poll_server+i].revents & POLLIN))
2025 pos->read_handler (pos); 2163 pos->read_handler (pos);
2026 pos->idle_handler (pos); 2164 pos->idle_handler (pos);
2027 i++; 2165 i++;
@@ -2029,19 +2167,19 @@ MHD_poll_all (struct MHD_Daemon *daemon,
2029 case MHD_EVENT_LOOP_INFO_WRITE: 2167 case MHD_EVENT_LOOP_INFO_WRITE:
2030 /* first, sanity checks */ 2168 /* first, sanity checks */
2031 if (i >= num_connections) 2169 if (i >= num_connections)
2032 break; /* connection list changed somehow, retry later ... */ 2170 break; /* connection list changed somehow, retry later ... */
2033 if (p[poll_server+i].fd != pos->socket_fd) 2171 if (p[poll_server+i].fd != pos->socket_fd)
2034 break; /* fd mismatch, something else happened, retry later ... */ 2172 break; /* fd mismatch, something else happened, retry later ... */
2035 /* normal handling */ 2173 /* normal handling */
2036 if (0 != (p[poll_server+i].revents & POLLIN)) 2174 if (0 != (p[poll_server+i].revents & POLLIN))
2037 pos->read_handler (pos); 2175 pos->read_handler (pos);
2038 if (0 != (p[poll_server+i].revents & POLLOUT)) 2176 if (0 != (p[poll_server+i].revents & POLLOUT))
2039 pos->write_handler (pos); 2177 pos->write_handler (pos);
2040 pos->idle_handler (pos); 2178 pos->idle_handler (pos);
2041 i++; 2179 i++;
2042 break; 2180 break;
2043 case MHD_EVENT_LOOP_INFO_BLOCK: 2181 case MHD_EVENT_LOOP_INFO_BLOCK:
2044 if (0 != (p[poll_server+i].revents & POLLIN)) 2182 if (0 != (p[poll_server+i].revents & POLLIN))
2045 pos->read_handler (pos); 2183 pos->read_handler (pos);
2046 pos->idle_handler (pos); 2184 pos->idle_handler (pos);
2047 break; 2185 break;
@@ -2074,7 +2212,7 @@ MHD_poll_listen_socket (struct MHD_Daemon *daemon,
2074 int timeout; 2212 int timeout;
2075 unsigned int poll_count; 2213 unsigned int poll_count;
2076 int poll_listen; 2214 int poll_listen;
2077 2215
2078 memset (&p, 0, sizeof (p)); 2216 memset (&p, 0, sizeof (p));
2079 poll_count = 0; 2217 poll_count = 0;
2080 poll_listen = -1; 2218 poll_listen = -1;
@@ -2110,10 +2248,10 @@ MHD_poll_listen_socket (struct MHD_Daemon *daemon,
2110 } 2248 }
2111 /* handle shutdown */ 2249 /* handle shutdown */
2112 if (MHD_YES == daemon->shutdown) 2250 if (MHD_YES == daemon->shutdown)
2113 return MHD_NO; 2251 return MHD_NO;
2114 if ( (-1 != poll_listen) && 2252 if ( (-1 != poll_listen) &&
2115 (0 != (p[poll_listen].revents & POLLIN)) ) 2253 (0 != (p[poll_listen].revents & POLLIN)) )
2116 (void) MHD_accept_connection (daemon); 2254 (void) MHD_accept_connection (daemon);
2117 return MHD_YES; 2255 return MHD_YES;
2118} 2256}
2119#endif 2257#endif
@@ -2175,7 +2313,7 @@ MHD_epoll (struct MHD_Daemon *daemon,
2175 int timeout_ms; 2313 int timeout_ms;
2176 MHD_UNSIGNED_LONG_LONG timeout_ll; 2314 MHD_UNSIGNED_LONG_LONG timeout_ll;
2177 int num_events; 2315 int num_events;
2178 unsigned int i; 2316 unsigned int i;
2179 unsigned int series_length; 2317 unsigned int series_length;
2180 2318
2181 if (-1 == daemon->epoll_fd) 2319 if (-1 == daemon->epoll_fd)
@@ -2187,7 +2325,7 @@ MHD_epoll (struct MHD_Daemon *daemon,
2187 (MHD_NO == daemon->listen_socket_in_epoll) ) 2325 (MHD_NO == daemon->listen_socket_in_epoll) )
2188 { 2326 {
2189 event.events = EPOLLIN; 2327 event.events = EPOLLIN;
2190 event.data.ptr = daemon; 2328 event.data.ptr = daemon;
2191 if (0 != epoll_ctl (daemon->epoll_fd, 2329 if (0 != epoll_ctl (daemon->epoll_fd,
2192 EPOLL_CTL_ADD, 2330 EPOLL_CTL_ADD,
2193 daemon->socket_fd, 2331 daemon->socket_fd,
@@ -2195,8 +2333,8 @@ MHD_epoll (struct MHD_Daemon *daemon,
2195 { 2333 {
2196#if HAVE_MESSAGES 2334#if HAVE_MESSAGES
2197 if (0 != (daemon->options & MHD_USE_DEBUG)) 2335 if (0 != (daemon->options & MHD_USE_DEBUG))
2198 MHD_DLOG (daemon, 2336 MHD_DLOG (daemon,
2199 "Call to epoll_ctl failed: %s\n", 2337 "Call to epoll_ctl failed: %s\n",
2200 STRERROR (errno)); 2338 STRERROR (errno));
2201#endif 2339#endif
2202 return MHD_NO; 2340 return MHD_NO;
@@ -2247,8 +2385,8 @@ MHD_epoll (struct MHD_Daemon *daemon,
2247 return MHD_YES; 2385 return MHD_YES;
2248#if HAVE_MESSAGES 2386#if HAVE_MESSAGES
2249 if (0 != (daemon->options & MHD_USE_DEBUG)) 2387 if (0 != (daemon->options & MHD_USE_DEBUG))
2250 MHD_DLOG (daemon, 2388 MHD_DLOG (daemon,
2251 "Call to epoll_wait failed: %s\n", 2389 "Call to epoll_wait failed: %s\n",
2252 STRERROR (errno)); 2390 STRERROR (errno));
2253#endif 2391#endif
2254 return MHD_NO; 2392 return MHD_NO;
@@ -2270,7 +2408,7 @@ MHD_epoll (struct MHD_Daemon *daemon,
2270 (pos->read_buffer_size > pos->read_buffer_offset) ) && 2408 (pos->read_buffer_size > pos->read_buffer_offset) ) &&
2271 (0 == (pos->epoll_state & MHD_EPOLL_STATE_IN_EREADY_EDLL) ) ) 2409 (0 == (pos->epoll_state & MHD_EPOLL_STATE_IN_EREADY_EDLL) ) )
2272 { 2410 {
2273 EDLL_insert (daemon->eready_head, 2411 EDLL_insert (daemon->eready_head,
2274 daemon->eready_tail, 2412 daemon->eready_tail,
2275 pos); 2413 pos);
2276 pos->epoll_state |= MHD_EPOLL_STATE_IN_EREADY_EDLL; 2414 pos->epoll_state |= MHD_EPOLL_STATE_IN_EREADY_EDLL;
@@ -2282,7 +2420,7 @@ MHD_epoll (struct MHD_Daemon *daemon,
2282 if ( (MHD_EVENT_LOOP_INFO_WRITE == pos->event_loop_info) && 2420 if ( (MHD_EVENT_LOOP_INFO_WRITE == pos->event_loop_info) &&
2283 (0 == (pos->epoll_state & MHD_EPOLL_STATE_IN_EREADY_EDLL) ) ) 2421 (0 == (pos->epoll_state & MHD_EPOLL_STATE_IN_EREADY_EDLL) ) )
2284 { 2422 {
2285 EDLL_insert (daemon->eready_head, 2423 EDLL_insert (daemon->eready_head,
2286 daemon->eready_tail, 2424 daemon->eready_tail,
2287 pos); 2425 pos);
2288 pos->epoll_state |= MHD_EPOLL_STATE_IN_EREADY_EDLL; 2426 pos->epoll_state |= MHD_EPOLL_STATE_IN_EREADY_EDLL;
@@ -2368,25 +2506,25 @@ MHD_epoll (struct MHD_Daemon *daemon,
2368int 2506int
2369MHD_run (struct MHD_Daemon *daemon) 2507MHD_run (struct MHD_Daemon *daemon)
2370{ 2508{
2371 if ( (MHD_YES == daemon->shutdown) || 2509 if ( (MHD_YES == daemon->shutdown) ||
2372 (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) || 2510 (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) ||
2373 (0 != (daemon->options & MHD_USE_SELECT_INTERNALLY)) ) 2511 (0 != (daemon->options & MHD_USE_SELECT_INTERNALLY)) )
2374 return MHD_NO; 2512 return MHD_NO;
2375 if (0 != (daemon->options & MHD_USE_POLL)) 2513 if (0 != (daemon->options & MHD_USE_POLL))
2376 { 2514 {
2377 MHD_poll (daemon, MHD_NO); 2515 MHD_poll (daemon, MHD_NO);
2378 MHD_cleanup_connections (daemon); 2516 MHD_cleanup_connections (daemon);
2379 } 2517 }
2380#if EPOLL_SUPPORT 2518#if EPOLL_SUPPORT
2381 else if (0 != (daemon->options & MHD_USE_EPOLL_LINUX_ONLY)) 2519 else if (0 != (daemon->options & MHD_USE_EPOLL_LINUX_ONLY))
2382 { 2520 {
2383 MHD_epoll (daemon, MHD_NO); 2521 MHD_epoll (daemon, MHD_NO);
2384 MHD_cleanup_connections (daemon); 2522 MHD_cleanup_connections (daemon);
2385 } 2523 }
2386#endif 2524#endif
2387 else 2525 else
2388 { 2526 {
2389 MHD_select (daemon, MHD_NO); 2527 MHD_select (daemon, MHD_NO);
2390 /* MHD_select does MHD_cleanup_connections already */ 2528 /* MHD_select does MHD_cleanup_connections already */
2391 } 2529 }
2392 return MHD_YES; 2530 return MHD_YES;
@@ -2407,13 +2545,13 @@ MHD_select_thread (void *cls)
2407 2545
2408 while (MHD_YES != daemon->shutdown) 2546 while (MHD_YES != daemon->shutdown)
2409 { 2547 {
2410 if (0 != (daemon->options & MHD_USE_POLL)) 2548 if (0 != (daemon->options & MHD_USE_POLL))
2411 MHD_poll (daemon, MHD_YES); 2549 MHD_poll (daemon, MHD_YES);
2412#if EPOLL_SUPPORT 2550#if EPOLL_SUPPORT
2413 else if (0 != (daemon->options & MHD_USE_EPOLL_LINUX_ONLY)) 2551 else if (0 != (daemon->options & MHD_USE_EPOLL_LINUX_ONLY))
2414 MHD_epoll (daemon, MHD_YES); 2552 MHD_epoll (daemon, MHD_YES);
2415#endif 2553#endif
2416 else 2554 else
2417 MHD_select (daemon, MHD_YES); 2555 MHD_select (daemon, MHD_YES);
2418 MHD_cleanup_connections (daemon); 2556 MHD_cleanup_connections (daemon);
2419 } 2557 }
@@ -2469,7 +2607,7 @@ MHD_start_daemon (unsigned int flags,
2469 * #MHD_start_daemon, this function will return -1. 2607 * #MHD_start_daemon, this function will return -1.
2470 * 2608 *
2471 * @param daemon daemon to stop accepting new connections for 2609 * @param daemon daemon to stop accepting new connections for
2472 * @return old listen socket on success, -1 if the daemon was 2610 * @return old listen socket on success, -1 if the daemon was
2473 * already not listening anymore 2611 * already not listening anymore
2474 * @ingroup specialized 2612 * @ingroup specialized
2475 */ 2613 */
@@ -2486,7 +2624,7 @@ MHD_quiesce_daemon (struct MHD_Daemon *daemon)
2486 (0 != (daemon->options & MHD_USE_SELECT_INTERNALLY)) ) 2624 (0 != (daemon->options & MHD_USE_SELECT_INTERNALLY)) )
2487 { 2625 {
2488#if HAVE_MESSAGES 2626#if HAVE_MESSAGES
2489 MHD_DLOG (daemon, 2627 MHD_DLOG (daemon,
2490 "Using MHD_quiesce_daemon in this mode requires MHD_USE_PIPE_FOR_SHUTDOWN\n"); 2628 "Using MHD_quiesce_daemon in this mode requires MHD_USE_PIPE_FOR_SHUTDOWN\n");
2491#endif 2629#endif
2492 return -1; 2630 return -1;
@@ -2536,13 +2674,13 @@ MHD_quiesce_daemon (struct MHD_Daemon *daemon)
2536 * @param va arguments to the format string (fprintf-style) 2674 * @param va arguments to the format string (fprintf-style)
2537 */ 2675 */
2538typedef void (*VfprintfFunctionPointerType)(void *cls, 2676typedef void (*VfprintfFunctionPointerType)(void *cls,
2539 const char *format, 2677 const char *format,
2540 va_list va); 2678 va_list va);
2541 2679
2542 2680
2543/** 2681/**
2544 * Parse a list of options given as varargs. 2682 * Parse a list of options given as varargs.
2545 * 2683 *
2546 * @param daemon the daemon to initialize 2684 * @param daemon the daemon to initialize
2547 * @param servaddr where to store the server's listen address 2685 * @param servaddr where to store the server's listen address
2548 * @param ap the options 2686 * @param ap the options
@@ -2556,7 +2694,7 @@ parse_options_va (struct MHD_Daemon *daemon,
2556 2694
2557/** 2695/**
2558 * Parse a list of options given as varargs. 2696 * Parse a list of options given as varargs.
2559 * 2697 *
2560 * @param daemon the daemon to initialize 2698 * @param daemon the daemon to initialize
2561 * @param servaddr where to store the server's listen address 2699 * @param servaddr where to store the server's listen address
2562 * @param ... the options 2700 * @param ... the options
@@ -2579,7 +2717,7 @@ parse_options (struct MHD_Daemon *daemon,
2579 2717
2580/** 2718/**
2581 * Parse a list of options given as varargs. 2719 * Parse a list of options given as varargs.
2582 * 2720 *
2583 * @param daemon the daemon to initialize 2721 * @param daemon the daemon to initialize
2584 * @param servaddr where to store the server's listen address 2722 * @param servaddr where to store the server's listen address
2585 * @param ap the options 2723 * @param ap the options
@@ -2597,7 +2735,7 @@ parse_options_va (struct MHD_Daemon *daemon,
2597 int ret; 2735 int ret;
2598 const char *pstr; 2736 const char *pstr;
2599#endif 2737#endif
2600 2738
2601 while (MHD_OPTION_END != (opt = (enum MHD_OPTION) va_arg (ap, int))) 2739 while (MHD_OPTION_END != (opt = (enum MHD_OPTION) va_arg (ap, int)))
2602 { 2740 {
2603 switch (opt) 2741 switch (opt)
@@ -2650,7 +2788,7 @@ parse_options_va (struct MHD_Daemon *daemon,
2650 else 2788 else
2651 MHD_DLOG (daemon, 2789 MHD_DLOG (daemon,
2652 "MHD HTTPS option %d passed to MHD but MHD_USE_SSL not set\n", 2790 "MHD HTTPS option %d passed to MHD but MHD_USE_SSL not set\n",
2653 opt); 2791 opt);
2654#endif 2792#endif
2655 break; 2793 break;
2656 case MHD_OPTION_HTTPS_MEM_CERT: 2794 case MHD_OPTION_HTTPS_MEM_CERT:
@@ -2660,7 +2798,7 @@ parse_options_va (struct MHD_Daemon *daemon,
2660 else 2798 else
2661 MHD_DLOG (daemon, 2799 MHD_DLOG (daemon,
2662 "MHD HTTPS option %d passed to MHD but MHD_USE_SSL not set\n", 2800 "MHD HTTPS option %d passed to MHD but MHD_USE_SSL not set\n",
2663 opt); 2801 opt);
2664#endif 2802#endif
2665 break; 2803 break;
2666 case MHD_OPTION_HTTPS_MEM_TRUST: 2804 case MHD_OPTION_HTTPS_MEM_TRUST:
@@ -2690,7 +2828,7 @@ parse_options_va (struct MHD_Daemon *daemon,
2690 "Setting priorities to `%s' failed: %s\n", 2828 "Setting priorities to `%s' failed: %s\n",
2691 pstr, 2829 pstr,
2692 gnutls_strerror (ret)); 2830 gnutls_strerror (ret));
2693#endif 2831#endif
2694 daemon->priority_cache = NULL; 2832 daemon->priority_cache = NULL;
2695 return MHD_NO; 2833 return MHD_NO;
2696 } 2834 }
@@ -2707,7 +2845,7 @@ parse_options_va (struct MHD_Daemon *daemon,
2707 break; 2845 break;
2708#endif 2846#endif
2709 case MHD_OPTION_LISTEN_SOCKET: 2847 case MHD_OPTION_LISTEN_SOCKET:
2710 daemon->socket_fd = va_arg (ap, int); 2848 daemon->socket_fd = va_arg (ap, int);
2711 break; 2849 break;
2712 case MHD_OPTION_EXTERNAL_LOGGER: 2850 case MHD_OPTION_EXTERNAL_LOGGER:
2713#if HAVE_MESSAGES 2851#if HAVE_MESSAGES
@@ -2829,7 +2967,7 @@ parse_options_va (struct MHD_Daemon *daemon,
2829#endif 2967#endif
2830 return MHD_NO; 2968 return MHD_NO;
2831 } 2969 }
2832 } 2970 }
2833 return MHD_YES; 2971 return MHD_YES;
2834} 2972}
2835 2973
@@ -2848,7 +2986,7 @@ create_socket (struct MHD_Daemon *daemon,
2848{ 2986{
2849 int ctype = type | SOCK_CLOEXEC; 2987 int ctype = type | SOCK_CLOEXEC;
2850 int fd; 2988 int fd;
2851 2989
2852 /* use SOCK_STREAM rather than ai_socktype: some getaddrinfo 2990 /* use SOCK_STREAM rather than ai_socktype: some getaddrinfo
2853 * implementations do not set ai_socktype, e.g. RHL6.2. */ 2991 * implementations do not set ai_socktype, e.g. RHL6.2. */
2854 fd = SOCKET (domain, ctype, protocol); 2992 fd = SOCKET (domain, ctype, protocol);
@@ -2883,19 +3021,19 @@ setup_epoll_to_listen (struct MHD_Daemon *daemon)
2883 { 3021 {
2884#if HAVE_MESSAGES 3022#if HAVE_MESSAGES
2885 if (0 != (daemon->options & MHD_USE_DEBUG)) 3023 if (0 != (daemon->options & MHD_USE_DEBUG))
2886 MHD_DLOG (daemon, 3024 MHD_DLOG (daemon,
2887 "Call to epoll_create1 failed: %s\n", 3025 "Call to epoll_create1 failed: %s\n",
2888 STRERROR (errno)); 3026 STRERROR (errno));
2889#endif 3027#endif
2890 return MHD_NO; 3028 return MHD_NO;
2891 } 3029 }
2892 if (0 == EPOLL_CLOEXEC) 3030 if (0 == EPOLL_CLOEXEC)
2893 make_nonblocking_noninheritable (daemon, 3031 make_nonblocking_noninheritable (daemon,
2894 daemon->epoll_fd); 3032 daemon->epoll_fd);
2895 if (-1 == daemon->socket_fd) 3033 if (-1 == daemon->socket_fd)
2896 return MHD_YES; /* non-listening daemon */ 3034 return MHD_YES; /* non-listening daemon */
2897 event.events = EPOLLIN; 3035 event.events = EPOLLIN;
2898 event.data.ptr = daemon; 3036 event.data.ptr = daemon;
2899 if (0 != epoll_ctl (daemon->epoll_fd, 3037 if (0 != epoll_ctl (daemon->epoll_fd,
2900 EPOLL_CTL_ADD, 3038 EPOLL_CTL_ADD,
2901 daemon->socket_fd, 3039 daemon->socket_fd,
@@ -2903,8 +3041,8 @@ setup_epoll_to_listen (struct MHD_Daemon *daemon)
2903 { 3041 {
2904#if HAVE_MESSAGES 3042#if HAVE_MESSAGES
2905 if (0 != (daemon->options & MHD_USE_DEBUG)) 3043 if (0 != (daemon->options & MHD_USE_DEBUG))
2906 MHD_DLOG (daemon, 3044 MHD_DLOG (daemon,
2907 "Call to epoll_ctl failed: %s\n", 3045 "Call to epoll_ctl failed: %s\n",
2908 STRERROR (errno)); 3046 STRERROR (errno));
2909#endif 3047#endif
2910 return MHD_NO; 3048 return MHD_NO;
@@ -2955,15 +3093,15 @@ MHD_start_daemon_va (unsigned int flags,
2955 3093
2956#ifndef HAVE_INET6 3094#ifndef HAVE_INET6
2957 if (0 != (flags & MHD_USE_IPv6)) 3095 if (0 != (flags & MHD_USE_IPv6))
2958 return NULL; 3096 return NULL;
2959#endif 3097#endif
2960#ifndef HAVE_POLL_H 3098#ifndef HAVE_POLL_H
2961 if (0 != (flags & MHD_USE_POLL)) 3099 if (0 != (flags & MHD_USE_POLL))
2962 return NULL; 3100 return NULL;
2963#endif 3101#endif
2964#if ! HTTPS_SUPPORT 3102#if ! HTTPS_SUPPORT
2965 if (0 != (flags & MHD_USE_SSL)) 3103 if (0 != (flags & MHD_USE_SSL))
2966 return NULL; 3104 return NULL;
2967#endif 3105#endif
2968 if (NULL == dh) 3106 if (NULL == dh)
2969 return NULL; 3107 return NULL;
@@ -3021,7 +3159,7 @@ MHD_start_daemon_va (unsigned int flags,
3021 ) 3159 )
3022 { 3160 {
3023#if HAVE_MESSAGES 3161#if HAVE_MESSAGES
3024 MHD_DLOG (daemon, 3162 MHD_DLOG (daemon,
3025 "Failed to create control pipe: %s\n", 3163 "Failed to create control pipe: %s\n",
3026 STRERROR (errno)); 3164 STRERROR (errno));
3027#endif 3165#endif
@@ -3034,7 +3172,7 @@ MHD_start_daemon_va (unsigned int flags,
3034 (daemon->wpipe[0] >= FD_SETSIZE) ) 3172 (daemon->wpipe[0] >= FD_SETSIZE) )
3035 { 3173 {
3036#if HAVE_MESSAGES 3174#if HAVE_MESSAGES
3037 MHD_DLOG (daemon, 3175 MHD_DLOG (daemon,
3038 "file descriptor for control pipe exceeds maximum value\n"); 3176 "file descriptor for control pipe exceeds maximum value\n");
3039#endif 3177#endif
3040 if (0 != CLOSE (daemon->wpipe[0])) 3178 if (0 != CLOSE (daemon->wpipe[0]))
@@ -3069,9 +3207,9 @@ MHD_start_daemon_va (unsigned int flags,
3069 return NULL; 3207 return NULL;
3070 } 3208 }
3071#ifdef DAUTH_SUPPORT 3209#ifdef DAUTH_SUPPORT
3072 if (daemon->nonce_nc_size > 0) 3210 if (daemon->nonce_nc_size > 0)
3073 { 3211 {
3074 if ( ( (size_t) (daemon->nonce_nc_size * sizeof (struct MHD_NonceNc))) / 3212 if ( ( (size_t) (daemon->nonce_nc_size * sizeof (struct MHD_NonceNc))) /
3075 sizeof(struct MHD_NonceNc) != daemon->nonce_nc_size) 3213 sizeof(struct MHD_NonceNc) != daemon->nonce_nc_size)
3076 { 3214 {
3077#if HAVE_MESSAGES 3215#if HAVE_MESSAGES
@@ -3083,7 +3221,7 @@ MHD_start_daemon_va (unsigned int flags,
3083 gnutls_priority_deinit (daemon->priority_cache); 3221 gnutls_priority_deinit (daemon->priority_cache);
3084#endif 3222#endif
3085 free (daemon); 3223 free (daemon);
3086 return NULL; 3224 return NULL;
3087 } 3225 }
3088 daemon->nnc = malloc (daemon->nonce_nc_size * sizeof (struct MHD_NonceNc)); 3226 daemon->nnc = malloc (daemon->nonce_nc_size * sizeof (struct MHD_NonceNc));
3089 if (NULL == daemon->nnc) 3227 if (NULL == daemon->nnc)
@@ -3101,7 +3239,7 @@ MHD_start_daemon_va (unsigned int flags,
3101 return NULL; 3239 return NULL;
3102 } 3240 }
3103 } 3241 }
3104 3242
3105 if (0 != pthread_mutex_init (&daemon->nnc_lock, NULL)) 3243 if (0 != pthread_mutex_init (&daemon->nnc_lock, NULL))
3106 { 3244 {
3107#if HAVE_MESSAGES 3245#if HAVE_MESSAGES
@@ -3119,7 +3257,7 @@ MHD_start_daemon_va (unsigned int flags,
3119#endif 3257#endif
3120 3258
3121 /* Thread pooling currently works only with internal select thread model */ 3259 /* Thread pooling currently works only with internal select thread model */
3122 if ( (0 == (flags & MHD_USE_SELECT_INTERNALLY)) && 3260 if ( (0 == (flags & MHD_USE_SELECT_INTERNALLY)) &&
3123 (daemon->worker_pool_size > 0) ) 3261 (daemon->worker_pool_size > 0) )
3124 { 3262 {
3125#if HAVE_MESSAGES 3263#if HAVE_MESSAGES
@@ -3179,8 +3317,8 @@ MHD_start_daemon_va (unsigned int flags,
3179 { 3317 {
3180#if HAVE_MESSAGES 3318#if HAVE_MESSAGES
3181 if (0 != (flags & MHD_USE_DEBUG)) 3319 if (0 != (flags & MHD_USE_DEBUG))
3182 MHD_DLOG (daemon, 3320 MHD_DLOG (daemon,
3183 "Call to socket failed: %s\n", 3321 "Call to socket failed: %s\n",
3184 STRERROR (errno)); 3322 STRERROR (errno));
3185#endif 3323#endif
3186 goto free_and_fail; 3324 goto free_and_fail;
@@ -3188,16 +3326,16 @@ MHD_start_daemon_va (unsigned int flags,
3188 if ( (0 > SETSOCKOPT (socket_fd, 3326 if ( (0 > SETSOCKOPT (socket_fd,
3189 SOL_SOCKET, 3327 SOL_SOCKET,
3190 SO_REUSEADDR, 3328 SO_REUSEADDR,
3191 &on, sizeof (on))) && 3329 &on, sizeof (on))) &&
3192 (0 != (flags & MHD_USE_DEBUG)) ) 3330 (0 != (flags & MHD_USE_DEBUG)) )
3193 { 3331 {
3194#if HAVE_MESSAGES 3332#if HAVE_MESSAGES
3195 MHD_DLOG (daemon, 3333 MHD_DLOG (daemon,
3196 "setsockopt failed: %s\n", 3334 "setsockopt failed: %s\n",
3197 STRERROR (errno)); 3335 STRERROR (errno));
3198#endif 3336#endif
3199 } 3337 }
3200 3338
3201 /* check for user supplied sockaddr */ 3339 /* check for user supplied sockaddr */
3202#if HAVE_INET6 3340#if HAVE_INET6
3203 if (0 != (flags & MHD_USE_IPv6)) 3341 if (0 != (flags & MHD_USE_IPv6))
@@ -3237,8 +3375,8 @@ MHD_start_daemon_va (unsigned int flags,
3237 { 3375 {
3238#ifdef IPPROTO_IPV6 3376#ifdef IPPROTO_IPV6
3239#ifdef IPV6_V6ONLY 3377#ifdef IPV6_V6ONLY
3240 /* Note: "IPV6_V6ONLY" is declared by Windows Vista ff., see "IPPROTO_IPV6 Socket Options" 3378 /* Note: "IPV6_V6ONLY" is declared by Windows Vista ff., see "IPPROTO_IPV6 Socket Options"
3241 (http://msdn.microsoft.com/en-us/library/ms738574%28v=VS.85%29.aspx); 3379 (http://msdn.microsoft.com/en-us/library/ms738574%28v=VS.85%29.aspx);
3242 and may also be missing on older POSIX systems; good luck if you have any of those, 3380 and may also be missing on older POSIX systems; good luck if you have any of those,
3243 your IPv6 socket may then also bind against IPv4 anyway... */ 3381 your IPv6 socket may then also bind against IPv4 anyway... */
3244#ifndef WINDOWS 3382#ifndef WINDOWS
@@ -3246,14 +3384,14 @@ MHD_start_daemon_va (unsigned int flags,
3246#else 3384#else
3247 const char on = 1; 3385 const char on = 1;
3248#endif 3386#endif
3249 if ( (0 > SETSOCKOPT (socket_fd, 3387 if ( (0 > SETSOCKOPT (socket_fd,
3250 IPPROTO_IPV6, IPV6_V6ONLY, 3388 IPPROTO_IPV6, IPV6_V6ONLY,
3251 &on, sizeof (on))) && 3389 &on, sizeof (on))) &&
3252 (0 != (flags & MHD_USE_DEBUG)) ) 3390 (0 != (flags & MHD_USE_DEBUG)) )
3253 { 3391 {
3254#if HAVE_MESSAGES 3392#if HAVE_MESSAGES
3255 MHD_DLOG (daemon, 3393 MHD_DLOG (daemon,
3256 "setsockopt failed: %s\n", 3394 "setsockopt failed: %s\n",
3257 STRERROR (errno)); 3395 STRERROR (errno));
3258#endif 3396#endif
3259 } 3397 }
@@ -3265,8 +3403,8 @@ MHD_start_daemon_va (unsigned int flags,
3265#if HAVE_MESSAGES 3403#if HAVE_MESSAGES
3266 if (0 != (flags & MHD_USE_DEBUG)) 3404 if (0 != (flags & MHD_USE_DEBUG))
3267 MHD_DLOG (daemon, 3405 MHD_DLOG (daemon,
3268 "Failed to bind to port %u: %s\n", 3406 "Failed to bind to port %u: %s\n",
3269 (unsigned int) port, 3407 (unsigned int) port,
3270 STRERROR (errno)); 3408 STRERROR (errno));
3271#endif 3409#endif
3272 if (0 != CLOSE (socket_fd)) 3410 if (0 != CLOSE (socket_fd))
@@ -3281,12 +3419,12 @@ MHD_start_daemon_va (unsigned int flags,
3281 { 3419 {
3282#if HAVE_MESSAGES 3420#if HAVE_MESSAGES
3283 MHD_DLOG (daemon, 3421 MHD_DLOG (daemon,
3284 "Failed to make listen socket non-blocking: %s\n", 3422 "Failed to make listen socket non-blocking: %s\n",
3285 STRERROR (errno)); 3423 STRERROR (errno));
3286#endif 3424#endif
3287 if (0 != CLOSE (socket_fd)) 3425 if (0 != CLOSE (socket_fd))
3288 MHD_PANIC ("close failed\n"); 3426 MHD_PANIC ("close failed\n");
3289 goto free_and_fail; 3427 goto free_and_fail;
3290 } 3428 }
3291 } 3429 }
3292#endif 3430#endif
@@ -3295,13 +3433,13 @@ MHD_start_daemon_va (unsigned int flags,
3295#if HAVE_MESSAGES 3433#if HAVE_MESSAGES
3296 if (0 != (flags & MHD_USE_DEBUG)) 3434 if (0 != (flags & MHD_USE_DEBUG))
3297 MHD_DLOG (daemon, 3435 MHD_DLOG (daemon,
3298 "Failed to listen for connections: %s\n", 3436 "Failed to listen for connections: %s\n",
3299 STRERROR (errno)); 3437 STRERROR (errno));
3300#endif 3438#endif
3301 if (0 != CLOSE (socket_fd)) 3439 if (0 != CLOSE (socket_fd))
3302 MHD_PANIC ("close failed\n"); 3440 MHD_PANIC ("close failed\n");
3303 goto free_and_fail; 3441 goto free_and_fail;
3304 } 3442 }
3305 } 3443 }
3306 else 3444 else
3307 { 3445 {
@@ -3353,7 +3491,7 @@ MHD_start_daemon_va (unsigned int flags,
3353 if ((0 != (flags & MHD_USE_SSL)) && (0 != MHD_TLS_init (daemon))) 3491 if ((0 != (flags & MHD_USE_SSL)) && (0 != MHD_TLS_init (daemon)))
3354 { 3492 {
3355#if HAVE_MESSAGES 3493#if HAVE_MESSAGES
3356 MHD_DLOG (daemon, 3494 MHD_DLOG (daemon,
3357 "Failed to initialize TLS support\n"); 3495 "Failed to initialize TLS support\n");
3358#endif 3496#endif
3359 if ( (-1 != socket_fd) && 3497 if ( (-1 != socket_fd) &&
@@ -3366,14 +3504,14 @@ MHD_start_daemon_va (unsigned int flags,
3366#endif 3504#endif
3367 if ( ( (0 != (flags & MHD_USE_THREAD_PER_CONNECTION)) || 3505 if ( ( (0 != (flags & MHD_USE_THREAD_PER_CONNECTION)) ||
3368 ( (0 != (flags & MHD_USE_SELECT_INTERNALLY)) && 3506 ( (0 != (flags & MHD_USE_SELECT_INTERNALLY)) &&
3369 (0 == daemon->worker_pool_size)) ) && 3507 (0 == daemon->worker_pool_size)) ) &&
3370 (0 == (daemon->options & MHD_USE_NO_LISTEN_SOCKET)) && 3508 (0 == (daemon->options & MHD_USE_NO_LISTEN_SOCKET)) &&
3371 (0 != (res_thread_create = 3509 (0 != (res_thread_create =
3372 create_thread (&daemon->pid, daemon, &MHD_select_thread, daemon)))) 3510 create_thread (&daemon->pid, daemon, &MHD_select_thread, daemon))))
3373 { 3511 {
3374#if HAVE_MESSAGES 3512#if HAVE_MESSAGES
3375 MHD_DLOG (daemon, 3513 MHD_DLOG (daemon,
3376 "Failed to create listen thread: %s\n", 3514 "Failed to create listen thread: %s\n",
3377 STRERROR (res_thread_create)); 3515 STRERROR (res_thread_create));
3378#endif 3516#endif
3379 pthread_mutex_destroy (&daemon->cleanup_connection_mutex); 3517 pthread_mutex_destroy (&daemon->cleanup_connection_mutex);
@@ -3465,12 +3603,12 @@ MHD_start_daemon_va (unsigned int flags,
3465 } 3603 }
3466 3604
3467 /* Spawn the worker thread */ 3605 /* Spawn the worker thread */
3468 if (0 != (res_thread_create = 3606 if (0 != (res_thread_create =
3469 create_thread (&d->pid, daemon, &MHD_select_thread, d))) 3607 create_thread (&d->pid, daemon, &MHD_select_thread, d)))
3470 { 3608 {
3471#if HAVE_MESSAGES 3609#if HAVE_MESSAGES
3472 MHD_DLOG (daemon, 3610 MHD_DLOG (daemon,
3473 "Failed to create pool thread: %s\n", 3611 "Failed to create pool thread: %s\n",
3474 STRERROR (res_thread_create)); 3612 STRERROR (res_thread_create));
3475#endif 3613#endif
3476 /* Free memory for this worker; cleanup below handles 3614 /* Free memory for this worker; cleanup below handles
@@ -3508,9 +3646,9 @@ thread_failed:
3508 return NULL; 3646 return NULL;
3509 3647
3510 free_and_fail: 3648 free_and_fail:
3511 /* clean up basic memory state in 'daemon' and return NULL to 3649 /* clean up basic memory state in 'daemon' and return NULL to
3512 indicate failure */ 3650 indicate failure */
3513#if EPOLL_SUPPORT 3651#if EPOLL_SUPPORT
3514 if (-1 != daemon->epoll_fd) 3652 if (-1 != daemon->epoll_fd)
3515 close (daemon->epoll_fd); 3653 close (daemon->epoll_fd);
3516#endif 3654#endif
@@ -3571,26 +3709,26 @@ close_all_connections (struct MHD_Daemon *daemon)
3571 struct MHD_Connection *pos; 3709 struct MHD_Connection *pos;
3572 void *unused; 3710 void *unused;
3573 int rc; 3711 int rc;
3574 3712
3575 /* first, make sure all threads are aware of shutdown; need to 3713 /* first, make sure all threads are aware of shutdown; need to
3576 traverse DLLs in peace... */ 3714 traverse DLLs in peace... */
3577 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) && 3715 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) &&
3578 (0 != pthread_mutex_lock (&daemon->cleanup_connection_mutex)) ) 3716 (0 != pthread_mutex_lock (&daemon->cleanup_connection_mutex)) )
3579 MHD_PANIC ("Failed to acquire cleanup mutex\n"); 3717 MHD_PANIC ("Failed to acquire cleanup mutex\n");
3580 for (pos = daemon->connections_head; NULL != pos; pos = pos->nextX) 3718 for (pos = daemon->connections_head; NULL != pos; pos = pos->nextX)
3581 SHUTDOWN (pos->socket_fd, 3719 SHUTDOWN (pos->socket_fd,
3582 (pos->read_closed == MHD_YES) ? SHUT_WR : SHUT_RDWR); 3720 (pos->read_closed == MHD_YES) ? SHUT_WR : SHUT_RDWR);
3583 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) && 3721 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) &&
3584 (0 != pthread_mutex_unlock (&daemon->cleanup_connection_mutex)) ) 3722 (0 != pthread_mutex_unlock (&daemon->cleanup_connection_mutex)) )
3585 MHD_PANIC ("Failed to release cleanup mutex\n"); 3723 MHD_PANIC ("Failed to release cleanup mutex\n");
3586 3724
3587 /* now, collect threads from thread pool */ 3725 /* now, collect threads from thread pool */
3588 if (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) 3726 if (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION))
3589 { 3727 {
3590 while (NULL != (pos = daemon->connections_head)) 3728 while (NULL != (pos = daemon->connections_head))
3591 { 3729 {
3592 if (0 != (rc = pthread_join (pos->pid, &unused))) 3730 if (0 != (rc = pthread_join (pos->pid, &unused)))
3593 MHD_PANIC ("Failed to join a thread\n"); 3731 MHD_PANIC ("Failed to join a thread\n");
3594 pos->thread_joined = MHD_YES; 3732 pos->thread_joined = MHD_YES;
3595 } 3733 }
3596 } 3734 }
@@ -3612,19 +3750,19 @@ static void
3612epoll_shutdown (struct MHD_Daemon *daemon) 3750epoll_shutdown (struct MHD_Daemon *daemon)
3613{ 3751{
3614 struct epoll_event event; 3752 struct epoll_event event;
3615 3753
3616 if (-1 == daemon->wpipe[1]) 3754 if (-1 == daemon->wpipe[1])
3617 { 3755 {
3618 /* wpipe was required in this mode, how could this happen? */ 3756 /* wpipe was required in this mode, how could this happen? */
3619 MHD_PANIC ("Internal error\n"); 3757 MHD_PANIC ("Internal error\n");
3620 } 3758 }
3621 event.events = EPOLLOUT; 3759 event.events = EPOLLOUT;
3622 event.data.ptr = NULL; 3760 event.data.ptr = NULL;
3623 if (0 != epoll_ctl (daemon->epoll_fd, 3761 if (0 != epoll_ctl (daemon->epoll_fd,
3624 EPOLL_CTL_ADD, 3762 EPOLL_CTL_ADD,
3625 daemon->wpipe[1], 3763 daemon->wpipe[1],
3626 &event)) 3764 &event))
3627 MHD_PANIC ("Failed to add wpipe to epoll set to signal termination\n"); 3765 MHD_PANIC ("Failed to add wpipe to epoll set to signal termination\n");
3628} 3766}
3629#endif 3767#endif
3630 3768
@@ -3681,7 +3819,7 @@ MHD_stop_daemon (struct MHD_Daemon *daemon)
3681 if ( (0 != (daemon->options & MHD_USE_EPOLL_LINUX_ONLY)) && 3819 if ( (0 != (daemon->options & MHD_USE_EPOLL_LINUX_ONLY)) &&
3682 (-1 != daemon->epoll_fd) && 3820 (-1 != daemon->epoll_fd) &&
3683 (-1 == fd) ) 3821 (-1 == fd) )
3684 epoll_shutdown (daemon); 3822 epoll_shutdown (daemon);
3685#endif 3823#endif
3686 3824
3687#if DEBUG_CLOSE 3825#if DEBUG_CLOSE
@@ -3697,11 +3835,11 @@ MHD_stop_daemon (struct MHD_Daemon *daemon)
3697 /* MHD_USE_NO_LISTEN_SOCKET disables thread pools, hence we need to check */ 3835 /* MHD_USE_NO_LISTEN_SOCKET disables thread pools, hence we need to check */
3698 for (i = 0; i < daemon->worker_pool_size; ++i) 3836 for (i = 0; i < daemon->worker_pool_size; ++i)
3699 { 3837 {
3700 if (0 != (rc = pthread_join (daemon->worker_pool[i].pid, &unused))) 3838 if (0 != (rc = pthread_join (daemon->worker_pool[i].pid, &unused)))
3701 MHD_PANIC ("Failed to join a thread\n"); 3839 MHD_PANIC ("Failed to join a thread\n");
3702 close_all_connections (&daemon->worker_pool[i]); 3840 close_all_connections (&daemon->worker_pool[i]);
3703 pthread_mutex_destroy (&daemon->worker_pool[i].cleanup_connection_mutex); 3841 pthread_mutex_destroy (&daemon->worker_pool[i].cleanup_connection_mutex);
3704#if EPOLL_SUPPORT 3842#if EPOLL_SUPPORT
3705 if ( (-1 != daemon->worker_pool[i].epoll_fd) && 3843 if ( (-1 != daemon->worker_pool[i].epoll_fd) &&
3706 (0 != CLOSE (daemon->worker_pool[i].epoll_fd)) ) 3844 (0 != CLOSE (daemon->worker_pool[i].epoll_fd)) )
3707 MHD_PANIC ("close failed\n"); 3845 MHD_PANIC ("close failed\n");
@@ -3739,7 +3877,7 @@ MHD_stop_daemon (struct MHD_Daemon *daemon)
3739#if EPOLL_SUPPORT 3877#if EPOLL_SUPPORT
3740 if ( (0 != (daemon->options & MHD_USE_EPOLL_LINUX_ONLY)) && 3878 if ( (0 != (daemon->options & MHD_USE_EPOLL_LINUX_ONLY)) &&
3741 (-1 != daemon->epoll_fd) && 3879 (-1 != daemon->epoll_fd) &&
3742 (0 != CLOSE (daemon->epoll_fd)) ) 3880 (0 != CLOSE (daemon->epoll_fd)) )
3743 MHD_PANIC ("close failed\n"); 3881 MHD_PANIC ("close failed\n");
3744#endif 3882#endif
3745 3883
@@ -3774,7 +3912,7 @@ MHD_stop_daemon (struct MHD_Daemon *daemon)
3774 */ 3912 */
3775const union MHD_DaemonInfo * 3913const union MHD_DaemonInfo *
3776MHD_get_daemon_info (struct MHD_Daemon *daemon, 3914MHD_get_daemon_info (struct MHD_Daemon *daemon,
3777 enum MHD_DaemonInfoType info_type, 3915 enum MHD_DaemonInfoType info_type,
3778 ...) 3916 ...)
3779{ 3917{
3780 switch (info_type) 3918 switch (info_type)
@@ -3811,7 +3949,7 @@ MHD_get_daemon_info (struct MHD_Daemon *daemon,
3811 * @param cls passed to @a cb 3949 * @param cls passed to @a cb
3812 * @ingroup logging 3950 * @ingroup logging
3813 */ 3951 */
3814void 3952void
3815MHD_set_panic_func (MHD_PanicCallback cb, void *cls) 3953MHD_set_panic_func (MHD_PanicCallback cb, void *cls)
3816{ 3954{
3817 mhd_panic = cb; 3955 mhd_panic = cb;
@@ -3850,7 +3988,7 @@ GCRY_THREAD_OPTION_PTHREAD_IMPL;
3850/** 3988/**
3851 * Initialize do setup work. 3989 * Initialize do setup work.
3852 */ 3990 */
3853void ATTRIBUTE_CONSTRUCTOR 3991void ATTRIBUTE_CONSTRUCTOR
3854MHD_init () 3992MHD_init ()
3855{ 3993{
3856 mhd_panic = &mhd_panic_std; 3994 mhd_panic = &mhd_panic_std;
@@ -3869,7 +4007,7 @@ MHD_init ()
3869} 4007}
3870 4008
3871 4009
3872void ATTRIBUTE_DESTRUCTOR 4010void ATTRIBUTE_DESTRUCTOR
3873MHD_fini () 4011MHD_fini ()
3874{ 4012{
3875#if HTTPS_SUPPORT 4013#if HTTPS_SUPPORT