annotate src/stream/ngx_stream_upstream.c @ 6640:e78eca6bfaf0

HTTP/2: fixed send timer handling. Checking for return value of c->send_chain() isn't sufficient since there are data can be left in the SSL buffer. Now the wew->ready flag is used instead. In particular, this fixed a connection leak in cases when all streams were closed, but there's still some data to be sent in the SSL buffer and the client forgot about the connection.
author Valentin Bartenev <vbart@nginx.com>
date Tue, 19 Jul 2016 20:31:09 +0300
parents 8ed51b02f655
children ab9b4fd8c5b7
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
6115
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
1
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
2 /*
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
3 * Copyright (C) Igor Sysoev
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
4 * Copyright (C) Nginx, Inc.
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
5 */
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
6
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
7
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
8 #include <ngx_config.h>
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
9 #include <ngx_core.h>
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
10 #include <ngx_stream.h>
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
11
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
12
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
13 static char *ngx_stream_upstream(ngx_conf_t *cf, ngx_command_t *cmd,
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
14 void *dummy);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
15 static char *ngx_stream_upstream_server(ngx_conf_t *cf, ngx_command_t *cmd,
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
16 void *conf);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
17 static void *ngx_stream_upstream_create_main_conf(ngx_conf_t *cf);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
18 static char *ngx_stream_upstream_init_main_conf(ngx_conf_t *cf, void *conf);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
19
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
20
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
21 static ngx_command_t ngx_stream_upstream_commands[] = {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
22
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
23 { ngx_string("upstream"),
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
24 NGX_STREAM_MAIN_CONF|NGX_CONF_BLOCK|NGX_CONF_TAKE1,
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
25 ngx_stream_upstream,
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
26 0,
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
27 0,
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
28 NULL },
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
29
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
30 { ngx_string("server"),
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
31 NGX_STREAM_UPS_CONF|NGX_CONF_1MORE,
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
32 ngx_stream_upstream_server,
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
33 NGX_STREAM_SRV_CONF_OFFSET,
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
34 0,
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
35 NULL },
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
36
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
37 ngx_null_command
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
38 };
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
39
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
40
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
41 static ngx_stream_module_t ngx_stream_upstream_module_ctx = {
6606
2f41d383c9c7 Stream: added preconfiguration step.
Vladimir Homutov <vl@nginx.com>
parents: 6459
diff changeset
42 NULL, /* preconfiguration */
6174
68c106e6fa0a Stream: added postconfiguration method to stream modules.
Vladimir Homutov <vl@nginx.com>
parents: 6115
diff changeset
43 NULL, /* postconfiguration */
68c106e6fa0a Stream: added postconfiguration method to stream modules.
Vladimir Homutov <vl@nginx.com>
parents: 6115
diff changeset
44
6115
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
45 ngx_stream_upstream_create_main_conf, /* create main configuration */
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
46 ngx_stream_upstream_init_main_conf, /* init main configuration */
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
47
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
48 NULL, /* create server configuration */
6629
8ed51b02f655 Stream: style.
Vladimir Homutov <vl@nginx.com>
parents: 6606
diff changeset
49 NULL /* merge server configuration */
6115
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
50 };
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
51
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
52
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
53 ngx_module_t ngx_stream_upstream_module = {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
54 NGX_MODULE_V1,
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
55 &ngx_stream_upstream_module_ctx, /* module context */
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
56 ngx_stream_upstream_commands, /* module directives */
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
57 NGX_STREAM_MODULE, /* module type */
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
58 NULL, /* init master */
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
59 NULL, /* init module */
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
60 NULL, /* init process */
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
61 NULL, /* init thread */
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
62 NULL, /* exit thread */
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
63 NULL, /* exit process */
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
64 NULL, /* exit master */
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
65 NGX_MODULE_V1_PADDING
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
66 };
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
67
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
68
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
69 static char *
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
70 ngx_stream_upstream(ngx_conf_t *cf, ngx_command_t *cmd, void *dummy)
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
71 {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
72 char *rv;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
73 void *mconf;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
74 ngx_str_t *value;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
75 ngx_url_t u;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
76 ngx_uint_t m;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
77 ngx_conf_t pcf;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
78 ngx_stream_module_t *module;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
79 ngx_stream_conf_ctx_t *ctx, *stream_ctx;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
80 ngx_stream_upstream_srv_conf_t *uscf;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
81
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
82 ngx_memzero(&u, sizeof(ngx_url_t));
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
83
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
84 value = cf->args->elts;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
85 u.host = value[1];
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
86 u.no_resolve = 1;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
87 u.no_port = 1;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
88
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
89 uscf = ngx_stream_upstream_add(cf, &u, NGX_STREAM_UPSTREAM_CREATE
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
90 |NGX_STREAM_UPSTREAM_WEIGHT
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
91 |NGX_STREAM_UPSTREAM_MAX_FAILS
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
92 |NGX_STREAM_UPSTREAM_FAIL_TIMEOUT
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
93 |NGX_STREAM_UPSTREAM_DOWN
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
94 |NGX_STREAM_UPSTREAM_BACKUP);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
95 if (uscf == NULL) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
96 return NGX_CONF_ERROR;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
97 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
98
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
99
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
100 ctx = ngx_pcalloc(cf->pool, sizeof(ngx_stream_conf_ctx_t));
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
101 if (ctx == NULL) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
102 return NGX_CONF_ERROR;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
103 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
104
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
105 stream_ctx = cf->ctx;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
106 ctx->main_conf = stream_ctx->main_conf;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
107
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
108 /* the upstream{}'s srv_conf */
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
109
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
110 ctx->srv_conf = ngx_pcalloc(cf->pool,
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
111 sizeof(void *) * ngx_stream_max_module);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
112 if (ctx->srv_conf == NULL) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
113 return NGX_CONF_ERROR;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
114 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
115
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
116 ctx->srv_conf[ngx_stream_upstream_module.ctx_index] = uscf;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
117
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
118 uscf->srv_conf = ctx->srv_conf;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
119
6379
cf5e822cf470 Dynamic modules: changed ngx_modules to cycle->modules.
Maxim Dounin <mdounin@mdounin.ru>
parents: 6174
diff changeset
120 for (m = 0; cf->cycle->modules[m]; m++) {
cf5e822cf470 Dynamic modules: changed ngx_modules to cycle->modules.
Maxim Dounin <mdounin@mdounin.ru>
parents: 6174
diff changeset
121 if (cf->cycle->modules[m]->type != NGX_STREAM_MODULE) {
6115
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
122 continue;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
123 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
124
6379
cf5e822cf470 Dynamic modules: changed ngx_modules to cycle->modules.
Maxim Dounin <mdounin@mdounin.ru>
parents: 6174
diff changeset
125 module = cf->cycle->modules[m]->ctx;
6115
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
126
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
127 if (module->create_srv_conf) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
128 mconf = module->create_srv_conf(cf);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
129 if (mconf == NULL) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
130 return NGX_CONF_ERROR;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
131 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
132
6379
cf5e822cf470 Dynamic modules: changed ngx_modules to cycle->modules.
Maxim Dounin <mdounin@mdounin.ru>
parents: 6174
diff changeset
133 ctx->srv_conf[cf->cycle->modules[m]->ctx_index] = mconf;
6115
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
134 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
135 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
136
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
137 uscf->servers = ngx_array_create(cf->pool, 4,
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
138 sizeof(ngx_stream_upstream_server_t));
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
139 if (uscf->servers == NULL) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
140 return NGX_CONF_ERROR;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
141 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
142
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
143
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
144 /* parse inside upstream{} */
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
145
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
146 pcf = *cf;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
147 cf->ctx = ctx;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
148 cf->cmd_type = NGX_STREAM_UPS_CONF;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
149
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
150 rv = ngx_conf_parse(cf, NULL);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
151
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
152 *cf = pcf;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
153
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
154 if (rv != NGX_CONF_OK) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
155 return rv;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
156 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
157
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
158 if (uscf->servers->nelts == 0) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
159 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0,
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
160 "no servers are inside upstream");
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
161 return NGX_CONF_ERROR;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
162 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
163
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
164 return rv;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
165 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
166
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
167
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
168 static char *
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
169 ngx_stream_upstream_server(ngx_conf_t *cf, ngx_command_t *cmd, void *conf)
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
170 {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
171 ngx_stream_upstream_srv_conf_t *uscf = conf;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
172
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
173 time_t fail_timeout;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
174 ngx_str_t *value, s;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
175 ngx_url_t u;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
176 ngx_int_t weight, max_fails;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
177 ngx_uint_t i;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
178 ngx_stream_upstream_server_t *us;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
179
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
180 us = ngx_array_push(uscf->servers);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
181 if (us == NULL) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
182 return NGX_CONF_ERROR;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
183 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
184
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
185 ngx_memzero(us, sizeof(ngx_stream_upstream_server_t));
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
186
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
187 value = cf->args->elts;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
188
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
189 weight = 1;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
190 max_fails = 1;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
191 fail_timeout = 10;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
192
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
193 for (i = 2; i < cf->args->nelts; i++) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
194
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
195 if (ngx_strncmp(value[i].data, "weight=", 7) == 0) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
196
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
197 if (!(uscf->flags & NGX_STREAM_UPSTREAM_WEIGHT)) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
198 goto not_supported;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
199 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
200
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
201 weight = ngx_atoi(&value[i].data[7], value[i].len - 7);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
202
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
203 if (weight == NGX_ERROR || weight == 0) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
204 goto invalid;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
205 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
206
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
207 continue;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
208 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
209
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
210 if (ngx_strncmp(value[i].data, "max_fails=", 10) == 0) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
211
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
212 if (!(uscf->flags & NGX_STREAM_UPSTREAM_MAX_FAILS)) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
213 goto not_supported;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
214 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
215
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
216 max_fails = ngx_atoi(&value[i].data[10], value[i].len - 10);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
217
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
218 if (max_fails == NGX_ERROR) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
219 goto invalid;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
220 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
221
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
222 continue;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
223 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
224
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
225 if (ngx_strncmp(value[i].data, "fail_timeout=", 13) == 0) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
226
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
227 if (!(uscf->flags & NGX_STREAM_UPSTREAM_FAIL_TIMEOUT)) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
228 goto not_supported;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
229 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
230
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
231 s.len = value[i].len - 13;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
232 s.data = &value[i].data[13];
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
233
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
234 fail_timeout = ngx_parse_time(&s, 1);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
235
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
236 if (fail_timeout == (time_t) NGX_ERROR) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
237 goto invalid;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
238 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
239
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
240 continue;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
241 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
242
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
243 if (ngx_strcmp(value[i].data, "backup") == 0) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
244
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
245 if (!(uscf->flags & NGX_STREAM_UPSTREAM_BACKUP)) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
246 goto not_supported;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
247 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
248
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
249 us->backup = 1;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
250
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
251 continue;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
252 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
253
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
254 if (ngx_strcmp(value[i].data, "down") == 0) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
255
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
256 if (!(uscf->flags & NGX_STREAM_UPSTREAM_DOWN)) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
257 goto not_supported;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
258 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
259
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
260 us->down = 1;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
261
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
262 continue;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
263 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
264
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
265 goto invalid;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
266 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
267
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
268 ngx_memzero(&u, sizeof(ngx_url_t));
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
269
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
270 u.url = value[1];
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
271
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
272 if (ngx_parse_url(cf->pool, &u) != NGX_OK) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
273 if (u.err) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
274 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0,
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
275 "%s in upstream \"%V\"", u.err, &u.url);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
276 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
277
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
278 return NGX_CONF_ERROR;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
279 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
280
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
281 if (u.no_port) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
282 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0,
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
283 "no port in upstream \"%V\"", &u.url);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
284 return NGX_CONF_ERROR;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
285 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
286
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
287 us->name = u.url;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
288 us->addrs = u.addrs;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
289 us->naddrs = u.naddrs;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
290 us->weight = weight;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
291 us->max_fails = max_fails;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
292 us->fail_timeout = fail_timeout;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
293
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
294 return NGX_CONF_OK;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
295
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
296 invalid:
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
297
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
298 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0,
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
299 "invalid parameter \"%V\"", &value[i]);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
300
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
301 return NGX_CONF_ERROR;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
302
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
303 not_supported:
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
304
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
305 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0,
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
306 "balancing method does not support parameter \"%V\"",
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
307 &value[i]);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
308
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
309 return NGX_CONF_ERROR;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
310 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
311
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
312
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
313 ngx_stream_upstream_srv_conf_t *
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
314 ngx_stream_upstream_add(ngx_conf_t *cf, ngx_url_t *u, ngx_uint_t flags)
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
315 {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
316 ngx_uint_t i;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
317 ngx_stream_upstream_server_t *us;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
318 ngx_stream_upstream_srv_conf_t *uscf, **uscfp;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
319 ngx_stream_upstream_main_conf_t *umcf;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
320
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
321 if (!(flags & NGX_STREAM_UPSTREAM_CREATE)) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
322
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
323 if (ngx_parse_url(cf->pool, u) != NGX_OK) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
324 if (u->err) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
325 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0,
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
326 "%s in upstream \"%V\"", u->err, &u->url);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
327 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
328
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
329 return NULL;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
330 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
331 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
332
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
333 umcf = ngx_stream_conf_get_module_main_conf(cf, ngx_stream_upstream_module);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
334
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
335 uscfp = umcf->upstreams.elts;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
336
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
337 for (i = 0; i < umcf->upstreams.nelts; i++) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
338
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
339 if (uscfp[i]->host.len != u->host.len
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
340 || ngx_strncasecmp(uscfp[i]->host.data, u->host.data, u->host.len)
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
341 != 0)
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
342 {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
343 continue;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
344 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
345
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
346 if ((flags & NGX_STREAM_UPSTREAM_CREATE)
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
347 && (uscfp[i]->flags & NGX_STREAM_UPSTREAM_CREATE))
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
348 {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
349 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0,
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
350 "duplicate upstream \"%V\"", &u->host);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
351 return NULL;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
352 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
353
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
354 if ((uscfp[i]->flags & NGX_STREAM_UPSTREAM_CREATE) && !u->no_port) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
355 ngx_conf_log_error(NGX_LOG_WARN, cf, 0,
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
356 "upstream \"%V\" may not have port %d",
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
357 &u->host, u->port);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
358 return NULL;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
359 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
360
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
361 if ((flags & NGX_STREAM_UPSTREAM_CREATE) && !uscfp[i]->no_port) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
362 ngx_log_error(NGX_LOG_WARN, cf->log, 0,
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
363 "upstream \"%V\" may not have port %d in %s:%ui",
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
364 &u->host, uscfp[i]->port,
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
365 uscfp[i]->file_name, uscfp[i]->line);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
366 return NULL;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
367 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
368
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
369 if (uscfp[i]->port != u->port) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
370 continue;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
371 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
372
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
373 if (flags & NGX_STREAM_UPSTREAM_CREATE) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
374 uscfp[i]->flags = flags;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
375 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
376
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
377 return uscfp[i];
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
378 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
379
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
380 uscf = ngx_pcalloc(cf->pool, sizeof(ngx_stream_upstream_srv_conf_t));
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
381 if (uscf == NULL) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
382 return NULL;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
383 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
384
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
385 uscf->flags = flags;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
386 uscf->host = u->host;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
387 uscf->file_name = cf->conf_file->file.name.data;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
388 uscf->line = cf->conf_file->line;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
389 uscf->port = u->port;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
390 uscf->no_port = u->no_port;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
391
6459
78fc2dce69e7 Stream: detect port absence in proxy_pass with IP literal.
Roman Arutyunyan <arut@nginx.com>
parents: 6379
diff changeset
392 if (u->naddrs == 1 && (u->port || u->family == AF_UNIX)) {
6115
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
393 uscf->servers = ngx_array_create(cf->pool, 1,
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
394 sizeof(ngx_stream_upstream_server_t));
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
395 if (uscf->servers == NULL) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
396 return NULL;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
397 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
398
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
399 us = ngx_array_push(uscf->servers);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
400 if (us == NULL) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
401 return NULL;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
402 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
403
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
404 ngx_memzero(us, sizeof(ngx_stream_upstream_server_t));
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
405
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
406 us->addrs = u->addrs;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
407 us->naddrs = 1;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
408 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
409
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
410 uscfp = ngx_array_push(&umcf->upstreams);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
411 if (uscfp == NULL) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
412 return NULL;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
413 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
414
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
415 *uscfp = uscf;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
416
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
417 return uscf;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
418 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
419
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
420
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
421 static void *
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
422 ngx_stream_upstream_create_main_conf(ngx_conf_t *cf)
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
423 {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
424 ngx_stream_upstream_main_conf_t *umcf;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
425
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
426 umcf = ngx_pcalloc(cf->pool, sizeof(ngx_stream_upstream_main_conf_t));
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
427 if (umcf == NULL) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
428 return NULL;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
429 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
430
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
431 if (ngx_array_init(&umcf->upstreams, cf->pool, 4,
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
432 sizeof(ngx_stream_upstream_srv_conf_t *))
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
433 != NGX_OK)
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
434 {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
435 return NULL;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
436 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
437
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
438 return umcf;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
439 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
440
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
441
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
442 static char *
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
443 ngx_stream_upstream_init_main_conf(ngx_conf_t *cf, void *conf)
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
444 {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
445 ngx_stream_upstream_main_conf_t *umcf = conf;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
446
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
447 ngx_uint_t i;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
448 ngx_stream_upstream_init_pt init;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
449 ngx_stream_upstream_srv_conf_t **uscfp;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
450
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
451 uscfp = umcf->upstreams.elts;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
452
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
453 for (i = 0; i < umcf->upstreams.nelts; i++) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
454
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
455 init = uscfp[i]->peer.init_upstream
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
456 ? uscfp[i]->peer.init_upstream
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
457 : ngx_stream_upstream_init_round_robin;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
458
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
459 if (init(cf, uscfp[i]) != NGX_OK) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
460 return NGX_CONF_ERROR;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
461 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
462 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
463
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
464 return NGX_CONF_OK;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
465 }