comparison src/http/ngx_http_upstream.c @ 5008:fd84344f1df7

Fixed and improved the "*_bind" directives of proxying modules. The "proxy_bind", "fastcgi_bind", "uwsgi_bind", "scgi_bind" and "memcached_bind" directives are now inherited; inherited value can be reset by the "off" parameter. Duplicate directives are now detected. Parameter value can now contain variables.
author Ruslan Ermilov <ru@nginx.com>
date Wed, 16 Jan 2013 09:42:57 +0000
parents c9059bd5445b
children 7fa7e60a7f66
comparison
equal deleted inserted replaced
5007:13c4c155f26f 5008:fd84344f1df7
132 132
133 static char *ngx_http_upstream(ngx_conf_t *cf, ngx_command_t *cmd, void *dummy); 133 static char *ngx_http_upstream(ngx_conf_t *cf, ngx_command_t *cmd, void *dummy);
134 static char *ngx_http_upstream_server(ngx_conf_t *cf, ngx_command_t *cmd, 134 static char *ngx_http_upstream_server(ngx_conf_t *cf, ngx_command_t *cmd,
135 void *conf); 135 void *conf);
136 136
137 static ngx_addr_t *ngx_http_upstream_get_local(ngx_http_request_t *r,
138 ngx_http_upstream_local_t *local);
139
137 static void *ngx_http_upstream_create_main_conf(ngx_conf_t *cf); 140 static void *ngx_http_upstream_create_main_conf(ngx_conf_t *cf);
138 static char *ngx_http_upstream_init_main_conf(ngx_conf_t *cf, void *conf); 141 static char *ngx_http_upstream_init_main_conf(ngx_conf_t *cf, void *conf);
139 142
140 #if (NGX_HTTP_SSL) 143 #if (NGX_HTTP_SSL)
141 static void ngx_http_upstream_ssl_init_connection(ngx_http_request_t *, 144 static void ngx_http_upstream_ssl_init_connection(ngx_http_request_t *,
505 if (u->create_request(r) != NGX_OK) { 508 if (u->create_request(r) != NGX_OK) {
506 ngx_http_finalize_request(r, NGX_HTTP_INTERNAL_SERVER_ERROR); 509 ngx_http_finalize_request(r, NGX_HTTP_INTERNAL_SERVER_ERROR);
507 return; 510 return;
508 } 511 }
509 512
510 u->peer.local = u->conf->local; 513 u->peer.local = ngx_http_upstream_get_local(r, u->conf->local);
511 514
512 clcf = ngx_http_get_module_loc_conf(r, ngx_http_core_module); 515 clcf = ngx_http_get_module_loc_conf(r, ngx_http_core_module);
513 516
514 u->output.alignment = clcf->directio_alignment; 517 u->output.alignment = clcf->directio_alignment;
515 u->output.pool = r->pool; 518 u->output.pool = r->pool;
4472 ngx_http_upstream_bind_set_slot(ngx_conf_t *cf, ngx_command_t *cmd, 4475 ngx_http_upstream_bind_set_slot(ngx_conf_t *cf, ngx_command_t *cmd,
4473 void *conf) 4476 void *conf)
4474 { 4477 {
4475 char *p = conf; 4478 char *p = conf;
4476 4479
4477 ngx_int_t rc; 4480 ngx_int_t rc;
4478 ngx_str_t *value; 4481 ngx_str_t *value;
4479 ngx_addr_t **paddr; 4482 ngx_http_complex_value_t cv;
4480 4483 ngx_http_upstream_local_t **plocal, *local;
4481 paddr = (ngx_addr_t **) (p + cmd->offset); 4484 ngx_http_compile_complex_value_t ccv;
4482 4485
4483 *paddr = ngx_palloc(cf->pool, sizeof(ngx_addr_t)); 4486 plocal = (ngx_http_upstream_local_t **) (p + cmd->offset);
4484 if (*paddr == NULL) { 4487
4488 if (*plocal != NGX_CONF_UNSET_PTR) {
4489 return "is duplicate";
4490 }
4491
4492 value = cf->args->elts;
4493
4494 if (ngx_strcmp(value[1].data, "off") == 0) {
4495 *plocal = NULL;
4496 return NGX_CONF_OK;
4497 }
4498
4499 ngx_memzero(&ccv, sizeof(ngx_http_compile_complex_value_t));
4500
4501 ccv.cf = cf;
4502 ccv.value = &value[1];
4503 ccv.complex_value = &cv;
4504
4505 if (ngx_http_compile_complex_value(&ccv) != NGX_OK) {
4485 return NGX_CONF_ERROR; 4506 return NGX_CONF_ERROR;
4486 } 4507 }
4487 4508
4488 value = cf->args->elts; 4509 local = ngx_pcalloc(cf->pool, sizeof(ngx_http_upstream_local_t));
4489 4510 if (local == NULL) {
4490 rc = ngx_parse_addr(cf->pool, *paddr, value[1].data, value[1].len); 4511 return NGX_CONF_ERROR;
4512 }
4513
4514 *plocal = local;
4515
4516 if (cv.lengths) {
4517 local->value = ngx_palloc(cf->pool, sizeof(ngx_http_complex_value_t));
4518 if (local->value == NULL) {
4519 return NGX_CONF_ERROR;
4520 }
4521
4522 *local->value = cv;
4523
4524 return NGX_CONF_OK;
4525 }
4526
4527 local->addr = ngx_palloc(cf->pool, sizeof(ngx_addr_t));
4528 if (local->addr == NULL) {
4529 return NGX_CONF_ERROR;
4530 }
4531
4532 rc = ngx_parse_addr(cf->pool, local->addr, value[1].data, value[1].len);
4491 4533
4492 switch (rc) { 4534 switch (rc) {
4493 case NGX_OK: 4535 case NGX_OK:
4494 (*paddr)->name = value[1]; 4536 local->addr->name = value[1];
4495 return NGX_CONF_OK; 4537 return NGX_CONF_OK;
4496 4538
4497 case NGX_DECLINED: 4539 case NGX_DECLINED:
4498 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0, 4540 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0,
4499 "invalid address \"%V\"", &value[1]); 4541 "invalid address \"%V\"", &value[1]);
4500 /* fall through */ 4542 /* fall through */
4501 4543
4502 default: 4544 default:
4503 return NGX_CONF_ERROR; 4545 return NGX_CONF_ERROR;
4546 }
4547 }
4548
4549
4550 static ngx_addr_t *
4551 ngx_http_upstream_get_local(ngx_http_request_t *r,
4552 ngx_http_upstream_local_t *local)
4553 {
4554 ngx_int_t rc;
4555 ngx_str_t val;
4556 ngx_addr_t *addr;
4557
4558 if (local == NULL) {
4559 return NULL;
4560 }
4561
4562 if (local->value == NULL) {
4563 return local->addr;
4564 }
4565
4566 if (ngx_http_complex_value(r, local->value, &val) != NGX_OK) {
4567 return NULL;
4568 }
4569
4570 if (val.len == 0) {
4571 return NULL;
4572 }
4573
4574 addr = ngx_palloc(r->pool, sizeof(ngx_addr_t));
4575 if (addr == NULL) {
4576 return NULL;
4577 }
4578
4579 rc = ngx_parse_addr(r->pool, addr, val.data, val.len);
4580
4581 switch (rc) {
4582 case NGX_OK:
4583 addr->name = val;
4584 return addr;
4585
4586 case NGX_DECLINED:
4587 ngx_log_error(NGX_LOG_ERR, r->connection->log, 0,
4588 "invalid local address \"%V\"", &val);
4589 /* fall through */
4590
4591 default:
4592 return NULL;
4504 } 4593 }
4505 } 4594 }
4506 4595
4507 4596
4508 char * 4597 char *