📄 ngx_http_upstream.c
字号:
c->log->action = "sending request to upstream"; rc = ngx_output_chain(&u->output, u->request_sent ? NULL : u->request_bufs); u->request_sent = 1; if (rc == NGX_ERROR) { ngx_http_upstream_next(r, u, NGX_HTTP_UPSTREAM_FT_ERROR); return; } if (c->write->timer_set) { ngx_del_timer(c->write); } if (rc == NGX_AGAIN) { ngx_add_timer(c->write, u->conf->send_timeout); if (ngx_handle_write_event(c->write, u->conf->send_lowat) == NGX_ERROR) { ngx_http_upstream_finalize_request(r, u, NGX_HTTP_INTERNAL_SERVER_ERROR); return; } return; } /* rc == NGX_OK */ if (c->tcp_nopush == NGX_TCP_NOPUSH_SET) { if (ngx_tcp_push(c->fd) == NGX_ERROR) { ngx_log_error(NGX_LOG_CRIT, c->log, ngx_socket_errno, ngx_tcp_push_n " failed"); ngx_http_upstream_finalize_request(r, u, NGX_HTTP_INTERNAL_SERVER_ERROR); return; } c->tcp_nopush = NGX_TCP_NOPUSH_UNSET; } ngx_add_timer(c->read, u->conf->read_timeout);#if 1 if (c->read->ready) { /* post aio operation */ /* * TODO comment * although we can post aio operation just in the end * of ngx_http_upstream_connect() CHECK IT !!! * it's better to do here because we postpone header buffer allocation */ ngx_http_upstream_process_header(c->read); return; }#endif c->write->handler = ngx_http_upstream_dummy_handler; if (ngx_handle_write_event(c->write, 0) == NGX_ERROR) { ngx_http_upstream_finalize_request(r, u, NGX_HTTP_INTERNAL_SERVER_ERROR); return; }}static voidngx_http_upstream_send_request_handler(ngx_event_t *wev){ ngx_connection_t *c; ngx_http_request_t *r; ngx_http_upstream_t *u; c = wev->data; r = c->data; u = r->upstream; ngx_log_debug0(NGX_LOG_DEBUG_HTTP, wev->log, 0, "http upstream send request handler"); if (wev->timedout) { ngx_http_upstream_next(r, u, NGX_HTTP_UPSTREAM_FT_TIMEOUT); return; }#if (NGX_HTTP_SSL) if (u->ssl && c->ssl == NULL) { ngx_http_upstream_ssl_init_connection(r, u, c); return; }#endif if (u->header_sent) { wev->handler = ngx_http_upstream_dummy_handler; (void) ngx_handle_write_event(wev, 0); return; } ngx_http_upstream_send_request(r, u);}static voidngx_http_upstream_process_header(ngx_event_t *rev){ ssize_t n; ngx_int_t rc; ngx_str_t *uri, args; ngx_uint_t i, flags; ngx_list_part_t *part; ngx_table_elt_t *h; ngx_connection_t *c; ngx_http_request_t *r; ngx_http_upstream_t *u; ngx_http_err_page_t *err_page; ngx_http_core_loc_conf_t *clcf; ngx_http_upstream_header_t *hh; ngx_http_upstream_main_conf_t *umcf; c = rev->data; r = c->data; u = r->upstream; ngx_log_debug0(NGX_LOG_DEBUG_HTTP, rev->log, 0, "http upstream process header"); c->log->action = "reading response header from upstream"; if (rev->timedout) { ngx_http_upstream_next(r, u, NGX_HTTP_UPSTREAM_FT_TIMEOUT); return; } if (!u->request_sent && ngx_http_upstream_test_connect(c) != NGX_OK) { ngx_http_upstream_next(r, u, NGX_HTTP_UPSTREAM_FT_ERROR); return; } if (u->buffer.start == NULL) { u->buffer.start = ngx_palloc(r->pool, u->conf->buffer_size); if (u->buffer.start == NULL) { ngx_http_upstream_finalize_request(r, u, NGX_HTTP_INTERNAL_SERVER_ERROR); return; } u->buffer.pos = u->buffer.start; u->buffer.last = u->buffer.start; u->buffer.end = u->buffer.start + u->conf->buffer_size; u->buffer.temporary = 1; u->buffer.tag = u->output.tag; if (ngx_list_init(&u->headers_in.headers, r->pool, 8, sizeof(ngx_table_elt_t)) != NGX_OK) { ngx_http_upstream_finalize_request(r, u, NGX_HTTP_INTERNAL_SERVER_ERROR); return; }#if 0 if (u->cache) { u->buffer.pos += u->cache->ctx.header_size; u->buffer.last = u->buffer.pos; }#endif } n = c->recv(c, u->buffer.last, u->buffer.end - u->buffer.last); if (n == NGX_AGAIN) {#if 0 ngx_add_timer(rev, u->read_timeout);#endif if (ngx_handle_read_event(rev, 0) == NGX_ERROR) { ngx_http_upstream_finalize_request(r, u, NGX_HTTP_INTERNAL_SERVER_ERROR); return; } return; } if (n == 0) { ngx_log_error(NGX_LOG_ERR, rev->log, 0, "upstream prematurely closed connection"); } if (n == NGX_ERROR || n == 0) { ngx_http_upstream_next(r, u, NGX_HTTP_UPSTREAM_FT_ERROR); return; } u->buffer.last += n;#if 0 u->valid_header_in = 0; u->peer.cached = 0;#endif rc = u->process_header(r); if (rc == NGX_AGAIN) {#if 0 ngx_add_timer(rev, u->read_timeout);#endif if (u->buffer.pos == u->buffer.end) { ngx_log_error(NGX_LOG_ERR, rev->log, 0, "upstream sent too big header"); ngx_http_upstream_next(r, u, NGX_HTTP_UPSTREAM_FT_INVALID_HEADER); return; } if (ngx_handle_read_event(rev, 0) == NGX_ERROR) { ngx_http_upstream_finalize_request(r, u, NGX_HTTP_INTERNAL_SERVER_ERROR); return; } return; } if (rc == NGX_HTTP_UPSTREAM_INVALID_HEADER) { ngx_http_upstream_next(r, u, NGX_HTTP_UPSTREAM_FT_INVALID_HEADER); return; } if (rc == NGX_ERROR) { ngx_http_upstream_finalize_request(r, u, NGX_HTTP_INTERNAL_SERVER_ERROR); return; } /* rc == NGX_OK */ if (u->headers_in.status_n >= NGX_HTTP_BAD_REQUEST && r->subrequest_in_memory) { u->buffer.last = u->buffer.pos; } if (u->headers_in.status_n == NGX_HTTP_INTERNAL_SERVER_ERROR) { if (u->peer.tries > 1 && (u->conf->next_upstream & NGX_HTTP_UPSTREAM_FT_HTTP_500)) { ngx_http_upstream_next(r, u, NGX_HTTP_UPSTREAM_FT_HTTP_500); return; }#if (NGX_HTTP_CACHE) if (u->peer.tries == 0 && u->stale && (u->conf->use_stale & NGX_HTTP_UPSTREAM_FT_HTTP_500)) { ngx_http_upstream_finalize_request(r, u, ngx_http_send_cached_response(r)); return; }#endif } if (u->headers_in.status_n == NGX_HTTP_NOT_FOUND) { if (u->peer.tries > 1 && u->conf->next_upstream & NGX_HTTP_UPSTREAM_FT_HTTP_404) { ngx_http_upstream_next(r, u, NGX_HTTP_UPSTREAM_FT_HTTP_404); return; } if (u->conf->intercept_404) { ngx_http_upstream_finalize_request(r, u, NGX_HTTP_NOT_FOUND); return; } } if (u->headers_in.status_n >= NGX_HTTP_BAD_REQUEST && u->conf->intercept_errors) { clcf = ngx_http_get_module_loc_conf(r, ngx_http_core_module); if (clcf->error_pages) { err_page = clcf->error_pages->elts; for (i = 0; i < clcf->error_pages->nelts; i++) { if (err_page[i].status == (ngx_int_t) u->headers_in.status_n) { if (u->headers_in.status_n == NGX_HTTP_UNAUTHORIZED) { r->headers_out.www_authenticate = ngx_list_push(&r->headers_out.headers); if (r->headers_out.www_authenticate == NULL) { ngx_http_upstream_finalize_request(r, u, NGX_HTTP_INTERNAL_SERVER_ERROR); return; } *r->headers_out.www_authenticate = *u->headers_in.www_authenticate; } ngx_http_upstream_finalize_request(r, u, u->headers_in.status_n); return; } } } } umcf = ngx_http_get_module_main_conf(r, ngx_http_upstream_module); if (u->headers_in.x_accel_redirect) { ngx_http_upstream_finalize_request(r, u, NGX_DECLINED); part = &u->headers_in.headers.part; h = part->elts; for (i = 0; /* void */; i++) { if (i >= part->nelts) { if (part->next == NULL) { break; } part = part->next; h = part->elts; i = 0; } hh = ngx_hash_find(&umcf->headers_in_hash, h[i].hash, h[i].lowcase_key, h[i].key.len); if (hh && hh->redirect) { if (hh->copy_handler(r, &h[i], hh->conf) != NGX_OK) { ngx_http_finalize_request(r, NGX_HTTP_INTERNAL_SERVER_ERROR); return; } } } uri = &u->headers_in.x_accel_redirect->value; args.len = 0; args.data = NULL; flags = 0; if (ngx_http_parse_unsafe_uri(r, uri, &args, &flags) != NGX_OK) { ngx_http_finalize_request(r, NGX_HTTP_NOT_FOUND); return; } if (flags & NGX_HTTP_ZERO_IN_URI) { r->zero_in_uri = 1; } if (r->method != NGX_HTTP_HEAD) { r->method = NGX_HTTP_GET; } ngx_http_internal_redirect(r, uri, &args); return; } part = &u->headers_in.headers.part; h = part->elts; for (i = 0; /* void */; i++) { if (i >= part->nelts) { if (part->next == NULL) { break; } part = part->next; h = part->elts; i = 0; } if (ngx_hash_find(&u->conf->hide_headers_hash, h[i].hash, h[i].lowcase_key, h[i].key.len)) { continue; } hh = ngx_hash_find(&umcf->headers_in_hash, h[i].hash, h[i].lowcase_key, h[i].key.len); if (hh) { if (hh->copy_handler(r, &h[i], hh->conf) != NGX_OK) { ngx_http_upstream_finalize_request(r, u, NGX_HTTP_INTERNAL_SERVER_ERROR); return; } continue; } if (ngx_http_upstream_copy_header_line(r, &h[i], 0) != NGX_OK) { ngx_http_upstream_finalize_request(r, u, NGX_HTTP_INTERNAL_SERVER_ERROR); return; } } if (r->headers_out.server && r->headers_out.server->value.data == NULL) { r->headers_out.server->hash = 0; } if (r->headers_out.date && r->headers_out.date->value.data == NULL) { r->headers_out.date->hash = 0; } r->headers_out.status = u->headers_in.status_n; r->headers_out.status_line = u->headers_in.status_line; u->headers_in.content_length_n = r->headers_out.content_length_n; if (r->headers_out.content_length_n != -1) { u->length = (size_t) r->headers_out.content_length_n; } else { u->length = NGX_MAX_SIZE_T_VALUE; } if (!r->subrequest_in_memory) { ngx_http_upstream_send_response(r, u); return; } /* subrequest content in memory */ if (u->input_filter == NULL) { u->input_filter_init = ngx_http_upstream_non_buffered_filter_init; u->input_filter = ngx_http_upstream_non_buffered_filter; u->input_filter_ctx = r; } if (u->input_filter_init(u->input_filter_ctx) == NGX_ERROR) {
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -