diff options
Diffstat (limited to 'src/http')
-rw-r--r-- | src/http/modules/ngx_http_event_proxy_handler.c | 95 | ||||
-rw-r--r-- | src/http/modules/ngx_http_index_handler.c | 42 | ||||
-rw-r--r-- | src/http/modules/ngx_http_static_handler.c | 3 | ||||
-rw-r--r-- | src/http/ngx_http.c | 340 | ||||
-rw-r--r-- | src/http/ngx_http.h | 28 | ||||
-rw-r--r-- | src/http/ngx_http_config.c | 316 | ||||
-rw-r--r-- | src/http/ngx_http_config.h | 9 | ||||
-rw-r--r-- | src/http/ngx_http_core.c | 335 | ||||
-rw-r--r-- | src/http/ngx_http_core.h | 30 | ||||
-rw-r--r-- | src/http/ngx_http_core_module.c | 710 | ||||
-rw-r--r-- | src/http/ngx_http_core_module.h | 86 | ||||
-rw-r--r-- | src/http/ngx_http_event.c | 113 | ||||
-rw-r--r-- | src/http/ngx_http_header_filter.c | 1 | ||||
-rw-r--r-- | src/http/ngx_http_output_filter.c | 25 | ||||
-rw-r--r-- | src/http/ngx_http_parse.c | 64 | ||||
-rw-r--r-- | src/http/ngx_http_parse_time.c | 67 | ||||
-rw-r--r-- | src/http/ngx_http_write_filter.c | 39 |
17 files changed, 1444 insertions, 859 deletions
diff --git a/src/http/modules/ngx_http_event_proxy_handler.c b/src/http/modules/ngx_http_event_proxy_handler.c index 9c2cc3ade..c4594e60a 100644 --- a/src/http/modules/ngx_http_event_proxy_handler.c +++ b/src/http/modules/ngx_http_event_proxy_handler.c @@ -39,13 +39,15 @@ int ngx_http_proxy_handler(ngx_http_request_t *r) p = (ngx_http_proxy_ctx_t *) ngx_http_get_module_ctx(r, ngx_http_proxy_module_ctx); - if (p == NULL) + if (p == NULL) { ngx_http_create_ctx(r, p, ngx_http_proxy_module_ctx, sizeof(ngx_http_proxy_ctx_t)); + } chain = ngx_http_proxy_create_request(r); - if (chain == NULL) + if (chain == NULL) { return NGX_ERROR; + } p->out = chain; @@ -75,11 +77,13 @@ static ngx_chain_t *ngx_http_proxy_create_request(ngx_http_request_t *r) header = (ngx_table_elt_t *) r->headers_in.headers->elts; for (i = 0; i < r->headers_in.headers->nelts; i++) { - if (&header[i] == r->headers_in.host) + if (&header[i] == r->headers_in.host) { continue; + } - if (&header[i] == r->headers_in.connection) + if (&header[i] == r->headers_in.connection) { continue; + } /* 2 is for ": " and 2 is for "\r\n" */ len += header[i].key.len + 2 + header[i].value.len + 2; @@ -98,11 +102,13 @@ static ngx_chain_t *ngx_http_proxy_create_request(ngx_http_request_t *r) hunk->last.mem += sizeof(conn_close) - 1; for (i = 0; i < r->headers_in.headers->nelts; i++) { - if (&header[i] == r->headers_in.host) + if (&header[i] == r->headers_in.host) { continue; + } - if (&header[i] == r->headers_in.connection) + if (&header[i] == r->headers_in.connection) { continue; + } ngx_memcpy(hunk->last.mem, header[i].key.data, header[i].key.len); hunk->last.mem += header[i].key.len; @@ -115,7 +121,7 @@ static ngx_chain_t *ngx_http_proxy_create_request(ngx_http_request_t *r) *(hunk->last.mem++) = CR; *(hunk->last.mem++) = LF; ngx_log_debug(r->connection->log, "proxy: '%s: %s'" _ - header[i].key.data _ header[i].value.data); + header[i].key.data _ header[i].value.data); } /* add "\r\n" at the header end */ @@ -157,9 +163,10 @@ static int ngx_http_proxy_connect(ngx_http_request_t *r, ngx_log_error(NGX_LOG_ALERT, c->log, ngx_socket_errno, "setsockopt(SO_RCVBUF) failed"); - if (ngx_close_socket(s) == -1) + if (ngx_close_socket(s) == -1) { ngx_log_error(NGX_LOG_ERR, c->log, ngx_socket_errno, ngx_close_socket_n " failed"); + } return NGX_ERROR; } @@ -170,9 +177,10 @@ static int ngx_http_proxy_connect(ngx_http_request_t *r, ngx_log_error(NGX_LOG_ALERT, c->log, ngx_socket_errno, ngx_nonblocking_n " failed"); - if (ngx_close_socket(s) == -1) + if (ngx_close_socket(s) == -1) { ngx_log_error(NGX_LOG_ERR, c->log, ngx_socket_errno, ngx_close_socket_n " failed"); + } return NGX_ERROR; } @@ -184,9 +192,10 @@ static int ngx_http_proxy_connect(ngx_http_request_t *r, if (err != NGX_EINPROGRESS) { ngx_log_error(NGX_LOG_ERR, c->log, err, "connect() failed"); - if (ngx_close_socket(s) == -1) + if (ngx_close_socket(s) == -1) { ngx_log_error(NGX_LOG_ERR, c->log, ngx_socket_errno, ngx_close_socket_n " failed"); + } return NGX_ERROR; } @@ -207,7 +216,6 @@ static int ngx_http_proxy_connect(ngx_http_request_t *r, pc->data = r; pc->fd = s; - pc->server = c->server; pc->servers = c->servers; pc->log = rev->log = wev->log = c->log; @@ -220,14 +228,16 @@ static int ngx_http_proxy_connect(ngx_http_request_t *r, rev->event_handler = ngx_http_proxy_read_response_header; #if (HAVE_CLEAR_EVENT) - if (ngx_add_event(rev, NGX_READ_EVENT, NGX_CLEAR_EVENT) != NGX_OK) + if (ngx_add_event(rev, NGX_READ_EVENT, NGX_CLEAR_EVENT) != NGX_OK) { #else - if (ngx_add_event(rev, NGX_READ_EVENT, NGX_LEVEL_EVENT) != NGX_OK) + if (ngx_add_event(rev, NGX_READ_EVENT, NGX_LEVEL_EVENT) != NGX_OK) { #endif return NGX_ERROR; + } - if (rc == -1) + if (rc == -1) { return ngx_add_event(wev, NGX_WRITE_EVENT, NGX_ONESHOT_EVENT); + } wev->write = 1; wev->ready = 1; @@ -249,8 +259,9 @@ static int ngx_http_proxy_send_request(ngx_event_t *ev) ngx_http_get_module_ctx(r, ngx_http_proxy_module_ctx); chain = ngx_event_write(c, p->out, 0); - if (chain == (ngx_chain_t *) -1) + if (chain == (ngx_chain_t *) -1) { return NGX_ERROR; + } p->out = chain; @@ -266,8 +277,9 @@ static int ngx_http_proxy_read_response_header(ngx_event_t *ev) ngx_http_request_t *r; ngx_http_proxy_ctx_t *p; - if (ev->timedout) + if (ev->timedout) { return NGX_ERROR; + } c = (ngx_connection_t *) ev->data; r = (ngx_http_request_t *) c->data; @@ -330,8 +342,9 @@ static int ngx_http_proxy_read_response_header(ngx_event_t *ev) do { rc = (p->state_handler)(r, p); - if (rc == NGX_ERROR) + if (rc == NGX_ERROR) { return rc; + } /* rc == NGX_OK || rc == NGX_AGAIN */ @@ -339,8 +352,9 @@ static int ngx_http_proxy_read_response_header(ngx_event_t *ev) #endif ev->event_handler = ngx_http_proxy_read_response_body; - if (p->header_in->end - p->header_in->last.mem == 0) + if (p->header_in->end - p->header_in->last.mem == 0) { return ngx_http_proxy_read_response_body(ev); + } return NGX_WAITING; } @@ -406,11 +420,15 @@ static int ngx_http_proxy_read_response_body(ngx_event_t *ev) #if (HAVE_KQUEUE) #if !(USE_KQUEUE) - if (ngx_event_type == NGX_KQUEUE_EVENT) + if (ngx_event_type == NGX_KQUEUE_EVENT) { #endif /* do not allocate new block if there is EOF */ - if (ev->eof && ev->available == 0) + if (ev->eof && ev->available == 0) { left = 1; + } +#if !(USE_KQUEUE) + } +#endif #endif if (left == 0) { ngx_test_null(ph, ngx_push_array(p->hunks), NGX_ERROR); @@ -427,11 +445,13 @@ static int ngx_http_proxy_read_response_body(ngx_event_t *ev) ngx_log_debug(c->log, "READ:%d" _ n); - if (n == NGX_AGAIN) + if (n == NGX_AGAIN) { return NGX_WAITING; + } - if (n == NGX_ERROR) + if (n == NGX_ERROR) { return NGX_ERROR; + } h->last.mem += n; left = h->end - h->last.mem; @@ -475,11 +495,13 @@ static int ngx_http_proxy_write_to_client(ngx_event_t *ev) h = ((ngx_hunk_t **) p->hunks->elts)[p->hunk_n]; rc = ngx_http_output_filter(r, h); - if (rc != NGX_OK) + if (rc != NGX_OK) { return rc; + } - if (p->hunk_n >= p->hunks->nelts) + if (p->hunk_n >= p->hunks->nelts) { break; + } p->hunk_n++; @@ -519,12 +541,15 @@ fprintf(stderr, "state: %d, pos: %x, end: %x, char: '%c', status: %d\n", /* "HTTP/" */ case sw_start: - if (p + 3 >= ctx->header_in->last.mem) + if (p + 3 >= ctx->header_in->last.mem) { return NGX_AGAIN; + } if (ch != 'H' || *p != 'T' || *(p + 1) != 'T' || *(p + 2) != 'P' || *(p + 3) != '/') + { return NGX_HTTP_PROXY_PARSE_NO_HEADER; + } p += 4; state = sw_first_major_digit; @@ -532,8 +557,9 @@ fprintf(stderr, "state: %d, pos: %x, end: %x, char: '%c', status: %d\n", /* first digit of major HTTP version */ case sw_first_major_digit: - if (ch < '1' || ch > '9') + if (ch < '1' || ch > '9') { return NGX_HTTP_PROXY_PARSE_NO_HEADER; + } state = sw_major_digit; break; @@ -545,15 +571,17 @@ fprintf(stderr, "state: %d, pos: %x, end: %x, char: '%c', status: %d\n", break; } - if (ch < '0' || ch > '9') + if (ch < '0' || ch > '9') { return NGX_HTTP_PROXY_PARSE_NO_HEADER; + } break; /* first digit of minor HTTP version */ case sw_first_minor_digit: - if (ch < '0' || ch > '9') + if (ch < '0' || ch > '9') { return NGX_HTTP_PROXY_PARSE_NO_HEADER; + } state = sw_minor_digit; break; @@ -565,15 +593,17 @@ fprintf(stderr, "state: %d, pos: %x, end: %x, char: '%c', status: %d\n", break; } - if (ch < '0' || ch > '9') + if (ch < '0' || ch > '9') { return NGX_HTTP_PROXY_PARSE_NO_HEADER; + } break; /* HTTP status code */ case sw_status: - if (ch < '0' || ch > '9') + if (ch < '0' || ch > '9') { return NGX_HTTP_PROXY_PARSE_NO_HEADER; + } ctx->status = ctx->status * 10 + ch - '0'; @@ -630,10 +660,13 @@ fprintf(stderr, "state: %d, pos: %x, end: %x, char: '%c', status: %d\n", ctx->header_in->pos.mem = p; if (state == sw_done) { - if (ctx->request_end == NULL) + if (ctx->request_end == NULL) { ctx->request_end = p - 1; + } + ctx->state = sw_start; return NGX_OK; + } else { ctx->state = state; return NGX_AGAIN; diff --git a/src/http/modules/ngx_http_index_handler.c b/src/http/modules/ngx_http_index_handler.c index a85823769..7b0a33f7b 100644 --- a/src/http/modules/ngx_http_index_handler.c +++ b/src/http/modules/ngx_http_index_handler.c @@ -9,11 +9,12 @@ #include <ngx_http.h> #include <ngx_http_config.h> +#include <ngx_http_core_module.h> #include <ngx_http_index_handler.h> static void *ngx_http_index_create_conf(ngx_pool_t *pool); -static void *ngx_http_index_merge_conf(ngx_pool_t *p, +static char *ngx_http_index_merge_conf(ngx_pool_t *p, void *parent, void *child); static char *ngx_http_index_set_index(ngx_conf_t *cf, ngx_command_t *cmd, char *conf); @@ -50,6 +51,7 @@ ngx_http_module_t ngx_http_index_module_ctx = { ngx_module_t ngx_http_index_module = { + 0, /* module index */ &ngx_http_index_module_ctx, /* module context */ ngx_http_index_commands, /* module directives */ NGX_HTTP_MODULE_TYPE, /* module type */ @@ -65,18 +67,23 @@ int ngx_http_index_handler(ngx_http_request_t *r) ngx_err_t err; ngx_fd_t fd; - ngx_http_index_conf_t *cf; + ngx_http_index_conf_t *cf; + ngx_http_core_loc_conf_t *core_cf; cf = (ngx_http_index_conf_t *) ngx_http_get_module_loc_conf(r, ngx_http_index_module_ctx); + core_cf = (ngx_http_core_loc_conf_t *) + ngx_http_get_module_loc_conf(r, ngx_http_core_module_ctx); + ngx_test_null(name, ngx_palloc(r->pool, - r->server->doc_root_len + r->uri.len + core_cf->doc_root.len + r->uri.len + cf->max_index_len), NGX_HTTP_INTERNAL_SERVER_ERROR); - loc.data = ngx_cpystrn(name, r->server->doc_root, r->server->doc_root_len); + loc.data = ngx_cpystrn(name, core_cf->doc_root.data, + core_cf->doc_root.len + 1); file = ngx_cpystrn(loc.data, r->uri.data, r->uri.len + 1); index = (ngx_str_t *) cf->indices->elts; @@ -101,7 +108,7 @@ int ngx_http_index_handler(ngx_http_request_t *r) return NGX_HTTP_INTERNAL_SERVER_ERROR; } - r->file.name.len = r->server->doc_root_len + r->uri.len + index[i].len; + r->file.name.len = core_cf->doc_root.len + r->uri.len + index[i].len; r->file.name.data = name; r->file.fd = fd; @@ -117,17 +124,34 @@ static void *ngx_http_index_create_conf(ngx_pool_t *pool) { ngx_http_index_conf_t *conf; - ngx_test_null(conf, ngx_pcalloc(pool, sizeof(ngx_http_index_conf_t)), NULL); + ngx_test_null(conf, ngx_pcalloc(pool, sizeof(ngx_http_index_conf_t)), + NGX_CONF_ERROR); ngx_test_null(conf->indices, ngx_create_array(pool, sizeof(ngx_str_t), 3), - NULL); + NGX_CONF_ERROR); return conf; } -static void *ngx_http_index_merge_conf(ngx_pool_t *p, void *parent, void *child) +static char *ngx_http_index_merge_conf(ngx_pool_t *p, void *parent, void *child) +{ + ngx_http_index_conf_t *prev = (ngx_http_index_conf_t *) parent; + ngx_http_index_conf_t *conf = (ngx_http_index_conf_t *) child; + ngx_str_t *index; + + ngx_test_null(index, ngx_push_array(conf->indices), NGX_CONF_ERROR); + index->len = sizeof(NGX_HTTP_INDEX) - 1; + index->data = NGX_HTTP_INDEX; + conf->max_index_len = sizeof(NGX_HTTP_INDEX); + + return NULL; +} + + +#if 0 +static char *ngx_http_index_merge_conf(ngx_pool_t *p, void *parent, void *child) { ngx_http_index_conf_t *prev = (ngx_http_index_conf_t *) parent; ngx_http_index_conf_t *conf = (ngx_http_index_conf_t *) child; @@ -146,7 +170,7 @@ static void *ngx_http_index_merge_conf(ngx_pool_t *p, void *parent, void *child) return conf; } - +#endif static char *ngx_http_index_set_index(ngx_conf_t *cf, ngx_command_t *cmd, char *conf) diff --git a/src/http/modules/ngx_http_static_handler.c b/src/http/modules/ngx_http_static_handler.c index 56f24cd07..fa6207309 100644 --- a/src/http/modules/ngx_http_static_handler.c +++ b/src/http/modules/ngx_http_static_handler.c @@ -117,6 +117,9 @@ int ngx_http_static_handler(ngx_http_request_t *r) } else if (strcasecmp(r->exten.data, "jpg") == 0) { r->headers_out.content_type->value.len = 10; r->headers_out.content_type->value.data = "image/jpeg"; + } else if (strcasecmp(r->exten.data, "pdf") == 0) { + r->headers_out.content_type->value.len = 15; + r->headers_out.content_type->value.data = "application/pdf"; } } else { diff --git a/src/http/ngx_http.c b/src/http/ngx_http.c index 80936c85e..6e3c676a1 100644 --- a/src/http/ngx_http.c +++ b/src/http/ngx_http.c @@ -5,15 +5,343 @@ #include <ngx_listen.h> #include <ngx_http.h> #include <ngx_http_config.h> +#include <ngx_http_core_module.h> -extern ngx_array_t *ngx_listening_sockets; +static char *ngx_http_block(ngx_conf_t *cf, ngx_command_t *cmd, char *dummy); + + +int ngx_http_max_module; + +ngx_array_t ngx_http_servers; /* array of ngx_http_core_srv_conf_t */ + +int ngx_http_post_accept_timeout = 10000; +int ngx_http_connection_pool_size = 16384; +int ngx_http_request_pool_size = 16384; +int ngx_http_client_header_timeout = 20000; +int ngx_http_client_header_buffer_size = 1024; + +/* STUB: per location */ +int ngx_http_lingering_timeout = 5000; +int ngx_http_lingering_time = 30; +/**/ + +int (*ngx_http_top_header_filter) (ngx_http_request_t *r); + + +static ngx_str_t http_name = ngx_string("http"); + + +static ngx_command_t ngx_http_commands[] = { + + {ngx_string("http"), + NGX_CONF_BLOCK|NGX_CONF_NOARGS, + ngx_http_block, + 0, + 0}, + + {ngx_string(""), 0, NULL, 0, 0} +}; + + +ngx_module_t ngx_http_module = { + 0, /* module index */ + &http_name, /* module context */ + ngx_http_commands, /* module directives */ + NGX_CORE_MODULE_TYPE, /* module type */ + NULL /* init module */ +}; + + +static char *ngx_http_block(ngx_conf_t *cf, ngx_command_t *cmd, char *dummy) +{ + int i, s, l, p, a, n, start; + int port_found, addr_found, virtual_names; + char *rv; + struct sockaddr_in *addr_in; + ngx_array_t in_ports; + ngx_listen_t *ls; + ngx_http_module_t *module; + ngx_http_conf_ctx_t *ctx, *prev; + ngx_http_in_port_t *in_port; + ngx_http_in_addr_t *in_addr, *inaddr; + ngx_http_core_srv_conf_t **cscf; + ngx_http_listen_t *lscf; + ngx_http_server_name_t *s_name, *name;; + + ngx_init_array(ngx_http_servers, cf->pool, 10, + sizeof(ngx_http_core_srv_conf_t *), NGX_CONF_ERROR); + + ngx_test_null(ctx, + ngx_pcalloc(cf->pool, sizeof(ngx_http_conf_ctx_t)), + NGX_CONF_ERROR); + + for (i = 0; ngx_modules[i]; i++) { + if (ngx_modules[i]->type != NGX_HTTP_MODULE_TYPE) { + continue; + } + + /* STUB */ + module = (ngx_http_module_t *) ngx_modules[i]->ctx; + module->index = ngx_http_max_module; + + ngx_modules[i]->index = ngx_http_max_module++; + } + + /* null loc_conf */ + ngx_test_null(ctx->loc_conf, + ngx_pcalloc(cf->pool, sizeof(void *) * ngx_http_max_module), + NGX_CONF_ERROR); + + for (i = 0; ngx_modules[i]; i++) { + if (ngx_modules[i]->type != NGX_HTTP_MODULE_TYPE) { + continue; + } + + module = (ngx_http_module_t *) ngx_modules[i]->ctx; + + if (module->create_loc_conf) { + ngx_test_null(ctx->loc_conf[module->index], + module->create_loc_conf(cf->pool), + NGX_CONF_ERROR); + } + } + + prev = cf->ctx; + cf->ctx = ctx; + cf->type = NGX_HTTP_MODULE_TYPE; + + rv = ngx_conf_parse(cf, NULL); + cf->ctx = prev; + + if (rv != NGX_CONF_OK) + return rv; + + ngx_http_init_filters(cf->pool, ngx_modules); + +#if 1 + ngx_init_array(in_ports, cf->pool, 10, sizeof(ngx_http_in_port_t), + NGX_CONF_ERROR); + + cscf = (ngx_http_core_srv_conf_t **) ngx_http_servers.elts; + for (s = 0; s < ngx_http_servers.nelts; s++) { + + lscf = (ngx_http_listen_t *) cscf[s]->listen.elts; + for (l = 0; l < cscf[s]->listen.nelts; l++) { + + port_found = 0; + + /* AF_INET only */ + + in_port = (ngx_http_in_port_t *) in_ports.elts; + for (p = 0; p < in_ports.nelts; p++) { + + if (lscf[l].port == in_port[p].port) { + + port_found = 1; + addr_found = 0; + + in_addr = (ngx_http_in_addr_t *) in_port[p].addr.elts; + for (a = 0; a < in_port[p].addr.nelts; a++) { + + if (lscf[l].addr == in_addr[a].addr) { + s_name = (ngx_http_server_name_t *) + cscf[s]->server_names.elts; + for (n = 0; n < cscf[s]->server_names.nelts; n++) { + ngx_test_null(name, + ngx_push_array(&in_addr[a].names), + NGX_CONF_ERROR); + + name->name = s_name[n].name; + name->core_srv_conf = s_name[n].core_srv_conf; + } + + if (lscf[l].flags & NGX_HTTP_DEFAULT_SERVER) { + if (in_addr[a].flags + & NGX_HTTP_DEFAULT_SERVER) { + + ngx_log_error(NGX_LOG_ERR, cf->log, 0, + "duplicate default server in %s:%d", + lscf[l].conf_file->file.name.data, + lscf[l].line); + + return NGX_CONF_ERROR; + } + + in_addr[a].flags |= NGX_HTTP_DEFAULT_SERVER; + in_addr[a].core_srv_conf = cscf[s]; + } + + addr_found = 1; + + break; + + /* "*:XX" is the last resort */ + } else if (in_addr[p].addr == INADDR_ANY) { + ngx_test_null(inaddr, + ngx_push_array(&in_port[p].addr), + NGX_CONF_ERROR); + + ngx_memcpy(inaddr, &in_addr[a], + sizeof(ngx_http_in_addr_t)); + + inaddr->addr = lscf[l].addr; + inaddr->flags = lscf[l].flags; + inaddr->core_srv_conf = cscf[s]; + + ngx_init_array(inaddr->names, cf->pool, 10, + sizeof(ngx_http_server_name_t), + NGX_CONF_ERROR); + + addr_found = 1; + + break; + } + } + + if (!addr_found) { + ngx_test_null(inaddr, + ngx_push_array(&in_port[p].addr), + NGX_CONF_ERROR); + + inaddr->addr = lscf[l].addr; + inaddr->flags = lscf[l].flags; + inaddr->core_srv_conf = cscf[s]; + + ngx_init_array(inaddr->names, cf->pool, 10, + sizeof(ngx_http_server_name_t), + NGX_CONF_ERROR); + } + } + } + + if (!port_found) { + ngx_test_null(in_port, + ngx_push_array(&in_ports), + NGX_CONF_ERROR); + + in_port->port = lscf[l].port; + + ngx_init_array(in_port->addr, cf->pool, 10, + sizeof(ngx_http_in_addr_t), + NGX_CONF_ERROR); + + ngx_test_null(inaddr, ngx_push_array(&in_port[p].addr), + NGX_CONF_ERROR); + + inaddr->addr = lscf[l].addr; + inaddr->flags = lscf[l].flags; + inaddr->core_srv_conf = cscf[s]; + + ngx_init_array(inaddr->names, cf->pool, 10, + sizeof(ngx_http_server_name_t), + NGX_CONF_ERROR); + } + } + } + + /* AF_INET only */ + + in_port = (ngx_http_in_port_t *) in_ports.elts; + for (p = 0; p < in_ports.nelts; p++) { + + in_addr = (ngx_http_in_addr_t *) in_port[p].addr.elts; + for (a = 0; a < in_port[p].addr.nelts; a++) { + + virtual_names = 0; + + name = (ngx_http_server_name_t *) in_addr[a].names.elts; + for (n = 0; n < in_addr[a].names.nelts; n++) { + if (in_addr[a].core_srv_conf != name[n].core_srv_conf) { + virtual_names = 1; + break; + } + } + + /* if all server names point to the same server + then we do not need to check them at run time */ + if (!virtual_names) { + in_addr[a].names.nelts = 0; + } + } + + /* if there is binding to "*:XX" then we need to bind to "*:XX" only + and ignore other binding */ + if (in_addr[a - 1].addr == INADDR_ANY) { + start = a - 1; + + } else { + start = 0; + } + + in_addr = (ngx_http_in_addr_t *) in_port[p].addr.elts; + for (a = start; a < in_port[p].addr.nelts; a++) { + + ngx_test_null(ls, ngx_push_array(&ngx_listening_sockets), + NGX_CONF_ERROR); + ngx_memzero(ls, sizeof(ngx_listen_t)); + + ngx_test_null(addr_in, + ngx_pcalloc(cf->pool, sizeof(struct sockaddr_in)), + NGX_CONF_ERROR); + + addr_in->sin_family = AF_INET; + addr_in->sin_addr.s_addr = in_addr[a].addr; + addr_in->sin_port = htons(in_port[p].port); + + ngx_test_null(ls->addr_text.data, + ngx_palloc(cf->pool, INET_ADDRSTRLEN + 6), + NGX_CONF_ERROR); + + ls->addr_text.len = + ngx_snprintf(ls->addr_text.data + + ngx_inet_ntop(AF_INET, + &in_addr[a].addr, + ls->addr_text.data, + INET_ADDRSTRLEN), + 6, ":%d", in_port[p].port); + + ls->family = AF_INET; + ls->type = SOCK_STREAM; + ls->protocol = IPPROTO_IP; +#if (NGX_OVERLAPPED) + ls->flags = WSA_FLAG_OVERLAPPED; +#endif + ls->sockaddr = (struct sockaddr *) addr_in; + ls->socklen = sizeof(struct sockaddr_in); + ls->addr = offsetof(struct sockaddr_in, sin_addr); + ls->addr_text_max_len = INET_ADDRSTRLEN; + ls->backlog = -1; + ls->post_accept_timeout = ngx_http_post_accept_timeout; + ls->nonblocking = 1; + + ls->handler = ngx_http_init_connection; + ls->log = cf->log; + ls->ctx = ctx; + ls->servers = &in_port[p].addr; + + if (in_port[p].addr.nelts == 1) { + in_addr = (ngx_http_in_addr_t *) in_port[p].addr.elts; + + if (in_addr[a].names.nelts == 0) { + ls->ctx = in_addr->core_srv_conf->ctx; + ls->servers = NULL; + } + } + } + } +#endif + + return NGX_CONF_OK; +} + + +#if 0 /* STUB */ static struct sockaddr_in addr; static char addr_text[22]; -static ngx_http_server_t ngx_http_server; int ngx_http_init(ngx_pool_t *pool, ngx_log_t *log) { @@ -40,8 +368,8 @@ int ngx_http_init(ngx_pool_t *pool, ngx_log_t *log) ngx_http_config_modules(pool, ngx_modules); -#if 0 +#if 0 /* STUB */ ngx_http_output_filter_set_stub(pool, ngx_http_modules); ngx_http_write_filter_set_stub(pool, ngx_http_modules); @@ -49,9 +377,10 @@ int ngx_http_init(ngx_pool_t *pool, ngx_log_t *log) ngx_http_init_modules(pool, ngx_http_modules); #endif + ngx_http_init_filters(pool, ngx_modules); - ls = ngx_push_array(ngx_listening_sockets); + ls = ngx_push_array(&ngx_listening_sockets); ngx_memzero(ls, sizeof(ngx_listen_t)); addr.sin_family = AF_INET; @@ -84,4 +413,5 @@ int ngx_http_init(ngx_pool_t *pool, ngx_log_t *log) return 1; } -/* */ +/**/ +#endif diff --git a/src/http/ngx_http.h b/src/http/ngx_http.h index 4d41bf263..9e8e3d162 100644 --- a/src/http/ngx_http.h +++ b/src/http/ngx_http.h @@ -114,8 +114,8 @@ struct ngx_http_request_s { #endif void **ctx; - void **loc_conf; void **srv_conf; + void **loc_conf; ngx_pool_t *pool; ngx_hunk_t *header_in; @@ -139,7 +139,6 @@ struct ngx_http_request_s { ngx_http_request_t *main; ngx_connection_t *connection; - ngx_http_server_t *server; int filter; @@ -192,9 +191,9 @@ typedef struct { int index; void *(*create_srv_conf)(ngx_pool_t *p); - void *(*init_srv_conf)(ngx_pool_t *p, void *conf); + char *(*init_srv_conf)(ngx_pool_t *p, void *conf); void *(*create_loc_conf)(ngx_pool_t *p); - void *(*merge_loc_conf)(ngx_pool_t *p, void *prev, void *conf); + char *(*merge_loc_conf)(ngx_pool_t *p, void *prev, void *conf); int (*translate_handler)(ngx_http_request_t *r); @@ -217,8 +216,8 @@ typedef struct { #define ngx_http_create_ctx(r, cx, module, size) \ do { \ - ngx_test_null(cx, ngx_pcalloc(r->pool, size), NGX_ERROR); \ - r->ctx[module.index] = cx; \ + ngx_test_null(cx, ngx_pcalloc(r->pool, size), NGX_ERROR); \ + r->ctx[module.index] = cx; \ } while (0) @@ -237,9 +236,22 @@ int ngx_http_init_connection(ngx_connection_t *c); int ngx_http_discard_body(ngx_http_request_t *r); -extern int ngx_max_module; +extern int ngx_max_module; +extern ngx_array_t ngx_http_servers; + + +extern int ngx_http_post_accept_timeout; +extern int ngx_http_connection_pool_size; +extern int ngx_http_request_pool_size; +extern int ngx_http_client_header_timeout; +extern int ngx_http_client_header_buffer_size; +extern int ngx_http_discarded_buffer_size; + +extern int ngx_http_lingering_timeout; +extern int ngx_http_lingering_time; + -extern ngx_http_module_t *ngx_http_modules[]; +extern ngx_http_module_t *ngx_http_modules[]; diff --git a/src/http/ngx_http_config.c b/src/http/ngx_http_config.c deleted file mode 100644 index 205b41ba0..000000000 --- a/src/http/ngx_http_config.c +++ /dev/null @@ -1,316 +0,0 @@ - -/* TODO: - ngx_http_conf_ctx_t ctx; on stack or in pool ? */ - - -#include <ngx_config.h> - -#include <ngx_core.h> -#include <ngx_conf_file.h> - -#include <ngx_http.h> -#include <ngx_http_core.h> -#include <ngx_http_config.h> -#include <ngx_http_write_filter.h> -#include <ngx_http_output_filter.h> -#include <ngx_http_index_handler.h> - - -/* STUB */ -void **ngx_srv_conf; -void **ngx_loc_conf; -/**/ - - -static char *ngx_http_block(ngx_conf_t *cf, ngx_command_t *cmd, char *dummy); -static char *ngx_server_block(ngx_conf_t *cf, ngx_command_t *cmd, char *dummy); - - -void **null_loc_conf; - - -static ngx_command_t ngx_http_commands[] = { - - {ngx_string("http"), - NGX_CONF_BLOCK|NGX_CONF_NOARGS, - ngx_http_block, - 0, - 0}, - - {ngx_string(""), 0, NULL, 0, 0} -}; - - -ngx_module_t ngx_http_module = { - NULL, /* module context */ - ngx_http_commands, /* module directives */ - NGX_CORE_MODULE_TYPE, /* module type */ - NULL /* init module */ -}; - - -static ngx_command_t ngx_http_core_commands[] = { - - {ngx_string("server"), - NGX_CONF_BLOCK|NGX_CONF_NOARGS, - ngx_server_block, - NGX_HTTP_MODULE_TYPE, - 0}, - - {ngx_string(""), 0, NULL, 0, 0} -}; - - -static ngx_http_module_t ngx_http_core_module_ctx = { - NGX_HTTP_MODULE, - - NULL, /* create server config */ - NULL, /* init server config */ - NULL, /* create location config */ - NULL, /* merge location config */ - - NULL, /* translate handler */ - - NULL, /* output header filter */ - NULL, /* next output header filter */ - NULL, /* output body filter */ - NULL /* next output body filter */ -}; - - -ngx_module_t ngx_http_core_module = { - &ngx_http_core_module_ctx, /* module context */ - ngx_http_core_commands, /* module directives */ - NGX_HTTP_MODULE_TYPE, /* module type */ - NULL /* init module */ -}; - - -static char *ngx_http_block(ngx_conf_t *cf, ngx_command_t *cmd, char *dummy) -{ - int i; - ngx_http_module_t *module; - ngx_http_conf_ctx_t ctx; - - for (i = 0; ngx_modules[i]; i++) { - if (ngx_modules[i]->type != NGX_HTTP_MODULE_TYPE) { - continue; - } - - module = (ngx_http_module_t *) ngx_modules[i]->ctx; - module->index = ngx_http_max_module++; - } - - ngx_test_null(null_loc_conf, - ngx_pcalloc(cf->pool, sizeof(void *) * ngx_http_max_module), - NGX_CONF_ERROR); - - ctx.srv_conf = NULL; - ctx.loc_conf = null_loc_conf; - ctx.locations = NULL; - - for (i = 0; ngx_modules[i]; i++) { - if (ngx_modules[i]->type != NGX_HTTP_MODULE_TYPE) { - continue; - } - - module = (ngx_http_module_t *) ngx_modules[i]->ctx; - - if (module->create_loc_conf) { - ngx_test_null(null_loc_conf[module->index], - module->create_loc_conf(cf->pool), - NGX_CONF_ERROR); - } - } - - cf->ctx = &ctx; - cf->type = NGX_HTTP_MODULE_TYPE; - return ngx_conf_parse(cf, NULL); -} - - -static char *ngx_server_block(ngx_conf_t *cf, ngx_command_t *cmd, char *dummy) -{ - int i, j; - char *rv; - void ***loc_conf; /* YES! 3 stars */ - ngx_http_module_t *module; - ngx_http_conf_ctx_t *ctx, *prev; - - ngx_test_null(ctx, - ngx_pcalloc(cf->pool, sizeof(ngx_http_conf_ctx_t)), - NGX_CONF_ERROR); - - /* server config */ - ngx_test_null(ctx->srv_conf, - ngx_pcalloc(cf->pool, sizeof(void *) * ngx_http_max_module), - NGX_CONF_ERROR); - - /* server location config */ - ngx_test_null(ctx->loc_conf, - ngx_pcalloc(cf->pool, sizeof(void *) * ngx_http_max_module), - NGX_CONF_ERROR); - - for (i = 0; ngx_modules[i]; i++) { - if (ngx_modules[i]->type != NGX_HTTP_MODULE_TYPE) { - continue; - } - - module = (ngx_http_module_t *) ngx_modules[i]->ctx; - - if (module->create_srv_conf) { - ngx_test_null(ctx->srv_conf[module->index], - module->create_srv_conf(cf->pool), - NGX_CONF_ERROR); - } - - if (module->create_loc_conf) { - ngx_test_null(ctx->loc_conf[module->index], - module->create_loc_conf(cf->pool), - NGX_CONF_ERROR); - } - } - - prev = cf->ctx; - cf->ctx = ctx; - rv = ngx_conf_parse(cf, NULL); - cf->ctx = prev; - - if (rv != NULL) - return rv; - - for (i = 0; ngx_modules[i]; i++) { - if (ngx_modules[i]->type != NGX_HTTP_MODULE_TYPE) { - continue; - } - - module = (ngx_http_module_t *) ngx_modules[i]->ctx; - - if (module->init_srv_conf) { - if (module->init_srv_conf(cf->pool, - ctx->srv_conf[module->index]) - == NGX_CONF_ERROR) { - return NGX_CONF_ERROR; - } - } - - if (module->merge_loc_conf) { - if (module->merge_loc_conf(cf->pool, - prev->loc_conf[module->index], - ctx->loc_conf[module->index]) - == NGX_CONF_ERROR) { - return NGX_CONF_ERROR; - } - - loc_conf = (void ***)ctx->locations->elts; - for (j = 0; j < ctx->locations->nelts; j++) { - if (module->merge_loc_conf(cf->pool, - ctx->loc_conf[module->index], - loc_conf[j][module->index]) - == NGX_CONF_ERROR) { - return NGX_CONF_ERROR; - } - } - } - } - - return NULL; -} - - -#if 0 -int ngx_location_block(ngx_conf_t *cf) -{ - ngx_http_conf_ctx_t *ctx, *prev; - - ngx_test_null(ctx, ngx_pcalloc(cf->pool, sizeof(ngx_http_conf_ctx_t)), - NGX_ERROR); - - ctx->srv_conf = cf->ctx->srv_conf; - - ngx_test_null(ctx->loc_conf, - ngx_pcalloc(cf->pool, sizeof(void *) * ngx_max_module), - NGX_ERROR); - - for (i = 0; modules[i]; i++) { - if (modules[i]->create_loc_conf) - ngx_test_null(ctx->loc_conf[i], - modules[i]->create_loc_conf(cf->pool), - NGX_ERROR); - - if (ngx_http_core_module.index == i) - ctx->loc_conf[i].location = cf->args[0]; - } - - push - - return ngx_conf_parse(cf); -} - -#endif - - -int ngx_http_config_modules(ngx_pool_t *pool, ngx_module_t **modules) -{ - int i; - ngx_http_module_t *module; - - for (i = 0; modules[i]; i++) { - if (modules[i]->type != NGX_HTTP_MODULE_TYPE) { - continue; - } - - module = (ngx_http_module_t *) modules[i]->ctx; - module->index = i; - } - - ngx_http_max_module = i; - -#if 0 - ngx_test_null(ngx_srv_conf, - ngx_pcalloc(pool, sizeof(void *) * ngx_http_max_module), - NGX_ERROR); - ngx_test_null(ngx_loc_conf, - ngx_pcalloc(pool, sizeof(void *) * ngx_http_max_module), - NGX_ERROR); - - for (i = 0; modules[i]; i++) { - if (modules[i]->create_srv_conf) - ngx_srv_conf[i] = modules[i]->create_srv_conf(pool); - - if (modules[i]->create_loc_conf) - ngx_loc_conf[i] = modules[i]->create_loc_conf(pool); - } -#endif -} - - -void ngx_http_init_filters(ngx_pool_t *pool, ngx_module_t **modules) -{ - int i; - ngx_http_module_t *module; - int (*ohf)(ngx_http_request_t *r); - int (*obf)(ngx_http_request_t *r, ngx_chain_t *ch); - - ohf = NULL; - obf = NULL; - - for (i = 0; modules[i]; i++) { - if (modules[i]->type != NGX_HTTP_MODULE_TYPE) { - continue; - } - - module = (ngx_http_module_t *) modules[i]->ctx; - if (module->output_header_filter) { - module->next_output_header_filter = ohf; - ohf = module->output_header_filter; - } - - if (module->output_body_filter) { - module->next_output_body_filter = obf; - obf = module->output_body_filter; - } - } - - ngx_http_top_header_filter = ohf; -} diff --git a/src/http/ngx_http_config.h b/src/http/ngx_http_config.h index 4bea178eb..27f8c6546 100644 --- a/src/http/ngx_http_config.h +++ b/src/http/ngx_http_config.h @@ -9,12 +9,15 @@ typedef struct { void **srv_conf; void **loc_conf; - ngx_array_t *locations; } ngx_http_conf_ctx_t; -#define NGX_HTTP_SRV_CONF offsetof(ngx_http_conf_ctx_t, srv_conf) -#define NGX_HTTP_LOC_CONF offsetof(ngx_http_conf_ctx_t, loc_conf) +#define NGX_HTTP_MAIN_CONF 0x1000000 +#define NGX_HTTP_SRV_CONF 0x2000000 +#define NGX_HTTP_LOC_CONF 0x6000000 + +#define NGX_HTTP_SRV_CONF_OFFSET offsetof(ngx_http_conf_ctx_t, srv_conf) +#define NGX_HTTP_LOC_CONF_OFFSET offsetof(ngx_http_conf_ctx_t, loc_conf) int ngx_http_config_modules(ngx_pool_t *pool, ngx_module_t **modules); diff --git a/src/http/ngx_http_core.c b/src/http/ngx_http_core.c deleted file mode 100644 index 30d8329df..000000000 --- a/src/http/ngx_http_core.c +++ /dev/null @@ -1,335 +0,0 @@ - -#include <ngx_config.h> - -#include <ngx_core.h> -#include <ngx_conf_file.h> - -#include <ngx_http.h> -#include <ngx_http_core.h> -#include <ngx_http_config.h> - -/* STUB */ -int ngx_http_static_handler(ngx_http_request_t *r); -int ngx_http_index_handler(ngx_http_request_t *r); -int ngx_http_proxy_handler(ngx_http_request_t *r); -/**/ - -static void *ngx_http_core_create_srv_conf(ngx_pool_t *pool); -static void *ngx_http_core_create_loc_conf(ngx_pool_t *pool); -static int ngx_http_core_translate_handler(ngx_http_request_t *r); - - -int (*ngx_http_top_header_filter) (ngx_http_request_t *r); - -int ngx_http_max_module; - -#if 0 -static ngx_command_t ngx_http_core_commands[] = { - - {ngx_string("send_timeout"), - NGX_CONF_TAKE1, - ngx_conf_set_time_slot, - NGX_HTTP_LOC_CONF, - offsetof(ngx_http_core_loc_conf_t, send_timeout)}, - - {ngx_string(""), 0, NULL, 0, 0} -}; -#endif - -ngx_http_module_t ngx_http_core_module_ctx = { - NGX_HTTP_MODULE, - - ngx_http_core_create_srv_conf, /* create server config */ - NULL, /* init server config */ - ngx_http_core_create_loc_conf, /* create location config */ - NULL, /* merge location config */ - - ngx_http_core_translate_handler, /* translate handler */ - - NULL, /* output header filter */ - NULL, /* next output header filter */ - NULL, /* output body filter */ - NULL, /* next output body filter */ -}; - -#if 0 -ngx_module_t ngx_http_core_module = { - &ngx_http_core_module_ctx, /* module context */ - ngx_http_core_commands, /* module directives */ - NGX_HTTP_MODULE_TYPE, /* module type */ - NULL /* init module */ -}; -#endif - -int ngx_http_handler(ngx_http_request_t *r) -{ - int rc, i; - ngx_http_module_t *module; - - r->connection->unexpected_eof = 0; - r->lingering_close = 1; - r->keepalive = 0; - -#if 0 - r->filter = NGX_HTTP_FILTER_NEED_IN_MEMORY; -#endif - - /* run translation phase */ - for (i = 0; ngx_modules[i]; i++) { - if (ngx_modules[i]->type != NGX_HTTP_MODULE_TYPE) { - continue; - } - - module = (ngx_http_module_t *) ngx_modules[i]->ctx; - if (module->translate_handler == NULL) { - continue; - } - - rc = module->translate_handler(r); - if (rc == NGX_OK) { - break; - } - - if (rc >= NGX_HTTP_SPECIAL_RESPONSE) { - return ngx_http_special_response(r, rc); - } - } - - rc = r->handler(r); - - if (rc >= NGX_HTTP_SPECIAL_RESPONSE) { - return ngx_http_special_response(r, rc); - } - - return rc; -} - - -static int ngx_http_core_translate_handler(ngx_http_request_t *r) -{ - char *loc, *last; - ngx_err_t err; - ngx_table_elt_t *h; - - /* TODO: find location conf */ - - if (r->uri.data[r->uri.len - 1] == '/') { - /* TODO: find index handler */ - /* STUB */ r->handler = ngx_http_index_handler; - - return NGX_OK; - } - - r->file.name.len = r->server->doc_root_len + r->uri.len + 2; - - ngx_test_null(r->file.name.data, - ngx_palloc(r->pool, r->file.name.len + 1), - NGX_HTTP_INTERNAL_SERVER_ERROR); - - loc = ngx_cpystrn(r->file.name.data, r->server->doc_root, - r->server->doc_root_len); - last = ngx_cpystrn(loc, r->uri.data, r->uri.len + 1); - - ngx_log_debug(r->connection->log, "HTTP filename: '%s'" _ - r->file.name.data); - -#if (WIN9X) - - /* There is no way to open file or directory in Win9X with - one syscall: Win9X has not FILE_FLAG_BACKUP_SEMANTICS flag. - so we need to check its type before opening */ - -#if 0 /* OLD: ngx_file_type() is to be removed */ - if (ngx_file_type(r->file.name.data, &r->file.info) == -1) { -#endif - - r->file.info.dwFileAttributes = GetFileAttributes(r->file.name.data); - if (r->file.info.dwFileAttributes == INVALID_FILE_ATTRIBUTES) { - err = ngx_errno; - ngx_log_error(NGX_LOG_ERR, r->connection->log, err, - "ngx_http_core_translate_handler: " - ngx_file_type_n " %s failed", r->file.name.data); - - if (err == ERROR_FILE_NOT_FOUND) { - return NGX_HTTP_NOT_FOUND; - } else if (err == ERROR_PATH_NOT_FOUND) { - return NGX_HTTP_NOT_FOUND; - } else { - return NGX_HTTP_INTERNAL_SERVER_ERROR; - } - } - -#else - - if (r->file.fd == NGX_INVALID_FILE) { - r->file.fd = ngx_open_file(r->file.name.data, NGX_FILE_RDONLY); - } - - if (r->file.fd == NGX_INVALID_FILE) { - err = ngx_errno; - ngx_log_error(NGX_LOG_ERR, r->connection->log, ngx_errno, - "ngx_http_core_handler: " - ngx_open_file_n " %s failed", r->file.name.data); - - if (err == NGX_ENOENT) { - return NGX_HTTP_NOT_FOUND; - } else { - return NGX_HTTP_INTERNAL_SERVER_ERROR; - } - } - - if (!r->file.info_valid) { - if (ngx_stat_fd(r->file.fd, &r->file.info) == NGX_FILE_ERROR) { - ngx_log_error(NGX_LOG_ERR, r->connection->log, ngx_errno, - "ngx_http_core_handler: " - ngx_stat_fd_n " %s failed", r->file.name.data); - - if (ngx_close_file(r->file.fd) == NGX_FILE_ERROR) { - ngx_log_error(NGX_LOG_ERR, r->connection->log, ngx_errno, - "ngx_http_core_handler: " - ngx_close_file_n " %s failed", r->file.name.data); - } - - return NGX_HTTP_INTERNAL_SERVER_ERROR; - } - - r->file.info_valid = 1; - } -#endif - - if (ngx_is_dir(r->file.info)) { - ngx_log_debug(r->connection->log, "HTTP DIR: '%s'" _ r->file.name.data); - -#if !(WIN9X) - if (ngx_close_file(r->file.fd) == NGX_FILE_ERROR) { - ngx_log_error(NGX_LOG_ERR, r->connection->log, ngx_errno, - "ngx_http_core_handler: " - ngx_close_file_n " %s failed", r->file.name.data); - } -#endif - - /* BROKEN: need to include server name */ - - ngx_test_null(h, ngx_push_table(r->headers_out.headers), - NGX_HTTP_INTERNAL_SERVER_ERROR); - - *last++ = '/'; - *last = '\0'; - h->key.len = 8; - h->key.data = "Location" ; - h->value.len = last - loc; - h->value.data = loc; - r->headers_out.location = h; - - return NGX_HTTP_MOVED_PERMANENTLY; - } - - /* TODO: r->handler = loc_conf->default_handler; */ - /* STUB */ r->handler = ngx_http_static_handler; - - return NGX_OK; -} - - -int ngx_http_send_header(ngx_http_request_t *r) -{ - return (*ngx_http_top_header_filter)(r); -} - - -int ngx_http_redirect(ngx_http_request_t *r, int redirect) -{ - /* STUB */ - - /* log request */ - - return ngx_http_close_request(r); -} - - -int ngx_http_error(ngx_http_request_t *r, int error) -{ - /* STUB */ - ngx_log_debug(r->connection->log, "http error: %d" _ error); - - /* log request */ - - ngx_http_special_response(r, error); - return ngx_http_close_request(r); -} - - -int ngx_http_close_request(ngx_http_request_t *r) -{ - ngx_log_debug(r->connection->log, "CLOSE#: %d" _ r->file.fd); - - ngx_http_log_handler(r); - - ngx_assert((r->file.fd != NGX_INVALID_FILE), /* void */ ; , - r->connection->log, "file already closed"); - - if (r->file.fd != NGX_INVALID_FILE) { - if (ngx_close_file(r->file.fd) == NGX_FILE_ERROR) { - ngx_log_error(NGX_LOG_ERR, r->connection->log, ngx_errno, - ngx_close_file_n " failed"); - } - } - -/* - if (r->logging) - ngx_http_log_request(r); -*/ - - ngx_destroy_pool(r->pool); - - ngx_log_debug(r->connection->log, "http close"); - - ngx_del_timer(r->connection->read); - ngx_del_timer(r->connection->write); - - return NGX_DONE; -} - - -int ngx_http_internal_redirect(ngx_http_request_t *r, ngx_str_t uri) -{ - ngx_log_debug(r->connection->log, "internal redirect: '%s'" _ uri.data); - - r->uri.len = uri.len; - r->uri.data = uri.data; - - /* NEEDED ? */ - r->uri_start = uri.data; - r->uri_end = uri.data + uri.len; - /**/ - - return ngx_http_handler(r); -} - - -static void *ngx_http_core_create_srv_conf(ngx_pool_t *pool) -{ - ngx_http_core_srv_conf_t *conf; - - ngx_test_null(conf, - ngx_pcalloc(pool, sizeof(ngx_http_core_srv_conf_t)), - NULL); - - return conf; -} - -static void *ngx_http_core_create_loc_conf(ngx_pool_t *pool) -{ - ngx_http_core_loc_conf_t *conf; - - ngx_test_null(conf, - ngx_pcalloc(pool, sizeof(ngx_http_core_loc_conf_t)), - NULL); - - conf->send_timeout = 10; -/* - conf->send_timeout = NGX_CONF_UNSET; -*/ - - return conf; -} diff --git a/src/http/ngx_http_core.h b/src/http/ngx_http_core.h deleted file mode 100644 index 513ed6e8f..000000000 --- a/src/http/ngx_http_core.h +++ /dev/null @@ -1,30 +0,0 @@ -#ifndef _NGX_HTTP_CORE_H_INCLUDED_ -#define _NGX_HTTP_CORE_H_INCLUDED_ - - -#include <ngx_http.h> - - -typedef struct { - int dummy; -} ngx_http_core_conf_t; - - -typedef struct { - int dummy; -} ngx_http_core_srv_conf_t; - - -typedef struct { - time_t send_timeout; -} ngx_http_core_loc_conf_t; - - -extern ngx_http_module_t ngx_http_core_module_ctx; -extern ngx_module_t ngx_http_core_module; - -extern int (*ngx_http_top_header_filter) (ngx_http_request_t *r); -extern int ngx_http_max_module; - - -#endif /* _NGX_HTTP_CORE_H_INCLUDED_ */ diff --git a/src/http/ngx_http_core_module.c b/src/http/ngx_http_core_module.c new file mode 100644 index 000000000..498bc770e --- /dev/null +++ b/src/http/ngx_http_core_module.c @@ -0,0 +1,710 @@ + +#include <ngx_config.h> + +#include <ngx_core.h> +#include <ngx_conf_file.h> + +#include <ngx_http.h> +#include <ngx_http_config.h> +#include <ngx_http_core_module.h> + +#if 0 +#include <ngx_http_write_filter.h> +#include <ngx_http_output_filter.h> +#include <ngx_http_index_handler.h> +#endif + +/* STUB */ +#include <ngx_http_output_filter.h> +int ngx_http_static_handler(ngx_http_request_t *r); +int ngx_http_index_handler(ngx_http_request_t *r); +int ngx_http_proxy_handler(ngx_http_request_t *r); +/**/ + + +static char *ngx_server_block(ngx_conf_t *cf, ngx_command_t *cmd, char *dummy); +static char *ngx_location_block(ngx_conf_t *cf, ngx_command_t *cmd, + char *dummy); +static void *ngx_http_core_create_srv_conf(ngx_pool_t *pool); +static char *ngx_http_core_init_srv_conf(ngx_pool_t *pool, void *conf); +static void *ngx_http_core_create_loc_conf(ngx_pool_t *pool); + + +static ngx_command_t ngx_http_core_commands[] = { + + {ngx_string("server"), + NGX_HTTP_MAIN_CONF|NGX_CONF_BLOCK|NGX_CONF_NOARGS, + ngx_server_block, + 0, + 0}, + + {ngx_string("location"), + NGX_HTTP_SRV_CONF|NGX_CONF_BLOCK|NGX_CONF_TAKE1, + ngx_location_block, + 0, + 0}, + + {ngx_string("root"), + NGX_HTTP_LOC_CONF|NGX_CONF_BLOCK|NGX_CONF_TAKE1, + ngx_conf_set_str_slot, + NGX_HTTP_LOC_CONF_OFFSET, + offsetof(ngx_http_core_loc_conf_t, doc_root)}, + + {ngx_string("send_timeout"), + NGX_HTTP_LOC_CONF|NGX_CONF_BLOCK|NGX_CONF_TAKE1, + ngx_conf_set_time_slot, + NGX_HTTP_LOC_CONF_OFFSET, + offsetof(ngx_http_core_loc_conf_t, send_timeout)}, + + {ngx_string(""), 0, NULL, 0, 0} +}; + + +ngx_http_module_t ngx_http_core_module_ctx = { + NGX_HTTP_MODULE, + + ngx_http_core_create_srv_conf, /* create server config */ + ngx_http_core_init_srv_conf, /* init server config */ + ngx_http_core_create_loc_conf, /* create location config */ + NULL, /* merge location config */ + + ngx_http_core_translate_handler, /* translate handler */ + + NULL, /* output header filter */ + NULL, /* next output header filter */ + NULL, /* output body filter */ + NULL /* next output body filter */ +}; + + +ngx_module_t ngx_http_core_module = { + 0, /* module index */ + &ngx_http_core_module_ctx, /* module context */ + ngx_http_core_commands, /* module directives */ + NGX_HTTP_MODULE_TYPE, /* module type */ + NULL /* init module */ +}; + + +int ngx_http_handler(ngx_http_request_t *r) +{ + int rc, i; + ngx_http_module_t *module; + ngx_http_conf_ctx_t *ctx; + + r->connection->unexpected_eof = 0; + r->lingering_close = 1; + r->keepalive = 0; + + ctx = (ngx_http_conf_ctx_t *) r->connection->ctx; + r->srv_conf = ctx->srv_conf; + r->loc_conf = ctx->loc_conf; + +ngx_log_debug(r->connection->log, "srv_conf: %0x" _ r->srv_conf); +ngx_log_debug(r->connection->log, "loc_conf: %0x" _ r->loc_conf); +ngx_log_debug(r->connection->log, "servers: %0x" _ r->connection->servers); + + +#if 1 + r->filter = NGX_HTTP_FILTER_NEED_IN_MEMORY; +#endif + + /* run translation phase */ + for (i = 0; ngx_modules[i]; i++) { + if (ngx_modules[i]->type != NGX_HTTP_MODULE_TYPE) { + continue; + } + + module = (ngx_http_module_t *) ngx_modules[i]->ctx; + + if (module->translate_handler == NULL) { + continue; + } + + rc = module->translate_handler(r); + if (rc == NGX_OK) { + break; + } + + if (rc >= NGX_HTTP_SPECIAL_RESPONSE) { + return ngx_http_special_response(r, rc); + } + } + + rc = r->handler(r); + + if (rc >= NGX_HTTP_SPECIAL_RESPONSE) { + return ngx_http_special_response(r, rc); + } + + return rc; +} + + +int ngx_http_core_translate_handler(ngx_http_request_t *r) +{ + int i, rc; + char *location, *last; + ngx_err_t err; + ngx_table_elt_t *h; + ngx_http_core_srv_conf_t *scf; + ngx_http_core_loc_conf_t **lcf, *loc_conf; + + scf = (ngx_http_core_srv_conf_t *) + ngx_http_get_module_srv_conf(r, ngx_http_core_module_ctx); + + /* find location config */ + lcf = (ngx_http_core_loc_conf_t **) scf->locations.elts; + for (i = 0; i < scf->locations.nelts; i++) { +ngx_log_debug(r->connection->log, "trans: %s" _ lcf[i]->name.data); + if (r->uri.len < lcf[i]->name.len) { + continue; + } + + rc = ngx_strncmp(r->uri.data, lcf[i]->name.data, lcf[i]->name.len); + + if (rc < 0) { + break; + } + + if (rc == 0) { + r->loc_conf = lcf[i]->loc_conf; + } + } + + if (r->uri.data[r->uri.len - 1] == '/') { + /* TODO: find index handler */ + /* STUB */ r->handler = ngx_http_index_handler; + + return NGX_OK; + } + + loc_conf = (ngx_http_core_loc_conf_t *) + ngx_http_get_module_loc_conf(r, ngx_http_core_module_ctx); + + r->file.name.len = loc_conf->doc_root.len + r->uri.len; + + ngx_test_null(r->file.name.data, + ngx_palloc(r->pool, r->file.name.len + 1), + NGX_HTTP_INTERNAL_SERVER_ERROR); + + location = ngx_cpystrn(r->file.name.data, loc_conf->doc_root.data, + loc_conf->doc_root.len + 1); + last = ngx_cpystrn(location, r->uri.data, r->uri.len + 1); + + ngx_log_debug(r->connection->log, "HTTP filename: '%s'" _ + r->file.name.data); + +#if (WIN9X) + + /* There is no way to open file or directory in Win9X with + one syscall: Win9X has not FILE_FLAG_BACKUP_SEMANTICS flag. + so we need to check its type before opening */ + + r->file.info.dwFileAttributes = GetFileAttributes(r->file.name.data); + if (r->file.info.dwFileAttributes == INVALID_FILE_ATTRIBUTES) { + err = ngx_errno; + ngx_log_error(NGX_LOG_ERR, r->connection->log, err, + "ngx_http_core_translate_handler: " + ngx_file_type_n " %s failed", r->file.name.data); + + if (err == ERROR_FILE_NOT_FOUND) { + return NGX_HTTP_NOT_FOUND; + } else if (err == ERROR_PATH_NOT_FOUND) { + return NGX_HTTP_NOT_FOUND; + } else { + return NGX_HTTP_INTERNAL_SERVER_ERROR; + } + } + +#else + + if (r->file.fd == NGX_INVALID_FILE) { + r->file.fd = ngx_open_file(r->file.name.data, NGX_FILE_RDONLY); + } + + if (r->file.fd == NGX_INVALID_FILE) { + err = ngx_errno; + ngx_log_error(NGX_LOG_ERR, r->connection->log, ngx_errno, + "ngx_http_core_handler: " + ngx_open_file_n " %s failed", r->file.name.data); + + if (err == NGX_ENOENT) { + return NGX_HTTP_NOT_FOUND; +#if (WIN32) + } else if (err == ERROR_PATH_NOT_FOUND) { + return NGX_HTTP_NOT_FOUND; +#endif + } else { + return NGX_HTTP_INTERNAL_SERVER_ERROR; + } + } + + if (!r->file.info_valid) { + if (ngx_stat_fd(r->file.fd, &r->file.info) == NGX_FILE_ERROR) { + ngx_log_error(NGX_LOG_ERR, r->connection->log, ngx_errno, + "ngx_http_core_handler: " + ngx_stat_fd_n " %s failed", r->file.name.data); + + if (ngx_close_file(r->file.fd) == NGX_FILE_ERROR) { + ngx_log_error(NGX_LOG_ERR, r->connection->log, ngx_errno, + "ngx_http_core_handler: " + ngx_close_file_n " %s failed", r->file.name.data); + } + + return NGX_HTTP_INTERNAL_SERVER_ERROR; + } + + r->file.info_valid = 1; + } +#endif + + if (ngx_is_dir(r->file.info)) { + ngx_log_debug(r->connection->log, "HTTP DIR: '%s'" _ r->file.name.data); + +#if !(WIN9X) + if (ngx_close_file(r->file.fd) == NGX_FILE_ERROR) { + ngx_log_error(NGX_LOG_ERR, r->connection->log, ngx_errno, + "ngx_http_core_handler: " + ngx_close_file_n " %s failed", r->file.name.data); + } +#endif + + /* BROKEN: need to include server name */ + + ngx_test_null(h, ngx_push_table(r->headers_out.headers), + NGX_HTTP_INTERNAL_SERVER_ERROR); + + *last++ = '/'; + *last = '\0'; + h->key.len = 8; + h->key.data = "Location" ; + h->value.len = last - location; + h->value.data = location; + r->headers_out.location = h; + + return NGX_HTTP_MOVED_PERMANENTLY; + } + + /* TODO: r->handler = loc_conf->default_handler; */ + /* STUB */ r->handler = ngx_http_static_handler; + + return NGX_OK; +} + + +int ngx_http_send_header(ngx_http_request_t *r) +{ + return (*ngx_http_top_header_filter)(r); +} + + +int ngx_http_redirect(ngx_http_request_t *r, int redirect) +{ + /* STUB */ + + /* log request */ + + return ngx_http_close_request(r); +} + + +int ngx_http_error(ngx_http_request_t *r, int error) +{ + /* STUB */ + ngx_log_debug(r->connection->log, "http error: %d" _ error); + + /* log request */ + + ngx_http_special_response(r, error); + return ngx_http_close_request(r); +} + + +int ngx_http_close_request(ngx_http_request_t *r) +{ + ngx_log_debug(r->connection->log, "CLOSE#: %d" _ r->file.fd); + + ngx_http_log_handler(r); + + ngx_assert((r->file.fd != NGX_INVALID_FILE), /* void */ ; , + r->connection->log, "file already closed"); + + if (r->file.fd != NGX_INVALID_FILE) { + if (ngx_close_file(r->file.fd) == NGX_FILE_ERROR) { + ngx_log_error(NGX_LOG_ERR, r->connection->log, ngx_errno, + ngx_close_file_n " failed"); + } + } + +/* + if (r->logging) + ngx_http_log_request(r); +*/ + + ngx_destroy_pool(r->pool); + + ngx_log_debug(r->connection->log, "http close"); + + ngx_del_timer(r->connection->read); + ngx_del_timer(r->connection->write); + + return NGX_DONE; +} + + +int ngx_http_internal_redirect(ngx_http_request_t *r, ngx_str_t uri) +{ + ngx_log_debug(r->connection->log, "internal redirect: '%s'" _ uri.data); + + r->uri.len = uri.len; + r->uri.data = uri.data; + + /* NEEDED ? */ + r->uri_start = uri.data; + r->uri_end = uri.data + uri.len; + /**/ + + return ngx_http_handler(r); +} + + +#if 0 +void *ngx_http_find_server_conf(ngx_http_request_t *r) +{ + int i; + ngx_http_listen_t *fs, *ls; + ngx_http_server_name_t *n; + + fs = NULL; + ls = (ngx_http_listen_t *) http->ports.elts; + + for (i = 0; i < http->ports.nelts; i++) { + if (s->family != ls[i].family || s->port != ls[i].port) { + continue; + } + + if (s->family == AF_INET) { + + if (ls[i].addr == INADDR_ANY || ls[i].addr == s->addr) { + fs = &ls[i]; + break; + } + + } else { + /* STUB: AF_INET only */ + } + } + + if (fs == NULL) { + ngx_log_error(NGX_LOG_ALERT, r->connection->log, 0, + "unknown local socket %s:%d", + s->addr_text.data, s->port); + return NULL; + } + + if (r->headers_in.host && fs->server_names.nelts) { + + n = (ngx_http_server_name_t *) fs->server_names.elts; + for (i = 0; i < fs->server_names.nelts; i++) { + if (r->headers_in.host->value.len != n[i].name.len) { + continue; + } + + if (ngx_strcmp(r->headers_in.host->value.data, n[i].name.data) == 0) { + return n[i].srv_conf; + } + } + } + + return fs->srv_conf; +} +#endif + + +static char *ngx_server_block(ngx_conf_t *cf, ngx_command_t *cmd, char *dummy) +{ + int i, j; + char *rv; + ngx_http_module_t *module; + ngx_http_conf_ctx_t *ctx, *prev; + ngx_http_core_srv_conf_t *scf; + ngx_http_core_loc_conf_t **lcf; + + ngx_test_null(ctx, + ngx_pcalloc(cf->pool, sizeof(ngx_http_conf_ctx_t)), + NGX_CONF_ERROR); + + /* server config */ + ngx_test_null(ctx->srv_conf, + ngx_pcalloc(cf->pool, sizeof(void *) * ngx_http_max_module), + NGX_CONF_ERROR); + + /* server location config */ + ngx_test_null(ctx->loc_conf, + ngx_pcalloc(cf->pool, sizeof(void *) * ngx_http_max_module), + NGX_CONF_ERROR); + + for (i = 0; ngx_modules[i]; i++) { + if (ngx_modules[i]->type != NGX_HTTP_MODULE_TYPE) { + continue; + } + + module = (ngx_http_module_t *) ngx_modules[i]->ctx; + + if (module->create_srv_conf) { + ngx_test_null(ctx->srv_conf[module->index], + module->create_srv_conf(cf->pool), + NGX_CONF_ERROR); +ngx_log_debug(cf->log, "srv_conf: %d:%0x" _ + module->index _ ctx->loc_conf[module->index]); + } + + if (module->create_loc_conf) { + ngx_test_null(ctx->loc_conf[module->index], + module->create_loc_conf(cf->pool), + NGX_CONF_ERROR); +ngx_log_debug(cf->log, "srv loc_conf: %d:%0x" _ + module->index _ ctx->loc_conf[module->index]); + } + } + + prev = cf->ctx; + cf->ctx = ctx; + rv = ngx_conf_parse(cf, NULL); + cf->ctx = prev; + + if (rv != NGX_CONF_OK) + return rv; + + + scf = ctx->srv_conf[ngx_http_core_module_ctx.index]; + scf->ctx = ctx; + + lcf = (ngx_http_core_loc_conf_t **)scf->locations.elts; + + for (i = 0; ngx_modules[i]; i++) { + if (ngx_modules[i]->type != NGX_HTTP_MODULE_TYPE) { + continue; + } + + module = (ngx_http_module_t *) ngx_modules[i]->ctx; + + if (module->init_srv_conf) { + if (module->init_srv_conf(cf->pool, + ctx->srv_conf[module->index]) + == NGX_CONF_ERROR) { + return NGX_CONF_ERROR; + } + } + + if (module->merge_loc_conf) { + if (module->merge_loc_conf(cf->pool, + prev->loc_conf[module->index], + ctx->loc_conf[module->index]) + == NGX_CONF_ERROR) { + return NGX_CONF_ERROR; + } + + for (j = 0; j < scf->locations.nelts; j++) { +ngx_log_debug(cf->log, "%d:%0x" _ j _ lcf[j]); +ngx_log_debug(cf->log, "%d:'%s'" _ lcf[j]->name.len _ lcf[j]->name.data); + if (module->merge_loc_conf(cf->pool, + ctx->loc_conf[module->index], + lcf[j]->loc_conf[module->index]) + == NGX_CONF_ERROR) { + return NGX_CONF_ERROR; + } + } + } + } + + return NGX_CONF_OK; +} + + +static char *ngx_location_block(ngx_conf_t *cf, ngx_command_t *cmd, char *dummy) +{ + int i; + char *rv; + void **loc; + ngx_str_t *location; + ngx_http_module_t *module; + ngx_http_conf_ctx_t *ctx, *prev; + ngx_http_core_srv_conf_t *scf; + ngx_http_core_loc_conf_t *lcf; + + ngx_test_null(ctx, + ngx_pcalloc(cf->pool, sizeof(ngx_http_conf_ctx_t)), + NGX_CONF_ERROR); + + prev = (ngx_http_conf_ctx_t *) cf->ctx; + ctx->srv_conf = prev->srv_conf; + + ngx_test_null(ctx->loc_conf, + ngx_pcalloc(cf->pool, sizeof(void *) * ngx_http_max_module), + NGX_CONF_ERROR); + + for (i = 0; ngx_modules[i]; i++) { + if (ngx_modules[i]->type != NGX_HTTP_MODULE_TYPE) { + continue; + } + + module = (ngx_http_module_t *) ngx_modules[i]->ctx; + + if (module->create_loc_conf) { + ngx_test_null(ctx->loc_conf[module->index], + module->create_loc_conf(cf->pool), + NGX_CONF_ERROR); +ngx_log_debug(cf->log, "loc_conf: %d:%0x" _ + module->index _ ctx->loc_conf[module->index]); + } + } + + lcf = (ngx_http_core_loc_conf_t *) + ctx->loc_conf[ngx_http_core_module_ctx.index]; + location = (ngx_str_t *) cf->args->elts; + lcf->name.len = location[1].len; + lcf->name.data = location[1].data; + lcf->loc_conf = ctx->loc_conf; + + scf = (ngx_http_core_srv_conf_t *) + ctx->srv_conf[ngx_http_core_module_ctx.index]; + ngx_test_null(loc, ngx_push_array(&scf->locations), NGX_CONF_ERROR); + *loc = lcf; + +ngx_log_debug(cf->log, "%0x:%s" _ lcf _ lcf->name.data); + + cf->ctx = ctx; + rv = ngx_conf_parse(cf, NULL); + cf->ctx = prev; + + return rv; +} + + +int ngx_http_config_modules(ngx_pool_t *pool, ngx_module_t **modules) +{ + int i; + ngx_http_module_t *module; + + for (i = 0; modules[i]; i++) { + if (modules[i]->type != NGX_HTTP_MODULE_TYPE) { + continue; + } + + module = (ngx_http_module_t *) modules[i]->ctx; + module->index = i; + } + + ngx_http_max_module = i; + +#if 0 + ngx_test_null(ngx_srv_conf, + ngx_pcalloc(pool, sizeof(void *) * ngx_http_max_module), + NGX_ERROR); + ngx_test_null(ngx_loc_conf, + ngx_pcalloc(pool, sizeof(void *) * ngx_http_max_module), + NGX_ERROR); + + for (i = 0; modules[i]; i++) { + if (modules[i]->create_srv_conf) + ngx_srv_conf[i] = modules[i]->create_srv_conf(pool); + + if (modules[i]->create_loc_conf) + ngx_loc_conf[i] = modules[i]->create_loc_conf(pool); + } +#endif +} + + +void ngx_http_init_filters(ngx_pool_t *pool, ngx_module_t **modules) +{ + int i; + ngx_http_module_t *module; + int (*ohf)(ngx_http_request_t *r); + int (*obf)(ngx_http_request_t *r, ngx_chain_t *ch); + + ohf = NULL; + obf = NULL; + + for (i = 0; modules[i]; i++) { + if (modules[i]->type != NGX_HTTP_MODULE_TYPE) { + continue; + } + + module = (ngx_http_module_t *) modules[i]->ctx; + + if (module->output_header_filter) { + module->next_output_header_filter = ohf; + ohf = module->output_header_filter; + } + + if (module->output_body_filter) { + module->next_output_body_filter = obf; + obf = module->output_body_filter; + } + } + + ngx_http_top_header_filter = ohf; +} + + +static void *ngx_http_core_create_srv_conf(ngx_pool_t *pool) +{ + ngx_http_core_srv_conf_t *scf, **cf; + + ngx_test_null(scf, + ngx_pcalloc(pool, sizeof(ngx_http_core_srv_conf_t)), + NGX_CONF_ERROR); + + ngx_init_array(scf->locations, pool, 5, sizeof(void *), NGX_CONF_ERROR); + ngx_init_array(scf->listen, pool, 5, sizeof(ngx_http_listen_t), + NGX_CONF_ERROR); + + ngx_test_null(cf, ngx_push_array(&ngx_http_servers), NGX_CONF_ERROR); + *cf = scf; + + return scf; +} + + +static char *ngx_http_core_init_srv_conf(ngx_pool_t *pool, void *conf) +{ + ngx_http_core_srv_conf_t *scf = (ngx_http_core_srv_conf_t *) conf; + + ngx_http_listen_t *l; + + if (scf->listen.nelts == 0) { + ngx_test_null(l, ngx_push_array(&scf->listen), NGX_CONF_ERROR); + l->addr = INADDR_ANY; + l->port = 8000; + l->family = AF_INET; + } + + return NGX_CONF_OK; +} + + +static void *ngx_http_core_create_loc_conf(ngx_pool_t *pool) +{ + ngx_http_core_loc_conf_t *lcf; + + ngx_test_null(lcf, + ngx_pcalloc(pool, sizeof(ngx_http_core_loc_conf_t)), + NGX_CONF_ERROR); + + lcf->doc_root.len = 4; + lcf->doc_root.data = "html"; + + lcf->send_timeout = 10; + lcf->discarded_buffer_size = 1500; + lcf->lingering_time = 30; + lcf->lingering_timeout = 5000; + +/* + lcf->send_timeout = NGX_CONF_UNSET; +*/ + + return lcf; +} diff --git a/src/http/ngx_http_core_module.h b/src/http/ngx_http_core_module.h new file mode 100644 index 000000000..ed0173bd5 --- /dev/null +++ b/src/http/ngx_http_core_module.h @@ -0,0 +1,86 @@ +#ifndef _NGX_HTTP_CORE_H_INCLUDED_ +#define _NGX_HTTP_CORE_H_INCLUDED_ + + +#include <ngx_string.h> +#include <ngx_array.h> +#include <ngx_http.h> + + +typedef struct { + int addr; + int port; + int family; + int flags; /* 'default' */ + ngx_conf_file_t *conf_file; + int line; +} ngx_http_listen_t; + + +typedef struct { + ngx_array_t locations; /* array of ngx_http_core_loc_conf_t */ + + ngx_array_t listen; /* 'listen', array of ngx_http_listen_t */ + ngx_array_t server_names; /* 'server_name', + array of ngx_http_server_name_t */ + ngx_http_conf_ctx_t *ctx; +} ngx_http_core_srv_conf_t; + + +typedef struct { + ngx_str_t name; + ngx_http_core_srv_conf_t *core_srv_conf; +} ngx_http_server_name_t; + + +typedef struct { + int port; + ngx_array_t addr; +} ngx_http_in_port_t; + +typedef struct { + u_int32_t addr; + ngx_array_t names; + int flags; + ngx_http_core_srv_conf_t *core_srv_conf; +} ngx_http_in_addr_t; + +#define NGX_HTTP_DEFAULT_SERVER 1 + + + +typedef struct { + ngx_str_t name; /* location name */ + void **loc_conf; /* used in translation handler */ + + ngx_str_t doc_root; /* 'root' */ + + time_t send_timeout; /* 'send_timeout' */ + size_t discarded_buffer_size; /* 'discarded_buffer_size */ + time_t lingering_time; /* 'lingering_time */ + ngx_msec_t lingering_timeout; /* 'lingering_timeout */ +} ngx_http_core_loc_conf_t; + + + + +#if 0 +typedef struct { + int dummy; +} ngx_http_core_conf_t; +#endif + + +extern ngx_http_module_t ngx_http_core_module_ctx; +extern ngx_module_t ngx_http_core_module; + +extern int (*ngx_http_top_header_filter) (ngx_http_request_t *r); +extern int ngx_http_max_module; + + + +int ngx_http_core_translate_handler(ngx_http_request_t *r); + + + +#endif /* _NGX_HTTP_CORE_H_INCLUDED_ */ diff --git a/src/http/ngx_http_event.c b/src/http/ngx_http_event.c index b2f587657..a5386965e 100644 --- a/src/http/ngx_http_event.c +++ b/src/http/ngx_http_event.c @@ -12,7 +12,7 @@ #include <ngx_inet.h> #include <ngx_http.h> #include <ngx_http_config.h> -#include <ngx_http_core.h> +#include <ngx_http_core_module.h> /* STUB */ #include <ngx_http_output_filter.h> @@ -75,16 +75,13 @@ int ngx_http_init_connection(ngx_connection_t *c) { ngx_event_t *ev; struct sockaddr *addr; - ngx_http_server_t *srv; ngx_http_log_ctx_t *ctx; ev = c->read; ev->event_handler = ngx_http_init_request; - srv = (ngx_http_server_t *) c->server; - ngx_test_null(c->pool, - ngx_create_pool(srv->connection_pool_size, ev->log), + ngx_create_pool(ngx_http_connection_pool_size, ev->log), NGX_ERROR); ngx_test_null(c->requests, ngx_create_array(c->pool, 10, sizeof(char *)), @@ -97,12 +94,12 @@ int ngx_http_init_connection(ngx_connection_t *c) ngx_memcpy(addr, c->sockaddr, c->socklen); c->sockaddr = addr; - ngx_test_null(c->addr_text.data, ngx_palloc(c->pool, c->addr_text.len), + ngx_test_null(c->addr_text.data, ngx_palloc(c->pool, c->addr_text_max_len), NGX_ERROR); c->addr_text.len = ngx_inet_ntop(c->family, (char *)c->sockaddr + c->addr, - c->addr_text.data, c->addr_text.len); + c->addr_text.data, c->addr_text_max_len); if (c->addr_text.len == 0) return NGX_ERROR; @@ -118,7 +115,6 @@ int ngx_http_init_connection(ngx_connection_t *c) return ngx_http_init_request(ev); } else { #endif - /* STUB: post_accept_timeout should be in http_conf */ ngx_add_timer(ev, c->post_accept_timeout); #if (USE_KQUEUE) return ngx_add_event(ev, NGX_READ_EVENT, NGX_CLEAR_EVENT); @@ -143,29 +139,22 @@ int ngx_http_init_connection(ngx_connection_t *c) static int ngx_http_init_request(ngx_event_t *ev) { - ngx_connection_t *c; - ngx_http_server_t *srv; - ngx_http_request_t *r; + ngx_connection_t *c; + ngx_http_request_t *r; c = (ngx_connection_t *) ev->data; - srv = (ngx_http_server_t *) c->server; ngx_test_null(r, ngx_pcalloc(c->pool, sizeof(ngx_http_request_t)), NGX_ERROR); c->data = r; r->connection = c; - r->server = srv; r->file.fd = NGX_INVALID_FILE; - /* STUB */ - r->srv_conf = ngx_srv_conf; - r->loc_conf = ngx_loc_conf; - /**/ - if (c->buffer == NULL) { ngx_test_null(c->buffer, - ngx_create_temp_hunk(c->pool, srv->header_buffer_size, + ngx_create_temp_hunk(c->pool, + ngx_http_client_header_buffer_size, 0, 0), NGX_ERROR); } else { @@ -174,7 +163,7 @@ static int ngx_http_init_request(ngx_event_t *ev) r->header_in = c->buffer; - ngx_test_null(r->pool, ngx_create_pool(srv->request_pool_size, ev->log), + ngx_test_null(r->pool, ngx_create_pool(ngx_http_request_pool_size, ev->log), ngx_http_close_request(r)); ngx_test_null(r->ctx, @@ -218,9 +207,7 @@ static int ngx_http_process_request_header(ngx_event_t *ev) if (r->header_timeout) { r->header_timeout = 0; ngx_del_timer(ev); - /* STUB: r->server->header_timeout - OR r->srv_conf->header_timeout ? */ - ngx_add_timer(ev, r->server->header_timeout); + ngx_add_timer(ev, ngx_http_client_header_timeout); } return NGX_AGAIN; } @@ -254,7 +241,7 @@ static int ngx_http_process_request_header(ngx_event_t *ev) if (r->header_timeout) { r->header_timeout = 0; ngx_del_timer(ev); - ngx_add_timer(ev, r->server->header_timeout); + ngx_add_timer(ev, ngx_http_client_header_timeout); } if (rc == NGX_OK) @@ -591,25 +578,29 @@ static int ngx_http_read_discarded_body(ngx_event_t *ev) { size_t size; ssize_t n; - ngx_connection_t *c; - ngx_http_request_t *r; - - c = (ngx_connection_t *) ev->data; - r = (ngx_http_request_t *) c->data; + ngx_connection_t *c; + ngx_http_request_t *r; + ngx_http_core_loc_conf_t *lcf; ngx_log_debug(ev->log, "http read discarded body"); if (ev->timedout) return NGX_ERROR; + c = (ngx_connection_t *) ev->data; + r = (ngx_http_request_t *) c->data; + + lcf = (ngx_http_core_loc_conf_t *) + ngx_http_get_module_loc_conf(r, ngx_http_core_module_ctx); + if (r->discarded_buffer == NULL) ngx_test_null(r->discarded_buffer, - ngx_palloc(r->pool, r->server->discarded_buffer_size), + ngx_palloc(r->pool, lcf->discarded_buffer_size), NGX_ERROR); size = r->client_content_length; - if (size > r->server->discarded_buffer_size) - size = r->server->discarded_buffer_size; + if (size > lcf->discarded_buffer_size) + size = lcf->discarded_buffer_size; n = ngx_event_recv(c, r->discarded_buffer, size); if (n == NGX_ERROR) @@ -624,34 +615,6 @@ static int ngx_http_read_discarded_body(ngx_event_t *ev) } -#if 0 -static int ngx_http_discarded_read(ngx_event_t *ev) -{ - ssize_t n; - ngx_connection_t *c; - ngx_http_request_t *r; - - c = (ngx_connection_t *) ev->data; - r = (ngx_http_request_t *) c->data; - - ngx_log_debug(ev->log, "http discarded read"); - - if (ev->timedout) - return NGX_ERROR; - - if (r->discarded_buffer == NULL) - ngx_test_null(r->discarded_buffer, - ngx_palloc(r->pool, r->server->discarded_buffer_size), - NGX_ERROR); - - n = ngx_event_recv(c, r->discarded_buffer, - r->server->discarded_buffer_size); - - return n; -} -#endif - - static int ngx_http_keepalive_handler(ngx_event_t *ev) { ssize_t n; @@ -690,11 +653,16 @@ static int ngx_http_keepalive_handler(ngx_event_t *ev) static int ngx_http_set_lingering_close(ngx_http_request_t *r) { - r->lingering_time = ngx_time() + r->server->lingering_time; + ngx_http_core_loc_conf_t *lcf; + + lcf = (ngx_http_core_loc_conf_t *) + ngx_http_get_module_loc_conf(r, ngx_http_core_module_ctx); + + r->lingering_time = ngx_time() + lcf->lingering_time; r->connection->read->event_handler = ngx_http_lingering_close_handler; ngx_del_timer(r->connection->read); - ngx_add_timer(r->connection->read, r->server->lingering_timeout); + ngx_add_timer(r->connection->read, lcf->lingering_timeout); if (r->connection->read->blocked) { if (ngx_add_event(r->connection->read, NGX_READ_EVENT, @@ -725,9 +693,7 @@ static int ngx_http_lingering_close_handler(ngx_event_t *ev) ngx_msec_t timer; ngx_connection_t *c; ngx_http_request_t *r; - - c = (ngx_connection_t *) ev->data; - r = (ngx_http_request_t *) c->data; + ngx_http_core_loc_conf_t *lcf; ngx_log_debug(ev->log, "http lingering close handler"); @@ -735,25 +701,30 @@ static int ngx_http_lingering_close_handler(ngx_event_t *ev) return ngx_http_close_request(r); } + c = (ngx_connection_t *) ev->data; + r = (ngx_http_request_t *) c->data; + timer = r->lingering_time - ngx_time(); if (timer <= 0) { return ngx_http_close_request(r); } + lcf = (ngx_http_core_loc_conf_t *) + ngx_http_get_module_loc_conf(r, ngx_http_core_module_ctx); + if (r->discarded_buffer == NULL) { if (r->header_in->end - r->header_in->last.mem - >= r->server->discarded_buffer_size) { + >= lcf->discarded_buffer_size) { r->discarded_buffer = r->header_in->last.mem; } else { ngx_test_null(r->discarded_buffer, - ngx_palloc(c->pool, r->server->discarded_buffer_size), + ngx_palloc(c->pool, lcf->discarded_buffer_size), ngx_http_close_request(r)); } } - n = ngx_event_recv(c, r->discarded_buffer, - r->server->discarded_buffer_size); + n = ngx_event_recv(c, r->discarded_buffer, lcf->discarded_buffer_size); ngx_log_debug(ev->log, "lingering read: %d" _ n); @@ -762,8 +733,8 @@ static int ngx_http_lingering_close_handler(ngx_event_t *ev) } timer *= 1000; - if (timer > r->server->lingering_timeout) { - timer = r->server->lingering_timeout; + if (timer > lcf->lingering_timeout) { + timer = lcf->lingering_timeout; } ngx_del_timer(ev); diff --git a/src/http/ngx_http_header_filter.c b/src/http/ngx_http_header_filter.c index 3e8567781..04a383733 100644 --- a/src/http/ngx_http_header_filter.c +++ b/src/http/ngx_http_header_filter.c @@ -34,6 +34,7 @@ ngx_http_module_t ngx_http_header_filter_module_ctx = { ngx_module_t ngx_http_header_filter_module = { + 0, /* module index */ &ngx_http_header_filter_module_ctx, /* module context */ NULL, /* module directives */ NGX_HTTP_MODULE_TYPE, /* module type */ diff --git a/src/http/ngx_http_output_filter.c b/src/http/ngx_http_output_filter.c index 345a4f161..3f699f868 100644 --- a/src/http/ngx_http_output_filter.c +++ b/src/http/ngx_http_output_filter.c @@ -14,14 +14,16 @@ static int ngx_http_output_filter_copy_hunk(ngx_hunk_t *dst, ngx_hunk_t *src); static void *ngx_http_output_filter_create_conf(ngx_pool_t *pool); +static char *ngx_http_output_filter_merge_conf(ngx_pool_t *pool, + void *parent, void *child); static ngx_command_t ngx_http_output_filter_commands[] = { {ngx_string("output_buffer"), - NGX_CONF_TAKE1, + NGX_HTTP_LOC_CONF|NGX_CONF_BLOCK|NGX_CONF_TAKE1, ngx_conf_set_size_slot, - NGX_HTTP_LOC_CONF, + NGX_HTTP_LOC_CONF_OFFSET, offsetof(ngx_http_output_filter_conf_t, hunk_size)}, {ngx_string(""), 0, NULL, 0, 0} @@ -34,7 +36,7 @@ static ngx_http_module_t ngx_http_output_filter_module_ctx = { NULL, /* create server config */ NULL, /* init server config */ ngx_http_output_filter_create_conf, /* create location config */ - NULL, /* merge location config */ + ngx_http_output_filter_merge_conf, /* merge location config */ NULL, /* translate handler */ @@ -47,6 +49,7 @@ static ngx_http_module_t ngx_http_output_filter_module_ctx = { ngx_module_t ngx_http_output_filter_module = { + 0, /* module index */ &ngx_http_output_filter_module_ctx, /* module context */ ngx_http_output_filter_commands, /* module directives */ NGX_HTTP_MODULE_TYPE, /* module type */ @@ -249,7 +252,7 @@ int ngx_http_output_filter(ngx_http_request_t *r, ngx_hunk_t *hunk) if (ctx->hunk) { ctx->hunk->pos.mem = ctx->hunk->last.mem = ctx->hunk->start; } -#if (!NGX_ONESHOT_EVENT) +#if (NGX_LEVEL_EVENT) ngx_del_event(r->connection->write, NGX_WRITE_EVENT); #endif } @@ -315,3 +318,17 @@ static void *ngx_http_output_filter_create_conf(ngx_pool_t *pool) return conf; } + + +static char *ngx_http_output_filter_merge_conf(ngx_pool_t *pool, + void *parent, void *child) +{ + ngx_http_output_filter_conf_t *prev = + (ngx_http_output_filter_conf_t *) parent; + ngx_http_output_filter_conf_t *conf = + (ngx_http_output_filter_conf_t *) child; + + ngx_conf_merge(conf->hunk_size, prev->hunk_size, 32768); + + return NULL; +} diff --git a/src/http/ngx_http_parse.c b/src/http/ngx_http_parse.c index 7d1cc2323..a741f090f 100644 --- a/src/http/ngx_http_parse.c +++ b/src/http/ngx_http_parse.c @@ -43,33 +43,39 @@ printf("\nstate: %d, pos: %x, end: %x, char: '%c' buf: %s", case sw_start: switch (ch) { case 'G': - if (p + 1 >= r->header_in->last.mem) + if (p + 1 >= r->header_in->last.mem) { return NGX_AGAIN; + } - if (*p != 'E' || *(p + 1) != 'T') + if (*p != 'E' || *(p + 1) != 'T') { return NGX_HTTP_PARSE_INVALID_METHOD; + } r->method = NGX_HTTP_GET; p += 2; break; case 'H': - if (p + 2 >= r->header_in->last.mem) + if (p + 2 >= r->header_in->last.mem) { return NGX_AGAIN; + } - if (*p != 'E' || *(p + 1) != 'A' || *(p + 2) != 'D') + if (*p != 'E' || *(p + 1) != 'A' || *(p + 2) != 'D') { return NGX_HTTP_PARSE_INVALID_METHOD; + } r->method = NGX_HTTP_HEAD; p += 3; break; case 'P': - if (p + 2 >= r->header_in->last.mem) + if (p + 2 >= r->header_in->last.mem) { return NGX_AGAIN; + } - if (*p != 'O' || *(p + 1) != 'S' || *(p + 2) != 'T') + if (*p != 'O' || *(p + 1) != 'S' || *(p + 2) != 'T') { return NGX_HTTP_PARSE_INVALID_METHOD; + } r->method = NGX_HTTP_POST; p += 3; @@ -226,8 +232,9 @@ printf("\nstate: %d, pos: %x, end: %x, char: '%c' buf: %s", return NGX_AGAIN; } - if (ch != 'T' || *p != 'T' || *(p + 1) != 'P' || *(p + 2) != '/') + if (ch != 'T' || *p != 'T' || *(p + 1) != 'P' || *(p + 2) != '/') { return NGX_HTTP_PARSE_INVALID_REQUEST; + } p += 3; state = sw_first_major_digit; @@ -235,8 +242,9 @@ printf("\nstate: %d, pos: %x, end: %x, char: '%c' buf: %s", /* first digit of major HTTP version */ case sw_first_major_digit: - if (ch < '1' || ch > '9') + if (ch < '1' || ch > '9') { return NGX_HTTP_PARSE_INVALID_REQUEST; + } r->http_major = ch - '0'; state = sw_major_digit; @@ -249,16 +257,18 @@ printf("\nstate: %d, pos: %x, end: %x, char: '%c' buf: %s", break; } - if (ch < '0' || ch > '9') + if (ch < '0' || ch > '9') { return NGX_HTTP_PARSE_INVALID_REQUEST; + } r->http_major = r->http_major * 10 + ch - '0'; break; /* first digit of minor HTTP version */ case sw_first_minor_digit: - if (ch < '0' || ch > '9') + if (ch < '0' || ch > '9') { return NGX_HTTP_PARSE_INVALID_REQUEST; + } r->http_minor = ch - '0'; state = sw_minor_digit; @@ -276,8 +286,9 @@ printf("\nstate: %d, pos: %x, end: %x, char: '%c' buf: %s", break; } - if (ch < '0' || ch > '9') + if (ch < '0' || ch > '9') { return NGX_HTTP_PARSE_INVALID_REQUEST; + } r->http_minor = r->http_minor * 10 + ch - '0'; break; @@ -299,14 +310,19 @@ printf("\nstate: %d, pos: %x, end: %x, char: '%c' buf: %s", r->header_in->pos.mem = p; if (state == sw_done) { - if (r->request_end == NULL) + if (r->request_end == NULL) { r->request_end = p - 1; + } + r->http_version = r->http_major * 1000 + r->http_minor; r->state = sw_start; - if (r->http_version == 9 && r->method == NGX_HTTP_HEAD) + + if (r->http_version == 9 && r->method == NGX_HTTP_HEAD) { return NGX_HTTP_PARSE_INVALID_HEAD; - else + } else { return NGX_OK; + } + } else { r->state = state; return NGX_AGAIN; @@ -358,14 +374,17 @@ printf("\nstate: %d, pos: %x, end: %x, char: '%c' buf: %s", r->header_name_start = p - 1; c = ch | 0x20; - if (c >= 'a' && c <= 'z') + if (c >= 'a' && c <= 'z') { break; + } - if (ch == '-') + if (ch == '-') { break; + } - if (ch >= '0' && ch <= '9') + if (ch >= '0' && ch <= '9') { break; + } return NGX_HTTP_PARSE_INVALID_HEADER; @@ -375,8 +394,9 @@ printf("\nstate: %d, pos: %x, end: %x, char: '%c' buf: %s", /* header name */ case sw_name: c = ch | 0x20; - if (c >= 'a' && c <= 'z') + if (c >= 'a' && c <= 'z') { break; + } if (ch == ':') { r->header_name_end = p - 1; @@ -384,11 +404,13 @@ printf("\nstate: %d, pos: %x, end: %x, char: '%c' buf: %s", break; } - if (ch == '-') + if (ch == '-') { break; + } - if (ch >= '0' && ch <= '9') + if (ch >= '0' && ch <= '9') { break; + } return NGX_HTTP_PARSE_INVALID_HEADER; @@ -476,9 +498,11 @@ printf("\nstate: %d, pos: %x, end: %x, char: '%c' buf: %s", if (state == sw_done) { r->state = sw_start; return NGX_OK; + } else if (state == sw_header_done) { r->state = sw_start; return NGX_HTTP_PARSE_HEADER_DONE; + } else { r->state = state; return NGX_AGAIN; diff --git a/src/http/ngx_http_parse_time.c b/src/http/ngx_http_parse_time.c index 9c606c26e..c236fd503 100644 --- a/src/http/ngx_http_parse_time.c +++ b/src/http/ngx_http_parse_time.c @@ -21,8 +21,9 @@ time_t ngx_http_parse_time(char *value, size_t len) end = value + len; for (p = value; p < end; p++) { - if (*p == ',') + if (*p == ',') { break; + } if (*p == ' ') { fmt = isoc; @@ -31,22 +32,26 @@ time_t ngx_http_parse_time(char *value, size_t len) } for (p++; p < end; p++) - if (*p != ' ') + if (*p != ' ') { break; + } - if (end - p < 18) + if (end - p < 18) { return NGX_ERROR; + } if (fmt != isoc) { - if (*p < '0' || *p > '9' || *(p + 1) < '0' || *(p + 1) > '9') + if (*p < '0' || *p > '9' || *(p + 1) < '0' || *(p + 1) > '9') { return NGX_ERROR; + } day = (*p - '0') * 10 + *(p + 1) - '0'; p += 2; if (*p == ' ') { - if (end - p < 18) + if (end - p < 18) { return NGX_ERROR; + } fmt = rfc822; } else if (*p == '-') { @@ -99,8 +104,9 @@ time_t ngx_http_parse_time(char *value, size_t len) p += 3; - if ((fmt == rfc822 && *p != ' ') || (fmt == rfc850 && *p != '-')) + if ((fmt == rfc822 && *p != ' ') || (fmt == rfc850 && *p != '-')) { return NGX_ERROR; + } p++; @@ -108,15 +114,18 @@ time_t ngx_http_parse_time(char *value, size_t len) if (*p < '0' || *p > '9' || *(p + 1) < '0' || *(p + 1) > '9' || *(p + 2) < '0' || *(p + 2) > '9' || *(p + 3) < '0' || *(p + 3) > '9') + { return NGX_ERROR; + } year = (*p - '0') * 1000 + (*(p + 1) - '0') * 100 + (*(p + 2) - '0') * 10 + *(p + 3) - '0'; p += 4; } else if (fmt == rfc850) { - if (*p < '0' || *p > '9' || *(p + 1) < '0' || *(p + 1) > '9') + if (*p < '0' || *p > '9' || *(p + 1) < '0' || *(p + 1) > '9') { return NGX_ERROR; + } year = (*p - '0') * 10 + *(p + 1) - '0'; year += (year < 70) ? 2000 : 1900; @@ -124,61 +133,74 @@ time_t ngx_http_parse_time(char *value, size_t len) } if (fmt == isoc) { - if (*p == ' ') + if (*p == ' ') { p++; + } - if (*p < '0' || *p > '9') + if (*p < '0' || *p > '9') { return NGX_ERROR; + } day = *p++ - '0'; if (*p != ' ') { - if (*p < '0' || *p > '9') + if (*p < '0' || *p > '9') { return NGX_ERROR; + } day = day * 10 + *p++ - '0'; } - if (end - p < 14) + if (end - p < 14) { return NGX_ERROR; + } } - if (*p++ != ' ') + if (*p++ != ' ') { return NGX_ERROR; + } - if (*p < '0' || *p > '9' || *(p + 1) < '0' || *(p + 1) > '9') + if (*p < '0' || *p > '9' || *(p + 1) < '0' || *(p + 1) > '9') { return NGX_ERROR; + } hour = (*p - '0') * 10 + *(p + 1) - '0'; p += 2; - if (*p++ != ':') + if (*p++ != ':') { return NGX_ERROR; + } - if (*p < '0' || *p > '9' || *(p + 1) < '0' || *(p + 1) > '9') + if (*p < '0' || *p > '9' || *(p + 1) < '0' || *(p + 1) > '9') { return NGX_ERROR; + } min = (*p - '0') * 10 + *(p + 1) - '0'; p += 2; - if (*p++ != ':') + if (*p++ != ':') { return NGX_ERROR; + } - if (*p < '0' || *p > '9' || *(p + 1) < '0' || *(p + 1) > '9') + if (*p < '0' || *p > '9' || *(p + 1) < '0' || *(p + 1) > '9') { return NGX_ERROR; + } sec = (*p - '0') * 10 + *(p + 1) - '0'; if (fmt == isoc) { p += 2; - if (*p++ != ' ') + if (*p++ != ' ') { return NGX_ERROR; + } if (*p < '0' || *p > '9' || *(p + 1) < '0' || *(p + 1) > '9' || *(p + 2) < '0' || *(p + 2) > '9' || *(p + 3) < '0' || *(p + 3) > '9') + { return NGX_ERROR; + } year = (*p - '0') * 1000 + (*(p + 1) - '0') * 100 + (*(p + 2) - '0') * 10 + *(p + 3) - '0'; @@ -188,19 +210,22 @@ time_t ngx_http_parse_time(char *value, size_t len) printf("%d.%d.%d %d:%d:%d\n", day, month + 1, year, hour, min, sec); #endif - if (hour > 23 || min > 59 || sec > 59) + if (hour > 23 || min > 59 || sec > 59) { return NGX_ERROR; + } if (day == 29 && month == 1) { - if ((year & 3) || ((year % 100 == 0) && (year % 400) != 0)) + if ((year & 3) || ((year % 100 == 0) && (year % 400) != 0)) { return NGX_ERROR; + } } else if (day > mday[month]) { return NGX_ERROR; } - if (sizeof(time_t) <= 4 && year >= 2038) + if (sizeof(time_t) <= 4 && year >= 2038) { return NGX_ERROR; + } /* shift new year to 1st March, needed for Gauss's formula */ if (--month <= 0) { diff --git a/src/http/ngx_http_write_filter.c b/src/http/ngx_http_write_filter.c index 45f6887c9..6b9bc7dd2 100644 --- a/src/http/ngx_http_write_filter.c +++ b/src/http/ngx_http_write_filter.c @@ -13,14 +13,16 @@ static void *ngx_http_write_filter_create_conf(ngx_pool_t *pool); +static char *ngx_http_write_filter_merge_conf(ngx_pool_t *pool, + void *parent, void *child); static ngx_command_t ngx_http_write_filter_commands[] = { {ngx_string("write_buffer"), - NGX_CONF_TAKE1, + NGX_HTTP_LOC_CONF|NGX_CONF_BLOCK|NGX_CONF_TAKE1, ngx_conf_set_size_slot, - NGX_HTTP_LOC_CONF, + NGX_HTTP_LOC_CONF_OFFSET, offsetof(ngx_http_write_filter_conf_t, buffer_output)}, {ngx_string(""), 0, NULL, 0, 0} @@ -33,7 +35,7 @@ ngx_http_module_t ngx_http_write_filter_module_ctx = { NULL, /* create server config */ NULL, /* init server config */ ngx_http_write_filter_create_conf, /* create location config */ - NULL, /* merge location config */ + ngx_http_write_filter_merge_conf, /* merge location config */ NULL, /* translate handler */ @@ -45,6 +47,7 @@ ngx_http_module_t ngx_http_write_filter_module_ctx = { ngx_module_t ngx_http_write_filter_module = { + 0, /* module index */ &ngx_http_write_filter_module_ctx, /* module context */ ngx_http_write_filter_commands, /* module directives */ NGX_HTTP_MODULE_TYPE, /* module type */ @@ -79,9 +82,12 @@ int ngx_http_write_filter(ngx_http_request_t *r, ngx_chain_t *in) prev = &ch->next; size += ch->hunk->last.file - ch->hunk->pos.file; - ngx_log_debug(r->connection->log, "old chunk: %x " QX_FMT " " QD_FMT _ +#if (NGX_DEBUG_WRITE_FILTER) + ngx_log_debug(r->connection->log, "write filter: old chunk: %x " + QX_FMT " " QD_FMT _ ch->hunk->type _ ch->hunk->pos.file _ ch->hunk->last.file - ch->hunk->pos.file); +#endif if (ch->hunk->type & (NGX_HUNK_FLUSH|NGX_HUNK_RECYCLED)) { flush = size; @@ -102,9 +108,12 @@ int ngx_http_write_filter(ngx_http_request_t *r, ngx_chain_t *in) prev = &ch->next; size += ch->hunk->last.file - ch->hunk->pos.file; - ngx_log_debug(r->connection->log, "new chunk: %x " QX_FMT " " QD_FMT _ +#if (NGX_DEBUG_WRITE_FILTER) + ngx_log_debug(r->connection->log, "write filter: new chunk: %x " + QX_FMT " " QD_FMT _ ch->hunk->type _ ch->hunk->pos.file _ ch->hunk->last.file - ch->hunk->pos.file); +#endif if (ch->hunk->type & (NGX_HUNK_FLUSH|NGX_HUNK_RECYCLED)) { flush = size; @@ -119,7 +128,10 @@ int ngx_http_write_filter(ngx_http_request_t *r, ngx_chain_t *in) ngx_http_get_module_loc_conf(r->main ? r->main : r, ngx_http_write_filter_module_ctx); - ngx_log_debug(r->connection->log, "l:%d f:%d" _ last _ flush); +#if (NGX_DEBUG_WRITE_FILTER) + ngx_log_debug(r->connection->log, "write filter: last:%d flush:%d" _ + last _ flush); +#endif if (!last && flush == 0 && size < conf->buffer_output) { return NGX_OK; @@ -150,3 +162,18 @@ static void *ngx_http_write_filter_create_conf(ngx_pool_t *pool) return conf; } + + +static char *ngx_http_write_filter_merge_conf(ngx_pool_t *pool, + void *parent, void *child) +{ + ngx_http_write_filter_conf_t *prev = + (ngx_http_write_filter_conf_t *) parent; + ngx_http_write_filter_conf_t *conf = + (ngx_http_write_filter_conf_t *) child; + + ngx_conf_merge(conf->buffer_output, prev->buffer_output, 1460); + + return NULL; +} + |