Lines Matching refs:daemon

22  * @file microhttpd/daemon.c
162 * Trace up to and return master daemon. If the supplied daemon
163 * is a master, then return the daemon itself.
165 * @param daemon handle to a daemon
166 * @return master daemon handle
169 MHD_get_master (struct MHD_Daemon *daemon)
171 while (NULL != daemon->master)
172 daemon = daemon->master;
173 return daemon;
214 * @param daemon handle to daemon where lock is
217 MHD_ip_count_lock (struct MHD_Daemon *daemon)
219 if (MHD_YES != MHD_mutex_lock_(&daemon->per_ip_connection_mutex))
229 * @param daemon handle to daemon where lock is
232 MHD_ip_count_unlock (struct MHD_Daemon *daemon)
234 if (MHD_YES != MHD_mutex_unlock_(&daemon->per_ip_connection_mutex))
300 * @param daemon handle to daemon where connection counts are tracked
307 MHD_ip_limit_add (struct MHD_Daemon *daemon,
316 daemon = MHD_get_master (daemon);
318 if (0 == daemon->per_ip_connection_limit)
331 MHD_ip_count_lock (daemon);
335 &daemon->per_ip_connection_count,
339 MHD_DLOG (daemon,
342 MHD_ip_count_unlock (daemon);
353 result = (key->count < daemon->per_ip_connection_limit);
357 MHD_ip_count_unlock (daemon);
366 * @param daemon handle to daemon where connection counts are tracked
371 MHD_ip_limit_del (struct MHD_Daemon *daemon,
379 daemon = MHD_get_master (daemon);
381 if (0 == daemon->per_ip_connection_limit)
387 MHD_ip_count_lock (daemon);
391 &daemon->per_ip_connection_count,
408 &daemon->per_ip_connection_count,
413 MHD_ip_count_unlock (daemon);
519 connection->daemon->num_tls_read_ready--;
542 connection->daemon->num_tls_read_ready++;
585 * Initialize security aspects of the HTTPS daemon
587 * @param daemon handle to daemon to initialize
591 MHD_TLS_init (struct MHD_Daemon *daemon)
594 daemon->tls_context = SSL_CTX_new (TLSv1_2_server_method());
595 if (NULL == daemon->tls_context)
597 if (NULL != daemon->https_mem_trust)
600 BIO* mem_bio = BIO_new_mem_buf ((void*)daemon->https_mem_trust, -1);
605 ret = SSL_CTX_add_client_CA (daemon->tls_context, x509);
610 MHD_DLOG (daemon,
617 if (NULL != daemon->https_mem_dhparams)
620 BIO* mem_bio = BIO_new_mem_buf ((void*)daemon->https_mem_dhparams, -1);
625 ret = SSL_CTX_set_tmp_dh (daemon->tls_context, dh);
630 MHD_DLOG (daemon,
638 if ( (NULL != daemon->https_mem_cert) &&
639 (NULL != daemon->https_mem_key) )
642 BIO* mem_bio = BIO_new_mem_buf ((void*)daemon->https_mem_key, -1);
644 (void*)daemon->https_key_password);
648 ret = SSL_CTX_use_PrivateKey (daemon->tls_context, key);
653 MHD_DLOG (daemon,
659 mem_bio = BIO_new_mem_buf ((void*)daemon->https_mem_cert, -1);
664 ret = SSL_CTX_use_certificate (daemon->tls_context, x509);
669 MHD_DLOG (daemon,
674 if (1 != SSL_CTX_check_private_key (daemon->tls_context))
677 MHD_DLOG (daemon,
686 MHD_DLOG (daemon,
691 if (NULL != daemon->https_mem_cipher)
693 ret = SSL_CTX_set_cipher_list (daemon->tls_context,
694 daemon->https_mem_cipher);
698 MHD_DLOG (daemon,
706 ret = SSL_CTX_set_cipher_list (daemon->tls_context,
711 MHD_DLOG (daemon,
721 MHD_TLS_deinit (struct MHD_Daemon *daemon)
723 SSL_CTX_free (daemon->tls_context);
769 * Obtain the `select()` sets for this daemon.
771 * daemon FDs in fd_sets, call FD_ZERO for each fd_set
775 * @param daemon daemon to get sets from
782 * daemon was not started with the right
788 MHD_get_fdset (struct MHD_Daemon *daemon,
794 return MHD_get_fdset2(daemon, read_fd_set,
800 * Obtain the `select()` sets for this daemon.
802 * daemon FDs in fd_sets, call FD_ZERO for each fd_set
807 * @param daemon daemon to get sets from
815 * daemon was not started with the right
821 MHD_get_fdset2 (struct MHD_Daemon *daemon,
830 if ( (NULL == daemon)
833 || (MHD_YES == daemon->shutdown)
834 || (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION))
835 || (0 != (daemon->options & MHD_USE_POLL)))
838 if (0 != (daemon->options & MHD_USE_EPOLL_LINUX_ONLY))
843 return add_to_fd_set (daemon->epoll_fd, read_fd_set, max_fd, fd_setsize);
846 if (MHD_INVALID_SOCKET != daemon->socket_fd &&
847 MHD_YES != add_to_fd_set (daemon->socket_fd, read_fd_set, max_fd, fd_setsize))
850 for (pos = daemon->connections_head; NULL != pos; pos = pos->next)
878 MHD_DLOG (daemon,
907 MHD_pipe spipe = con->daemon->wpipe[0];
920 timeout = con->daemon->connection_timeout;
921 while ( (MHD_YES != con->daemon->shutdown) &&
944 if (0 == (con->daemon->options & MHD_USE_POLL))
991 MHD_DLOG (con->daemon,
1003 MHD_DLOG (con->daemon,
1076 MHD_DLOG (con->daemon,
1107 MHD_DLOG (con->daemon,
1123 if (NULL != con->daemon->notify_connection)
1124 con->daemon->notify_connection (con->daemon->notify_connection_cls,
1192 if (0 != (connection->daemon->options & MHD_USE_SSL))
1260 * @param daemon daemon with options
1267 const struct MHD_Daemon *daemon,
1276 if (0 != daemon->thread_stack_size)
1280 if (0 != (ret = pthread_attr_setstacksize (&attr, daemon->thread_stack_size)))
1296 if (0 != daemon->thread_stack_size)
1301 MHD_DLOG (daemon,
1308 *thread = (HANDLE)_beginthreadex(NULL, (unsigned)daemon->thread_stack_size, start_routine,
1334 * @param daemon daemon that manages the connection
1341 * @return #MHD_YES on success, #MHD_NO if this daemon could
1347 internal_add_connection (struct MHD_Daemon *daemon,
1362 if (NULL != daemon->worker_pool)
1367 for (i=0;i<daemon->worker_pool_size;i++)
1369 worker = &daemon->worker_pool[(i + client_socket) % daemon->worker_pool_size];
1387 (0 == (daemon->options & (MHD_USE_POLL | MHD_USE_EPOLL_LINUX_ONLY))) )
1390 MHD_DLOG (daemon,
1407 MHD_DLOG (daemon,
1412 if ( (daemon->connections == daemon->connection_limit) ||
1413 (MHD_NO == MHD_ip_limit_add (daemon, addr, addrlen)) )
1417 MHD_DLOG (daemon,
1429 if ( (NULL != daemon->apc) &&
1430 (MHD_NO == daemon->apc (daemon->apc_cls,
1435 MHD_DLOG (daemon,
1441 MHD_ip_limit_del (daemon, addr, addrlen);
1462 MHD_DLOG (daemon,
1468 MHD_ip_limit_del (daemon, addr, addrlen);
1475 connection->pool = MHD_pool_create (daemon->pool_size);
1479 MHD_DLOG (daemon,
1485 MHD_ip_limit_del (daemon, addr, addrlen);
1493 connection->connection_timeout = daemon->connection_timeout;
1498 MHD_DLOG (daemon,
1504 MHD_ip_limit_del (daemon, addr, addrlen);
1513 connection->daemon = daemon;
1521 if (0 == (connection->daemon->options & MHD_USE_EPOLL_TURBO))
1528 if (0 != (daemon->options & MHD_USE_SSL))
1538 MHD_DLOG (daemon,
1548 MHD_DLOG (daemon,
1558 if (0 != (daemon->options & MHD_USE_SSL))
1564 connection->tls_session = SSL_new (daemon->tls_context);
1576 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) &&
1577 (MHD_YES != MHD_mutex_lock_ (&daemon->cleanup_connection_mutex)) )
1579 XDLL_insert (daemon->normal_timeout_head,
1580 daemon->normal_timeout_tail,
1582 DLL_insert (daemon->connections_head,
1583 daemon->connections_tail,
1585 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) &&
1586 (MHD_YES != MHD_mutex_unlock_ (&daemon->cleanup_connection_mutex)) )
1589 if (NULL != daemon->notify_connection)
1590 daemon->notify_connection (daemon->notify_connection_cls,
1596 if (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION))
1599 daemon,
1606 MHD_DLOG (daemon,
1615 (MHD_INVALID_PIPE_ != daemon->wpipe[1]) &&
1616 (1 != MHD_pipe_write_ (daemon->wpipe[1], "n", 1)) )
1619 MHD_DLOG (daemon,
1624 if (0 != (daemon->options & MHD_USE_EPOLL_LINUX_ONLY))
1626 if (0 == (daemon->options & MHD_USE_EPOLL_TURBO))
1632 if (0 != epoll_ctl (daemon->epoll_fd,
1639 MHD_DLOG (daemon,
1651 EDLL_insert (daemon->eready_head,
1652 daemon->eready_tail,
1657 daemon->connections++;
1660 if (NULL != daemon->notify_connection)
1661 daemon->notify_connection (daemon->notify_connection_cls,
1667 MHD_ip_limit_del (daemon, addr, addrlen);
1668 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) &&
1669 (MHD_YES != MHD_mutex_lock_ (&daemon->cleanup_connection_mutex)) )
1671 DLL_remove (daemon->connections_head,
1672 daemon->connections_tail,
1674 XDLL_remove (daemon->normal_timeout_head,
1675 daemon->normal_timeout_tail,
1677 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) &&
1678 (MHD_YES != MHD_mutex_unlock_ (&daemon->cleanup_connection_mutex)) )
1701 * connections allowed (per daemon, as well as per IP, if such limits
1713 * resume all connections before stopping the daemon.
1720 struct MHD_Daemon *daemon;
1722 daemon = connection->daemon;
1723 if (MHD_USE_SUSPEND_RESUME != (daemon->options & MHD_USE_SUSPEND_RESUME))
1725 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) &&
1726 (MHD_YES != MHD_mutex_lock_ (&daemon->cleanup_connection_mutex)) )
1728 DLL_remove (daemon->connections_head,
1729 daemon->connections_tail,
1731 DLL_insert (daemon->suspended_connections_head,
1732 daemon->suspended_connections_tail,
1734 if (connection->connection_timeout == daemon->connection_timeout)
1735 XDLL_remove (daemon->normal_timeout_head,
1736 daemon->normal_timeout_tail,
1739 XDLL_remove (daemon->manual_timeout_head,
1740 daemon->manual_timeout_tail,
1743 if (0 != (daemon->options & MHD_USE_EPOLL_LINUX_ONLY))
1747 EDLL_remove (daemon->eready_head,
1748 daemon->eready_tail,
1754 if (0 != epoll_ctl (daemon->epoll_fd,
1765 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) &&
1766 (MHD_YES != MHD_mutex_unlock_ (&daemon->cleanup_connection_mutex)) )
1782 struct MHD_Daemon *daemon;
1784 daemon = connection->daemon;
1785 if (MHD_USE_SUSPEND_RESUME != (daemon->options & MHD_USE_SUSPEND_RESUME))
1787 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) &&
1788 (MHD_YES != MHD_mutex_lock_ (&daemon->cleanup_connection_mutex)) )
1791 daemon->resuming = MHD_YES;
1792 if ( (MHD_INVALID_PIPE_ != daemon->wpipe[1]) &&
1793 (1 != MHD_pipe_write_ (daemon->wpipe[1], "r", 1)) )
1796 MHD_DLOG (daemon,
1800 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) &&
1801 (MHD_YES != MHD_mutex_unlock_ (&daemon->cleanup_connection_mutex)) )
1810 * @param daemon daemon context
1814 resume_suspended_connections (struct MHD_Daemon *daemon)
1821 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) &&
1822 (MHD_YES != MHD_mutex_lock_ (&daemon->cleanup_connection_mutex)) )
1824 if (MHD_YES == daemon->resuming)
1825 next = daemon->suspended_connections_head;
1833 DLL_remove (daemon->suspended_connections_head,
1834 daemon->suspended_connections_tail,
1836 DLL_insert (daemon->connections_head,
1837 daemon->connections_tail,
1839 if (pos->connection_timeout == daemon->connection_timeout)
1840 XDLL_insert (daemon->normal_timeout_head,
1841 daemon->normal_timeout_tail,
1844 XDLL_insert (daemon->manual_timeout_head,
1845 daemon->manual_timeout_tail,
1848 if (0 != (daemon->options & MHD_USE_EPOLL_LINUX_ONLY))
1854 EDLL_insert (daemon->eready_head,
1855 daemon->eready_tail,
1864 daemon->resuming = MHD_NO;
1865 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) &&
1866 (MHD_YES != MHD_mutex_unlock_ (&daemon->cleanup_connection_mutex)) )
1875 * @param daemon daemon context
1879 make_nonblocking_noninheritable (struct MHD_Daemon *daemon,
1889 MHD_DLOG (daemon,
1899 MHD_DLOG (daemon,
1910 if (0 == (daemon->options & MHD_USE_SSL))
1919 MHD_DLOG (daemon,
1946 * @param daemon daemon that manages the connection
1951 * @return #MHD_YES on success, #MHD_NO if this daemon could
1958 MHD_add_connection (struct MHD_Daemon *daemon,
1963 make_nonblocking_noninheritable (daemon,
1965 return internal_add_connection (daemon,
1977 * @param daemon handle with the listen socket
1985 MHD_accept_connection (struct MHD_Daemon *daemon)
2000 if (MHD_INVALID_SOCKET == (fd = daemon->socket_fd))
2008 if (0 == (daemon->options & MHD_USE_SSL))
2022 (MHD_INVALID_SOCKET == daemon->socket_fd) )
2025 MHD_DLOG (daemon,
2038 make_nonblocking_noninheritable (daemon, s);
2042 MHD_DLOG (daemon,
2047 (void) internal_add_connection (daemon, s,
2059 * @param daemon daemon to clean up
2062 MHD_cleanup_connections (struct MHD_Daemon *daemon)
2066 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) &&
2067 (MHD_YES != MHD_mutex_lock_ (&daemon->cleanup_connection_mutex)) )
2069 while (NULL != (pos = daemon->cleanup_head))
2071 DLL_remove (daemon->cleanup_head,
2072 daemon->cleanup_tail,
2074 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) &&
2087 if (NULL != daemon->notify_connection)
2088 daemon->notify_connection (daemon->notify_connection_cls,
2092 MHD_ip_limit_del (daemon, pos->addr, pos->addr_len);
2096 EDLL_remove (daemon->eready_head,
2097 daemon->eready_tail,
2101 if ( (0 != (daemon->options & MHD_USE_EPOLL_LINUX_ONLY)) &&
2102 (MHD_INVALID_SOCKET != daemon->epoll_fd) &&
2111 if (0 != epoll_ctl (daemon->epoll_fd,
2135 daemon->connections--;
2137 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) &&
2138 (MHD_YES != MHD_mutex_unlock_ (&daemon->cleanup_connection_mutex)) )
2144 * Obtain timeout value for `select()` for this daemon (only needed if
2150 * @param daemon daemon to query for timeout
2158 MHD_get_timeout (struct MHD_Daemon *daemon,
2166 if (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION))
2169 MHD_DLOG (daemon,
2176 if (0 != daemon->num_tls_read_ready)
2187 for (pos = daemon->manual_timeout_head; NULL != pos; pos = pos->nextX)
2195 if ( (0 != (daemon->options & MHD_USE_SSL)) &&
2203 pos = daemon->normal_timeout_head;
2211 if ( (0 != (daemon->options & MHD_USE_SSL)) &&
2241 * @param daemon daemon to run select loop for
2249 MHD_run_from_select (struct MHD_Daemon *daemon,
2260 if (0 != (daemon->options & MHD_USE_EPOLL_LINUX_ONLY))
2264 if (daemon->epoll_fd >= FD_SETSIZE)
2266 if (FD_ISSET (daemon->epoll_fd, read_fd_set))
2267 return MHD_run (daemon);
2273 if ( (MHD_INVALID_SOCKET != (ds = daemon->socket_fd)) &&
2275 (void) MHD_accept_connection (daemon);
2277 if ( (MHD_INVALID_PIPE_ != daemon->wpipe[0]) &&
2278 (FD_ISSET (daemon->wpipe[0], (fd_set*)read_fd_set)) )
2279 (void) MHD_pipe_read_ (daemon->wpipe[0], &tmp, sizeof (tmp));
2281 if (0 == (daemon->options & MHD_USE_THREAD_PER_CONNECTION))
2284 next = daemon->connections_head;
2320 MHD_cleanup_connections (daemon);
2329 * @param daemon daemon to run select() loop for
2334 MHD_select (struct MHD_Daemon *daemon,
2348 if (MHD_YES == daemon->shutdown)
2354 if (0 == (daemon->options & MHD_USE_THREAD_PER_CONNECTION))
2356 if ( (MHD_USE_SUSPEND_RESUME == (daemon->options & MHD_USE_SUSPEND_RESUME)) &&
2357 (MHD_YES == resume_suspended_connections (daemon)) )
2361 if (MHD_NO == MHD_get_fdset2 (daemon, &rs, &ws, &es, &max, FD_SETSIZE))
2369 if ( (MHD_INVALID_SOCKET != daemon->socket_fd) &&
2370 (daemon->connections == daemon->connection_limit) &&
2371 (0 != (daemon->options & MHD_USE_PIPE_FOR_SHUTDOWN)) )
2372 FD_CLR (daemon->socket_fd, &rs);
2377 if ( (MHD_INVALID_SOCKET != daemon->socket_fd) &&
2378 (MHD_YES != add_to_fd_set (daemon->socket_fd,
2384 if ( (MHD_INVALID_PIPE_ != daemon->wpipe[0]) &&
2385 (MHD_YES != add_to_fd_set (daemon->wpipe[0],
2398 else if ( (0 == (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) &&
2399 (MHD_YES == MHD_get_timeout (daemon, &ltimeout)) )
2409 if (MHD_YES == daemon->shutdown)
2416 MHD_DLOG (daemon,
2422 return MHD_run_from_select (daemon, &rs, &ws, &es);
2431 * @param daemon daemon to run poll loop for
2436 MHD_poll_all (struct MHD_Daemon *daemon,
2443 if ( (MHD_USE_SUSPEND_RESUME == (daemon->options & MHD_USE_SUSPEND_RESUME)) &&
2444 (MHD_YES == resume_suspended_connections (daemon)) )
2449 for (pos = daemon->connections_head; NULL != pos; pos = pos->next)
2465 MHD_DLOG(daemon,
2474 if ( (MHD_INVALID_SOCKET != daemon->socket_fd) &&
2475 (daemon->connections < daemon->connection_limit) )
2478 p[poll_server].fd = daemon->socket_fd;
2485 if (MHD_INVALID_PIPE_ != daemon->wpipe[0])
2487 p[poll_server].fd = daemon->wpipe[0];
2495 else if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) ||
2496 (MHD_YES != MHD_get_timeout (daemon, &ltimeout)) )
2502 for (pos = daemon->connections_head; NULL != pos; pos = pos->next)
2538 MHD_DLOG (daemon,
2546 if (MHD_YES == daemon->shutdown)
2552 next = daemon->connections_head;
2597 (void) MHD_accept_connection (daemon);
2602 (void) MHD_pipe_read_ (daemon->wpipe[0], &tmp, sizeof (tmp));
2613 * @param daemon daemon to run poll loop for
2618 MHD_poll_listen_socket (struct MHD_Daemon *daemon,
2629 if (MHD_INVALID_SOCKET != daemon->socket_fd)
2631 p[poll_count].fd = daemon->socket_fd;
2637 if (MHD_INVALID_PIPE_ != daemon->wpipe[0])
2639 p[poll_count].fd = daemon->wpipe[0];
2655 MHD_DLOG (daemon,
2662 if (MHD_YES == daemon->shutdown)
2666 (void) MHD_accept_connection (daemon);
2675 * @param daemon daemon to run poll()-loop for
2680 MHD_poll (struct MHD_Daemon *daemon,
2684 if (MHD_YES == daemon->shutdown)
2686 if (0 == (daemon->options & MHD_USE_THREAD_PER_CONNECTION))
2687 return MHD_poll_all (daemon, may_block);
2689 return MHD_poll_listen_socket (daemon, may_block);
2713 * @param daemon daemon to run poll loop for
2718 MHD_epoll (struct MHD_Daemon *daemon,
2732 if (-1 == daemon->epoll_fd)
2734 if (MHD_YES == daemon->shutdown)
2736 if ( (MHD_INVALID_SOCKET != daemon->socket_fd) &&
2737 (daemon->connections < daemon->connection_limit) &&
2738 (MHD_NO == daemon->listen_socket_in_epoll) )
2741 event.data.ptr = daemon;
2742 if (0 != epoll_ctl (daemon->epoll_fd,
2744 daemon->socket_fd,
2748 MHD_DLOG (daemon,
2754 daemon->listen_socket_in_epoll = MHD_YES;
2756 if ( (MHD_YES == daemon->listen_socket_in_epoll) &&
2757 (daemon->connections == daemon->connection_limit) )
2761 if (0 != epoll_ctl (daemon->epoll_fd,
2763 daemon->socket_fd,
2766 daemon->listen_socket_in_epoll = MHD_NO;
2770 if (MHD_YES == MHD_get_timeout (daemon,
2792 num_events = epoll_wait (daemon->epoll_fd,
2799 MHD_DLOG (daemon,
2809 if ( (MHD_INVALID_PIPE_ != daemon->wpipe[0]) &&
2810 (daemon->wpipe[0] == events[i].data.fd) )
2812 (void) MHD_pipe_read_ (daemon->wpipe[0], &tmp, sizeof (tmp));
2815 if (daemon != events[i].data.ptr)
2828 EDLL_insert (daemon->eready_head,
2829 daemon->eready_tail,
2840 EDLL_insert (daemon->eready_head,
2841 daemon->eready_tail,
2852 while ( (MHD_YES == MHD_accept_connection (daemon)) &&
2853 (daemon->connections < daemon->connection_limit) &&
2862 if ( (MHD_USE_SUSPEND_RESUME == (daemon->options & MHD_USE_SUSPEND_RESUME)) &&
2863 (MHD_YES == resume_suspended_connections (daemon)) )
2867 while (NULL != (pos = daemon->eready_tail))
2869 EDLL_remove (daemon->eready_head,
2870 daemon->eready_tail,
2888 next = daemon->manual_timeout_head;
2898 next = daemon->normal_timeout_tail;
2924 * @param daemon daemon to run
2926 * daemon was not started with the right
2931 MHD_run (struct MHD_Daemon *daemon)
2933 if ( (MHD_YES == daemon->shutdown) ||
2934 (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) ||
2935 (0 != (daemon->options & MHD_USE_SELECT_INTERNALLY)) )
2937 if (0 != (daemon->options & MHD_USE_POLL))
2939 MHD_poll (daemon, MHD_NO);
2940 MHD_cleanup_connections (daemon);
2943 else if (0 != (daemon->options & MHD_USE_EPOLL_LINUX_ONLY))
2945 MHD_epoll (daemon, MHD_NO);
2946 MHD_cleanup_connections (daemon);
2951 MHD_select (daemon, MHD_NO);
2959 * Thread that runs the select loop until the daemon
2968 struct MHD_Daemon *daemon = cls;
2970 while (MHD_YES != daemon->shutdown)
2972 if (0 != (daemon->options & MHD_USE_POLL))
2973 MHD_poll (daemon, MHD_YES);
2975 else if (0 != (daemon->options & MHD_USE_EPOLL_LINUX_ONLY))
2976 MHD_epoll (daemon, MHD_YES);
2979 MHD_select (daemon, MHD_YES);
2980 MHD_cleanup_connections (daemon);
3019 * @return NULL on error, handle to daemon on success
3029 struct MHD_Daemon *daemon;
3033 daemon = MHD_start_daemon_va (flags, port, apc, apc_cls, dh, dh_cls, ap);
3035 return daemon;
3049 * #MHD_USE_PIPE_FOR_SHUTDOWN when using this API. If this daemon is
3053 * @param daemon daemon to stop accepting new connections for
3055 * the daemon was already not listening anymore
3059 MHD_quiesce_daemon (struct MHD_Daemon *daemon)
3064 ret = daemon->socket_fd;
3067 if ( (MHD_INVALID_PIPE_ == daemon->wpipe[1]) &&
3068 (0 != (daemon->options & (MHD_USE_SELECT_INTERNALLY | MHD_USE_THREAD_PER_CONNECTION))) )
3071 MHD_DLOG (daemon,
3077 if (NULL != daemon->worker_pool)
3078 for (i = 0; i < daemon->worker_pool_size; i++)
3080 daemon->worker_pool[i].socket_fd = MHD_INVALID_SOCKET;
3082 if ( (0 != (daemon->options & MHD_USE_EPOLL_LINUX_ONLY)) &&
3083 (-1 != daemon->worker_pool[i].epoll_fd) &&
3084 (MHD_YES == daemon->worker_pool[i].listen_socket_in_epoll) )
3086 if (0 != epoll_ctl (daemon->worker_pool[i].epoll_fd,
3091 daemon->worker_pool[i].listen_socket_in_epoll = MHD_NO;
3095 daemon->socket_fd = MHD_INVALID_SOCKET;
3097 if ( (0 != (daemon->options & MHD_USE_EPOLL_LINUX_ONLY)) &&
3098 (-1 != daemon->epoll_fd) &&
3099 (MHD_YES == daemon->listen_socket_in_epoll) )
3101 if (0 != epoll_ctl (daemon->epoll_fd,
3106 daemon->listen_socket_in_epoll = MHD_NO;
3128 * @param daemon the daemon to initialize
3134 parse_options_va (struct MHD_Daemon *daemon,
3142 * @param daemon the daemon to initialize
3148 parse_options (struct MHD_Daemon *daemon,
3156 ret = parse_options_va (daemon, servaddr, ap);
3165 * @param daemon the daemon to initialize
3171 parse_options_va (struct MHD_Daemon *daemon,
3188 daemon->pool_size = va_arg (ap, size_t);
3191 daemon->pool_increment= va_arg (ap, size_t);
3194 daemon->connection_limit = va_arg (ap, unsigned int);
3197 daemon->connection_timeout = va_arg (ap, unsigned int);
3200 daemon->notify_completed =
3202 daemon->notify_completed_cls = va_arg (ap, void *);
3205 daemon->notify_connection =
3207 daemon->notify_connection_cls = va_arg (ap, void *);
3210 daemon->per_ip_connection_limit = va_arg (ap, unsigned int);
3216 daemon->uri_log_callback =
3218 daemon->uri_log_callback_cls = va_arg (ap, void *);
3221 daemon->worker_pool_size = va_arg (ap, unsigned int);
3222 if (daemon->worker_pool_size >= (SIZE_MAX / sizeof (struct MHD_Daemon)))
3225 MHD_DLOG (daemon,
3227 daemon->worker_pool_size);
3234 if (0 != (daemon->options & MHD_USE_SSL))
3236 daemon->https_mem_key = va_arg (ap, const char *);
3241 MHD_DLOG (daemon,
3248 if (0 != (daemon->options & MHD_USE_SSL))
3250 daemon->https_key_password = va_arg (ap, const char *);
3255 MHD_DLOG (daemon,
3262 if (0 != (daemon->options & MHD_USE_SSL))
3264 daemon->https_mem_cert = va_arg (ap, const char *);
3269 MHD_DLOG (daemon,
3276 if (0 != (daemon->options & MHD_USE_SSL))
3278 daemon->https_mem_trust = va_arg (ap, const char *);
3283 MHD_DLOG (daemon,
3292 if (0 != (daemon->options & MHD_USE_SSL))
3294 daemon->https_mem_dhparams = va_arg (ap, const char *);
3299 MHD_DLOG (daemon,
3306 if (0 != (daemon->options & MHD_USE_SSL))
3308 daemon->https_mem_cipher = va_arg (ap, const char *);
3313 MHD_DLOG (daemon,
3324 daemon->digest_auth_rand_size = va_arg (ap, size_t);
3325 daemon->digest_auth_random = va_arg (ap, const char *);
3328 daemon->nonce_nc_size = va_arg (ap, unsigned int);
3332 daemon->socket_fd = va_arg (ap, MHD_socket);
3336 daemon->custom_error_log =
3338 daemon->custom_error_log_cls = va_arg (ap, void *);
3345 daemon->thread_stack_size = va_arg (ap, size_t);
3349 daemon->fastopen_queue_size = va_arg (ap, unsigned int);
3353 daemon->listening_address_reuse = va_arg (ap, unsigned int) ? 1 : -1;
3366 if (MHD_YES != parse_options (daemon,
3381 if (MHD_YES != parse_options (daemon,
3390 if (MHD_YES != parse_options (daemon,
3399 if (MHD_YES != parse_options (daemon,
3416 if (MHD_YES != parse_options (daemon,
3429 if (MHD_YES != parse_options (daemon,
3439 if (MHD_YES != parse_options (daemon,
3454 daemon->unescape_callback =
3456 daemon->unescape_callback_cls = va_arg (ap, void *);
3463 MHD_DLOG (daemon,
3469 MHD_DLOG (daemon,
3484 * @param daemon daemon for which we create the socket
3490 create_socket (struct MHD_Daemon *daemon,
3507 make_nonblocking_noninheritable (daemon, fd);
3514 * Setup epoll() FD for the daemon and initialize it to listen
3517 * @param daemon daemon to initialize for epoll()
3521 setup_epoll_to_listen (struct MHD_Daemon *daemon)
3526 daemon->epoll_fd = epoll_create1 (EPOLL_CLOEXEC);
3528 daemon->epoll_fd = epoll_create (MAX_EVENTS);
3530 if (-1 == daemon->epoll_fd)
3533 MHD_DLOG (daemon,
3542 int fdflags = fcntl (daemon->epoll_fd, F_GETFD);
3543 if (0 > fdflags || 0 > fcntl (daemon->epoll_fd, F_SETFD, fdflags | FD_CLOEXEC))
3546 MHD_DLOG (daemon,
3554 make_nonblocking_noninheritable (daemon,
3555 daemon->epoll_fd);
3556 if (MHD_INVALID_SOCKET == daemon->socket_fd)
3557 return MHD_YES; /* non-listening daemon */
3559 event.data.ptr = daemon;
3560 if (0 != epoll_ctl (daemon->epoll_fd,
3562 daemon->socket_fd,
3566 MHD_DLOG (daemon,
3572 if ( (MHD_INVALID_PIPE_ != daemon->wpipe[0]) &&
3573 (MHD_USE_SUSPEND_RESUME == (daemon->options & MHD_USE_SUSPEND_RESUME)) )
3577 event.data.fd = daemon->wpipe[0];
3578 if (0 != epoll_ctl (daemon->epoll_fd,
3580 daemon->wpipe[0],
3584 MHD_DLOG (daemon,
3591 daemon->listen_socket_in_epoll = MHD_YES;
3611 * @return NULL on error, handle to daemon on success
3623 struct MHD_Daemon *daemon;
3653 if (NULL == (daemon = malloc (sizeof (struct MHD_Daemon))))
3655 memset (daemon, 0, sizeof (struct MHD_Daemon));
3657 daemon->epoll_fd = -1;
3660 daemon->socket_fd = MHD_INVALID_SOCKET;
3661 daemon->listening_address_reuse = 0;
3662 daemon->options = flags;
3666 daemon->options |= MHD_USE_EPOLL_TURBO;
3668 daemon->port = port;
3669 daemon->apc = apc;
3670 daemon->apc_cls = apc_cls;
3671 daemon->default_handler = dh;
3672 daemon->default_handler_cls = dh_cls;
3673 daemon->connections = 0;
3674 daemon->connection_limit = MHD_MAX_CONNECTIONS_DEFAULT;
3675 daemon->pool_size = MHD_POOL_SIZE_DEFAULT;
3676 daemon->pool_increment = MHD_BUF_INC_SIZE;
3677 daemon->unescape_callback = &unescape_wrapper;
3678 daemon->connection_timeout = 0; /* no timeout */
3679 daemon->wpipe[0] = MHD_INVALID_PIPE_;
3680 daemon->wpipe[1] = MHD_INVALID_PIPE_;
3682 daemon->custom_error_log = (MHD_LogCallback) &vfprintf;
3683 daemon->custom_error_log_cls = stderr;
3686 use_pipe = (0 != (daemon->options & (MHD_USE_NO_LISTEN_SOCKET | MHD_USE_PIPE_FOR_SHUTDOWN)));
3692 if ( (use_pipe) && (0 != MHD_pipe_ (daemon->wpipe)) )
3695 MHD_DLOG (daemon,
3699 free (daemon);
3705 (daemon->wpipe[0] >= FD_SETSIZE) )
3708 MHD_DLOG (daemon,
3711 if (0 != MHD_pipe_close_ (daemon->wpipe[0]))
3713 if (0 != MHD_pipe_close_ (daemon->wpipe[1]))
3715 free (daemon);
3720 daemon->digest_auth_rand_size = 0;
3721 daemon->digest_auth_random = NULL;
3722 daemon->nonce_nc_size = 4; /* tiny */
3726 if (MHD_YES != parse_options_va (daemon, &servaddr, ap))
3728 free (daemon);
3732 if (daemon->nonce_nc_size > 0)
3734 if ( ( (size_t) (daemon->nonce_nc_size * sizeof (struct MHD_NonceNc))) /
3735 sizeof(struct MHD_NonceNc) != daemon->nonce_nc_size)
3738 MHD_DLOG (daemon,
3741 free (daemon);
3744 daemon->nnc = malloc (daemon->nonce_nc_size * sizeof (struct MHD_NonceNc));
3745 if (NULL == daemon->nnc)
3748 MHD_DLOG (daemon,
3752 free (daemon);
3757 if (MHD_YES != MHD_mutex_create_ (&daemon->nnc_lock))
3760 MHD_DLOG (daemon,
3763 free (daemon->nnc);
3764 free (daemon);
3771 (daemon->worker_pool_size > 0) )
3774 MHD_DLOG (daemon,
3784 MHD_DLOG (daemon,
3794 MHD_DLOG (daemon,
3800 if ( (MHD_INVALID_SOCKET == daemon->socket_fd) &&
3801 (0 == (daemon->options & MHD_USE_NO_LISTEN_SOCKET)) )
3805 socket_fd = create_socket (daemon,
3808 socket_fd = create_socket (daemon,
3813 MHD_DLOG (daemon,
3821 if (0 == daemon->listening_address_reuse)
3831 MHD_DLOG (daemon,
3837 else if (daemon->listening_address_reuse > 0)
3852 MHD_DLOG (daemon,
3874 MHD_DLOG (daemon,
3884 MHD_DLOG (daemon,
3891 else /* if (daemon->listening_address_reuse < 0) */
3905 MHD_DLOG (daemon,
3913 MHD_DLOG (daemon,
3953 daemon->socket_fd = socket_fd;
3974 MHD_DLOG (daemon,
3985 MHD_DLOG (daemon,
3997 if (0 == daemon->fastopen_queue_size)
3998 daemon->fastopen_queue_size = MHD_TCP_FASTOPEN_QUEUE_SIZE_DEFAULT;
4001 &daemon->fastopen_queue_size,
4002 sizeof (daemon->fastopen_queue_size)))
4005 MHD_DLOG (daemon,
4019 MHD_DLOG (daemon,
4032 MHD_DLOG (daemon,
4043 socket_fd = daemon->socket_fd;
4050 MHD_DLOG (daemon,
4063 (0 == daemon->worker_pool_size) &&
4064 (0 == (daemon->options & MHD_USE_NO_LISTEN_SOCKET)) )
4069 MHD_DLOG (daemon,
4074 if (MHD_YES != setup_epoll_to_listen (daemon))
4081 MHD_DLOG (daemon,
4088 if (MHD_YES != MHD_mutex_create_ (&daemon->per_ip_connection_mutex))
4091 MHD_DLOG (daemon,
4099 if (MHD_YES != MHD_mutex_create_ (&daemon->cleanup_connection_mutex))
4102 MHD_DLOG (daemon,
4105 (void) MHD_mutex_destroy_ (&daemon->cleanup_connection_mutex);
4113 /* initialize HTTPS daemon certificate aspects & send / recv functions */
4114 if ((0 != (flags & MHD_USE_SSL)) && (0 != MHD_TLS_init (daemon)))
4117 MHD_DLOG (daemon,
4123 (void) MHD_mutex_destroy_ (&daemon->cleanup_connection_mutex);
4124 (void) MHD_mutex_destroy_ (&daemon->per_ip_connection_mutex);
4130 (0 == daemon->worker_pool_size)) ) &&
4131 (0 == (daemon->options & MHD_USE_NO_LISTEN_SOCKET)) &&
4133 create_thread (&daemon->pid, daemon, &MHD_select_thread, daemon))))
4136 MHD_DLOG (daemon,
4140 (void) MHD_mutex_destroy_ (&daemon->cleanup_connection_mutex);
4141 (void) MHD_mutex_destroy_ (&daemon->per_ip_connection_mutex);
4147 if ( (daemon->worker_pool_size > 0) &&
4148 (0 == (daemon->options & MHD_USE_NO_LISTEN_SOCKET)) )
4159 unsigned int conns_per_thread = daemon->connection_limit
4160 / daemon->worker_pool_size;
4161 unsigned int leftover_conns = daemon->connection_limit
4162 % daemon->worker_pool_size;
4182 daemon->worker_pool = malloc (sizeof (struct MHD_Daemon)
4183 * daemon->worker_pool_size);
4184 if (NULL == daemon->worker_pool)
4188 for (i = 0; i < daemon->worker_pool_size; ++i)
4191 struct MHD_Daemon *d = &daemon->worker_pool[i];
4193 memcpy (d, daemon, sizeof (struct MHD_Daemon));
4197 d->master = daemon;
4205 MHD_DLOG (daemon,
4217 MHD_DLOG (daemon,
4235 if ( (0 != (daemon->options & MHD_USE_EPOLL_LINUX_ONLY)) &&
4243 MHD_DLOG (daemon,
4251 create_thread (&d->pid, daemon, &MHD_select_thread, d)))
4254 MHD_DLOG (daemon,
4268 daemon->https_key_password = NULL;
4271 return daemon;
4283 (void) MHD_mutex_destroy_ (&daemon->cleanup_connection_mutex);
4284 (void) MHD_mutex_destroy_ (&daemon->per_ip_connection_mutex);
4285 if (NULL != daemon->worker_pool)
4286 free (daemon->worker_pool);
4291 as though we had fully initialized our daemon, but
4294 daemon->worker_pool_size = i;
4295 MHD_stop_daemon (daemon);
4299 /* clean up basic memory state in 'daemon' and return NULL to
4302 if (-1 != daemon->epoll_fd)
4303 close (daemon->epoll_fd);
4306 free (daemon->nnc);
4307 (void) MHD_mutex_destroy_ (&daemon->nnc_lock);
4309 free (daemon);
4323 struct MHD_Daemon *daemon = pos->daemon;
4327 if (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION))
4329 if (pos->connection_timeout == pos->daemon->connection_timeout)
4330 XDLL_remove (daemon->normal_timeout_head,
4331 daemon->normal_timeout_tail,
4334 XDLL_remove (daemon->manual_timeout_head,
4335 daemon->manual_timeout_tail,
4337 DLL_remove (daemon->connections_head,
4338 daemon->connections_tail,
4341 DLL_insert (daemon->cleanup_head,
4342 daemon->cleanup_tail,
4348 * Close all connections for the daemon; must only be called after
4352 * @param daemon daemon to close down
4355 close_all_connections (struct MHD_Daemon *daemon)
4361 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) &&
4362 (MHD_YES != MHD_mutex_lock_ (&daemon->cleanup_connection_mutex)) )
4364 for (pos = daemon->connections_head; NULL != pos; pos = pos->next)
4369 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) &&
4370 (MHD_INVALID_PIPE_ != daemon->wpipe[1]) &&
4371 (1 != MHD_pipe_write_ (daemon->wpipe[1], "e", 1)) )
4375 if ( (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) &&
4376 (MHD_YES != MHD_mutex_unlock_ (&daemon->cleanup_connection_mutex)) )
4380 if (0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION))
4382 for (pos = daemon->connections_head; NULL != pos; pos = pos->next)
4391 while (NULL != (pos = daemon->connections_head))
4393 MHD_cleanup_connections (daemon);
4401 * @param daemon daemon of which the epoll() instance must be signalled
4404 epoll_shutdown (struct MHD_Daemon *daemon)
4408 if (MHD_INVALID_PIPE_ == daemon->wpipe[1])
4415 if (0 != epoll_ctl (daemon->epoll_fd,
4417 daemon->wpipe[1],
4425 * Shutdown an HTTP daemon.
4427 * @param daemon daemon to stop
4431 MHD_stop_daemon (struct MHD_Daemon *daemon)
4436 if (NULL == daemon)
4438 daemon->shutdown = MHD_YES;
4439 fd = daemon->socket_fd;
4440 daemon->socket_fd = MHD_INVALID_SOCKET;
4442 if (NULL != daemon->worker_pool)
4445 for (i = 0; i < daemon->worker_pool_size; ++i)
4447 daemon->worker_pool[i].shutdown = MHD_YES;
4448 daemon->worker_pool[i].socket_fd = MHD_INVALID_SOCKET;
4450 if ( (0 != (daemon->options & MHD_USE_EPOLL_LINUX_ONLY)) &&
4451 (-1 != daemon->worker_pool[i].epoll_fd) &&
4453 epoll_shutdown (&daemon->worker_pool[i]);
4457 if (MHD_INVALID_PIPE_ != daemon->wpipe[1])
4459 if (1 != MHD_pipe_write_ (daemon->wpipe[1], "e", 1))
4471 if ( (0 != (daemon->options & MHD_USE_EPOLL_LINUX_ONLY)) &&
4472 (-1 != daemon->epoll_fd) &&
4474 epoll_shutdown (daemon);
4479 MHD_DLOG (daemon,
4486 if (NULL != daemon->worker_pool)
4489 for (i = 0; i < daemon->worker_pool_size; ++i)
4491 if (MHD_INVALID_PIPE_ != daemon->worker_pool[i].wpipe[1])
4493 if (1 != MHD_pipe_write_ (daemon->worker_pool[i].wpipe[1], "e", 1))
4496 if (0 != MHD_join_thread_ (daemon->worker_pool[i].pid))
4498 close_all_connections (&daemon->worker_pool[i]);
4499 (void) MHD_mutex_destroy_ (&daemon->worker_pool[i].cleanup_connection_mutex);
4501 if ( (-1 != daemon->worker_pool[i].epoll_fd) &&
4502 (0 != MHD_socket_close_ (daemon->worker_pool[i].epoll_fd)) )
4505 if ( (MHD_USE_SUSPEND_RESUME == (daemon->options & MHD_USE_SUSPEND_RESUME)) )
4507 if (MHD_INVALID_PIPE_ != daemon->worker_pool[i].wpipe[1])
4509 if (0 != MHD_pipe_close_ (daemon->worker_pool[i].wpipe[0]))
4511 if (0 != MHD_pipe_close_ (daemon->worker_pool[i].wpipe[1]))
4516 free (daemon->worker_pool);
4521 if ((0 != (daemon->options & MHD_USE_THREAD_PER_CONNECTION)) ||
4522 ((0 != (daemon->options & MHD_USE_SELECT_INTERNALLY))
4523 && (0 == daemon->worker_pool_size)))
4525 if (0 != MHD_join_thread_ (daemon->pid))
4531 close_all_connections (daemon);
4538 if (0 != (daemon->options & MHD_USE_SSL))
4540 MHD_TLS_deinit (daemon);
4544 if ( (0 != (daemon->options & MHD_USE_EPOLL_LINUX_ONLY)) &&
4545 (-1 != daemon->epoll_fd) &&
4546 (0 != MHD_socket_close_ (daemon->epoll_fd)) )
4551 free (daemon->nnc);
4552 (void) MHD_mutex_destroy_ (&daemon->nnc_lock);
4554 (void) MHD_mutex_destroy_ (&daemon->per_ip_connection_mutex);
4555 (void) MHD_mutex_destroy_ (&daemon->cleanup_connection_mutex);
4557 if (MHD_INVALID_PIPE_ != daemon->wpipe[1])
4559 if (0 != MHD_pipe_close_ (daemon->wpipe[0]))
4561 if (0 != MHD_pipe_close_ (daemon->wpipe[1]))
4564 free (daemon);
4569 * Obtain information about the given daemon
4572 * @param daemon what daemon to get information about
4580 MHD_get_daemon_info (struct MHD_Daemon *daemon,
4591 return (const union MHD_DaemonInfo *) &daemon->socket_fd;
4594 return (const union MHD_DaemonInfo *) &daemon->epoll_fd;
4597 MHD_cleanup_connections (daemon);
4598 if (daemon->worker_pool)
4603 daemon->connections = 0;
4604 for (i=0;i<daemon->worker_pool_size;i++)
4606 MHD_cleanup_connections (&daemon->worker_pool[i]);
4607 daemon->connections += daemon->worker_pool[i].connections;
4610 return (const union MHD_DaemonInfo *) &daemon->connections;
4801 /* end of daemon.c */