1b7579f77SDag-Erling Smørgrav /* 2b7579f77SDag-Erling Smørgrav * util/netevent.h - event notification 3b7579f77SDag-Erling Smørgrav * 4b7579f77SDag-Erling Smørgrav * Copyright (c) 2007, NLnet Labs. All rights reserved. 5b7579f77SDag-Erling Smørgrav * 6b7579f77SDag-Erling Smørgrav * This software is open source. 7b7579f77SDag-Erling Smørgrav * 8b7579f77SDag-Erling Smørgrav * Redistribution and use in source and binary forms, with or without 9b7579f77SDag-Erling Smørgrav * modification, are permitted provided that the following conditions 10b7579f77SDag-Erling Smørgrav * are met: 11b7579f77SDag-Erling Smørgrav * 12b7579f77SDag-Erling Smørgrav * Redistributions of source code must retain the above copyright notice, 13b7579f77SDag-Erling Smørgrav * this list of conditions and the following disclaimer. 14b7579f77SDag-Erling Smørgrav * 15b7579f77SDag-Erling Smørgrav * Redistributions in binary form must reproduce the above copyright notice, 16b7579f77SDag-Erling Smørgrav * this list of conditions and the following disclaimer in the documentation 17b7579f77SDag-Erling Smørgrav * and/or other materials provided with the distribution. 18b7579f77SDag-Erling Smørgrav * 19b7579f77SDag-Erling Smørgrav * Neither the name of the NLNET LABS nor the names of its contributors may 20b7579f77SDag-Erling Smørgrav * be used to endorse or promote products derived from this software without 21b7579f77SDag-Erling Smørgrav * specific prior written permission. 22b7579f77SDag-Erling Smørgrav * 23b7579f77SDag-Erling Smørgrav * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 2417d15b25SDag-Erling Smørgrav * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 2517d15b25SDag-Erling Smørgrav * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 2617d15b25SDag-Erling Smørgrav * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 2717d15b25SDag-Erling Smørgrav * HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 2817d15b25SDag-Erling Smørgrav * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED 2917d15b25SDag-Erling Smørgrav * TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 3017d15b25SDag-Erling Smørgrav * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF 3117d15b25SDag-Erling Smørgrav * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING 3217d15b25SDag-Erling Smørgrav * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 3317d15b25SDag-Erling Smørgrav * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 34b7579f77SDag-Erling Smørgrav */ 35b7579f77SDag-Erling Smørgrav 36b7579f77SDag-Erling Smørgrav /** 37b7579f77SDag-Erling Smørgrav * \file 38b7579f77SDag-Erling Smørgrav * 39b7579f77SDag-Erling Smørgrav * This file contains event notification functions. 40b7579f77SDag-Erling Smørgrav * 41b7579f77SDag-Erling Smørgrav * There are three types of communication points 42b7579f77SDag-Erling Smørgrav * o UDP socket - perthread buffer. 43b7579f77SDag-Erling Smørgrav * o TCP-accept socket - array of TCP-sockets, socketcount. 44b7579f77SDag-Erling Smørgrav * o TCP socket - own buffer, parent-TCPaccept, read/write state, 45b7579f77SDag-Erling Smørgrav * number of bytes read/written, timeout. 46b7579f77SDag-Erling Smørgrav * 47b7579f77SDag-Erling Smørgrav * There are sockets aimed towards our clients and towards the internet. 48b7579f77SDag-Erling Smørgrav * o frontside - aimed towards our clients, queries come in, answers back. 49b7579f77SDag-Erling Smørgrav * o behind - aimed towards internet, to the authoritative DNS servers. 50b7579f77SDag-Erling Smørgrav * 51b7579f77SDag-Erling Smørgrav * Several event types are available: 52b7579f77SDag-Erling Smørgrav * o comm_base - for thread safety of the comm points, one per thread. 53b7579f77SDag-Erling Smørgrav * o comm_point - udp and tcp networking, with callbacks. 54b7579f77SDag-Erling Smørgrav * o comm_timer - a timeout with callback. 55b7579f77SDag-Erling Smørgrav * o comm_signal - callbacks when signal is caught. 56b7579f77SDag-Erling Smørgrav * o comm_reply - holds reply info during networking callback. 57b7579f77SDag-Erling Smørgrav * 58b7579f77SDag-Erling Smørgrav */ 59b7579f77SDag-Erling Smørgrav 60b7579f77SDag-Erling Smørgrav #ifndef NET_EVENT_H 61b7579f77SDag-Erling Smørgrav #define NET_EVENT_H 62b7579f77SDag-Erling Smørgrav 638f76bb7dSCy Schubert #include <sys/time.h> 6465b390aaSDag-Erling Smørgrav #include "dnscrypt/dnscrypt.h" 65c0caa2e2SCy Schubert #ifdef HAVE_NGHTTP2_NGHTTP2_H 66c0caa2e2SCy Schubert #include <nghttp2/nghttp2.h> 67c0caa2e2SCy Schubert #endif 68*46d2f618SCy Schubert #ifdef HAVE_NGTCP2 69*46d2f618SCy Schubert #include <ngtcp2/ngtcp2.h> 70*46d2f618SCy Schubert #endif 7165b390aaSDag-Erling Smørgrav 7217d15b25SDag-Erling Smørgrav struct sldns_buffer; 73b7579f77SDag-Erling Smørgrav struct comm_point; 74b7579f77SDag-Erling Smørgrav struct comm_reply; 754c75e3aaSDag-Erling Smørgrav struct tcl_list; 76e2d15004SDag-Erling Smørgrav struct ub_event_base; 775469a995SCy Schubert struct unbound_socket; 78*46d2f618SCy Schubert struct doq_server_socket; 79*46d2f618SCy Schubert struct doq_table; 80*46d2f618SCy Schubert struct doq_conn; 81*46d2f618SCy Schubert struct config_file; 82*46d2f618SCy Schubert struct ub_randstate; 83b7579f77SDag-Erling Smørgrav 84c0caa2e2SCy Schubert struct mesh_state; 85c0caa2e2SCy Schubert struct mesh_area; 86c0caa2e2SCy Schubert 87b7579f77SDag-Erling Smørgrav /* internal event notification data storage structure. */ 88b7579f77SDag-Erling Smørgrav struct internal_event; 89b7579f77SDag-Erling Smørgrav struct internal_base; 90e2d15004SDag-Erling Smørgrav struct internal_timer; /* A sub struct of the comm_timer super struct */ 91b7579f77SDag-Erling Smørgrav 92c0caa2e2SCy Schubert enum listen_type; 93c0caa2e2SCy Schubert 94b7579f77SDag-Erling Smørgrav /** callback from communication point function type */ 953005e0a3SDag-Erling Smørgrav typedef int comm_point_callback_type(struct comm_point*, void*, int, 96b7579f77SDag-Erling Smørgrav struct comm_reply*); 97b7579f77SDag-Erling Smørgrav 98b7579f77SDag-Erling Smørgrav /** to pass no_error to callback function */ 99b7579f77SDag-Erling Smørgrav #define NETEVENT_NOERROR 0 100b7579f77SDag-Erling Smørgrav /** to pass closed connection to callback function */ 101b7579f77SDag-Erling Smørgrav #define NETEVENT_CLOSED -1 102b7579f77SDag-Erling Smørgrav /** to pass timeout happened to callback function */ 103b7579f77SDag-Erling Smørgrav #define NETEVENT_TIMEOUT -2 104b7579f77SDag-Erling Smørgrav /** to pass fallback from capsforID to callback function; 0x20 failed */ 105b7579f77SDag-Erling Smørgrav #define NETEVENT_CAPSFAIL -3 10657bddd21SDag-Erling Smørgrav /** to pass done transfer to callback function; http file is complete */ 10757bddd21SDag-Erling Smørgrav #define NETEVENT_DONE -4 108369c6923SCy Schubert /** to pass write of the write packet is done to callback function 109369c6923SCy Schubert * used when tcp_write_and_read is enabled */ 110369c6923SCy Schubert #define NETEVENT_PKT_WRITTEN -5 111b7579f77SDag-Erling Smørgrav 112b7579f77SDag-Erling Smørgrav /** timeout to slow accept calls when not possible, in msec. */ 113b7579f77SDag-Erling Smørgrav #define NETEVENT_SLOW_ACCEPT_TIME 2000 114865f46b2SCy Schubert /** timeout to slow down log print, so it does not spam the logs, in sec */ 115865f46b2SCy Schubert #define SLOW_LOG_TIME 10 116*46d2f618SCy Schubert /** for doq, the maximum dcid length, in ngtcp2 it is 20. */ 117*46d2f618SCy Schubert #define DOQ_MAX_CIDLEN 24 118b7579f77SDag-Erling Smørgrav 119b7579f77SDag-Erling Smørgrav /** 120b7579f77SDag-Erling Smørgrav * A communication point dispatcher. Thread specific. 121b7579f77SDag-Erling Smørgrav */ 122b7579f77SDag-Erling Smørgrav struct comm_base { 123b7579f77SDag-Erling Smørgrav /** behind the scenes structure. with say libevent info. alloced */ 124b7579f77SDag-Erling Smørgrav struct internal_base* eb; 125b7579f77SDag-Erling Smørgrav /** callback to stop listening on accept sockets, 126b7579f77SDag-Erling Smørgrav * performed when accept() will not function properly */ 127b7579f77SDag-Erling Smørgrav void (*stop_accept)(void*); 128b7579f77SDag-Erling Smørgrav /** callback to start listening on accept sockets, performed 129b7579f77SDag-Erling Smørgrav * after stop_accept() then a timeout has passed. */ 130b7579f77SDag-Erling Smørgrav void (*start_accept)(void*); 131b7579f77SDag-Erling Smørgrav /** user argument for stop_accept and start_accept functions */ 132b7579f77SDag-Erling Smørgrav void* cb_arg; 133b7579f77SDag-Erling Smørgrav }; 134b7579f77SDag-Erling Smørgrav 135b7579f77SDag-Erling Smørgrav /** 136b7579f77SDag-Erling Smørgrav * Reply information for a communication point. 137b7579f77SDag-Erling Smørgrav */ 138b7579f77SDag-Erling Smørgrav struct comm_reply { 139b7579f77SDag-Erling Smørgrav /** the comm_point with fd to send reply on to. */ 140b7579f77SDag-Erling Smørgrav struct comm_point* c; 141b7579f77SDag-Erling Smørgrav /** the address (for UDP based communication) */ 142865f46b2SCy Schubert struct sockaddr_storage remote_addr; 143b7579f77SDag-Erling Smørgrav /** length of address */ 144865f46b2SCy Schubert socklen_t remote_addrlen; 145865f46b2SCy Schubert /** return type 0 (none), 4(IP4), 6(IP6) 146865f46b2SCy Schubert * used only with listen_type_udp_ancil* */ 147b7579f77SDag-Erling Smørgrav int srctype; 14865b390aaSDag-Erling Smørgrav /* DnsCrypt context */ 14965b390aaSDag-Erling Smørgrav #ifdef USE_DNSCRYPT 15065b390aaSDag-Erling Smørgrav uint8_t client_nonce[crypto_box_HALF_NONCEBYTES]; 15165b390aaSDag-Erling Smørgrav uint8_t nmkey[crypto_box_BEFORENMBYTES]; 152c7f4d7adSDag-Erling Smørgrav const dnsccert *dnsc_cert; 15365b390aaSDag-Erling Smørgrav int is_dnscrypted; 15465b390aaSDag-Erling Smørgrav #endif 155b7579f77SDag-Erling Smørgrav /** the return source interface data */ 156b7579f77SDag-Erling Smørgrav union { 157b7579f77SDag-Erling Smørgrav #ifdef IPV6_PKTINFO 158b7579f77SDag-Erling Smørgrav struct in6_pktinfo v6info; 159b7579f77SDag-Erling Smørgrav #endif 160b7579f77SDag-Erling Smørgrav #ifdef IP_PKTINFO 161b7579f77SDag-Erling Smørgrav struct in_pktinfo v4info; 162b7579f77SDag-Erling Smørgrav #elif defined(IP_RECVDSTADDR) 163b7579f77SDag-Erling Smørgrav struct in_addr v4addr; 164b7579f77SDag-Erling Smørgrav #endif 165b7579f77SDag-Erling Smørgrav } 166b7579f77SDag-Erling Smørgrav /** variable with return source data */ 167b7579f77SDag-Erling Smørgrav pktinfo; 16865b390aaSDag-Erling Smørgrav /** max udp size for udp packets */ 16965b390aaSDag-Erling Smørgrav size_t max_udp_size; 170865f46b2SCy Schubert /* if set, the request came through a proxy */ 171865f46b2SCy Schubert int is_proxied; 172865f46b2SCy Schubert /** the client address 173865f46b2SCy Schubert * the same as remote_addr if not proxied */ 174865f46b2SCy Schubert struct sockaddr_storage client_addr; 175865f46b2SCy Schubert /** the original address length */ 176865f46b2SCy Schubert socklen_t client_addrlen; 177*46d2f618SCy Schubert #ifdef HAVE_NGTCP2 178*46d2f618SCy Schubert /** the doq ifindex, together with addr and localaddr in pktinfo, 179*46d2f618SCy Schubert * and dcid makes the doq_conn_key to find the connection */ 180*46d2f618SCy Schubert int doq_ifindex; 181*46d2f618SCy Schubert /** the doq dcid, the connection id used to find the connection */ 182*46d2f618SCy Schubert uint8_t doq_dcid[DOQ_MAX_CIDLEN]; 183*46d2f618SCy Schubert /** the length of the doq dcid */ 184*46d2f618SCy Schubert size_t doq_dcidlen; 185*46d2f618SCy Schubert /** the doq stream id where the query came in on */ 186*46d2f618SCy Schubert int64_t doq_streamid; 187*46d2f618SCy Schubert /** port number for doq */ 188*46d2f618SCy Schubert int doq_srcport; 189*46d2f618SCy Schubert #endif /* HAVE_NGTCP2 */ 190b7579f77SDag-Erling Smørgrav }; 191b7579f77SDag-Erling Smørgrav 192b7579f77SDag-Erling Smørgrav /** 193b7579f77SDag-Erling Smørgrav * Communication point to the network 194b7579f77SDag-Erling Smørgrav * These behaviours can be accomplished by setting the flags 195b7579f77SDag-Erling Smørgrav * and passing return values from the callback. 196b7579f77SDag-Erling Smørgrav * udp frontside: called after readdone. sendafter. 197b7579f77SDag-Erling Smørgrav * tcp frontside: called readdone, sendafter. close. 198b7579f77SDag-Erling Smørgrav * udp behind: called after readdone. No send after. 199b7579f77SDag-Erling Smørgrav * tcp behind: write done, read done, then called. No send after. 200b7579f77SDag-Erling Smørgrav */ 201b7579f77SDag-Erling Smørgrav struct comm_point { 202b7579f77SDag-Erling Smørgrav /** behind the scenes structure, with say libevent info. alloced. */ 203b7579f77SDag-Erling Smørgrav struct internal_event* ev; 204f44e67d1SCy Schubert /** if the event is added or not */ 205f44e67d1SCy Schubert int event_added; 206b7579f77SDag-Erling Smørgrav 207335c7cdaSCy Schubert /** Reference to struct that is part of the listening ports, 208335c7cdaSCy Schubert * where for listening ports information is kept about the address. */ 2095469a995SCy Schubert struct unbound_socket* socket; 2105469a995SCy Schubert 211b7579f77SDag-Erling Smørgrav /** file descriptor for communication point */ 212b7579f77SDag-Erling Smørgrav int fd; 213b7579f77SDag-Erling Smørgrav 214b7579f77SDag-Erling Smørgrav /** timeout (NULL if it does not). Malloced. */ 215b7579f77SDag-Erling Smørgrav struct timeval* timeout; 216b7579f77SDag-Erling Smørgrav 217b7579f77SDag-Erling Smørgrav /** buffer pointer. Either to perthread, or own buffer or NULL */ 21817d15b25SDag-Erling Smørgrav struct sldns_buffer* buffer; 219b7579f77SDag-Erling Smørgrav 220b7579f77SDag-Erling Smørgrav /* -------- TCP Handler -------- */ 221b7579f77SDag-Erling Smørgrav /** Read/Write state for TCP */ 222b7579f77SDag-Erling Smørgrav int tcp_is_reading; 223b7579f77SDag-Erling Smørgrav /** The current read/write count for TCP */ 224b7579f77SDag-Erling Smørgrav size_t tcp_byte_count; 225b7579f77SDag-Erling Smørgrav /** parent communication point (for TCP sockets) */ 226b7579f77SDag-Erling Smørgrav struct comm_point* tcp_parent; 227b7579f77SDag-Erling Smørgrav /** sockaddr from peer, for TCP handlers */ 228b7579f77SDag-Erling Smørgrav struct comm_reply repinfo; 229b7579f77SDag-Erling Smørgrav 230b7579f77SDag-Erling Smørgrav /* -------- TCP Accept -------- */ 231b7579f77SDag-Erling Smørgrav /** the number of TCP handlers for this tcp-accept socket */ 232b7579f77SDag-Erling Smørgrav int max_tcp_count; 23309a3aaf3SDag-Erling Smørgrav /** current number of tcp handler in-use for this accept socket */ 23409a3aaf3SDag-Erling Smørgrav int cur_tcp_count; 235b7579f77SDag-Erling Smørgrav /** malloced array of tcp handlers for a tcp-accept, 236b7579f77SDag-Erling Smørgrav of size max_tcp_count. */ 237b7579f77SDag-Erling Smørgrav struct comm_point** tcp_handlers; 238b7579f77SDag-Erling Smørgrav /** linked list of free tcp_handlers to use for new queries. 239b7579f77SDag-Erling Smørgrav For tcp_accept the first entry, for tcp_handlers the next one. */ 240b7579f77SDag-Erling Smørgrav struct comm_point* tcp_free; 241b7579f77SDag-Erling Smørgrav 242b7579f77SDag-Erling Smørgrav /* -------- SSL TCP DNS ------- */ 243b7579f77SDag-Erling Smørgrav /** the SSL object with rw bio (owned) or for commaccept ctx ref */ 244b7579f77SDag-Erling Smørgrav void* ssl; 245b7579f77SDag-Erling Smørgrav /** handshake state for init and renegotiate */ 246b7579f77SDag-Erling Smørgrav enum { 247b7579f77SDag-Erling Smørgrav /** no handshake, it has been done */ 248b7579f77SDag-Erling Smørgrav comm_ssl_shake_none = 0, 249b7579f77SDag-Erling Smørgrav /** ssl initial handshake wants to read */ 250b7579f77SDag-Erling Smørgrav comm_ssl_shake_read, 251b7579f77SDag-Erling Smørgrav /** ssl initial handshake wants to write */ 252b7579f77SDag-Erling Smørgrav comm_ssl_shake_write, 253b7579f77SDag-Erling Smørgrav /** ssl_write wants to read */ 254b7579f77SDag-Erling Smørgrav comm_ssl_shake_hs_read, 255b7579f77SDag-Erling Smørgrav /** ssl_read wants to write */ 256b7579f77SDag-Erling Smørgrav comm_ssl_shake_hs_write 257b7579f77SDag-Erling Smørgrav } ssl_shake_state; 258b7579f77SDag-Erling Smørgrav 25957bddd21SDag-Erling Smørgrav /* -------- HTTP ------- */ 260c0caa2e2SCy Schubert /** Do not allow connection to use HTTP version lower than this. 0=no 261c0caa2e2SCy Schubert * minimum. */ 262c0caa2e2SCy Schubert enum { 263c0caa2e2SCy Schubert http_version_none = 0, 264c0caa2e2SCy Schubert http_version_2 = 2 265c0caa2e2SCy Schubert } http_min_version; 266c0caa2e2SCy Schubert /** http endpoint */ 267c0caa2e2SCy Schubert char* http_endpoint; 268c0caa2e2SCy Schubert /* -------- HTTP/1.1 ------- */ 26957bddd21SDag-Erling Smørgrav /** Currently reading in http headers */ 27057bddd21SDag-Erling Smørgrav int http_in_headers; 27157bddd21SDag-Erling Smørgrav /** Currently reading in chunk headers, 0=not, 1=firstline, 2=unused 27257bddd21SDag-Erling Smørgrav * (more lines), 3=trailer headers after chunk */ 27357bddd21SDag-Erling Smørgrav int http_in_chunk_headers; 27457bddd21SDag-Erling Smørgrav /** chunked transfer */ 27557bddd21SDag-Erling Smørgrav int http_is_chunked; 27657bddd21SDag-Erling Smørgrav /** http temp buffer (shared buffer for temporary work) */ 27757bddd21SDag-Erling Smørgrav struct sldns_buffer* http_temp; 27857bddd21SDag-Erling Smørgrav /** http stored content in buffer */ 27957bddd21SDag-Erling Smørgrav size_t http_stored; 280c0caa2e2SCy Schubert /* -------- HTTP/2 ------- */ 281c0caa2e2SCy Schubert /** http2 session */ 282c0caa2e2SCy Schubert struct http2_session* h2_session; 283c0caa2e2SCy Schubert /** set to 1 if h2 is negotiated to be used (using alpn) */ 284c0caa2e2SCy Schubert int use_h2; 285c0caa2e2SCy Schubert /** stream currently being handled */ 286c0caa2e2SCy Schubert struct http2_stream* h2_stream; 287c0caa2e2SCy Schubert /** maximum allowed query buffer size, per stream */ 288c0caa2e2SCy Schubert size_t http2_stream_max_qbuffer_size; 289c0caa2e2SCy Schubert /** maximum number of HTTP/2 streams per connection. Send in HTTP/2 290c0caa2e2SCy Schubert * SETTINGS frame. */ 291c0caa2e2SCy Schubert uint32_t http2_max_streams; 292*46d2f618SCy Schubert /* -------- DoQ ------- */ 293*46d2f618SCy Schubert #ifdef HAVE_NGTCP2 294*46d2f618SCy Schubert /** the doq server socket, with list of doq connections */ 295*46d2f618SCy Schubert struct doq_server_socket* doq_socket; 296*46d2f618SCy Schubert #endif 29757bddd21SDag-Erling Smørgrav 298ff825849SDag-Erling Smørgrav /* -------- dnstap ------- */ 299ff825849SDag-Erling Smørgrav /** the dnstap environment */ 300ff825849SDag-Erling Smørgrav struct dt_env* dtenv; 301ff825849SDag-Erling Smørgrav 302b7579f77SDag-Erling Smørgrav /** is this a UDP, TCP-accept or TCP socket. */ 303b7579f77SDag-Erling Smørgrav enum comm_point_type { 304b7579f77SDag-Erling Smørgrav /** UDP socket - handle datagrams. */ 305b7579f77SDag-Erling Smørgrav comm_udp, 306b7579f77SDag-Erling Smørgrav /** TCP accept socket - only creates handlers if readable. */ 307b7579f77SDag-Erling Smørgrav comm_tcp_accept, 308b7579f77SDag-Erling Smørgrav /** TCP handler socket - handle byteperbyte readwrite. */ 309b7579f77SDag-Erling Smørgrav comm_tcp, 31057bddd21SDag-Erling Smørgrav /** HTTP handler socket */ 31157bddd21SDag-Erling Smørgrav comm_http, 312*46d2f618SCy Schubert /** DOQ handler socket */ 313*46d2f618SCy Schubert comm_doq, 314b7579f77SDag-Erling Smørgrav /** AF_UNIX socket - for internal commands. */ 315b7579f77SDag-Erling Smørgrav comm_local, 316b7579f77SDag-Erling Smørgrav /** raw - not DNS format - for pipe readers and writers */ 317b7579f77SDag-Erling Smørgrav comm_raw 318b7579f77SDag-Erling Smørgrav } 319b7579f77SDag-Erling Smørgrav /** variable with type of socket, UDP,TCP-accept,TCP,pipe */ 320b7579f77SDag-Erling Smørgrav type; 321b7579f77SDag-Erling Smørgrav 322865f46b2SCy Schubert /* -------- PROXYv2 ------- */ 323865f46b2SCy Schubert /** if set, PROXYv2 is expected on this connection */ 324865f46b2SCy Schubert int pp2_enabled; 325865f46b2SCy Schubert /** header state for the PROXYv2 header (for TCP) */ 326865f46b2SCy Schubert enum { 327865f46b2SCy Schubert /** no header encounter yet */ 328865f46b2SCy Schubert pp2_header_none = 0, 329865f46b2SCy Schubert /** read the static part of the header */ 330865f46b2SCy Schubert pp2_header_init, 331865f46b2SCy Schubert /** read the full header */ 332865f46b2SCy Schubert pp2_header_done 333865f46b2SCy Schubert } pp2_header_state; 334865f46b2SCy Schubert 335b7579f77SDag-Erling Smørgrav /* ---------- Behaviour ----------- */ 336b7579f77SDag-Erling Smørgrav /** if set the connection is NOT closed on delete. */ 337b7579f77SDag-Erling Smørgrav int do_not_close; 338b7579f77SDag-Erling Smørgrav 339b7579f77SDag-Erling Smørgrav /** if set, the connection is closed on error, on timeout, 340b7579f77SDag-Erling Smørgrav and after read/write completes. No callback is done. */ 341b7579f77SDag-Erling Smørgrav int tcp_do_close; 342b7579f77SDag-Erling Smørgrav 343369c6923SCy Schubert /** flag that indicates the stream is both written and read from. */ 344369c6923SCy Schubert int tcp_write_and_read; 345369c6923SCy Schubert 346369c6923SCy Schubert /** byte count for written length over write channel, for when 347369c6923SCy Schubert * tcp_write_and_read is enabled. When tcp_write_and_read is enabled, 348369c6923SCy Schubert * this is the counter for writing, the one for reading is in the 349369c6923SCy Schubert * commpoint.buffer sldns buffer. The counter counts from 0 to 350369c6923SCy Schubert * 2+tcp_write_pkt_len, and includes the tcp length bytes. */ 351369c6923SCy Schubert size_t tcp_write_byte_count; 352369c6923SCy Schubert 353369c6923SCy Schubert /** packet to write currently over the write channel. for when 354369c6923SCy Schubert * tcp_write_and_read is enabled. When tcp_write_and_read is enabled, 355369c6923SCy Schubert * this is the buffer for the written packet, the commpoint.buffer 356369c6923SCy Schubert * sldns buffer is the buffer for the received packet. */ 357369c6923SCy Schubert uint8_t* tcp_write_pkt; 358369c6923SCy Schubert /** length of tcp_write_pkt in bytes */ 359369c6923SCy Schubert size_t tcp_write_pkt_len; 360369c6923SCy Schubert 361369c6923SCy Schubert /** if set try to read another packet again (over connection with 362369c6923SCy Schubert * multiple packets), once set, tries once, then zero again, 363369c6923SCy Schubert * so set it in the packet complete section. 364369c6923SCy Schubert * The pointer itself has to be set before the callback is invoked, 365369c6923SCy Schubert * when you set things up, and continue to exist also after the 366369c6923SCy Schubert * commpoint is closed and deleted in your callback. So that after 367369c6923SCy Schubert * the callback cleans up netevent can see what it has to do. 368369c6923SCy Schubert * Or leave NULL if it is not used at all. */ 369369c6923SCy Schubert int* tcp_more_read_again; 370369c6923SCy Schubert 371369c6923SCy Schubert /** if set try to write another packet (over connection with 372369c6923SCy Schubert * multiple packets), once set, tries once, then zero again, 373369c6923SCy Schubert * so set it in the packet complete section. 374369c6923SCy Schubert * The pointer itself has to be set before the callback is invoked, 375369c6923SCy Schubert * when you set things up, and continue to exist also after the 376369c6923SCy Schubert * commpoint is closed and deleted in your callback. So that after 377369c6923SCy Schubert * the callback cleans up netevent can see what it has to do. 378369c6923SCy Schubert * Or leave NULL if it is not used at all. */ 379369c6923SCy Schubert int* tcp_more_write_again; 380369c6923SCy Schubert 381b7579f77SDag-Erling Smørgrav /** if set, read/write completes: 382b7579f77SDag-Erling Smørgrav read/write state of tcp is toggled. 383b7579f77SDag-Erling Smørgrav buffer reset/bytecount reset. 384b7579f77SDag-Erling Smørgrav this flag cleared. 385b7579f77SDag-Erling Smørgrav So that when that is done the callback is called. */ 386b7579f77SDag-Erling Smørgrav int tcp_do_toggle_rw; 387b7579f77SDag-Erling Smørgrav 388b5663de9SDag-Erling Smørgrav /** timeout in msec for TCP wait times for this connection */ 389b5663de9SDag-Erling Smørgrav int tcp_timeout_msec; 390b5663de9SDag-Erling Smørgrav 3914c75e3aaSDag-Erling Smørgrav /** if set, tcp keepalive is enabled on this connection */ 3924c75e3aaSDag-Erling Smørgrav int tcp_keepalive; 3934c75e3aaSDag-Erling Smørgrav 394b7579f77SDag-Erling Smørgrav /** if set, checks for pending error from nonblocking connect() call.*/ 395b7579f77SDag-Erling Smørgrav int tcp_check_nb_connect; 396b7579f77SDag-Erling Smørgrav 3974c75e3aaSDag-Erling Smørgrav /** if set, check for connection limit on tcp accept. */ 3984c75e3aaSDag-Erling Smørgrav struct tcl_list* tcp_conn_limit; 3994c75e3aaSDag-Erling Smørgrav /** the entry for the connection. */ 4004c75e3aaSDag-Erling Smørgrav struct tcl_addr* tcl_addr; 4014c75e3aaSDag-Erling Smørgrav 402e86b9096SDag-Erling Smørgrav /** the structure to keep track of open requests on this channel */ 403e86b9096SDag-Erling Smørgrav struct tcp_req_info* tcp_req_info; 404e86b9096SDag-Erling Smørgrav 405b5663de9SDag-Erling Smørgrav #ifdef USE_MSG_FASTOPEN 406b5663de9SDag-Erling Smørgrav /** used to track if the sendto() call should be done when using TFO. */ 407b5663de9SDag-Erling Smørgrav int tcp_do_fastopen; 408b5663de9SDag-Erling Smørgrav #endif 409b5663de9SDag-Erling Smørgrav 41065b390aaSDag-Erling Smørgrav #ifdef USE_DNSCRYPT 41165b390aaSDag-Erling Smørgrav /** Is this a dnscrypt channel */ 41265b390aaSDag-Erling Smørgrav int dnscrypt; 41365b390aaSDag-Erling Smørgrav /** encrypted buffer pointer. Either to perthread, or own buffer or NULL */ 41465b390aaSDag-Erling Smørgrav struct sldns_buffer* dnscrypt_buffer; 41565b390aaSDag-Erling Smørgrav #endif 416b7579f77SDag-Erling Smørgrav /** number of queries outstanding on this socket, used by 417b7579f77SDag-Erling Smørgrav * outside network for udp ports */ 418b7579f77SDag-Erling Smørgrav int inuse; 4198f76bb7dSCy Schubert /** the timestamp when the packet was received by the kernel */ 4208f76bb7dSCy Schubert struct timeval recv_tv; 421b7579f77SDag-Erling Smørgrav /** callback when done. 422b7579f77SDag-Erling Smørgrav tcp_accept does not get called back, is NULL then. 423b7579f77SDag-Erling Smørgrav If a timeout happens, callback with timeout=1 is called. 424b7579f77SDag-Erling Smørgrav If an error happens, callback is called with error set 425b7579f77SDag-Erling Smørgrav nonzero. If not NETEVENT_NOERROR, it is an errno value. 426b7579f77SDag-Erling Smørgrav If the connection is closed (by remote end) then the 427b7579f77SDag-Erling Smørgrav callback is called with error set to NETEVENT_CLOSED=-1. 428b7579f77SDag-Erling Smørgrav If a timeout happens on the connection, the error is set to 429b7579f77SDag-Erling Smørgrav NETEVENT_TIMEOUT=-2. 430b7579f77SDag-Erling Smørgrav The reply_info can be copied if the reply needs to happen at a 431b7579f77SDag-Erling Smørgrav later time. It consists of a struct with commpoint and address. 432b7579f77SDag-Erling Smørgrav It can be passed to a msg send routine some time later. 433b7579f77SDag-Erling Smørgrav Note the reply information is temporary and must be copied. 434b7579f77SDag-Erling Smørgrav NULL is passed for_reply info, in cases where error happened. 435b7579f77SDag-Erling Smørgrav 436b7579f77SDag-Erling Smørgrav declare as: 437b7579f77SDag-Erling Smørgrav int my_callback(struct comm_point* c, void* my_arg, int error, 438b7579f77SDag-Erling Smørgrav struct comm_reply *reply_info); 439b7579f77SDag-Erling Smørgrav 440b7579f77SDag-Erling Smørgrav if the routine returns 0, nothing is done. 441b7579f77SDag-Erling Smørgrav Notzero, the buffer will be sent back to client. 442b7579f77SDag-Erling Smørgrav For UDP this is done without changing the commpoint. 443b7579f77SDag-Erling Smørgrav In TCP it sets write state. 444b7579f77SDag-Erling Smørgrav */ 4453005e0a3SDag-Erling Smørgrav comm_point_callback_type* callback; 446b7579f77SDag-Erling Smørgrav /** argument to pass to callback. */ 447b7579f77SDag-Erling Smørgrav void *cb_arg; 448b7579f77SDag-Erling Smørgrav }; 449b7579f77SDag-Erling Smørgrav 450b7579f77SDag-Erling Smørgrav /** 451b7579f77SDag-Erling Smørgrav * Structure only for making timeout events. 452b7579f77SDag-Erling Smørgrav */ 453b7579f77SDag-Erling Smørgrav struct comm_timer { 454e2d15004SDag-Erling Smørgrav /** the internal event stuff (derived) */ 455b7579f77SDag-Erling Smørgrav struct internal_timer* ev_timer; 456b7579f77SDag-Erling Smørgrav 457b7579f77SDag-Erling Smørgrav /** callback function, takes user arg only */ 458b7579f77SDag-Erling Smørgrav void (*callback)(void*); 459b7579f77SDag-Erling Smørgrav 460b7579f77SDag-Erling Smørgrav /** callback user argument */ 461b7579f77SDag-Erling Smørgrav void* cb_arg; 462b7579f77SDag-Erling Smørgrav }; 463b7579f77SDag-Erling Smørgrav 464b7579f77SDag-Erling Smørgrav /** 465b7579f77SDag-Erling Smørgrav * Structure only for signal events. 466b7579f77SDag-Erling Smørgrav */ 467b7579f77SDag-Erling Smørgrav struct comm_signal { 468b7579f77SDag-Erling Smørgrav /** the communication base */ 469b7579f77SDag-Erling Smørgrav struct comm_base* base; 470b7579f77SDag-Erling Smørgrav 471b7579f77SDag-Erling Smørgrav /** the internal event stuff */ 472b7579f77SDag-Erling Smørgrav struct internal_signal* ev_signal; 473b7579f77SDag-Erling Smørgrav 474b7579f77SDag-Erling Smørgrav /** callback function, takes signal number and user arg */ 475b7579f77SDag-Erling Smørgrav void (*callback)(int, void*); 476b7579f77SDag-Erling Smørgrav 477b7579f77SDag-Erling Smørgrav /** callback user argument */ 478b7579f77SDag-Erling Smørgrav void* cb_arg; 479b7579f77SDag-Erling Smørgrav }; 480b7579f77SDag-Erling Smørgrav 481b7579f77SDag-Erling Smørgrav /** 482b7579f77SDag-Erling Smørgrav * Create a new comm base. 483b7579f77SDag-Erling Smørgrav * @param sigs: if true it attempts to create a default loop for 484b7579f77SDag-Erling Smørgrav * signal handling. 485b7579f77SDag-Erling Smørgrav * @return: the new comm base. NULL on error. 486b7579f77SDag-Erling Smørgrav */ 487b7579f77SDag-Erling Smørgrav struct comm_base* comm_base_create(int sigs); 488b7579f77SDag-Erling Smørgrav 489b7579f77SDag-Erling Smørgrav /** 490e2d15004SDag-Erling Smørgrav * Create comm base that uses the given ub_event_base (underlying pluggable 491e2d15004SDag-Erling Smørgrav * event mechanism pointer). 492e2d15004SDag-Erling Smørgrav * @param base: underlying pluggable event base. 49317d15b25SDag-Erling Smørgrav * @return: the new comm base. NULL on error. 49417d15b25SDag-Erling Smørgrav */ 495e2d15004SDag-Erling Smørgrav struct comm_base* comm_base_create_event(struct ub_event_base* base); 49617d15b25SDag-Erling Smørgrav 49717d15b25SDag-Erling Smørgrav /** 49817d15b25SDag-Erling Smørgrav * Delete comm base structure but not the underlying lib event base. 49917d15b25SDag-Erling Smørgrav * All comm points must have been deleted. 50017d15b25SDag-Erling Smørgrav * @param b: the base to delete. 50117d15b25SDag-Erling Smørgrav */ 50217d15b25SDag-Erling Smørgrav void comm_base_delete_no_base(struct comm_base* b); 50317d15b25SDag-Erling Smørgrav 50417d15b25SDag-Erling Smørgrav /** 505b7579f77SDag-Erling Smørgrav * Destroy a comm base. 506b7579f77SDag-Erling Smørgrav * All comm points must have been deleted. 507b7579f77SDag-Erling Smørgrav * @param b: the base to delete. 508b7579f77SDag-Erling Smørgrav */ 509b7579f77SDag-Erling Smørgrav void comm_base_delete(struct comm_base* b); 510b7579f77SDag-Erling Smørgrav 511b7579f77SDag-Erling Smørgrav /** 512b7579f77SDag-Erling Smørgrav * Obtain two pointers. The pointers never change (until base_delete()). 513b7579f77SDag-Erling Smørgrav * The pointers point to time values that are updated regularly. 514b7579f77SDag-Erling Smørgrav * @param b: the communication base that will update the time values. 515b7579f77SDag-Erling Smørgrav * @param tt: pointer to time in seconds is returned. 516b7579f77SDag-Erling Smørgrav * @param tv: pointer to time in microseconds is returned. 517b7579f77SDag-Erling Smørgrav */ 51817d15b25SDag-Erling Smørgrav void comm_base_timept(struct comm_base* b, time_t** tt, struct timeval** tv); 519b7579f77SDag-Erling Smørgrav 520b7579f77SDag-Erling Smørgrav /** 521b7579f77SDag-Erling Smørgrav * Dispatch the comm base events. 522b7579f77SDag-Erling Smørgrav * @param b: the communication to perform. 523b7579f77SDag-Erling Smørgrav */ 524b7579f77SDag-Erling Smørgrav void comm_base_dispatch(struct comm_base* b); 525b7579f77SDag-Erling Smørgrav 526b7579f77SDag-Erling Smørgrav /** 527b7579f77SDag-Erling Smørgrav * Exit from dispatch loop. 528b7579f77SDag-Erling Smørgrav * @param b: the communication base that is in dispatch(). 529b7579f77SDag-Erling Smørgrav */ 530b7579f77SDag-Erling Smørgrav void comm_base_exit(struct comm_base* b); 531b7579f77SDag-Erling Smørgrav 532b7579f77SDag-Erling Smørgrav /** 533b7579f77SDag-Erling Smørgrav * Set the slow_accept mode handlers. You can not provide these if you do 534b7579f77SDag-Erling Smørgrav * not perform accept() calls. 535b7579f77SDag-Erling Smørgrav * @param b: comm base 536b7579f77SDag-Erling Smørgrav * @param stop_accept: function that stops listening to accept fds. 537b7579f77SDag-Erling Smørgrav * @param start_accept: function that resumes listening to accept fds. 538b7579f77SDag-Erling Smørgrav * @param arg: callback arg to pass to the functions. 539b7579f77SDag-Erling Smørgrav */ 540b7579f77SDag-Erling Smørgrav void comm_base_set_slow_accept_handlers(struct comm_base* b, 541b7579f77SDag-Erling Smørgrav void (*stop_accept)(void*), void (*start_accept)(void*), void* arg); 542b7579f77SDag-Erling Smørgrav 543b7579f77SDag-Erling Smørgrav /** 544b7579f77SDag-Erling Smørgrav * Access internal data structure (for util/tube.c on windows) 545b7579f77SDag-Erling Smørgrav * @param b: comm base 546e2d15004SDag-Erling Smørgrav * @return ub_event_base. 547b7579f77SDag-Erling Smørgrav */ 548e2d15004SDag-Erling Smørgrav struct ub_event_base* comm_base_internal(struct comm_base* b); 549b7579f77SDag-Erling Smørgrav 550b7579f77SDag-Erling Smørgrav /** 551b7579f77SDag-Erling Smørgrav * Create an UDP comm point. Calls malloc. 552b7579f77SDag-Erling Smørgrav * setups the structure with the parameters you provide. 553b7579f77SDag-Erling Smørgrav * @param base: in which base to alloc the commpoint. 554b7579f77SDag-Erling Smørgrav * @param fd: file descriptor of open UDP socket. 555b7579f77SDag-Erling Smørgrav * @param buffer: shared buffer by UDP sockets from this thread. 556865f46b2SCy Schubert * @param pp2_enabled: if the comm point will support PROXYv2. 557b7579f77SDag-Erling Smørgrav * @param callback: callback function pointer. 558b7579f77SDag-Erling Smørgrav * @param callback_arg: will be passed to your callback function. 5595469a995SCy Schubert * @param socket: and opened socket properties will be passed to your callback function. 560b7579f77SDag-Erling Smørgrav * @return: returns the allocated communication point. NULL on error. 561b7579f77SDag-Erling Smørgrav * Sets timeout to NULL. Turns off TCP options. 562b7579f77SDag-Erling Smørgrav */ 563b7579f77SDag-Erling Smørgrav struct comm_point* comm_point_create_udp(struct comm_base* base, 564865f46b2SCy Schubert int fd, struct sldns_buffer* buffer, int pp2_enabled, 5655469a995SCy Schubert comm_point_callback_type* callback, void* callback_arg, struct unbound_socket* socket); 566b7579f77SDag-Erling Smørgrav 567b7579f77SDag-Erling Smørgrav /** 568b7579f77SDag-Erling Smørgrav * Create an UDP with ancillary data comm point. Calls malloc. 569b7579f77SDag-Erling Smørgrav * Uses recvmsg instead of recv to get udp message. 570b7579f77SDag-Erling Smørgrav * setups the structure with the parameters you provide. 571b7579f77SDag-Erling Smørgrav * @param base: in which base to alloc the commpoint. 572b7579f77SDag-Erling Smørgrav * @param fd: file descriptor of open UDP socket. 573b7579f77SDag-Erling Smørgrav * @param buffer: shared buffer by UDP sockets from this thread. 574865f46b2SCy Schubert * @param pp2_enabled: if the comm point will support PROXYv2. 575b7579f77SDag-Erling Smørgrav * @param callback: callback function pointer. 576b7579f77SDag-Erling Smørgrav * @param callback_arg: will be passed to your callback function. 5775469a995SCy Schubert * @param socket: and opened socket properties will be passed to your callback function. 578b7579f77SDag-Erling Smørgrav * @return: returns the allocated communication point. NULL on error. 579b7579f77SDag-Erling Smørgrav * Sets timeout to NULL. Turns off TCP options. 580b7579f77SDag-Erling Smørgrav */ 581b7579f77SDag-Erling Smørgrav struct comm_point* comm_point_create_udp_ancil(struct comm_base* base, 582865f46b2SCy Schubert int fd, struct sldns_buffer* buffer, int pp2_enabled, 5835469a995SCy Schubert comm_point_callback_type* callback, void* callback_arg, struct unbound_socket* socket); 584b7579f77SDag-Erling Smørgrav 585b7579f77SDag-Erling Smørgrav /** 586*46d2f618SCy Schubert * Create an UDP comm point for DoQ. Calls malloc. 587*46d2f618SCy Schubert * setups the structure with the parameters you provide. 588*46d2f618SCy Schubert * @param base: in which base to alloc the commpoint. 589*46d2f618SCy Schubert * @param fd : file descriptor of open UDP socket. 590*46d2f618SCy Schubert * @param buffer: shared buffer by UDP sockets from this thread. 591*46d2f618SCy Schubert * @param callback: callback function pointer. 592*46d2f618SCy Schubert * @param callback_arg: will be passed to your callback function. 593*46d2f618SCy Schubert * @param socket: and opened socket properties will be passed to your callback function. 594*46d2f618SCy Schubert * @param table: the doq connection table for the host. 595*46d2f618SCy Schubert * @param rnd: random generator to use. 596*46d2f618SCy Schubert * @param ssl_service_key: the ssl service key file. 597*46d2f618SCy Schubert * @param ssl_service_pem: the ssl service pem file. 598*46d2f618SCy Schubert * @param cfg: config file struct. 599*46d2f618SCy Schubert * @return: returns the allocated communication point. NULL on error. 600*46d2f618SCy Schubert * Sets timeout to NULL. Turns off TCP options. 601*46d2f618SCy Schubert */ 602*46d2f618SCy Schubert struct comm_point* comm_point_create_doq(struct comm_base* base, 603*46d2f618SCy Schubert int fd, struct sldns_buffer* buffer, 604*46d2f618SCy Schubert comm_point_callback_type* callback, void* callback_arg, 605*46d2f618SCy Schubert struct unbound_socket* socket, struct doq_table* table, 606*46d2f618SCy Schubert struct ub_randstate* rnd, const char* ssl_service_key, 607*46d2f618SCy Schubert const char* ssl_service_pem, struct config_file* cfg); 608*46d2f618SCy Schubert 609*46d2f618SCy Schubert /** 610b7579f77SDag-Erling Smørgrav * Create a TCP listener comm point. Calls malloc. 611b7579f77SDag-Erling Smørgrav * Setups the structure with the parameters you provide. 612b7579f77SDag-Erling Smørgrav * Also Creates TCP Handlers, pre allocated for you. 613b7579f77SDag-Erling Smørgrav * Uses the parameters you provide. 614b7579f77SDag-Erling Smørgrav * @param base: in which base to alloc the commpoint. 615b7579f77SDag-Erling Smørgrav * @param fd: file descriptor of open TCP socket set to listen nonblocking. 616b7579f77SDag-Erling Smørgrav * @param num: becomes max_tcp_count, the routine allocates that 617b7579f77SDag-Erling Smørgrav * many tcp handler commpoints. 6184c75e3aaSDag-Erling Smørgrav * @param idle_timeout: TCP idle timeout in ms. 619c0caa2e2SCy Schubert * @param harden_large_queries: whether query size should be limited. 620c0caa2e2SCy Schubert * @param http_max_streams: maximum number of HTTP/2 streams per connection. 621c0caa2e2SCy Schubert * @param http_endpoint: HTTP endpoint to service queries on 6224c75e3aaSDag-Erling Smørgrav * @param tcp_conn_limit: TCP connection limit info. 623b7579f77SDag-Erling Smørgrav * @param bufsize: size of buffer to create for handlers. 624e86b9096SDag-Erling Smørgrav * @param spoolbuf: shared spool buffer for tcp_req_info structures. 625e86b9096SDag-Erling Smørgrav * or NULL to not create those structures in the tcp handlers. 626c0caa2e2SCy Schubert * @param port_type: the type of port we are creating a TCP listener for. Used 627c0caa2e2SCy Schubert * to select handler type to use. 628865f46b2SCy Schubert * @param pp2_enabled: if the comm point will support PROXYv2. 629b7579f77SDag-Erling Smørgrav * @param callback: callback function pointer for TCP handlers. 630b7579f77SDag-Erling Smørgrav * @param callback_arg: will be passed to your callback function. 6315469a995SCy Schubert * @param socket: and opened socket properties will be passed to your callback function. 632b7579f77SDag-Erling Smørgrav * @return: returns the TCP listener commpoint. You can find the 633b7579f77SDag-Erling Smørgrav * TCP handlers in the array inside the listener commpoint. 634b7579f77SDag-Erling Smørgrav * returns NULL on error. 635b7579f77SDag-Erling Smørgrav * Inits timeout to NULL. All handlers are on the free list. 636b7579f77SDag-Erling Smørgrav */ 637b7579f77SDag-Erling Smørgrav struct comm_point* comm_point_create_tcp(struct comm_base* base, 638c0caa2e2SCy Schubert int fd, int num, int idle_timeout, int harden_large_queries, 639c0caa2e2SCy Schubert uint32_t http_max_streams, char* http_endpoint, 640c0caa2e2SCy Schubert struct tcl_list* tcp_conn_limit, 641e86b9096SDag-Erling Smørgrav size_t bufsize, struct sldns_buffer* spoolbuf, 642865f46b2SCy Schubert enum listen_type port_type, int pp2_enabled, 6435469a995SCy Schubert comm_point_callback_type* callback, void* callback_arg, struct unbound_socket* socket); 644b7579f77SDag-Erling Smørgrav 645b7579f77SDag-Erling Smørgrav /** 646b7579f77SDag-Erling Smørgrav * Create an outgoing TCP commpoint. No file descriptor is opened, left at -1. 647b7579f77SDag-Erling Smørgrav * @param base: in which base to alloc the commpoint. 648b7579f77SDag-Erling Smørgrav * @param bufsize: size of buffer to create for handlers. 649b7579f77SDag-Erling Smørgrav * @param callback: callback function pointer for the handler. 650b7579f77SDag-Erling Smørgrav * @param callback_arg: will be passed to your callback function. 651b7579f77SDag-Erling Smørgrav * @return: the commpoint or NULL on error. 652b7579f77SDag-Erling Smørgrav */ 653b7579f77SDag-Erling Smørgrav struct comm_point* comm_point_create_tcp_out(struct comm_base* base, 6543005e0a3SDag-Erling Smørgrav size_t bufsize, comm_point_callback_type* callback, void* callback_arg); 655b7579f77SDag-Erling Smørgrav 656b7579f77SDag-Erling Smørgrav /** 65757bddd21SDag-Erling Smørgrav * Create an outgoing HTTP commpoint. No file descriptor is opened, left at -1. 65857bddd21SDag-Erling Smørgrav * @param base: in which base to alloc the commpoint. 65957bddd21SDag-Erling Smørgrav * @param bufsize: size of buffer to create for handlers. 66057bddd21SDag-Erling Smørgrav * @param callback: callback function pointer for the handler. 66157bddd21SDag-Erling Smørgrav * @param callback_arg: will be passed to your callback function. 66257bddd21SDag-Erling Smørgrav * @param temp: sldns buffer, shared between other http_out commpoints, for 66357bddd21SDag-Erling Smørgrav * temporary data when performing callbacks. 66457bddd21SDag-Erling Smørgrav * @return: the commpoint or NULL on error. 66557bddd21SDag-Erling Smørgrav */ 66657bddd21SDag-Erling Smørgrav struct comm_point* comm_point_create_http_out(struct comm_base* base, 66757bddd21SDag-Erling Smørgrav size_t bufsize, comm_point_callback_type* callback, 66857bddd21SDag-Erling Smørgrav void* callback_arg, struct sldns_buffer* temp); 66957bddd21SDag-Erling Smørgrav 67057bddd21SDag-Erling Smørgrav /** 671b7579f77SDag-Erling Smørgrav * Create commpoint to listen to a local domain file descriptor. 672b7579f77SDag-Erling Smørgrav * @param base: in which base to alloc the commpoint. 673b7579f77SDag-Erling Smørgrav * @param fd: file descriptor of open AF_UNIX socket set to listen nonblocking. 674b7579f77SDag-Erling Smørgrav * @param bufsize: size of buffer to create for handlers. 675b7579f77SDag-Erling Smørgrav * @param callback: callback function pointer for the handler. 676b7579f77SDag-Erling Smørgrav * @param callback_arg: will be passed to your callback function. 677b7579f77SDag-Erling Smørgrav * @return: the commpoint or NULL on error. 678b7579f77SDag-Erling Smørgrav */ 679b7579f77SDag-Erling Smørgrav struct comm_point* comm_point_create_local(struct comm_base* base, 680b7579f77SDag-Erling Smørgrav int fd, size_t bufsize, 6813005e0a3SDag-Erling Smørgrav comm_point_callback_type* callback, void* callback_arg); 682b7579f77SDag-Erling Smørgrav 683b7579f77SDag-Erling Smørgrav /** 684b7579f77SDag-Erling Smørgrav * Create commpoint to listen to a local domain pipe descriptor. 685b7579f77SDag-Erling Smørgrav * @param base: in which base to alloc the commpoint. 686b7579f77SDag-Erling Smørgrav * @param fd: file descriptor. 687b7579f77SDag-Erling Smørgrav * @param writing: true if you want to listen to writes, false for reads. 688b7579f77SDag-Erling Smørgrav * @param callback: callback function pointer for the handler. 689b7579f77SDag-Erling Smørgrav * @param callback_arg: will be passed to your callback function. 690b7579f77SDag-Erling Smørgrav * @return: the commpoint or NULL on error. 691b7579f77SDag-Erling Smørgrav */ 692b7579f77SDag-Erling Smørgrav struct comm_point* comm_point_create_raw(struct comm_base* base, 693b7579f77SDag-Erling Smørgrav int fd, int writing, 6943005e0a3SDag-Erling Smørgrav comm_point_callback_type* callback, void* callback_arg); 695b7579f77SDag-Erling Smørgrav 696b7579f77SDag-Erling Smørgrav /** 697b7579f77SDag-Erling Smørgrav * Close a comm point fd. 698b7579f77SDag-Erling Smørgrav * @param c: comm point to close. 699b7579f77SDag-Erling Smørgrav */ 700b7579f77SDag-Erling Smørgrav void comm_point_close(struct comm_point* c); 701b7579f77SDag-Erling Smørgrav 702b7579f77SDag-Erling Smørgrav /** 703b7579f77SDag-Erling Smørgrav * Close and deallocate (free) the comm point. If the comm point is 704b7579f77SDag-Erling Smørgrav * a tcp-accept point, also its tcp-handler points are deleted. 705b7579f77SDag-Erling Smørgrav * @param c: comm point to delete. 706b7579f77SDag-Erling Smørgrav */ 707b7579f77SDag-Erling Smørgrav void comm_point_delete(struct comm_point* c); 708b7579f77SDag-Erling Smørgrav 709b7579f77SDag-Erling Smørgrav /** 710b7579f77SDag-Erling Smørgrav * Send reply. Put message into commpoint buffer. 711b7579f77SDag-Erling Smørgrav * @param repinfo: The reply info copied from a commpoint callback call. 712b7579f77SDag-Erling Smørgrav */ 713b7579f77SDag-Erling Smørgrav void comm_point_send_reply(struct comm_reply* repinfo); 714b7579f77SDag-Erling Smørgrav 715b7579f77SDag-Erling Smørgrav /** 716b7579f77SDag-Erling Smørgrav * Drop reply. Cleans up. 717b7579f77SDag-Erling Smørgrav * @param repinfo: The reply info copied from a commpoint callback call. 718b7579f77SDag-Erling Smørgrav */ 719b7579f77SDag-Erling Smørgrav void comm_point_drop_reply(struct comm_reply* repinfo); 720b7579f77SDag-Erling Smørgrav 721b7579f77SDag-Erling Smørgrav /** 722b7579f77SDag-Erling Smørgrav * Send an udp message over a commpoint. 723b7579f77SDag-Erling Smørgrav * @param c: commpoint to send it from. 724b7579f77SDag-Erling Smørgrav * @param packet: what to send. 725369c6923SCy Schubert * @param addr: where to send it to. If NULL, send is performed, 726369c6923SCy Schubert * for connected sockets, to the connected address. 727b7579f77SDag-Erling Smørgrav * @param addrlen: length of addr. 7287341cb0cSXin LI * @param is_connected: if the UDP socket is connect()ed. 729b7579f77SDag-Erling Smørgrav * @return: false on a failure. 730b7579f77SDag-Erling Smørgrav */ 73117d15b25SDag-Erling Smørgrav int comm_point_send_udp_msg(struct comm_point* c, struct sldns_buffer* packet, 7327341cb0cSXin LI struct sockaddr* addr, socklen_t addrlen,int is_connected); 733b7579f77SDag-Erling Smørgrav 734b7579f77SDag-Erling Smørgrav /** 735b7579f77SDag-Erling Smørgrav * Stop listening for input on the commpoint. No callbacks will happen. 736b7579f77SDag-Erling Smørgrav * @param c: commpoint to disable. The fd is not closed. 737b7579f77SDag-Erling Smørgrav */ 738b7579f77SDag-Erling Smørgrav void comm_point_stop_listening(struct comm_point* c); 739b7579f77SDag-Erling Smørgrav 740b7579f77SDag-Erling Smørgrav /** 741b7579f77SDag-Erling Smørgrav * Start listening again for input on the comm point. 742b7579f77SDag-Erling Smørgrav * @param c: commpoint to enable again. 743b7579f77SDag-Erling Smørgrav * @param newfd: new fd, or -1 to leave fd be. 744b5663de9SDag-Erling Smørgrav * @param msec: timeout in milliseconds, or -1 for no (change to the) timeout. 745b5663de9SDag-Erling Smørgrav * So seconds*1000. 746b7579f77SDag-Erling Smørgrav */ 747b5663de9SDag-Erling Smørgrav void comm_point_start_listening(struct comm_point* c, int newfd, int msec); 748b7579f77SDag-Erling Smørgrav 749b7579f77SDag-Erling Smørgrav /** 750b7579f77SDag-Erling Smørgrav * Stop listening and start listening again for reading or writing. 751b7579f77SDag-Erling Smørgrav * @param c: commpoint 752b7579f77SDag-Erling Smørgrav * @param rd: if true, listens for reading. 753b7579f77SDag-Erling Smørgrav * @param wr: if true, listens for writing. 754b7579f77SDag-Erling Smørgrav */ 755b7579f77SDag-Erling Smørgrav void comm_point_listen_for_rw(struct comm_point* c, int rd, int wr); 756b7579f77SDag-Erling Smørgrav 757b7579f77SDag-Erling Smørgrav /** 758f44e67d1SCy Schubert * For TCP handlers that use c->tcp_timeout_msec, this routine adjusts 759f44e67d1SCy Schubert * it with the minimum. Otherwise, a 0 value advertised without the 760f44e67d1SCy Schubert * minimum applied moves to a 0 in comm_point_start_listening and that 761f44e67d1SCy Schubert * routine treats it as no timeout, listen forever, which is not wanted. 762f44e67d1SCy Schubert * @param c: comm point to use the tcp_timeout_msec of. 763f44e67d1SCy Schubert * @return adjusted tcp_timeout_msec value with the minimum if smaller. 764f44e67d1SCy Schubert */ 765f44e67d1SCy Schubert int adjusted_tcp_timeout(struct comm_point* c); 766f44e67d1SCy Schubert 767f44e67d1SCy Schubert /** 768b7579f77SDag-Erling Smørgrav * Get size of memory used by comm point. 769b7579f77SDag-Erling Smørgrav * For TCP handlers this includes subhandlers. 770b7579f77SDag-Erling Smørgrav * For UDP handlers, this does not include the (shared) UDP buffer. 771b7579f77SDag-Erling Smørgrav * @param c: commpoint. 772b7579f77SDag-Erling Smørgrav * @return size in bytes. 773b7579f77SDag-Erling Smørgrav */ 774b7579f77SDag-Erling Smørgrav size_t comm_point_get_mem(struct comm_point* c); 775b7579f77SDag-Erling Smørgrav 776b7579f77SDag-Erling Smørgrav /** 777b7579f77SDag-Erling Smørgrav * create timer. Not active upon creation. 778b7579f77SDag-Erling Smørgrav * @param base: event handling base. 779b7579f77SDag-Erling Smørgrav * @param cb: callback function: void myfunc(void* myarg); 780b7579f77SDag-Erling Smørgrav * @param cb_arg: user callback argument. 781b7579f77SDag-Erling Smørgrav * @return: the new timer or NULL on error. 782b7579f77SDag-Erling Smørgrav */ 783b7579f77SDag-Erling Smørgrav struct comm_timer* comm_timer_create(struct comm_base* base, 784b7579f77SDag-Erling Smørgrav void (*cb)(void*), void* cb_arg); 785b7579f77SDag-Erling Smørgrav 786b7579f77SDag-Erling Smørgrav /** 787b7579f77SDag-Erling Smørgrav * disable timer. Stops callbacks from happening. 788b7579f77SDag-Erling Smørgrav * @param timer: to disable. 789b7579f77SDag-Erling Smørgrav */ 790b7579f77SDag-Erling Smørgrav void comm_timer_disable(struct comm_timer* timer); 791b7579f77SDag-Erling Smørgrav 792b7579f77SDag-Erling Smørgrav /** 793b7579f77SDag-Erling Smørgrav * reset timevalue for timer. 794b7579f77SDag-Erling Smørgrav * @param timer: timer to (re)set. 795b7579f77SDag-Erling Smørgrav * @param tv: when the timer should activate. if NULL timer is disabled. 796b7579f77SDag-Erling Smørgrav */ 797b7579f77SDag-Erling Smørgrav void comm_timer_set(struct comm_timer* timer, struct timeval* tv); 798b7579f77SDag-Erling Smørgrav 799b7579f77SDag-Erling Smørgrav /** 800b7579f77SDag-Erling Smørgrav * delete timer. 801b7579f77SDag-Erling Smørgrav * @param timer: to delete. 802b7579f77SDag-Erling Smørgrav */ 803b7579f77SDag-Erling Smørgrav void comm_timer_delete(struct comm_timer* timer); 804b7579f77SDag-Erling Smørgrav 805b7579f77SDag-Erling Smørgrav /** 806b7579f77SDag-Erling Smørgrav * see if timeout has been set to a value. 807b7579f77SDag-Erling Smørgrav * @param timer: the timer to examine. 808b7579f77SDag-Erling Smørgrav * @return: false if disabled or not set. 809b7579f77SDag-Erling Smørgrav */ 810b7579f77SDag-Erling Smørgrav int comm_timer_is_set(struct comm_timer* timer); 811b7579f77SDag-Erling Smørgrav 812b7579f77SDag-Erling Smørgrav /** 813b7579f77SDag-Erling Smørgrav * Get size of memory used by comm timer. 814b7579f77SDag-Erling Smørgrav * @param timer: the timer to examine. 815b7579f77SDag-Erling Smørgrav * @return size in bytes. 816b7579f77SDag-Erling Smørgrav */ 817b7579f77SDag-Erling Smørgrav size_t comm_timer_get_mem(struct comm_timer* timer); 818b7579f77SDag-Erling Smørgrav 819b7579f77SDag-Erling Smørgrav /** 820b7579f77SDag-Erling Smørgrav * Create a signal handler. Call signal_bind() later to bind to a signal. 821b7579f77SDag-Erling Smørgrav * @param base: communication base to use. 822b7579f77SDag-Erling Smørgrav * @param callback: called when signal is caught. 823b7579f77SDag-Erling Smørgrav * @param cb_arg: user argument to callback 824b7579f77SDag-Erling Smørgrav * @return: the signal struct or NULL on error. 825b7579f77SDag-Erling Smørgrav */ 826b7579f77SDag-Erling Smørgrav struct comm_signal* comm_signal_create(struct comm_base* base, 827b7579f77SDag-Erling Smørgrav void (*callback)(int, void*), void* cb_arg); 828b7579f77SDag-Erling Smørgrav 829b7579f77SDag-Erling Smørgrav /** 83024e36522SCy Schubert * Bind signal struct to catch a signal. A single comm_signal can be bound 831b7579f77SDag-Erling Smørgrav * to multiple signals, calling comm_signal_bind multiple times. 832b7579f77SDag-Erling Smørgrav * @param comsig: the communication point, with callback information. 833b7579f77SDag-Erling Smørgrav * @param sig: signal number. 834b7579f77SDag-Erling Smørgrav * @return: true on success. false on error. 835b7579f77SDag-Erling Smørgrav */ 836b7579f77SDag-Erling Smørgrav int comm_signal_bind(struct comm_signal* comsig, int sig); 837b7579f77SDag-Erling Smørgrav 838b7579f77SDag-Erling Smørgrav /** 839b7579f77SDag-Erling Smørgrav * Delete the signal communication point. 840b7579f77SDag-Erling Smørgrav * @param comsig: to delete. 841b7579f77SDag-Erling Smørgrav */ 842b7579f77SDag-Erling Smørgrav void comm_signal_delete(struct comm_signal* comsig); 843b7579f77SDag-Erling Smørgrav 844b7579f77SDag-Erling Smørgrav /** 845b7579f77SDag-Erling Smørgrav * perform accept(2) with error checking. 846b7579f77SDag-Erling Smørgrav * @param c: commpoint with accept fd. 847b7579f77SDag-Erling Smørgrav * @param addr: remote end returned here. 848b7579f77SDag-Erling Smørgrav * @param addrlen: length of remote end returned here. 849b7579f77SDag-Erling Smørgrav * @return new fd, or -1 on error. 850b7579f77SDag-Erling Smørgrav * if -1, error message has been printed if necessary, simply drop 851b7579f77SDag-Erling Smørgrav * out of the reading handler. 852b7579f77SDag-Erling Smørgrav */ 853b7579f77SDag-Erling Smørgrav int comm_point_perform_accept(struct comm_point* c, 854b7579f77SDag-Erling Smørgrav struct sockaddr_storage* addr, socklen_t* addrlen); 855b7579f77SDag-Erling Smørgrav 856b7579f77SDag-Erling Smørgrav /**** internal routines ****/ 857b7579f77SDag-Erling Smørgrav 858b7579f77SDag-Erling Smørgrav /** 859b7579f77SDag-Erling Smørgrav * This routine is published for checks and tests, and is only used internally. 860b7579f77SDag-Erling Smørgrav * handle libevent callback for udp comm point. 861b7579f77SDag-Erling Smørgrav * @param fd: file descriptor. 862b7579f77SDag-Erling Smørgrav * @param event: event bits from libevent: 863b7579f77SDag-Erling Smørgrav * EV_READ, EV_WRITE, EV_SIGNAL, EV_TIMEOUT. 864b7579f77SDag-Erling Smørgrav * @param arg: the comm_point structure. 865b7579f77SDag-Erling Smørgrav */ 866b7579f77SDag-Erling Smørgrav void comm_point_udp_callback(int fd, short event, void* arg); 867b7579f77SDag-Erling Smørgrav 868b7579f77SDag-Erling Smørgrav /** 869b7579f77SDag-Erling Smørgrav * This routine is published for checks and tests, and is only used internally. 870b7579f77SDag-Erling Smørgrav * handle libevent callback for udp ancillary data comm point. 871b7579f77SDag-Erling Smørgrav * @param fd: file descriptor. 872b7579f77SDag-Erling Smørgrav * @param event: event bits from libevent: 873b7579f77SDag-Erling Smørgrav * EV_READ, EV_WRITE, EV_SIGNAL, EV_TIMEOUT. 874b7579f77SDag-Erling Smørgrav * @param arg: the comm_point structure. 875b7579f77SDag-Erling Smørgrav */ 876b7579f77SDag-Erling Smørgrav void comm_point_udp_ancil_callback(int fd, short event, void* arg); 877b7579f77SDag-Erling Smørgrav 878b7579f77SDag-Erling Smørgrav /** 879b7579f77SDag-Erling Smørgrav * This routine is published for checks and tests, and is only used internally. 880*46d2f618SCy Schubert * handle libevent callback for doq comm point. 881*46d2f618SCy Schubert * @param fd: file descriptor. 882*46d2f618SCy Schubert * @param event: event bits from libevent: 883*46d2f618SCy Schubert * EV_READ, EV_WRITE, EV_SIGNAL, EV_TIMEOUT. 884*46d2f618SCy Schubert * @param arg: the comm_point structure. 885*46d2f618SCy Schubert */ 886*46d2f618SCy Schubert void comm_point_doq_callback(int fd, short event, void* arg); 887*46d2f618SCy Schubert 888*46d2f618SCy Schubert /** 889*46d2f618SCy Schubert * This routine is published for checks and tests, and is only used internally. 890b7579f77SDag-Erling Smørgrav * handle libevent callback for tcp accept comm point 891b7579f77SDag-Erling Smørgrav * @param fd: file descriptor. 892b7579f77SDag-Erling Smørgrav * @param event: event bits from libevent: 893b7579f77SDag-Erling Smørgrav * EV_READ, EV_WRITE, EV_SIGNAL, EV_TIMEOUT. 894b7579f77SDag-Erling Smørgrav * @param arg: the comm_point structure. 895b7579f77SDag-Erling Smørgrav */ 896b7579f77SDag-Erling Smørgrav void comm_point_tcp_accept_callback(int fd, short event, void* arg); 897b7579f77SDag-Erling Smørgrav 898b7579f77SDag-Erling Smørgrav /** 899b7579f77SDag-Erling Smørgrav * This routine is published for checks and tests, and is only used internally. 900b7579f77SDag-Erling Smørgrav * handle libevent callback for tcp data comm point 901b7579f77SDag-Erling Smørgrav * @param fd: file descriptor. 902b7579f77SDag-Erling Smørgrav * @param event: event bits from libevent: 903b7579f77SDag-Erling Smørgrav * EV_READ, EV_WRITE, EV_SIGNAL, EV_TIMEOUT. 904b7579f77SDag-Erling Smørgrav * @param arg: the comm_point structure. 905b7579f77SDag-Erling Smørgrav */ 906b7579f77SDag-Erling Smørgrav void comm_point_tcp_handle_callback(int fd, short event, void* arg); 907b7579f77SDag-Erling Smørgrav 908b7579f77SDag-Erling Smørgrav /** 909b7579f77SDag-Erling Smørgrav * This routine is published for checks and tests, and is only used internally. 91057bddd21SDag-Erling Smørgrav * handle libevent callback for tcp data comm point 91157bddd21SDag-Erling Smørgrav * @param fd: file descriptor. 91257bddd21SDag-Erling Smørgrav * @param event: event bits from libevent: 91357bddd21SDag-Erling Smørgrav * EV_READ, EV_WRITE, EV_SIGNAL, EV_TIMEOUT. 91457bddd21SDag-Erling Smørgrav * @param arg: the comm_point structure. 91557bddd21SDag-Erling Smørgrav */ 91657bddd21SDag-Erling Smørgrav void comm_point_http_handle_callback(int fd, short event, void* arg); 91757bddd21SDag-Erling Smørgrav 91857bddd21SDag-Erling Smørgrav /** 919c0caa2e2SCy Schubert * HTTP2 session. HTTP2 related info per comm point. 920c0caa2e2SCy Schubert */ 921c0caa2e2SCy Schubert struct http2_session { 922c0caa2e2SCy Schubert /** first item in list of streams */ 923c0caa2e2SCy Schubert struct http2_stream* first_stream; 924c0caa2e2SCy Schubert #ifdef HAVE_NGHTTP2 925c0caa2e2SCy Schubert /** nghttp2 session */ 926c0caa2e2SCy Schubert nghttp2_session *session; 927c0caa2e2SCy Schubert /** store nghttp2 callbacks for easy reuse */ 928c0caa2e2SCy Schubert nghttp2_session_callbacks* callbacks; 929c0caa2e2SCy Schubert #endif 930c0caa2e2SCy Schubert /** comm point containing buffer used to build answer in worker or 931c0caa2e2SCy Schubert * module */ 932c0caa2e2SCy Schubert struct comm_point* c; 933c0caa2e2SCy Schubert /** session is instructed to get dropped (comm port will be closed) */ 934c0caa2e2SCy Schubert int is_drop; 935c0caa2e2SCy Schubert /** postpone dropping the session, can be used to prevent dropping 936c0caa2e2SCy Schubert * while being in a callback */ 937c0caa2e2SCy Schubert int postpone_drop; 938c0caa2e2SCy Schubert }; 939c0caa2e2SCy Schubert 940c0caa2e2SCy Schubert /** enum of HTTP status */ 941c0caa2e2SCy Schubert enum http_status { 942c0caa2e2SCy Schubert HTTP_STATUS_OK = 200, 943c0caa2e2SCy Schubert HTTP_STATUS_BAD_REQUEST = 400, 944c0caa2e2SCy Schubert HTTP_STATUS_NOT_FOUND = 404, 945c0caa2e2SCy Schubert HTTP_STATUS_PAYLOAD_TOO_LARGE = 413, 946c0caa2e2SCy Schubert HTTP_STATUS_URI_TOO_LONG = 414, 947c0caa2e2SCy Schubert HTTP_STATUS_UNSUPPORTED_MEDIA_TYPE = 415, 948c0caa2e2SCy Schubert HTTP_STATUS_NOT_IMPLEMENTED = 501 949c0caa2e2SCy Schubert }; 950c0caa2e2SCy Schubert 951c0caa2e2SCy Schubert /** 952c0caa2e2SCy Schubert * HTTP stream. Part of list of HTTP2 streams per session. 953c0caa2e2SCy Schubert */ 954c0caa2e2SCy Schubert struct http2_stream { 955c0caa2e2SCy Schubert /** next stream in list per session */ 956c0caa2e2SCy Schubert struct http2_stream* next; 957c0caa2e2SCy Schubert /** previous stream in list per session */ 958c0caa2e2SCy Schubert struct http2_stream* prev; 959c0caa2e2SCy Schubert /** HTTP2 stream ID is an unsigned 31-bit integer */ 960c0caa2e2SCy Schubert int32_t stream_id; 961c0caa2e2SCy Schubert /** HTTP method used for this stream */ 962c0caa2e2SCy Schubert enum { 963c0caa2e2SCy Schubert HTTP_METHOD_POST = 1, 964c0caa2e2SCy Schubert HTTP_METHOD_GET, 965c0caa2e2SCy Schubert HTTP_METHOD_UNSUPPORTED 966c0caa2e2SCy Schubert } http_method; 967c0caa2e2SCy Schubert /** message contains invalid content type */ 968c0caa2e2SCy Schubert int invalid_content_type; 969c0caa2e2SCy Schubert /** message body content type */ 970c0caa2e2SCy Schubert size_t content_length; 971c0caa2e2SCy Schubert /** HTTP response status */ 972c0caa2e2SCy Schubert enum http_status status; 973c0caa2e2SCy Schubert /** request for non existing endpoint */ 974c0caa2e2SCy Schubert int invalid_endpoint; 975c0caa2e2SCy Schubert /** query in request is too large */ 976c0caa2e2SCy Schubert int query_too_large; 977c0caa2e2SCy Schubert /** buffer to store query into. Can't use session shared buffer as query 978c0caa2e2SCy Schubert * can arrive in parts, intertwined with frames for other queries. */ 979c0caa2e2SCy Schubert struct sldns_buffer* qbuffer; 980c0caa2e2SCy Schubert /** buffer to store response into. Can't use shared buffer as a next 981c0caa2e2SCy Schubert * query read callback can overwrite it before it is send out. */ 982c0caa2e2SCy Schubert struct sldns_buffer* rbuffer; 983c0caa2e2SCy Schubert /** mesh area containing mesh state */ 984c0caa2e2SCy Schubert struct mesh_area* mesh; 985c0caa2e2SCy Schubert /** mesh state for query. Used to remove mesh reply before closing 986c0caa2e2SCy Schubert * stream. */ 987c0caa2e2SCy Schubert struct mesh_state* mesh_state; 988c0caa2e2SCy Schubert }; 989c0caa2e2SCy Schubert 990c0caa2e2SCy Schubert #ifdef HAVE_NGHTTP2 991c0caa2e2SCy Schubert /** nghttp2 receive cb. Read from SSL connection into nghttp2 buffer */ 992c0caa2e2SCy Schubert ssize_t http2_recv_cb(nghttp2_session* session, uint8_t* buf, 993c0caa2e2SCy Schubert size_t len, int flags, void* cb_arg); 994c0caa2e2SCy Schubert /** nghttp2 send callback. Send from nghttp2 buffer to ssl socket */ 995c0caa2e2SCy Schubert ssize_t http2_send_cb(nghttp2_session* session, const uint8_t* buf, 996c0caa2e2SCy Schubert size_t len, int flags, void* cb_arg); 997c0caa2e2SCy Schubert /** nghttp2 callback on closing stream */ 998c0caa2e2SCy Schubert int http2_stream_close_cb(nghttp2_session* session, int32_t stream_id, 999c0caa2e2SCy Schubert uint32_t error_code, void* cb_arg); 1000c0caa2e2SCy Schubert #endif 1001c0caa2e2SCy Schubert 1002c0caa2e2SCy Schubert /** 1003c0caa2e2SCy Schubert * Create new http2 stream 1004c0caa2e2SCy Schubert * @param stream_id: ID for stream to create. 1005c0caa2e2SCy Schubert * @return malloc'ed stream, NULL on error 1006c0caa2e2SCy Schubert */ 1007c0caa2e2SCy Schubert struct http2_stream* http2_stream_create(int32_t stream_id); 1008c0caa2e2SCy Schubert 1009c0caa2e2SCy Schubert /** 1010c0caa2e2SCy Schubert * Add new stream to session linked list 1011c0caa2e2SCy Schubert * @param h2_session: http2 session to add stream to 1012c0caa2e2SCy Schubert * @param h2_stream: stream to add to session list 1013c0caa2e2SCy Schubert */ 1014c0caa2e2SCy Schubert void http2_session_add_stream(struct http2_session* h2_session, 1015c0caa2e2SCy Schubert struct http2_stream* h2_stream); 1016c0caa2e2SCy Schubert 1017c0caa2e2SCy Schubert /** Add mesh state to stream. To be able to remove mesh reply on stream closure 1018c0caa2e2SCy Schubert */ 1019c0caa2e2SCy Schubert void http2_stream_add_meshstate(struct http2_stream* h2_stream, 1020c0caa2e2SCy Schubert struct mesh_area* mesh, struct mesh_state* m); 1021c0caa2e2SCy Schubert 102256850988SCy Schubert /** Remove mesh state from stream. When the mesh state has been removed. */ 102356850988SCy Schubert void http2_stream_remove_mesh_state(struct http2_stream* h2_stream); 102456850988SCy Schubert 1025c0caa2e2SCy Schubert /** 1026*46d2f618SCy Schubert * DoQ socket address storage for IP4 or IP6 address. Smaller than 1027*46d2f618SCy Schubert * the sockaddr_storage because not with af_unix pathnames. 1028*46d2f618SCy Schubert */ 1029*46d2f618SCy Schubert struct doq_addr_storage { 1030*46d2f618SCy Schubert union { 1031*46d2f618SCy Schubert struct sockaddr_in in; 1032*46d2f618SCy Schubert #ifdef AF_INET6 1033*46d2f618SCy Schubert struct sockaddr_in6 in6; 1034*46d2f618SCy Schubert #endif 1035*46d2f618SCy Schubert } sockaddr; 1036*46d2f618SCy Schubert }; 1037*46d2f618SCy Schubert 1038*46d2f618SCy Schubert /** 1039*46d2f618SCy Schubert * The DoQ server socket information, for DNS over QUIC. 1040*46d2f618SCy Schubert */ 1041*46d2f618SCy Schubert struct doq_server_socket { 1042*46d2f618SCy Schubert /** the doq connection table */ 1043*46d2f618SCy Schubert struct doq_table* table; 1044*46d2f618SCy Schubert /** random generator */ 1045*46d2f618SCy Schubert struct ub_randstate* rnd; 1046*46d2f618SCy Schubert /** if address validation is enabled */ 1047*46d2f618SCy Schubert uint8_t validate_addr; 1048*46d2f618SCy Schubert /** the ssl service key file */ 1049*46d2f618SCy Schubert char* ssl_service_key; 1050*46d2f618SCy Schubert /** the ssl service pem file */ 1051*46d2f618SCy Schubert char* ssl_service_pem; 1052*46d2f618SCy Schubert /** the ssl verify pem file */ 1053*46d2f618SCy Schubert char* ssl_verify_pem; 1054*46d2f618SCy Schubert /** the server scid length */ 1055*46d2f618SCy Schubert int sv_scidlen; 1056*46d2f618SCy Schubert /** the idle timeout in nanoseconds */ 1057*46d2f618SCy Schubert uint64_t idle_timeout; 1058*46d2f618SCy Schubert /** the static secret for the server */ 1059*46d2f618SCy Schubert uint8_t* static_secret; 1060*46d2f618SCy Schubert /** length of the static secret */ 1061*46d2f618SCy Schubert size_t static_secret_len; 1062*46d2f618SCy Schubert /** ssl context, SSL_CTX* */ 1063*46d2f618SCy Schubert void* ctx; 1064*46d2f618SCy Schubert #ifndef HAVE_NGTCP2_CRYPTO_QUICTLS_CONFIGURE_SERVER_CONTEXT 1065*46d2f618SCy Schubert /** quic method functions, SSL_QUIC_METHOD* */ 1066*46d2f618SCy Schubert void* quic_method; 1067*46d2f618SCy Schubert #endif 1068*46d2f618SCy Schubert /** the comm point for this doq server socket */ 1069*46d2f618SCy Schubert struct comm_point* cp; 1070*46d2f618SCy Schubert /** the buffer for packets, doq in and out */ 1071*46d2f618SCy Schubert struct sldns_buffer* pkt_buf; 1072*46d2f618SCy Schubert /** the current doq connection when we are in callbacks to worker, 1073*46d2f618SCy Schubert * so that we have the already locked structure at our disposal. */ 1074*46d2f618SCy Schubert struct doq_conn* current_conn; 1075*46d2f618SCy Schubert /** if the callback event on the fd has write flags */ 1076*46d2f618SCy Schubert uint8_t event_has_write; 1077*46d2f618SCy Schubert /** if there is a blocked packet in the blocked_pkt buffer */ 1078*46d2f618SCy Schubert int have_blocked_pkt; 1079*46d2f618SCy Schubert /** store blocked packet, a packet that could not be send on the 1080*46d2f618SCy Schubert * nonblocking socket. It has to be sent later, when the write on 1081*46d2f618SCy Schubert * the udp socket unblocks. */ 1082*46d2f618SCy Schubert struct sldns_buffer* blocked_pkt; 1083*46d2f618SCy Schubert #ifdef HAVE_NGTCP2 1084*46d2f618SCy Schubert /** the ecn info for the blocked packet, congestion information. */ 1085*46d2f618SCy Schubert struct ngtcp2_pkt_info blocked_pkt_pi; 1086*46d2f618SCy Schubert #endif 1087*46d2f618SCy Schubert /** the packet destination for the blocked packet. */ 1088*46d2f618SCy Schubert struct doq_pkt_addr* blocked_paddr; 1089*46d2f618SCy Schubert /** timer for this worker on this comm_point to wait on. */ 1090*46d2f618SCy Schubert struct comm_timer* timer; 1091*46d2f618SCy Schubert /** the timer that is marked by the doq_socket as waited on. */ 1092*46d2f618SCy Schubert struct timeval marked_time; 1093*46d2f618SCy Schubert /** the current time for use by time functions, time_t. */ 1094*46d2f618SCy Schubert time_t* now_tt; 1095*46d2f618SCy Schubert /** the current time for use by time functions, timeval. */ 1096*46d2f618SCy Schubert struct timeval* now_tv; 1097*46d2f618SCy Schubert /** config file for the worker. */ 1098*46d2f618SCy Schubert struct config_file* cfg; 1099*46d2f618SCy Schubert }; 1100*46d2f618SCy Schubert 1101*46d2f618SCy Schubert /** 1102*46d2f618SCy Schubert * DoQ packet address information. From pktinfo, stores local and remote 1103*46d2f618SCy Schubert * address and ifindex, so the packet can be sent there. 1104*46d2f618SCy Schubert */ 1105*46d2f618SCy Schubert struct doq_pkt_addr { 1106*46d2f618SCy Schubert /** the remote addr, and local addr */ 1107*46d2f618SCy Schubert struct doq_addr_storage addr, localaddr; 1108*46d2f618SCy Schubert /** length of addr and length of localaddr */ 1109*46d2f618SCy Schubert socklen_t addrlen, localaddrlen; 1110*46d2f618SCy Schubert /** interface index from pktinfo ancillary information */ 1111*46d2f618SCy Schubert int ifindex; 1112*46d2f618SCy Schubert }; 1113*46d2f618SCy Schubert 1114*46d2f618SCy Schubert /** Initialize the pkt addr with lengths set to sizeof. That is ready for 1115*46d2f618SCy Schubert * a call to recv. */ 1116*46d2f618SCy Schubert void doq_pkt_addr_init(struct doq_pkt_addr* paddr); 1117*46d2f618SCy Schubert 1118*46d2f618SCy Schubert /** send doq packet over UDP. */ 1119*46d2f618SCy Schubert void doq_send_pkt(struct comm_point* c, struct doq_pkt_addr* paddr, 1120*46d2f618SCy Schubert uint32_t ecn); 1121*46d2f618SCy Schubert 1122*46d2f618SCy Schubert /** doq timer callback function. */ 1123*46d2f618SCy Schubert void doq_timer_cb(void* arg); 1124*46d2f618SCy Schubert 1125*46d2f618SCy Schubert /** 112657bddd21SDag-Erling Smørgrav * This routine is published for checks and tests, and is only used internally. 1127b7579f77SDag-Erling Smørgrav * handle libevent callback for timer comm. 1128b7579f77SDag-Erling Smørgrav * @param fd: file descriptor (always -1). 1129b7579f77SDag-Erling Smørgrav * @param event: event bits from libevent: 1130b7579f77SDag-Erling Smørgrav * EV_READ, EV_WRITE, EV_SIGNAL, EV_TIMEOUT. 1131b7579f77SDag-Erling Smørgrav * @param arg: the comm_timer structure. 1132b7579f77SDag-Erling Smørgrav */ 1133b7579f77SDag-Erling Smørgrav void comm_timer_callback(int fd, short event, void* arg); 1134b7579f77SDag-Erling Smørgrav 1135b7579f77SDag-Erling Smørgrav /** 1136b7579f77SDag-Erling Smørgrav * This routine is published for checks and tests, and is only used internally. 1137b7579f77SDag-Erling Smørgrav * handle libevent callback for signal comm. 1138b7579f77SDag-Erling Smørgrav * @param fd: file descriptor (used for the signal number). 1139b7579f77SDag-Erling Smørgrav * @param event: event bits from libevent: 1140b7579f77SDag-Erling Smørgrav * EV_READ, EV_WRITE, EV_SIGNAL, EV_TIMEOUT. 1141b7579f77SDag-Erling Smørgrav * @param arg: the internal commsignal structure. 1142b7579f77SDag-Erling Smørgrav */ 1143b7579f77SDag-Erling Smørgrav void comm_signal_callback(int fd, short event, void* arg); 1144b7579f77SDag-Erling Smørgrav 1145b7579f77SDag-Erling Smørgrav /** 1146b7579f77SDag-Erling Smørgrav * This routine is published for checks and tests, and is only used internally. 1147b7579f77SDag-Erling Smørgrav * libevent callback for AF_UNIX fds 1148b7579f77SDag-Erling Smørgrav * @param fd: file descriptor. 1149b7579f77SDag-Erling Smørgrav * @param event: event bits from libevent: 1150b7579f77SDag-Erling Smørgrav * EV_READ, EV_WRITE, EV_SIGNAL, EV_TIMEOUT. 1151b7579f77SDag-Erling Smørgrav * @param arg: the comm_point structure. 1152b7579f77SDag-Erling Smørgrav */ 1153b7579f77SDag-Erling Smørgrav void comm_point_local_handle_callback(int fd, short event, void* arg); 1154b7579f77SDag-Erling Smørgrav 1155b7579f77SDag-Erling Smørgrav /** 1156b7579f77SDag-Erling Smørgrav * This routine is published for checks and tests, and is only used internally. 1157b7579f77SDag-Erling Smørgrav * libevent callback for raw fd access. 1158b7579f77SDag-Erling Smørgrav * @param fd: file descriptor. 1159b7579f77SDag-Erling Smørgrav * @param event: event bits from libevent: 1160b7579f77SDag-Erling Smørgrav * EV_READ, EV_WRITE, EV_SIGNAL, EV_TIMEOUT. 1161b7579f77SDag-Erling Smørgrav * @param arg: the comm_point structure. 1162b7579f77SDag-Erling Smørgrav */ 1163b7579f77SDag-Erling Smørgrav void comm_point_raw_handle_callback(int fd, short event, void* arg); 1164b7579f77SDag-Erling Smørgrav 1165b7579f77SDag-Erling Smørgrav /** 1166b7579f77SDag-Erling Smørgrav * This routine is published for checks and tests, and is only used internally. 1167b7579f77SDag-Erling Smørgrav * libevent callback for timeout on slow accept. 1168b7579f77SDag-Erling Smørgrav * @param fd: file descriptor. 1169b7579f77SDag-Erling Smørgrav * @param event: event bits from libevent: 1170b7579f77SDag-Erling Smørgrav * EV_READ, EV_WRITE, EV_SIGNAL, EV_TIMEOUT. 1171b7579f77SDag-Erling Smørgrav * @param arg: the comm_point structure. 1172b7579f77SDag-Erling Smørgrav */ 1173b7579f77SDag-Erling Smørgrav void comm_base_handle_slow_accept(int fd, short event, void* arg); 1174b7579f77SDag-Erling Smørgrav 1175b7579f77SDag-Erling Smørgrav #ifdef USE_WINSOCK 1176b7579f77SDag-Erling Smørgrav /** 1177b7579f77SDag-Erling Smørgrav * Callback for openssl BIO to on windows detect WSAEWOULDBLOCK and notify 1178b7579f77SDag-Erling Smørgrav * the winsock_event of this for proper TCP nonblocking implementation. 1179b7579f77SDag-Erling Smørgrav * @param c: comm_point, fd must be set its struct event is registered. 1180b7579f77SDag-Erling Smørgrav * @param ssl: openssl SSL, fd must be set so it has a bio. 1181b7579f77SDag-Erling Smørgrav */ 1182b7579f77SDag-Erling Smørgrav void comm_point_tcp_win_bio_cb(struct comm_point* c, void* ssl); 1183b7579f77SDag-Erling Smørgrav #endif 1184b7579f77SDag-Erling Smørgrav 118525039b37SCy Schubert /** 118625039b37SCy Schubert * See if errno for tcp connect has to be logged or not. This uses errno 118725039b37SCy Schubert * @param addr: apart from checking errno, the addr is checked for ip4mapped 118825039b37SCy Schubert * and broadcast type, hence passed. 118925039b37SCy Schubert * @param addrlen: length of the addr parameter. 119025039b37SCy Schubert * @return true if it needs to be logged. 119125039b37SCy Schubert */ 1192b7579f77SDag-Erling Smørgrav int tcp_connect_errno_needs_log(struct sockaddr* addr, socklen_t addrlen); 1193b7579f77SDag-Erling Smørgrav 119425039b37SCy Schubert #ifdef HAVE_SSL 119525039b37SCy Schubert /** 119625039b37SCy Schubert * True if the ssl handshake error has to be squelched from the logs 119725039b37SCy Schubert * @param err: the error returned by the openssl routine, ERR_get_error. 119825039b37SCy Schubert * This is a packed structure with elements that are examined. 119925039b37SCy Schubert * @return true if the error is squelched (not logged). 120025039b37SCy Schubert */ 120125039b37SCy Schubert int squelch_err_ssl_handshake(unsigned long err); 120225039b37SCy Schubert #endif 120325039b37SCy Schubert 1204b7579f77SDag-Erling Smørgrav #endif /* NET_EVENT_H */ 1205