1 #include "first.h" 2 3 #include "base.h" 4 #include "buffer.h" 5 #include "burl.h" /* HTTP_PARSEOPT_HEADER_STRICT */ 6 #include "settings.h" /* BUFFER_MAX_REUSE_SIZE MAX_READ_LIMIT MAX_WRITE_LIMIT */ 7 #include "log.h" 8 #include "connections.h" 9 #include "fdevent.h" 10 #include "http_header.h" 11 12 #include "request.h" 13 #include "response.h" 14 #include "network.h" 15 #include "http_chunk.h" 16 #include "stat_cache.h" 17 18 #include "plugin.h" 19 20 #include "inet_ntop_cache.h" 21 22 #include <sys/stat.h> 23 24 #include <stdlib.h> 25 #include <unistd.h> 26 #include <errno.h> 27 #include <string.h> 28 29 #ifdef HAVE_SYS_FILIO_H 30 # include <sys/filio.h> 31 #endif 32 33 #include "sys-socket.h" 34 35 #define HTTP_LINGER_TIMEOUT 5 36 37 #define connection_set_state(r, n) ((r)->state = (n)) 38 39 __attribute_cold__ 40 static connection *connection_init(server *srv); 41 42 static void connection_reset(connection *con); 43 44 45 static connection *connections_get_new_connection(server *srv) { 46 connections * const conns = &srv->conns; 47 size_t i; 48 49 if (conns->size == conns->used) { 50 conns->size += srv->max_conns >= 128 ? 128 : srv->max_conns > 16 ? 16 : srv->max_conns; 51 conns->ptr = realloc(conns->ptr, sizeof(*conns->ptr) * conns->size); 52 force_assert(NULL != conns->ptr); 53 54 for (i = conns->used; i < conns->size; i++) { 55 conns->ptr[i] = connection_init(srv); 56 connection_reset(conns->ptr[i]); 57 } 58 } 59 60 conns->ptr[conns->used]->ndx = conns->used; 61 return conns->ptr[conns->used++]; 62 } 63 64 static void connection_del(server *srv, connection *con) { 65 connections * const conns = &srv->conns; 66 67 if (-1 == con->ndx) return; 68 uint32_t i = (uint32_t)con->ndx; 69 70 /* not last element */ 71 72 if (i != --conns->used) { 73 connection * const temp = conns->ptr[i]; 74 conns->ptr[i] = conns->ptr[conns->used]; 75 conns->ptr[conns->used] = temp; 76 77 conns->ptr[i]->ndx = i; 78 conns->ptr[conns->used]->ndx = -1; 79 } 80 81 con->ndx = -1; 82 #if 0 83 fprintf(stderr, "%s.%d: del: (%d)", __FILE__, __LINE__, conns->used); 84 for (i = 0; i < conns->used; i++) { 85 fprintf(stderr, "%d ", conns->ptr[i]->fd); 86 } 87 fprintf(stderr, "\n"); 88 #endif 89 } 90 91 #if 0 /* DEBUG_DEV */ 92 __attribute_cold__ 93 static void connection_plugin_ctx_check(server * const srv, request_st * const r) { 94 /* plugins should have cleaned themselves up */ 95 for (uint32_t i = 0; i < srv->plugins.used; ++i) { 96 plugin *p = ((plugin **)(srv->plugins.ptr))[i]; 97 plugin_data_base *pd = p->data; 98 if (!pd) continue; 99 if (NULL == r->plugin_ctx[pd->id] 100 && NULL == r->con->plugin_ctx[pd->id]) continue; 101 log_error(r->conf.errh, __FILE__, __LINE__, 102 "missing cleanup in %s", p->name); 103 r->plugin_ctx[pd->id] = NULL; 104 r->con->plugin_ctx[pd->id] = NULL; 105 } 106 } 107 #endif 108 109 static void connection_close(connection *con) { 110 if (con->fd < 0) con->fd = -con->fd; 111 112 plugins_call_handle_connection_close(con); 113 114 server * const srv = con->srv; 115 request_st * const r = &con->request; 116 117 #if 0 /* DEBUG_DEV */ 118 /* plugins should have cleaned themselves up */ 119 for (uint32_t i = 0; i < srv->plugins.used; ++i) { 120 if (NULL != r->plugin_ctx[i] || NULL != con->plugin_ctx[i]) { 121 connection_plugin_ctx_check(srv, r); 122 break; 123 } 124 } 125 #endif 126 127 connection_set_state(r, CON_STATE_CONNECT); 128 buffer_clear(&r->uri.authority); 129 buffer_reset(&r->uri.path); 130 buffer_reset(&r->uri.query); 131 buffer_reset(&r->target_orig); 132 buffer_reset(&r->target); /*(see comments in connection_reset())*/ 133 buffer_reset(&r->pathinfo); /*(see comments in connection_reset())*/ 134 135 chunkqueue_reset(con->read_queue); 136 con->request_count = 0; 137 con->is_ssl_sock = 0; 138 139 fdevent_fdnode_event_del(srv->ev, con->fdn); 140 fdevent_unregister(srv->ev, con->fd); 141 con->fdn = NULL; 142 #ifdef __WIN32 143 if (0 == closesocket(con->fd)) 144 #else 145 if (0 == close(con->fd)) 146 #endif 147 --srv->cur_fds; 148 else 149 log_perror(r->conf.errh, __FILE__, __LINE__, 150 "(warning) close: %d", con->fd); 151 152 if (r->conf.log_state_handling) { 153 log_error(r->conf.errh, __FILE__, __LINE__, 154 "connection closed for fd %d", con->fd); 155 } 156 con->fd = -1; 157 158 connection_del(srv, con); 159 } 160 161 static void connection_read_for_eos_plain(connection * const con) { 162 /* we have to do the linger_on_close stuff regardless 163 * of r->keep_alive; even non-keepalive sockets 164 * may still have unread data, and closing before reading 165 * it will make the client not see all our output. 166 */ 167 ssize_t len; 168 const int type = con->dst_addr.plain.sa_family; 169 char buf[16384]; 170 do { 171 len = fdevent_socket_read_discard(con->fd, buf, sizeof(buf), 172 type, SOCK_STREAM); 173 } while (len > 0 || (len < 0 && errno == EINTR)); 174 175 if (len < 0 && errno == EAGAIN) return; 176 #if defined(EWOULDBLOCK) && EWOULDBLOCK != EAGAIN 177 if (len < 0 && errno == EWOULDBLOCK) return; 178 #endif 179 180 /* 0 == len || (len < 0 && (errno is a non-recoverable error)) */ 181 con->close_timeout_ts = log_epoch_secs - (HTTP_LINGER_TIMEOUT+1); 182 } 183 184 static void connection_read_for_eos_ssl(connection * const con) { 185 if (con->network_read(con, con->read_queue, MAX_READ_LIMIT) < 0) 186 con->close_timeout_ts = log_epoch_secs - (HTTP_LINGER_TIMEOUT+1); 187 chunkqueue_reset(con->read_queue); 188 } 189 190 static void connection_read_for_eos(connection * const con) { 191 !con->is_ssl_sock 192 ? connection_read_for_eos_plain(con) 193 : connection_read_for_eos_ssl(con); 194 } 195 196 static void connection_handle_close_state(connection *con) { 197 connection_read_for_eos(con); 198 199 if (log_epoch_secs - con->close_timeout_ts > HTTP_LINGER_TIMEOUT) { 200 connection_close(con); 201 } 202 } 203 204 static void connection_handle_shutdown(connection *con) { 205 plugins_call_handle_connection_shut_wr(con); 206 207 connection_reset(con); 208 ++con->srv->con_closed; 209 210 /* close the connection */ 211 if (con->fd >= 0 212 && (con->is_ssl_sock || 0 == shutdown(con->fd, SHUT_WR))) { 213 con->close_timeout_ts = log_epoch_secs; 214 215 request_st * const r = &con->request; 216 connection_set_state(r, CON_STATE_CLOSE); 217 if (r->conf.log_state_handling) { 218 log_error(r->conf.errh, __FILE__, __LINE__, 219 "shutdown for fd %d", con->fd); 220 } 221 } else { 222 connection_close(con); 223 } 224 } 225 226 __attribute_cold__ 227 static void connection_fdwaitqueue_append(connection *con) { 228 connection_list_append(&con->srv->fdwaitqueue, con); 229 } 230 231 static void connection_handle_response_end_state(request_st * const r, connection * const con) { 232 /* call request_done hook if http_status set (e.g. to log request) */ 233 /* (even if error, connection dropped, as long as http_status is set) */ 234 if (r->http_status) plugins_call_handle_request_done(r); 235 236 if (r->state != CON_STATE_ERROR) ++con->srv->con_written; 237 238 if (r->reqbody_length != r->reqbody_queue->bytes_in 239 || r->state == CON_STATE_ERROR) { 240 /* request body is present and has not been read completely */ 241 r->keep_alive = 0; 242 } 243 244 if (r->keep_alive) { 245 connection_reset(con); 246 #if 0 247 r->start_ts = con->read_idle_ts = log_epoch_secs; 248 #endif 249 connection_set_state(r, CON_STATE_REQUEST_START); 250 } else { 251 connection_handle_shutdown(con); 252 } 253 } 254 255 __attribute_cold__ 256 static void connection_handle_errdoc_init(request_st * const r) { 257 /* modules that produce headers required with error response should 258 * typically also produce an error document. Make an exception for 259 * mod_auth WWW-Authenticate response header. */ 260 buffer *www_auth = NULL; 261 if (401 == r->http_status) { 262 const buffer *vb = http_header_response_get(r, HTTP_HEADER_OTHER, CONST_STR_LEN("WWW-Authenticate")); 263 if (NULL != vb) www_auth = buffer_init_buffer(vb); 264 } 265 266 buffer_reset(&r->physical.path); 267 r->resp_htags = 0; 268 array_reset_data_strings(&r->resp_headers); 269 http_response_body_clear(r, 0); 270 271 if (NULL != www_auth) { 272 http_header_response_set(r, HTTP_HEADER_OTHER, CONST_STR_LEN("WWW-Authenticate"), CONST_BUF_LEN(www_auth)); 273 buffer_free(www_auth); 274 } 275 } 276 277 __attribute_cold__ 278 static void connection_handle_errdoc(request_st * const r) { 279 if (NULL == r->handler_module 280 ? r->error_handler_saved_status >= 65535 281 : (!r->conf.error_intercept||r->error_handler_saved_status)) 282 return; 283 284 connection_handle_errdoc_init(r); 285 r->resp_body_finished = 1; 286 287 /* try to send static errorfile */ 288 if (!buffer_string_is_empty(r->conf.errorfile_prefix)) { 289 buffer_copy_buffer(&r->physical.path, r->conf.errorfile_prefix); 290 buffer_append_int(&r->physical.path, r->http_status); 291 buffer_append_string_len(&r->physical.path, CONST_STR_LEN(".html")); 292 if (0 == http_chunk_append_file(r, &r->physical.path)) { 293 stat_cache_entry *sce = stat_cache_get_entry(&r->physical.path); 294 const buffer *content_type = (NULL != sce) 295 ? stat_cache_content_type_get(sce, r) 296 : NULL; 297 if (content_type) 298 http_header_response_set(r, HTTP_HEADER_CONTENT_TYPE, 299 CONST_STR_LEN("Content-Type"), 300 CONST_BUF_LEN(content_type)); 301 return; 302 } 303 } 304 305 /* build default error-page */ 306 buffer_reset(&r->physical.path); 307 buffer * const b = r->tmp_buf; 308 buffer_copy_string_len(b, CONST_STR_LEN( 309 "<?xml version=\"1.0\" encoding=\"iso-8859-1\"?>\n" 310 "<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\"\n" 311 " \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n" 312 "<html xmlns=\"http://www.w3.org/1999/xhtml\" xml:lang=\"en\" lang=\"en\">\n" 313 " <head>\n" 314 " <title>")); 315 http_status_append(b, r->http_status); 316 buffer_append_string_len(b, CONST_STR_LEN( 317 "</title>\n" 318 " </head>\n" 319 " <body>\n" 320 " <h1>")); 321 http_status_append(b, r->http_status); 322 buffer_append_string_len(b, CONST_STR_LEN( 323 "</h1>\n" 324 " </body>\n" 325 "</html>\n")); 326 (void)http_chunk_append_mem(r, CONST_BUF_LEN(b)); 327 328 http_header_response_set(r, HTTP_HEADER_CONTENT_TYPE, 329 CONST_STR_LEN("Content-Type"), 330 CONST_STR_LEN("text/html")); 331 } 332 333 __attribute_cold__ 334 static void 335 connection_merge_trailers (request_st * const r) 336 { 337 /* attempt to merge trailers into headers; header not yet sent by caller */ 338 if (buffer_string_is_empty(&r->gw_dechunk->b)) return; 339 const int done = r->gw_dechunk->done; 340 if (!done) return; /* XXX: !done; could scan for '\n' and send only those */ 341 342 /* do not include trailers if success status (when response was read from 343 * backend) subsequently changed to error status. http_chunk could add the 344 * trailers, but such actions are better on a different code layer than in 345 * http_chunk.c */ 346 if (done < 400 && r->http_status >= 400) return; 347 348 /* XXX: trailers passed through; no sanity check currently done 349 * https://tools.ietf.org/html/rfc7230#section-4.1.2 350 * 351 * Not checking for disallowed fields 352 * Not handling (deprecated) line wrapping 353 * Not strictly checking fields 354 */ 355 const char *k = strchr(r->gw_dechunk->b.ptr, '\n'); /*(skip final chunk)*/ 356 if (NULL == k) return; /*(should not happen)*/ 357 ++k; 358 for (const char *v, *e; (e = strchr(k, '\n')); k = e+1) { 359 v = memchr(k, ':', (size_t)(e - k)); 360 if (NULL == v || v == k || *k == ' ' || *k == '\t') continue; 361 uint32_t klen = (uint32_t)(v - k); 362 do { ++v; } while (*v == ' ' || *v == '\t'); 363 if (*v == '\r' || *v == '\n') continue; 364 enum http_header_e id = http_header_hkey_get(k, klen); 365 http_header_response_insert(r, id, k, klen, v, (size_t)(e - v)); 366 } 367 http_header_response_unset(r, HTTP_HEADER_OTHER, CONST_STR_LEN("Trailer")); 368 buffer_clear(&r->gw_dechunk->b); 369 } 370 371 static int connection_handle_write_prepare(request_st * const r) { 372 if (NULL == r->handler_module) { 373 /* static files */ 374 switch(r->http_method) { 375 case HTTP_METHOD_GET: 376 case HTTP_METHOD_POST: 377 case HTTP_METHOD_HEAD: 378 break; 379 case HTTP_METHOD_OPTIONS: 380 /* 381 * 400 is coming from the request-parser BEFORE uri.path is set 382 * 403 is from the response handler when no module handled request 383 * 384 * */ 385 if ((!r->http_status || r->http_status == 200) 386 && !buffer_string_is_empty(&r->uri.path) 387 && r->uri.path.ptr[0] != '*') { 388 http_response_body_clear(r, 0); 389 http_header_response_append(r, HTTP_HEADER_OTHER, CONST_STR_LEN("Allow"), CONST_STR_LEN("OPTIONS, GET, HEAD, POST")); 390 r->http_status = 200; 391 r->resp_body_finished = 1; 392 393 } 394 break; 395 default: 396 if (0 == r->http_status) { 397 r->http_status = 501; 398 } 399 break; 400 } 401 } 402 403 if (r->http_status == 0) { 404 r->http_status = 403; 405 } 406 407 switch(r->http_status) { 408 case 204: /* class: header only */ 409 case 205: 410 case 304: 411 /* disable chunked encoding again as we have no body */ 412 http_response_body_clear(r, 1); 413 r->resp_body_finished = 1; 414 break; 415 default: /* class: header + body */ 416 /* only custom body for 4xx and 5xx */ 417 if (r->http_status >= 400 && r->http_status < 600) 418 connection_handle_errdoc(r); 419 break; 420 } 421 422 if (r->gw_dechunk) 423 connection_merge_trailers(r); 424 425 /* Allow filter plugins to change response headers before they are written. */ 426 switch(plugins_call_handle_response_start(r)) { 427 case HANDLER_GO_ON: 428 case HANDLER_FINISHED: 429 break; 430 default: 431 log_error(r->conf.errh, __FILE__, __LINE__, 432 "response_start plugin failed"); 433 return -1; 434 } 435 436 if (r->resp_body_finished) { 437 /* we have all the content and chunked encoding is not used, set a content-length */ 438 439 if (!(r->resp_htags & (HTTP_HEADER_CONTENT_LENGTH|HTTP_HEADER_TRANSFER_ENCODING))) { 440 off_t qlen = chunkqueue_length(r->write_queue); 441 442 /** 443 * The Content-Length header only can be sent if we have content: 444 * - HEAD doesn't have a content-body (but have a content-length) 445 * - 1xx, 204 and 304 don't have a content-body (RFC 2616 Section 4.3) 446 * 447 * Otherwise generate a Content-Length header as chunked encoding is not 448 * available 449 */ 450 if ((r->http_status >= 100 && r->http_status < 200) || 451 r->http_status == 204 || 452 r->http_status == 304) { 453 /* no Content-Body, no Content-Length */ 454 http_header_response_unset(r, HTTP_HEADER_CONTENT_LENGTH, CONST_STR_LEN("Content-Length")); 455 } else if (qlen > 0) { 456 buffer * const tb = r->tmp_buf; 457 buffer_clear(tb); 458 buffer_append_int(tb, qlen); 459 http_header_response_set(r, HTTP_HEADER_CONTENT_LENGTH, 460 CONST_STR_LEN("Content-Length"), 461 CONST_BUF_LEN(tb)); 462 } else if (r->http_method != HTTP_METHOD_HEAD) { 463 /* qlen = 0 is important for Redirects (301, ...) as they MAY have 464 * a content. Browsers are waiting for a Content otherwise 465 */ 466 http_header_response_set(r, HTTP_HEADER_CONTENT_LENGTH, 467 CONST_STR_LEN("Content-Length"), 468 CONST_STR_LEN("0")); 469 } 470 } 471 } else { 472 /** 473 * the file isn't finished yet, but we have all headers 474 * 475 * to get keep-alive we either need: 476 * - Content-Length: ... (HTTP/1.0 and HTTP/1.0) or 477 * - Transfer-Encoding: chunked (HTTP/1.1) 478 * - Upgrade: ... (lighttpd then acts as transparent proxy) 479 */ 480 481 if (!(r->resp_htags & (HTTP_HEADER_CONTENT_LENGTH|HTTP_HEADER_TRANSFER_ENCODING|HTTP_HEADER_UPGRADE))) { 482 if (r->http_method == HTTP_METHOD_CONNECT 483 && r->http_status == 200) { 484 /*(no transfer-encoding if successful CONNECT)*/ 485 } else if (r->http_version == HTTP_VERSION_1_1) { 486 off_t qlen = chunkqueue_length(r->write_queue); 487 r->resp_send_chunked = 1; 488 if (qlen) { 489 /* create initial Transfer-Encoding: chunked segment */ 490 buffer * const b = chunkqueue_prepend_buffer_open(r->write_queue); 491 buffer_append_uint_hex(b, (uintmax_t)qlen); 492 buffer_append_string_len(b, CONST_STR_LEN("\r\n")); 493 chunkqueue_prepend_buffer_commit(r->write_queue); 494 chunkqueue_append_mem(r->write_queue, CONST_STR_LEN("\r\n")); 495 } 496 http_header_response_append(r, HTTP_HEADER_TRANSFER_ENCODING, CONST_STR_LEN("Transfer-Encoding"), CONST_STR_LEN("chunked")); 497 } else { 498 r->keep_alive = 0; 499 } 500 } 501 } 502 503 if (r->http_method == HTTP_METHOD_HEAD) { 504 /** 505 * a HEAD request has the same as a GET 506 * without the content 507 */ 508 http_response_body_clear(r, 1); 509 r->resp_body_finished = 1; 510 } 511 512 http_response_write_header(r); 513 514 return 0; 515 } 516 517 static void connection_handle_write(connection *con) { 518 int rc = connection_write_chunkqueue(con, con->write_queue, MAX_WRITE_LIMIT); 519 request_st * const r = &con->request; 520 switch (rc) { 521 case 0: 522 if (r->resp_body_finished) { 523 connection_set_state(r, CON_STATE_RESPONSE_END); 524 } 525 break; 526 case -1: /* error on our side */ 527 log_error(r->conf.errh, __FILE__, __LINE__, 528 "connection closed: write failed on fd %d", con->fd); 529 connection_set_state(r, CON_STATE_ERROR); 530 break; 531 case -2: /* remote close */ 532 connection_set_state(r, CON_STATE_ERROR); 533 break; 534 case 1: 535 con->is_writable = 0; 536 537 /* not finished yet -> WRITE */ 538 break; 539 } 540 } 541 542 static void connection_handle_write_state(request_st * const r, connection * const con) { 543 do { 544 /* only try to write if we have something in the queue */ 545 if (!chunkqueue_is_empty(con->write_queue)) { 546 if (con->is_writable) { 547 connection_handle_write(con); 548 if (r->state != CON_STATE_WRITE) break; 549 } 550 } else if (r->resp_body_finished) { 551 connection_set_state(r, CON_STATE_RESPONSE_END); 552 break; 553 } 554 555 if (r->handler_module && !r->resp_body_finished) { 556 const plugin * const p = r->handler_module; 557 int rc = p->handle_subrequest(r, p->data); 558 switch(rc) { 559 case HANDLER_WAIT_FOR_EVENT: 560 case HANDLER_FINISHED: 561 case HANDLER_GO_ON: 562 break; 563 case HANDLER_WAIT_FOR_FD: 564 connection_fdwaitqueue_append(con); 565 break; 566 case HANDLER_COMEBACK: 567 default: 568 log_error(r->conf.errh, __FILE__, __LINE__, 569 "unexpected subrequest handler ret-value: %d %d", 570 con->fd, rc); 571 /* fall through */ 572 case HANDLER_ERROR: 573 connection_set_state(r, CON_STATE_ERROR); 574 break; 575 } 576 } 577 } while (r->state == CON_STATE_WRITE 578 && (!chunkqueue_is_empty(con->write_queue) 579 ? con->is_writable 580 : r->resp_body_finished)); 581 } 582 583 584 __attribute_cold__ 585 static void 586 request_init (request_st * const r, connection * const con, server * const srv) 587 { 588 r->write_queue = chunkqueue_init(); 589 r->read_queue = chunkqueue_init(); 590 r->reqbody_queue = chunkqueue_init(); 591 592 r->resp_header_len = 0; 593 r->loops_per_request = 0; 594 r->con = con; 595 r->tmp_buf = srv->tmp_buf; 596 597 /* init plugin-specific per-request structures */ 598 r->plugin_ctx = calloc(1, (srv->plugins.used + 1) * sizeof(void *)); 599 force_assert(NULL != r->plugin_ctx); 600 601 r->cond_cache = calloc(srv->config_context->used, sizeof(cond_cache_t)); 602 force_assert(NULL != r->cond_cache); 603 604 #ifdef HAVE_PCRE_H 605 if (srv->config_context->used > 1) {/*(save 128b per con if no conditions)*/ 606 r->cond_match = 607 calloc(srv->config_context->used, sizeof(cond_match_t)); 608 force_assert(NULL != r->cond_match); 609 } 610 #endif 611 612 config_reset_config(r); 613 } 614 615 __attribute_cold__ 616 static connection *connection_init(server *srv) { 617 connection * const con = calloc(1, sizeof(*con)); 618 force_assert(NULL != con); 619 620 con->fd = 0; 621 con->ndx = -1; 622 con->bytes_written = 0; 623 con->bytes_read = 0; 624 625 con->dst_addr_buf = buffer_init(); 626 con->srv = srv; 627 con->plugin_slots = srv->plugin_slots; 628 con->config_data_base = srv->config_data_base; 629 630 request_st * const r = &con->request; 631 request_init(r, con, srv); 632 con->write_queue = r->write_queue; 633 con->read_queue = r->read_queue; 634 635 /* init plugin-specific per-connection structures */ 636 con->plugin_ctx = calloc(1, (srv->plugins.used + 1) * sizeof(void *)); 637 force_assert(NULL != con->plugin_ctx); 638 639 return con; 640 } 641 642 643 static void 644 request_free (request_st * const r) 645 { 646 chunkqueue_free(r->reqbody_queue); 647 chunkqueue_free(r->write_queue); 648 chunkqueue_free(r->read_queue); 649 array_free_data(&r->rqst_headers); 650 array_free_data(&r->resp_headers); 651 array_free_data(&r->env); 652 653 free(r->target.ptr); 654 free(r->target_orig.ptr); 655 656 free(r->uri.scheme.ptr); 657 free(r->uri.authority.ptr); 658 free(r->uri.path.ptr); 659 free(r->uri.query.ptr); 660 661 free(r->physical.doc_root.ptr); 662 free(r->physical.path.ptr); 663 free(r->physical.basedir.ptr); 664 free(r->physical.etag.ptr); 665 free(r->physical.rel_path.ptr); 666 667 free(r->pathinfo.ptr); 668 free(r->server_name_buf.ptr); 669 670 free(r->plugin_ctx); 671 free(r->cond_cache); 672 free(r->cond_match); 673 674 /* note: r is not zeroed here and r is not freed here */ 675 } 676 677 void connections_free(server *srv) { 678 connections * const conns = &srv->conns; 679 for (uint32_t i = 0; i < conns->size; ++i) { 680 connection *con = conns->ptr[i]; 681 request_st * const r = &con->request; 682 683 connection_reset(con); 684 if (con->write_queue != r->write_queue) 685 chunkqueue_free(con->write_queue); 686 if (con->read_queue != r->read_queue) 687 chunkqueue_free(con->read_queue); 688 request_free(r); 689 690 free(con->plugin_ctx); 691 buffer_free(con->dst_addr_buf); 692 693 free(con); 694 } 695 696 free(conns->ptr); 697 conns->ptr = NULL; 698 } 699 700 701 static void 702 request_reset (request_st * const r) { 703 plugins_call_handle_request_reset(r); 704 705 connection_response_reset(r); 706 707 r->resp_header_len = 0; 708 r->loops_per_request = 0; 709 710 r->http_method = HTTP_METHOD_UNSET; 711 r->http_version = HTTP_VERSION_UNSET; 712 713 /*con->proto_default_port = 80;*//*set to default in connection_accepted()*/ 714 715 r->http_host = NULL; 716 r->reqbody_length = 0; 717 r->te_chunked = 0; 718 r->rqst_htags = 0; 719 720 buffer_clear(&r->uri.scheme); 721 722 if (r->rqst_header_len <= BUFFER_MAX_REUSE_SIZE) { 723 r->rqst_headers.used = 0; 724 /* (Note: total header size not recalculated on HANDLER_COMEBACK 725 * even if other request headers changed during processing) 726 * (While this might delay release of larger buffers, it is not 727 * expected to be the general case. For those systems where it 728 * is a typical case, the larger buffers are likely to be reused) */ 729 buffer_clear(&r->target); 730 buffer_clear(&r->pathinfo); 731 /*buffer_clear(&r->target_orig);*/ /* reset later; used by mod_status*/ 732 /*buffer_clear(&r->uri.path);*/ /* reset later; used by mod_status*/ 733 /*buffer_clear(&r->uri.query);*/ /* reset later; used by mod_status*/ 734 /*buffer_clear(&r->uri.authority);*//* reset later; used by mod_status*/ 735 /*buffer_clear(&r->server_name_buf);*//* reset when used */ 736 } 737 else { 738 buffer_reset(&r->target); 739 buffer_reset(&r->pathinfo); 740 /*buffer_reset(&r->target_orig);*/ /* reset later; used by mod_status*/ 741 /*buffer_reset(&r->uri.path);*/ /* reset later; used by mod_status*/ 742 /*buffer_reset(&r->uri.query);*/ /* reset later; used by mod_status*/ 743 /*buffer_clear(&r->uri.authority);*//* reset later; used by mod_status*/ 744 /*buffer_clear(&r->server_name_buf);*//* reset when used */ 745 array_reset_data_strings(&r->rqst_headers); 746 } 747 r->rqst_header_len = 0; 748 if (0 != r->env.used) 749 array_reset_data_strings(&r->env); 750 751 chunkqueue_reset(r->reqbody_queue); 752 753 /* The cond_cache gets reset in response.c */ 754 /* config_cond_cache_reset(r); */ 755 756 r->async_callback = 0; 757 r->error_handler_saved_status = 0; 758 /*r->error_handler_saved_method = HTTP_METHOD_UNSET;*/ 759 /*(error_handler_saved_method value is not valid unless error_handler_saved_status is set)*/ 760 761 config_reset_config(r); 762 } 763 764 static void connection_reset(connection *con) { 765 request_st * const r = &con->request; 766 request_reset(r); 767 con->is_readable = 1; 768 769 con->bytes_written = 0; 770 con->bytes_written_cur_second = 0; 771 con->bytes_read = 0; 772 } 773 774 775 __attribute_noinline__ 776 static void connection_discard_blank_line(request_st * const r, const char * const s, unsigned short * const hoff) { 777 if ((s[0] == '\r' && s[1] == '\n') 778 || (s[0] == '\n' 779 && !(r->conf.http_parseopts & HTTP_PARSEOPT_HEADER_STRICT))) { 780 hoff[2] += hoff[1]; 781 memmove(hoff+1, hoff+2, (--hoff[0] - 1) * sizeof(unsigned short)); 782 } 783 } 784 785 static chunk * connection_read_header_more(connection *con, chunkqueue *cq, chunk *c, const size_t olen) { 786 if ((NULL == c || NULL == c->next) && con->is_readable) { 787 con->read_idle_ts = log_epoch_secs; 788 if (0 != con->network_read(con, cq, MAX_READ_LIMIT)) { 789 request_st * const r = &con->request; 790 connection_set_state(r, CON_STATE_ERROR); 791 } 792 } 793 794 if (cq->first != cq->last && 0 != olen) { 795 const size_t clen = chunkqueue_length(cq); 796 size_t block = (olen + (16384-1)) & (16384-1); 797 block += (block - olen > 1024 ? 0 : 16384); 798 chunkqueue_compact_mem(cq, block > clen ? clen : block); 799 } 800 801 /* detect if data is added to chunk */ 802 c = cq->first; 803 return (c && (size_t)c->offset + olen < buffer_string_length(c->mem)) 804 ? c 805 : NULL; 806 } 807 808 __attribute_hot__ 809 static uint32_t connection_read_header_hoff(const char *n, const uint32_t clen, unsigned short hoff[8192]) { 810 uint32_t hlen = 0; 811 for (const char *b; (n = memchr((b = n),'\n',clen-hlen)); ++n) { 812 uint32_t x = (uint32_t)(n - b + 1); 813 hlen += x; 814 if (x <= 2 && (x == 1 || n[-1] == '\r')) { 815 hoff[hoff[0]+1] = hlen; 816 return hlen; 817 } 818 if (++hoff[0] >= /*sizeof(hoff)/sizeof(hoff[0])-1*/ 8192-1) break; 819 hoff[hoff[0]] = hlen; 820 } 821 return 0; 822 } 823 824 /** 825 * handle request header read 826 * 827 * we get called by the state-engine and by the fdevent-handler 828 */ 829 static int connection_handle_read_state(connection * const con) { 830 chunkqueue * const cq = con->read_queue; 831 chunk *c = cq->first; 832 uint32_t clen = 0; 833 uint32_t header_len = 0; 834 request_st * const r = &con->request; 835 int keepalive_request_start = 0; 836 int pipelined_request_start = 0; 837 unsigned short hoff[8192]; /* max num header lines + 3; 16k on stack */ 838 839 if (con->request_count > 1 && 0 == con->bytes_read) { 840 keepalive_request_start = 1; 841 if (NULL != c) { /* !chunkqueue_is_empty(cq)) */ 842 pipelined_request_start = 1; 843 /* partial header of next request has already been read, 844 * so optimistically check for more data received on 845 * socket while processing the previous request */ 846 con->is_readable = 1; 847 /*(if partially read next request and unable to read() any bytes, 848 * then will unnecessarily scan again before subsequent read())*/ 849 } 850 } 851 852 do { 853 if (NULL == c) continue; 854 clen = buffer_string_length(c->mem) - c->offset; 855 if (0 == clen) continue; 856 if (c->offset > USHRT_MAX) /*(highly unlikely)*/ 857 chunkqueue_compact_mem(cq, clen); 858 859 hoff[0] = 1; /* number of lines */ 860 hoff[1] = (unsigned short)c->offset; /* base offset for all lines */ 861 /*hoff[2] = ...;*/ /* offset from base for 2nd line */ 862 863 header_len = 864 connection_read_header_hoff(c->mem->ptr + c->offset, clen, hoff); 865 866 /* casting to (unsigned short) might truncate, and the hoff[] 867 * addition might overflow, but max_request_field_size is USHRT_MAX, 868 * so failure will be detected below */ 869 const uint32_t max_request_field_size=r->conf.max_request_field_size; 870 if ((header_len ? header_len : clen) > max_request_field_size 871 || hoff[0] >= sizeof(hoff)/sizeof(hoff[0])-1) { 872 log_error(r->conf.errh, __FILE__, __LINE__, "%s", 873 "oversized request-header -> sending Status 431"); 874 r->http_status = 431; /* Request Header Fields Too Large */ 875 r->keep_alive = 0; 876 connection_set_state(r, CON_STATE_REQUEST_END); 877 return 1; 878 } 879 880 if (0 != header_len) break; 881 if (((unsigned char *)c->mem->ptr)[c->offset] < 32) { 882 /* expecting ASCII method beginning with alpha char 883 * or HTTP/2 pseudo-header beginning with ':' */ 884 /*(TLS handshake begins with SYN 0x16 (decimal 22))*/ 885 log_error(r->conf.errh, __FILE__, __LINE__, "%s", 886 "invalid request-line -> sending Status 400"); 887 r->http_status = 400; /* Bad Request */ 888 r->keep_alive = 0; 889 connection_set_state(r, CON_STATE_REQUEST_END); 890 return 1; 891 } 892 } while ((c = connection_read_header_more(con, cq, c, clen))); 893 894 if (keepalive_request_start) { 895 if (0 != con->bytes_read) { 896 /* update r->start_ts timestamp when first byte of 897 * next request is received on a keep-alive connection */ 898 r->start_ts = log_epoch_secs; 899 if (r->conf.high_precision_timestamps) 900 log_clock_gettime_realtime(&r->start_hp); 901 } 902 if (pipelined_request_start && c) con->read_idle_ts = log_epoch_secs; 903 } 904 905 if (NULL == c) return 0; /* incomplete request headers */ 906 907 #ifdef __COVERITY__ 908 if (buffer_string_length(c->mem) < hoff[1]) { 909 return 1; 910 } 911 #endif 912 913 char * const hdrs = c->mem->ptr + hoff[1]; 914 915 if (con->request_count > 1) { 916 /* skip past \r\n or \n after previous POST request when keep-alive */ 917 if (hoff[2] - hoff[1] <= 2) 918 connection_discard_blank_line(r, hdrs, hoff); 919 920 /* clear buffers which may have been kept for reporting on keep-alive, 921 * (e.g. mod_status) */ 922 buffer_clear(&r->uri.authority); 923 buffer_reset(&r->uri.path); 924 buffer_reset(&r->uri.query); 925 buffer_reset(&r->target_orig); 926 } 927 928 if (r->conf.log_request_header) { 929 log_error(r->conf.errh, __FILE__, __LINE__, 930 "fd: %d request-len: %d\n%.*s", con->fd, (int)header_len, 931 (int)header_len, hdrs); 932 } 933 934 r->http_status = http_request_parse(r, hdrs, hoff, con->proto_default_port); 935 if (0 == r->http_status) { 936 r->conditional_is_valid = (1 << COMP_SERVER_SOCKET) 937 | (1 << COMP_HTTP_SCHEME) 938 | (1 << COMP_HTTP_HOST) 939 | (1 << COMP_HTTP_REMOTE_IP) 940 | (1 << COMP_HTTP_REQUEST_METHOD) 941 | (1 << COMP_HTTP_URL) 942 | (1 << COMP_HTTP_QUERY_STRING) 943 | (1 << COMP_HTTP_REQUEST_HEADER); 944 } 945 else { 946 r->keep_alive = 0; 947 r->reqbody_length = 0; 948 949 if (r->conf.log_request_header_on_error) { 950 /*(http_request_parse() modifies hdrs only to 951 * undo line-wrapping in-place using spaces)*/ 952 log_error(r->conf.errh, __FILE__, __LINE__, "request-header:\n%.*s", 953 (int)header_len, hdrs); 954 } 955 } 956 957 r->rqst_header_len = header_len; 958 chunkqueue_mark_written(cq, header_len); 959 connection_set_state(r, CON_STATE_REQUEST_END); 960 return 1; 961 } 962 963 static handler_t connection_handle_fdevent(void *context, int revents) { 964 connection *con = context; 965 966 joblist_append(con); 967 968 if (con->is_ssl_sock) { 969 /* ssl may read and write for both reads and writes */ 970 if (revents & (FDEVENT_IN | FDEVENT_OUT)) { 971 con->is_readable = 1; 972 con->is_writable = 1; 973 } 974 } else { 975 if (revents & FDEVENT_IN) { 976 con->is_readable = 1; 977 } 978 if (revents & FDEVENT_OUT) { 979 con->is_writable = 1; 980 /* we don't need the event twice */ 981 } 982 } 983 984 request_st * const r = &con->request; 985 986 if (r->state == CON_STATE_READ) { 987 connection_handle_read_state(con); 988 } 989 990 if (r->state == CON_STATE_WRITE && 991 !chunkqueue_is_empty(con->write_queue) && 992 con->is_writable) { 993 connection_handle_write(con); 994 } 995 996 if (r->state == CON_STATE_CLOSE) { 997 /* flush the read buffers */ 998 connection_read_for_eos(con); 999 } 1000 1001 1002 /* attempt (above) to read data in kernel socket buffers 1003 * prior to handling FDEVENT_HUP and FDEVENT_ERR */ 1004 1005 if ((revents & ~(FDEVENT_IN | FDEVENT_OUT)) && r->state != CON_STATE_ERROR) { 1006 if (r->state == CON_STATE_CLOSE) { 1007 con->close_timeout_ts = log_epoch_secs - (HTTP_LINGER_TIMEOUT+1); 1008 } else if (revents & FDEVENT_HUP) { 1009 connection_set_state(r, CON_STATE_ERROR); 1010 } else if (revents & FDEVENT_RDHUP) { 1011 int events = fdevent_fdnode_interest(con->fdn); 1012 events &= ~(FDEVENT_IN|FDEVENT_RDHUP); 1013 r->conf.stream_request_body &= ~(FDEVENT_STREAM_REQUEST_BUFMIN|FDEVENT_STREAM_REQUEST_POLLIN); 1014 r->conf.stream_request_body |= FDEVENT_STREAM_REQUEST_POLLRDHUP; 1015 con->is_readable = 1; /*(can read 0 for end-of-stream)*/ 1016 if (chunkqueue_is_empty(con->read_queue)) r->keep_alive = 0; 1017 if (r->reqbody_length < -1) { /*(transparent proxy mode; no more data to read)*/ 1018 r->reqbody_length = r->reqbody_queue->bytes_in; 1019 } 1020 if (sock_addr_get_family(&con->dst_addr) == AF_UNIX) { 1021 /* future: will getpeername() on AF_UNIX properly check if still connected? */ 1022 fdevent_fdnode_event_set(con->srv->ev, con->fdn, events); 1023 } else if (fdevent_is_tcp_half_closed(con->fd)) { 1024 /* Success of fdevent_is_tcp_half_closed() after FDEVENT_RDHUP indicates TCP FIN received, 1025 * but does not distinguish between client shutdown(fd, SHUT_WR) and client close(fd). 1026 * Remove FDEVENT_RDHUP so that we do not spin on the ready event. 1027 * However, a later TCP RST will not be detected until next write to socket. 1028 * future: might getpeername() to check for TCP RST on half-closed sockets 1029 * (without FDEVENT_RDHUP interest) when checking for write timeouts 1030 * once a second in server.c, though getpeername() on Windows might not indicate this */ 1031 r->conf.stream_request_body |= FDEVENT_STREAM_REQUEST_TCP_FIN; 1032 fdevent_fdnode_event_set(con->srv->ev, con->fdn, events); 1033 } else { 1034 /* Failure of fdevent_is_tcp_half_closed() indicates TCP RST 1035 * (or unable to tell (unsupported OS), though should not 1036 * be setting FDEVENT_RDHUP in that case) */ 1037 connection_set_state(r, CON_STATE_ERROR); 1038 } 1039 } else if (revents & FDEVENT_ERR) { /* error, connection reset */ 1040 connection_set_state(r, CON_STATE_ERROR); 1041 } else { 1042 log_error(r->conf.errh, __FILE__, __LINE__, 1043 "connection closed: poll() -> ??? %d", revents); 1044 } 1045 } 1046 1047 return HANDLER_FINISHED; 1048 } 1049 1050 1051 connection *connection_accept(server *srv, server_socket *srv_socket) { 1052 int cnt; 1053 sock_addr cnt_addr; 1054 size_t cnt_len = sizeof(cnt_addr); /*(size_t intentional; not socklen_t)*/ 1055 1056 /** 1057 * check if we can still open a new connections 1058 * 1059 * see #1216 1060 */ 1061 1062 if (srv->conns.used >= srv->max_conns) { 1063 return NULL; 1064 } 1065 1066 cnt = fdevent_accept_listenfd(srv_socket->fd, (struct sockaddr *) &cnt_addr, &cnt_len); 1067 if (-1 == cnt) { 1068 switch (errno) { 1069 case EAGAIN: 1070 #if EWOULDBLOCK != EAGAIN 1071 case EWOULDBLOCK: 1072 #endif 1073 case EINTR: 1074 /* we were stopped _before_ we had a connection */ 1075 case ECONNABORTED: /* this is a FreeBSD thingy */ 1076 /* we were stopped _after_ we had a connection */ 1077 break; 1078 case EMFILE: 1079 /* out of fds */ 1080 break; 1081 default: 1082 log_perror(srv->errh, __FILE__, __LINE__, "accept failed"); 1083 } 1084 return NULL; 1085 } else { 1086 if (sock_addr_get_family(&cnt_addr) != AF_UNIX) { 1087 network_accept_tcp_nagle_disable(cnt); 1088 } 1089 return connection_accepted(srv, srv_socket, &cnt_addr, cnt); 1090 } 1091 } 1092 1093 1094 __attribute_cold__ 1095 static int connection_read_cq_err(connection *con) { 1096 request_st * const r = &con->request; 1097 #if defined(__WIN32) 1098 int lastError = WSAGetLastError(); 1099 switch (lastError) { 1100 case EAGAIN: 1101 return 0; 1102 case EINTR: 1103 /* we have been interrupted before we could read */ 1104 con->is_readable = 1; 1105 return 0; 1106 case ECONNRESET: 1107 /* suppress logging for this error, expected for keep-alive */ 1108 break; 1109 default: 1110 log_error(r->conf.errh, __FILE__, __LINE__, 1111 "connection closed - recv failed: %d", lastError); 1112 break; 1113 } 1114 #else /* __WIN32 */ 1115 switch (errno) { 1116 case EAGAIN: 1117 return 0; 1118 case EINTR: 1119 /* we have been interrupted before we could read */ 1120 con->is_readable = 1; 1121 return 0; 1122 case ECONNRESET: 1123 /* suppress logging for this error, expected for keep-alive */ 1124 break; 1125 default: 1126 log_perror(r->conf.errh, __FILE__, __LINE__, 1127 "connection closed - read failed"); 1128 break; 1129 } 1130 #endif /* __WIN32 */ 1131 1132 connection_set_state(r, CON_STATE_ERROR); 1133 return -1; 1134 } 1135 1136 1137 /* 0: everything ok, -1: error, -2: con closed */ 1138 static int connection_read_cq(connection *con, chunkqueue *cq, off_t max_bytes) { 1139 ssize_t len; 1140 size_t mem_len = 0; 1141 1142 do { 1143 /* obtain chunk memory into which to read 1144 * fill previous chunk if it has a reasonable amount of space available 1145 * (use mem_len=0 to obtain large buffer at least half of chunk_buf_sz) 1146 */ 1147 chunk *ckpt = cq->last; 1148 char * const mem = chunkqueue_get_memory(cq, &mem_len); 1149 if (mem_len > (size_t)max_bytes) mem_len = (size_t)max_bytes; 1150 1151 #if defined(__WIN32) 1152 len = recv(con->fd, mem, mem_len, 0); 1153 #else 1154 len = read(con->fd, mem, mem_len); 1155 #endif 1156 1157 chunkqueue_use_memory(cq, ckpt, len > 0 ? len : 0); 1158 1159 if (len != (ssize_t)mem_len) { 1160 /* we got less then expected, wait for the next fd-event */ 1161 con->is_readable = 0; 1162 1163 if (len > 0) { 1164 con->bytes_read += len; 1165 return 0; 1166 } 1167 else if (0 == len) /* other end close connection -> KEEP-ALIVE */ 1168 return -2; /* (pipelining) */ 1169 else 1170 return connection_read_cq_err(con); 1171 } 1172 1173 con->bytes_read += len; 1174 max_bytes -= len; 1175 1176 int frd; 1177 mem_len = (0 == fdevent_ioctl_fionread(con->fd, S_IFSOCK, &frd)) 1178 ? (frd < max_bytes) ? (size_t)frd : (size_t)max_bytes 1179 : 0; 1180 } while (max_bytes); 1181 return 0; 1182 } 1183 1184 1185 static int connection_write_cq(connection *con, chunkqueue *cq, off_t max_bytes) { 1186 request_st * const r = &con->request; 1187 return con->srv->network_backend_write(con->fd,cq,max_bytes,r->conf.errh); 1188 } 1189 1190 1191 connection *connection_accepted(server *srv, server_socket *srv_socket, sock_addr *cnt_addr, int cnt) { 1192 connection *con; 1193 1194 srv->cur_fds++; 1195 1196 /* ok, we have the connection, register it */ 1197 #if 0 1198 log_error(srv->errh, __FILE__, __LINE__, "accepted() %d", cnt); 1199 #endif 1200 srv->con_opened++; 1201 1202 con = connections_get_new_connection(srv); 1203 1204 con->fd = cnt; 1205 con->fdn = fdevent_register(srv->ev, con->fd, connection_handle_fdevent, con); 1206 con->network_read = connection_read_cq; 1207 con->network_write = connection_write_cq; 1208 1209 request_st * const r = &con->request; 1210 connection_set_state(r, CON_STATE_REQUEST_START); 1211 1212 con->connection_start = log_epoch_secs; 1213 con->dst_addr = *cnt_addr; 1214 buffer_copy_string(con->dst_addr_buf, inet_ntop_cache_get_ip(srv, &(con->dst_addr))); 1215 con->srv_socket = srv_socket; 1216 con->is_ssl_sock = srv_socket->is_ssl; 1217 con->proto_default_port = 80; /* "http" */ 1218 1219 config_cond_cache_reset(r); 1220 r->conditional_is_valid = (1 << COMP_SERVER_SOCKET) 1221 | (1 << COMP_HTTP_REMOTE_IP); 1222 1223 if (HANDLER_GO_ON != plugins_call_handle_connection_accept(con)) { 1224 connection_reset(con); 1225 connection_close(con); 1226 return NULL; 1227 } 1228 if (r->http_status < 0) connection_set_state(r, CON_STATE_WRITE); 1229 return con; 1230 } 1231 1232 1233 static int connection_handle_request(request_st * const r) { 1234 const plugin *p = r->handler_module; 1235 int rc; 1236 if (NULL != p 1237 || ((rc = http_response_prepare(r)) == HANDLER_GO_ON 1238 && NULL != (p = r->handler_module))) 1239 rc = p->handle_subrequest(r, p->data); 1240 switch (rc) { 1241 case HANDLER_WAIT_FOR_EVENT: 1242 if (!r->resp_body_finished && (!r->resp_body_started || 0 == r->conf.stream_response_body)) { 1243 break; /* come back here */ 1244 } 1245 /* response headers received from backend; fall through to start response */ 1246 /* fall through */ 1247 case HANDLER_GO_ON: /*(HANDLER_FINISHED if request not handled)*/ 1248 case HANDLER_FINISHED: 1249 if (r->http_status == 0) r->http_status = 200; 1250 if (r->error_handler_saved_status > 0) { 1251 r->http_method = r->error_handler_saved_method; 1252 } 1253 if (NULL == r->handler_module || r->conf.error_intercept) { 1254 if (r->error_handler_saved_status) { 1255 const int subreq_status = r->http_status; 1256 if (r->error_handler_saved_status > 0) { 1257 r->http_status = r->error_handler_saved_status; 1258 } else if (r->http_status == 404 || r->http_status == 403) { 1259 /* error-handler-404 is a 404 */ 1260 r->http_status = -r->error_handler_saved_status; 1261 } else { 1262 /* error-handler-404 is back and has generated content */ 1263 /* if Status: was set, take it otherwise use 200 */ 1264 } 1265 if (200 <= subreq_status && subreq_status <= 299) { 1266 /*(flag value to indicate that error handler succeeded) 1267 *(for (NULL == r->handler_module))*/ 1268 r->error_handler_saved_status = 65535; /* >= 1000 */ 1269 } 1270 } else if (r->http_status >= 400) { 1271 const buffer *error_handler = NULL; 1272 if (!buffer_string_is_empty(r->conf.error_handler)) { 1273 error_handler = r->conf.error_handler; 1274 } else if ((r->http_status == 404 || r->http_status == 403) 1275 && !buffer_string_is_empty(r->conf.error_handler_404)) { 1276 error_handler = r->conf.error_handler_404; 1277 } 1278 1279 if (error_handler) { 1280 /* call error-handler */ 1281 1282 /* set REDIRECT_STATUS to save current HTTP status code 1283 * for access by dynamic handlers 1284 * https://redmine.lighttpd.net/issues/1828 */ 1285 buffer * const tb = r->tmp_buf; 1286 buffer_clear(tb); 1287 buffer_append_int(tb, r->http_status); 1288 http_header_env_set(r, CONST_STR_LEN("REDIRECT_STATUS"), CONST_BUF_LEN(tb)); 1289 1290 if (error_handler == r->conf.error_handler) { 1291 plugins_call_handle_request_reset(r); 1292 1293 if (r->reqbody_length) { 1294 if (r->reqbody_length != r->reqbody_queue->bytes_in) { 1295 r->keep_alive = 0; 1296 } 1297 r->reqbody_length = 0; 1298 chunkqueue_reset(r->reqbody_queue); 1299 } 1300 1301 r->con->is_writable = 1; 1302 r->resp_body_finished = 0; 1303 r->resp_body_started = 0; 1304 1305 r->error_handler_saved_status = r->http_status; 1306 r->error_handler_saved_method = r->http_method; 1307 1308 r->http_method = HTTP_METHOD_GET; 1309 } else { /*(preserve behavior for server.error-handler-404)*/ 1310 r->error_handler_saved_status = -r->http_status; /*(negative to flag old behavior)*/ 1311 } 1312 1313 if (r->http_version == HTTP_VERSION_UNSET) r->http_version = HTTP_VERSION_1_0; 1314 1315 buffer_copy_buffer(&r->target, error_handler); 1316 connection_handle_errdoc_init(r); 1317 r->http_status = 0; /*(after connection_handle_errdoc_init())*/ 1318 http_response_comeback(r); 1319 return 1; 1320 } 1321 } 1322 } 1323 1324 /* we have something to send, go on */ 1325 connection_set_state(r, CON_STATE_RESPONSE_START); 1326 break; 1327 case HANDLER_WAIT_FOR_FD: 1328 connection_fdwaitqueue_append(r->con); 1329 break; 1330 case HANDLER_COMEBACK: 1331 http_response_comeback(r); 1332 return 1; 1333 /*case HANDLER_ERROR:*/ 1334 default: 1335 /* something went wrong */ 1336 connection_set_state(r, CON_STATE_ERROR); 1337 break; 1338 } 1339 1340 return 0; 1341 } 1342 1343 1344 int connection_state_machine(connection *con) { 1345 request_st * const r = &con->request; 1346 request_state_t ostate; 1347 int rc; 1348 const int log_state_handling = r->conf.log_state_handling; 1349 1350 if (log_state_handling) { 1351 log_error(r->conf.errh, __FILE__, __LINE__, 1352 "state at enter %d %s", con->fd, connection_get_state(r->state)); 1353 } 1354 1355 do { 1356 if (log_state_handling) { 1357 log_error(r->conf.errh, __FILE__, __LINE__, 1358 "state for fd %d %s", con->fd, connection_get_state(r->state)); 1359 } 1360 1361 switch ((ostate = r->state)) { 1362 case CON_STATE_REQUEST_START: /* transient */ 1363 r->start_ts = con->read_idle_ts = log_epoch_secs; 1364 if (r->conf.high_precision_timestamps) 1365 log_clock_gettime_realtime(&r->start_hp); 1366 1367 con->request_count++; 1368 r->loops_per_request = 0; 1369 1370 connection_set_state(r, CON_STATE_READ); 1371 /* fall through */ 1372 case CON_STATE_READ: 1373 if (!connection_handle_read_state(con)) break; 1374 /*if (r->state != CON_STATE_REQUEST_END) break;*/ 1375 /* fall through */ 1376 case CON_STATE_REQUEST_END: /* transient */ 1377 ostate = (0 == r->reqbody_length) 1378 ? CON_STATE_HANDLE_REQUEST 1379 : CON_STATE_READ_POST; 1380 connection_set_state(r, ostate); 1381 /* fall through */ 1382 case CON_STATE_READ_POST: 1383 case CON_STATE_HANDLE_REQUEST: 1384 if (connection_handle_request(r)) { 1385 /* redo loop; will not match r->state */ 1386 ostate = CON_STATE_CONNECT; 1387 break; 1388 } 1389 1390 if (r->state == CON_STATE_HANDLE_REQUEST 1391 && ostate == CON_STATE_READ_POST) { 1392 ostate = CON_STATE_HANDLE_REQUEST; 1393 } 1394 1395 if (r->state != CON_STATE_RESPONSE_START) break; 1396 /* fall through */ 1397 case CON_STATE_RESPONSE_START: /* transient */ 1398 if (-1 == connection_handle_write_prepare(r)) { 1399 connection_set_state(r, CON_STATE_ERROR); 1400 break; 1401 } 1402 connection_set_state(r, CON_STATE_WRITE); 1403 /* fall through */ 1404 case CON_STATE_WRITE: 1405 connection_handle_write_state(r, con); 1406 if (r->state != CON_STATE_RESPONSE_END) break; 1407 /* fall through */ 1408 case CON_STATE_RESPONSE_END: /* transient */ 1409 case CON_STATE_ERROR: /* transient */ 1410 connection_handle_response_end_state(r, con); 1411 break; 1412 case CON_STATE_CLOSE: 1413 connection_handle_close_state(con); 1414 break; 1415 case CON_STATE_CONNECT: 1416 break; 1417 default: 1418 log_error(r->conf.errh, __FILE__, __LINE__, 1419 "unknown state: %d %d", con->fd, r->state); 1420 break; 1421 } 1422 } while (ostate != (request_state_t)r->state); 1423 1424 if (log_state_handling) { 1425 log_error(r->conf.errh, __FILE__, __LINE__, 1426 "state at exit: %d %s", con->fd, connection_get_state(r->state)); 1427 } 1428 1429 rc = 0; 1430 switch(r->state) { 1431 case CON_STATE_READ: 1432 rc = FDEVENT_IN | FDEVENT_RDHUP; 1433 break; 1434 case CON_STATE_WRITE: 1435 /* request write-fdevent only if we really need it 1436 * - if we have data to write 1437 * - if the socket is not writable yet 1438 */ 1439 if (!chunkqueue_is_empty(con->write_queue) && 1440 (con->is_writable == 0) && 1441 (con->traffic_limit_reached == 0)) { 1442 rc |= FDEVENT_OUT; 1443 } 1444 /* fall through */ 1445 case CON_STATE_READ_POST: 1446 if (r->conf.stream_request_body & FDEVENT_STREAM_REQUEST_POLLIN) { 1447 rc |= FDEVENT_IN | FDEVENT_RDHUP; 1448 } 1449 break; 1450 case CON_STATE_CLOSE: 1451 rc = FDEVENT_IN; 1452 break; 1453 default: 1454 break; 1455 } 1456 if (con->fd >= 0) { 1457 const int events = fdevent_fdnode_interest(con->fdn); 1458 if (con->is_readable < 0) { 1459 con->is_readable = 0; 1460 rc |= FDEVENT_IN; 1461 } 1462 if (con->is_writable < 0) { 1463 con->is_writable = 0; 1464 rc |= FDEVENT_OUT; 1465 } 1466 if (events & FDEVENT_RDHUP) { 1467 rc |= FDEVENT_RDHUP; 1468 } 1469 if (rc != events) { 1470 /* update timestamps when enabling interest in events */ 1471 if ((rc & FDEVENT_IN) && !(events & FDEVENT_IN)) { 1472 con->read_idle_ts = log_epoch_secs; 1473 } 1474 if ((rc & FDEVENT_OUT) && !(events & FDEVENT_OUT)) { 1475 con->write_request_ts = log_epoch_secs; 1476 } 1477 fdevent_fdnode_event_set(con->srv->ev, con->fdn, rc); 1478 } 1479 } 1480 1481 return 0; 1482 } 1483 1484 static void connection_check_timeout (connection * const con, const time_t cur_ts) { 1485 const int waitevents = fdevent_fdnode_interest(con->fdn); 1486 int changed = 0; 1487 int t_diff; 1488 1489 request_st * const r = &con->request; 1490 if (r->state == CON_STATE_CLOSE) { 1491 if (cur_ts - con->close_timeout_ts > HTTP_LINGER_TIMEOUT) { 1492 changed = 1; 1493 } 1494 } else if (waitevents & FDEVENT_IN) { 1495 if (con->request_count == 1 || r->state != CON_STATE_READ) { 1496 /* e.g. CON_STATE_READ_POST || CON_STATE_WRITE */ 1497 if (cur_ts - con->read_idle_ts > r->conf.max_read_idle) { 1498 /* time - out */ 1499 if (r->conf.log_request_handling) { 1500 log_error(r->conf.errh, __FILE__, __LINE__, 1501 "connection closed - read timeout: %d", con->fd); 1502 } 1503 1504 connection_set_state(r, CON_STATE_ERROR); 1505 changed = 1; 1506 } 1507 } else { 1508 if (cur_ts - con->read_idle_ts > con->keep_alive_idle) { 1509 /* time - out */ 1510 if (r->conf.log_request_handling) { 1511 log_error(r->conf.errh, __FILE__, __LINE__, 1512 "connection closed - keep-alive timeout: %d", 1513 con->fd); 1514 } 1515 1516 connection_set_state(r, CON_STATE_ERROR); 1517 changed = 1; 1518 } 1519 } 1520 } 1521 1522 /* max_write_idle timeout currently functions as backend timeout, 1523 * too, after response has been started. 1524 * future: have separate backend timeout, and then change this 1525 * to check for write interest before checking for timeout */ 1526 /*if (waitevents & FDEVENT_OUT)*/ 1527 if ((r->state == CON_STATE_WRITE) && 1528 (con->write_request_ts != 0)) { 1529 #if 0 1530 if (cur_ts - con->write_request_ts > 60) { 1531 log_error(r->conf.errh, __FILE__, __LINE__, 1532 "connection closed - pre-write-request-timeout: %d %d", 1533 con->fd, cur_ts - con->write_request_ts); 1534 } 1535 #endif 1536 1537 if (cur_ts - con->write_request_ts > r->conf.max_write_idle) { 1538 /* time - out */ 1539 if (r->conf.log_timeouts) { 1540 log_error(r->conf.errh, __FILE__, __LINE__, 1541 "NOTE: a request from %.*s for %.*s timed out after writing " 1542 "%lld bytes. We waited %d seconds. If this is a problem, " 1543 "increase server.max-write-idle", 1544 BUFFER_INTLEN_PTR(con->dst_addr_buf), 1545 BUFFER_INTLEN_PTR(&r->target), 1546 (long long)con->bytes_written, (int)r->conf.max_write_idle); 1547 } 1548 connection_set_state(r, CON_STATE_ERROR); 1549 changed = 1; 1550 } 1551 } 1552 1553 if (0 == (t_diff = cur_ts - con->connection_start)) t_diff = 1; 1554 1555 if (con->traffic_limit_reached && 1556 (r->conf.bytes_per_second == 0 || 1557 con->bytes_written < (off_t)r->conf.bytes_per_second * t_diff)) { 1558 /* enable connection again */ 1559 con->traffic_limit_reached = 0; 1560 1561 changed = 1; 1562 } 1563 1564 con->bytes_written_cur_second = 0; 1565 1566 if (changed) { 1567 connection_state_machine(con); 1568 } 1569 } 1570 1571 void connection_periodic_maint (server * const srv, const time_t cur_ts) { 1572 /* check all connections for timeouts */ 1573 connections * const conns = &srv->conns; 1574 for (size_t ndx = 0; ndx < conns->used; ++ndx) { 1575 connection_check_timeout(conns->ptr[ndx], cur_ts); 1576 } 1577 } 1578 1579 void connection_graceful_shutdown_maint (server *srv) { 1580 connections * const conns = &srv->conns; 1581 for (size_t ndx = 0; ndx < conns->used; ++ndx) { 1582 connection * const con = conns->ptr[ndx]; 1583 int changed = 0; 1584 1585 request_st * const r = &con->request; 1586 if (r->state == CON_STATE_CLOSE) { 1587 /* reduce remaining linger timeout to be 1588 * (from zero) *up to* one more second, but no more */ 1589 if (HTTP_LINGER_TIMEOUT > 1) 1590 con->close_timeout_ts -= (HTTP_LINGER_TIMEOUT - 1); 1591 if (log_epoch_secs - con->close_timeout_ts > HTTP_LINGER_TIMEOUT) 1592 changed = 1; 1593 } 1594 else if (r->state == CON_STATE_READ && con->request_count > 1 1595 && chunkqueue_is_empty(con->read_queue)) { 1596 /* close connections in keep-alive waiting for next request */ 1597 connection_set_state(r, CON_STATE_ERROR); 1598 changed = 1; 1599 } 1600 1601 r->keep_alive = 0; /* disable keep-alive */ 1602 1603 r->conf.bytes_per_second = 0; /* disable rate limit */ 1604 r->conf.global_bytes_per_second = 0; /* disable rate limit */ 1605 if (con->traffic_limit_reached) { 1606 con->traffic_limit_reached = 0; 1607 changed = 1; 1608 } 1609 1610 if (changed) { 1611 connection_state_machine(con); 1612 } 1613 } 1614 } 1615