Mercurial > hg > nginx-quic
annotate src/stream/ngx_stream_proxy_module.c @ 6443:fc72784b1f52
Threads: writing via threads pools in event pipe.
The "aio_write" directive is introduced, which enables use of aio
for writing. Currently it is meaningful only with "aio threads".
Note that aio operations can be done by both event pipe and output
chain, so proper mapping between r->aio and p->aio is provided when
calling ngx_event_pipe() and in output filter.
In collaboration with Valentin Bartenev.
author | Maxim Dounin <mdounin@mdounin.ru> |
---|---|
date | Fri, 18 Mar 2016 06:44:49 +0300 |
parents | 8f038068f4bc |
children | a01e315b3a78 |
rev | line source |
---|---|
6115 | 1 |
2 /* | |
3 * Copyright (C) Roman Arutyunyan | |
4 * Copyright (C) Nginx, Inc. | |
5 */ | |
6 | |
7 | |
8 #include <ngx_config.h> | |
9 #include <ngx_core.h> | |
10 #include <ngx_stream.h> | |
11 | |
12 | |
13 typedef struct { | |
14 ngx_msec_t connect_timeout; | |
15 ngx_msec_t timeout; | |
16 ngx_msec_t next_upstream_timeout; | |
6215
8ee6a08ea3eb
Stream: added proxy_buffer_size to set the size of data buffers.
Roman Arutyunyan <arut@nginx.com>
parents:
6208
diff
changeset
|
17 size_t buffer_size; |
6208
7a14a0d754ad
Stream: renamed rate limiting directives.
Roman Arutyunyan <arut@nginx.com>
parents:
6204
diff
changeset
|
18 size_t upload_rate; |
7a14a0d754ad
Stream: renamed rate limiting directives.
Roman Arutyunyan <arut@nginx.com>
parents:
6204
diff
changeset
|
19 size_t download_rate; |
6436 | 20 ngx_uint_t responses; |
6115 | 21 ngx_uint_t next_upstream_tries; |
22 ngx_flag_t next_upstream; | |
6184
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
23 ngx_flag_t proxy_protocol; |
6183
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
24 ngx_addr_t *local; |
6115 | 25 |
26 #if (NGX_STREAM_SSL) | |
27 ngx_flag_t ssl_enable; | |
28 ngx_flag_t ssl_session_reuse; | |
29 ngx_uint_t ssl_protocols; | |
30 ngx_str_t ssl_ciphers; | |
31 ngx_str_t ssl_name; | |
32 ngx_flag_t ssl_server_name; | |
33 | |
34 ngx_flag_t ssl_verify; | |
35 ngx_uint_t ssl_verify_depth; | |
36 ngx_str_t ssl_trusted_certificate; | |
37 ngx_str_t ssl_crl; | |
38 ngx_str_t ssl_certificate; | |
39 ngx_str_t ssl_certificate_key; | |
40 ngx_array_t *ssl_passwords; | |
41 | |
42 ngx_ssl_t *ssl; | |
43 #endif | |
44 | |
45 ngx_stream_upstream_srv_conf_t *upstream; | |
46 } ngx_stream_proxy_srv_conf_t; | |
47 | |
48 | |
49 static void ngx_stream_proxy_handler(ngx_stream_session_t *s); | |
50 static void ngx_stream_proxy_connect(ngx_stream_session_t *s); | |
51 static void ngx_stream_proxy_init_upstream(ngx_stream_session_t *s); | |
52 static void ngx_stream_proxy_upstream_handler(ngx_event_t *ev); | |
53 static void ngx_stream_proxy_downstream_handler(ngx_event_t *ev); | |
6200
abee77018d3a
Stream: common handler for upstream and downstream.
Roman Arutyunyan <arut@nginx.com>
parents:
6184
diff
changeset
|
54 static void ngx_stream_proxy_process_connection(ngx_event_t *ev, |
abee77018d3a
Stream: common handler for upstream and downstream.
Roman Arutyunyan <arut@nginx.com>
parents:
6184
diff
changeset
|
55 ngx_uint_t from_upstream); |
6115 | 56 static void ngx_stream_proxy_connect_handler(ngx_event_t *ev); |
57 static ngx_int_t ngx_stream_proxy_test_connect(ngx_connection_t *c); | |
6435
d1c791479bbb
Stream: post first read events from client and upstream.
Roman Arutyunyan <arut@nginx.com>
parents:
6393
diff
changeset
|
58 static void ngx_stream_proxy_process(ngx_stream_session_t *s, |
6115 | 59 ngx_uint_t from_upstream, ngx_uint_t do_write); |
60 static void ngx_stream_proxy_next_upstream(ngx_stream_session_t *s); | |
61 static void ngx_stream_proxy_finalize(ngx_stream_session_t *s, ngx_int_t rc); | |
62 static u_char *ngx_stream_proxy_log_error(ngx_log_t *log, u_char *buf, | |
63 size_t len); | |
64 | |
65 static void *ngx_stream_proxy_create_srv_conf(ngx_conf_t *cf); | |
66 static char *ngx_stream_proxy_merge_srv_conf(ngx_conf_t *cf, void *parent, | |
67 void *child); | |
68 static char *ngx_stream_proxy_pass(ngx_conf_t *cf, ngx_command_t *cmd, | |
69 void *conf); | |
6183
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
70 static char *ngx_stream_proxy_bind(ngx_conf_t *cf, ngx_command_t *cmd, |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
71 void *conf); |
6184
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
72 static ngx_int_t ngx_stream_proxy_send_proxy_protocol(ngx_stream_session_t *s); |
6115 | 73 |
74 #if (NGX_STREAM_SSL) | |
75 | |
76 static char *ngx_stream_proxy_ssl_password_file(ngx_conf_t *cf, | |
77 ngx_command_t *cmd, void *conf); | |
78 static void ngx_stream_proxy_ssl_init_connection(ngx_stream_session_t *s); | |
79 static void ngx_stream_proxy_ssl_handshake(ngx_connection_t *pc); | |
80 static ngx_int_t ngx_stream_proxy_ssl_name(ngx_stream_session_t *s); | |
81 static ngx_int_t ngx_stream_proxy_set_ssl(ngx_conf_t *cf, | |
82 ngx_stream_proxy_srv_conf_t *pscf); | |
83 | |
84 | |
85 static ngx_conf_bitmask_t ngx_stream_proxy_ssl_protocols[] = { | |
86 { ngx_string("SSLv2"), NGX_SSL_SSLv2 }, | |
87 { ngx_string("SSLv3"), NGX_SSL_SSLv3 }, | |
88 { ngx_string("TLSv1"), NGX_SSL_TLSv1 }, | |
89 { ngx_string("TLSv1.1"), NGX_SSL_TLSv1_1 }, | |
90 { ngx_string("TLSv1.2"), NGX_SSL_TLSv1_2 }, | |
91 { ngx_null_string, 0 } | |
92 }; | |
93 | |
94 #endif | |
95 | |
96 | |
6217
b544f8e0d921
Stream: deprecated proxy_downstream_buffer, proxy_upstream_buffer.
Roman Arutyunyan <arut@nginx.com>
parents:
6216
diff
changeset
|
97 static ngx_conf_deprecated_t ngx_conf_deprecated_proxy_downstream_buffer = { |
b544f8e0d921
Stream: deprecated proxy_downstream_buffer, proxy_upstream_buffer.
Roman Arutyunyan <arut@nginx.com>
parents:
6216
diff
changeset
|
98 ngx_conf_deprecated, "proxy_downstream_buffer", "proxy_buffer_size" |
b544f8e0d921
Stream: deprecated proxy_downstream_buffer, proxy_upstream_buffer.
Roman Arutyunyan <arut@nginx.com>
parents:
6216
diff
changeset
|
99 }; |
b544f8e0d921
Stream: deprecated proxy_downstream_buffer, proxy_upstream_buffer.
Roman Arutyunyan <arut@nginx.com>
parents:
6216
diff
changeset
|
100 |
b544f8e0d921
Stream: deprecated proxy_downstream_buffer, proxy_upstream_buffer.
Roman Arutyunyan <arut@nginx.com>
parents:
6216
diff
changeset
|
101 static ngx_conf_deprecated_t ngx_conf_deprecated_proxy_upstream_buffer = { |
b544f8e0d921
Stream: deprecated proxy_downstream_buffer, proxy_upstream_buffer.
Roman Arutyunyan <arut@nginx.com>
parents:
6216
diff
changeset
|
102 ngx_conf_deprecated, "proxy_upstream_buffer", "proxy_buffer_size" |
b544f8e0d921
Stream: deprecated proxy_downstream_buffer, proxy_upstream_buffer.
Roman Arutyunyan <arut@nginx.com>
parents:
6216
diff
changeset
|
103 }; |
b544f8e0d921
Stream: deprecated proxy_downstream_buffer, proxy_upstream_buffer.
Roman Arutyunyan <arut@nginx.com>
parents:
6216
diff
changeset
|
104 |
b544f8e0d921
Stream: deprecated proxy_downstream_buffer, proxy_upstream_buffer.
Roman Arutyunyan <arut@nginx.com>
parents:
6216
diff
changeset
|
105 |
6115 | 106 static ngx_command_t ngx_stream_proxy_commands[] = { |
107 | |
108 { ngx_string("proxy_pass"), | |
109 NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1, | |
110 ngx_stream_proxy_pass, | |
111 NGX_STREAM_SRV_CONF_OFFSET, | |
112 0, | |
113 NULL }, | |
114 | |
6183
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
115 { ngx_string("proxy_bind"), |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
116 NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1, |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
117 ngx_stream_proxy_bind, |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
118 NGX_STREAM_SRV_CONF_OFFSET, |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
119 0, |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
120 NULL }, |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
121 |
6115 | 122 { ngx_string("proxy_connect_timeout"), |
123 NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1, | |
124 ngx_conf_set_msec_slot, | |
125 NGX_STREAM_SRV_CONF_OFFSET, | |
126 offsetof(ngx_stream_proxy_srv_conf_t, connect_timeout), | |
127 NULL }, | |
128 | |
129 { ngx_string("proxy_timeout"), | |
130 NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1, | |
131 ngx_conf_set_msec_slot, | |
132 NGX_STREAM_SRV_CONF_OFFSET, | |
133 offsetof(ngx_stream_proxy_srv_conf_t, timeout), | |
134 NULL }, | |
135 | |
6215
8ee6a08ea3eb
Stream: added proxy_buffer_size to set the size of data buffers.
Roman Arutyunyan <arut@nginx.com>
parents:
6208
diff
changeset
|
136 { ngx_string("proxy_buffer_size"), |
6115 | 137 NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1, |
138 ngx_conf_set_size_slot, | |
139 NGX_STREAM_SRV_CONF_OFFSET, | |
6215
8ee6a08ea3eb
Stream: added proxy_buffer_size to set the size of data buffers.
Roman Arutyunyan <arut@nginx.com>
parents:
6208
diff
changeset
|
140 offsetof(ngx_stream_proxy_srv_conf_t, buffer_size), |
6115 | 141 NULL }, |
142 | |
6217
b544f8e0d921
Stream: deprecated proxy_downstream_buffer, proxy_upstream_buffer.
Roman Arutyunyan <arut@nginx.com>
parents:
6216
diff
changeset
|
143 { ngx_string("proxy_downstream_buffer"), |
b544f8e0d921
Stream: deprecated proxy_downstream_buffer, proxy_upstream_buffer.
Roman Arutyunyan <arut@nginx.com>
parents:
6216
diff
changeset
|
144 NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1, |
b544f8e0d921
Stream: deprecated proxy_downstream_buffer, proxy_upstream_buffer.
Roman Arutyunyan <arut@nginx.com>
parents:
6216
diff
changeset
|
145 ngx_conf_set_size_slot, |
b544f8e0d921
Stream: deprecated proxy_downstream_buffer, proxy_upstream_buffer.
Roman Arutyunyan <arut@nginx.com>
parents:
6216
diff
changeset
|
146 NGX_STREAM_SRV_CONF_OFFSET, |
b544f8e0d921
Stream: deprecated proxy_downstream_buffer, proxy_upstream_buffer.
Roman Arutyunyan <arut@nginx.com>
parents:
6216
diff
changeset
|
147 offsetof(ngx_stream_proxy_srv_conf_t, buffer_size), |
b544f8e0d921
Stream: deprecated proxy_downstream_buffer, proxy_upstream_buffer.
Roman Arutyunyan <arut@nginx.com>
parents:
6216
diff
changeset
|
148 &ngx_conf_deprecated_proxy_downstream_buffer }, |
b544f8e0d921
Stream: deprecated proxy_downstream_buffer, proxy_upstream_buffer.
Roman Arutyunyan <arut@nginx.com>
parents:
6216
diff
changeset
|
149 |
b544f8e0d921
Stream: deprecated proxy_downstream_buffer, proxy_upstream_buffer.
Roman Arutyunyan <arut@nginx.com>
parents:
6216
diff
changeset
|
150 { ngx_string("proxy_upstream_buffer"), |
b544f8e0d921
Stream: deprecated proxy_downstream_buffer, proxy_upstream_buffer.
Roman Arutyunyan <arut@nginx.com>
parents:
6216
diff
changeset
|
151 NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1, |
b544f8e0d921
Stream: deprecated proxy_downstream_buffer, proxy_upstream_buffer.
Roman Arutyunyan <arut@nginx.com>
parents:
6216
diff
changeset
|
152 ngx_conf_set_size_slot, |
b544f8e0d921
Stream: deprecated proxy_downstream_buffer, proxy_upstream_buffer.
Roman Arutyunyan <arut@nginx.com>
parents:
6216
diff
changeset
|
153 NGX_STREAM_SRV_CONF_OFFSET, |
b544f8e0d921
Stream: deprecated proxy_downstream_buffer, proxy_upstream_buffer.
Roman Arutyunyan <arut@nginx.com>
parents:
6216
diff
changeset
|
154 offsetof(ngx_stream_proxy_srv_conf_t, buffer_size), |
b544f8e0d921
Stream: deprecated proxy_downstream_buffer, proxy_upstream_buffer.
Roman Arutyunyan <arut@nginx.com>
parents:
6216
diff
changeset
|
155 &ngx_conf_deprecated_proxy_upstream_buffer }, |
b544f8e0d921
Stream: deprecated proxy_downstream_buffer, proxy_upstream_buffer.
Roman Arutyunyan <arut@nginx.com>
parents:
6216
diff
changeset
|
156 |
6208
7a14a0d754ad
Stream: renamed rate limiting directives.
Roman Arutyunyan <arut@nginx.com>
parents:
6204
diff
changeset
|
157 { ngx_string("proxy_upload_rate"), |
6201
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
158 NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1, |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
159 ngx_conf_set_size_slot, |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
160 NGX_STREAM_SRV_CONF_OFFSET, |
6208
7a14a0d754ad
Stream: renamed rate limiting directives.
Roman Arutyunyan <arut@nginx.com>
parents:
6204
diff
changeset
|
161 offsetof(ngx_stream_proxy_srv_conf_t, upload_rate), |
6201
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
162 NULL }, |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
163 |
6208
7a14a0d754ad
Stream: renamed rate limiting directives.
Roman Arutyunyan <arut@nginx.com>
parents:
6204
diff
changeset
|
164 { ngx_string("proxy_download_rate"), |
6201
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
165 NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1, |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
166 ngx_conf_set_size_slot, |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
167 NGX_STREAM_SRV_CONF_OFFSET, |
6208
7a14a0d754ad
Stream: renamed rate limiting directives.
Roman Arutyunyan <arut@nginx.com>
parents:
6204
diff
changeset
|
168 offsetof(ngx_stream_proxy_srv_conf_t, download_rate), |
6201
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
169 NULL }, |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
170 |
6436 | 171 { ngx_string("proxy_responses"), |
172 NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1, | |
173 ngx_conf_set_num_slot, | |
174 NGX_STREAM_SRV_CONF_OFFSET, | |
175 offsetof(ngx_stream_proxy_srv_conf_t, responses), | |
176 NULL }, | |
177 | |
6115 | 178 { ngx_string("proxy_next_upstream"), |
179 NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_FLAG, | |
180 ngx_conf_set_flag_slot, | |
181 NGX_STREAM_SRV_CONF_OFFSET, | |
182 offsetof(ngx_stream_proxy_srv_conf_t, next_upstream), | |
183 NULL }, | |
184 | |
185 { ngx_string("proxy_next_upstream_tries"), | |
186 NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1, | |
187 ngx_conf_set_num_slot, | |
188 NGX_STREAM_SRV_CONF_OFFSET, | |
189 offsetof(ngx_stream_proxy_srv_conf_t, next_upstream_tries), | |
190 NULL }, | |
191 | |
192 { ngx_string("proxy_next_upstream_timeout"), | |
193 NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1, | |
194 ngx_conf_set_msec_slot, | |
195 NGX_STREAM_SRV_CONF_OFFSET, | |
196 offsetof(ngx_stream_proxy_srv_conf_t, next_upstream_timeout), | |
197 NULL }, | |
198 | |
6184
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
199 { ngx_string("proxy_protocol"), |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
200 NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_FLAG, |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
201 ngx_conf_set_flag_slot, |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
202 NGX_STREAM_SRV_CONF_OFFSET, |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
203 offsetof(ngx_stream_proxy_srv_conf_t, proxy_protocol), |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
204 NULL }, |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
205 |
6115 | 206 #if (NGX_STREAM_SSL) |
207 | |
208 { ngx_string("proxy_ssl"), | |
209 NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_FLAG, | |
210 ngx_conf_set_flag_slot, | |
211 NGX_STREAM_SRV_CONF_OFFSET, | |
212 offsetof(ngx_stream_proxy_srv_conf_t, ssl_enable), | |
213 NULL }, | |
214 | |
215 { ngx_string("proxy_ssl_session_reuse"), | |
216 NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_FLAG, | |
217 ngx_conf_set_flag_slot, | |
218 NGX_STREAM_SRV_CONF_OFFSET, | |
219 offsetof(ngx_stream_proxy_srv_conf_t, ssl_session_reuse), | |
220 NULL }, | |
221 | |
222 { ngx_string("proxy_ssl_protocols"), | |
223 NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_1MORE, | |
224 ngx_conf_set_bitmask_slot, | |
225 NGX_STREAM_SRV_CONF_OFFSET, | |
226 offsetof(ngx_stream_proxy_srv_conf_t, ssl_protocols), | |
227 &ngx_stream_proxy_ssl_protocols }, | |
228 | |
229 { ngx_string("proxy_ssl_ciphers"), | |
230 NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1, | |
231 ngx_conf_set_str_slot, | |
232 NGX_STREAM_SRV_CONF_OFFSET, | |
233 offsetof(ngx_stream_proxy_srv_conf_t, ssl_ciphers), | |
234 NULL }, | |
235 | |
236 { ngx_string("proxy_ssl_name"), | |
237 NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1, | |
238 ngx_conf_set_str_slot, | |
239 NGX_STREAM_SRV_CONF_OFFSET, | |
240 offsetof(ngx_stream_proxy_srv_conf_t, ssl_name), | |
241 NULL }, | |
242 | |
243 { ngx_string("proxy_ssl_server_name"), | |
244 NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_FLAG, | |
245 ngx_conf_set_flag_slot, | |
246 NGX_STREAM_SRV_CONF_OFFSET, | |
247 offsetof(ngx_stream_proxy_srv_conf_t, ssl_server_name), | |
248 NULL }, | |
249 | |
250 { ngx_string("proxy_ssl_verify"), | |
251 NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_FLAG, | |
252 ngx_conf_set_flag_slot, | |
253 NGX_STREAM_SRV_CONF_OFFSET, | |
254 offsetof(ngx_stream_proxy_srv_conf_t, ssl_verify), | |
255 NULL }, | |
256 | |
257 { ngx_string("proxy_ssl_verify_depth"), | |
258 NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1, | |
259 ngx_conf_set_num_slot, | |
260 NGX_STREAM_SRV_CONF_OFFSET, | |
261 offsetof(ngx_stream_proxy_srv_conf_t, ssl_verify_depth), | |
262 NULL }, | |
263 | |
264 { ngx_string("proxy_ssl_trusted_certificate"), | |
265 NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1, | |
266 ngx_conf_set_str_slot, | |
267 NGX_STREAM_SRV_CONF_OFFSET, | |
268 offsetof(ngx_stream_proxy_srv_conf_t, ssl_trusted_certificate), | |
269 NULL }, | |
270 | |
271 { ngx_string("proxy_ssl_crl"), | |
272 NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1, | |
273 ngx_conf_set_str_slot, | |
274 NGX_STREAM_SRV_CONF_OFFSET, | |
275 offsetof(ngx_stream_proxy_srv_conf_t, ssl_crl), | |
276 NULL }, | |
277 | |
278 { ngx_string("proxy_ssl_certificate"), | |
279 NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1, | |
280 ngx_conf_set_str_slot, | |
281 NGX_STREAM_SRV_CONF_OFFSET, | |
282 offsetof(ngx_stream_proxy_srv_conf_t, ssl_certificate), | |
283 NULL }, | |
284 | |
285 { ngx_string("proxy_ssl_certificate_key"), | |
286 NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1, | |
287 ngx_conf_set_str_slot, | |
288 NGX_STREAM_SRV_CONF_OFFSET, | |
289 offsetof(ngx_stream_proxy_srv_conf_t, ssl_certificate_key), | |
290 NULL }, | |
291 | |
292 { ngx_string("proxy_ssl_password_file"), | |
293 NGX_STREAM_MAIN_CONF|NGX_STREAM_SRV_CONF|NGX_CONF_TAKE1, | |
294 ngx_stream_proxy_ssl_password_file, | |
295 NGX_STREAM_SRV_CONF_OFFSET, | |
296 0, | |
297 NULL }, | |
298 | |
299 #endif | |
300 | |
301 ngx_null_command | |
302 }; | |
303 | |
304 | |
305 static ngx_stream_module_t ngx_stream_proxy_module_ctx = { | |
6174
68c106e6fa0a
Stream: added postconfiguration method to stream modules.
Vladimir Homutov <vl@nginx.com>
parents:
6157
diff
changeset
|
306 NULL, /* postconfiguration */ |
68c106e6fa0a
Stream: added postconfiguration method to stream modules.
Vladimir Homutov <vl@nginx.com>
parents:
6157
diff
changeset
|
307 |
6115 | 308 NULL, /* create main configuration */ |
309 NULL, /* init main configuration */ | |
310 | |
311 ngx_stream_proxy_create_srv_conf, /* create server configuration */ | |
312 ngx_stream_proxy_merge_srv_conf /* merge server configuration */ | |
313 }; | |
314 | |
315 | |
316 ngx_module_t ngx_stream_proxy_module = { | |
317 NGX_MODULE_V1, | |
318 &ngx_stream_proxy_module_ctx, /* module context */ | |
319 ngx_stream_proxy_commands, /* module directives */ | |
320 NGX_STREAM_MODULE, /* module type */ | |
321 NULL, /* init master */ | |
322 NULL, /* init module */ | |
323 NULL, /* init process */ | |
324 NULL, /* init thread */ | |
325 NULL, /* exit thread */ | |
326 NULL, /* exit process */ | |
327 NULL, /* exit master */ | |
328 NGX_MODULE_V1_PADDING | |
329 }; | |
330 | |
331 | |
332 static void | |
333 ngx_stream_proxy_handler(ngx_stream_session_t *s) | |
334 { | |
335 u_char *p; | |
336 ngx_connection_t *c; | |
337 ngx_stream_upstream_t *u; | |
338 ngx_stream_proxy_srv_conf_t *pscf; | |
339 ngx_stream_upstream_srv_conf_t *uscf; | |
340 | |
341 c = s->connection; | |
342 | |
343 pscf = ngx_stream_get_module_srv_conf(s, ngx_stream_proxy_module); | |
344 | |
345 ngx_log_debug0(NGX_LOG_DEBUG_STREAM, c->log, 0, | |
346 "proxy connection handler"); | |
347 | |
348 u = ngx_pcalloc(c->pool, sizeof(ngx_stream_upstream_t)); | |
349 if (u == NULL) { | |
350 ngx_stream_proxy_finalize(s, NGX_ERROR); | |
351 return; | |
352 } | |
353 | |
354 s->upstream = u; | |
355 | |
356 s->log_handler = ngx_stream_proxy_log_error; | |
357 | |
358 u->peer.log = c->log; | |
359 u->peer.log_error = NGX_ERROR_ERR; | |
360 | |
6183
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
361 u->peer.local = pscf->local; |
6436 | 362 u->peer.type = c->type; |
6183
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
363 |
6115 | 364 uscf = pscf->upstream; |
365 | |
366 if (uscf->peer.init(s, uscf) != NGX_OK) { | |
367 ngx_stream_proxy_finalize(s, NGX_ERROR); | |
368 return; | |
369 } | |
370 | |
371 u->peer.start_time = ngx_current_msec; | |
372 | |
373 if (pscf->next_upstream_tries | |
374 && u->peer.tries > pscf->next_upstream_tries) | |
375 { | |
376 u->peer.tries = pscf->next_upstream_tries; | |
377 } | |
378 | |
6184
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
379 u->proxy_protocol = pscf->proxy_protocol; |
6201
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
380 u->start_sec = ngx_time(); |
6184
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
381 |
6436 | 382 c->write->handler = ngx_stream_proxy_downstream_handler; |
383 c->read->handler = ngx_stream_proxy_downstream_handler; | |
384 | |
385 if (c->type == SOCK_DGRAM) { | |
386 ngx_stream_proxy_connect(s); | |
387 return; | |
388 } | |
389 | |
6215
8ee6a08ea3eb
Stream: added proxy_buffer_size to set the size of data buffers.
Roman Arutyunyan <arut@nginx.com>
parents:
6208
diff
changeset
|
390 p = ngx_pnalloc(c->pool, pscf->buffer_size); |
6115 | 391 if (p == NULL) { |
392 ngx_stream_proxy_finalize(s, NGX_ERROR); | |
393 return; | |
394 } | |
395 | |
396 u->downstream_buf.start = p; | |
6215
8ee6a08ea3eb
Stream: added proxy_buffer_size to set the size of data buffers.
Roman Arutyunyan <arut@nginx.com>
parents:
6208
diff
changeset
|
397 u->downstream_buf.end = p + pscf->buffer_size; |
6115 | 398 u->downstream_buf.pos = p; |
399 u->downstream_buf.last = p; | |
400 | |
6184
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
401 if (u->proxy_protocol |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
402 #if (NGX_STREAM_SSL) |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
403 && pscf->ssl == NULL |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
404 #endif |
6216 | 405 && pscf->buffer_size >= NGX_PROXY_PROTOCOL_MAX_HEADER) |
6184
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
406 { |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
407 /* optimization for a typical case */ |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
408 |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
409 ngx_log_debug0(NGX_LOG_DEBUG_STREAM, c->log, 0, |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
410 "stream proxy send PROXY protocol header"); |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
411 |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
412 p = ngx_proxy_protocol_write(c, u->downstream_buf.last, |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
413 u->downstream_buf.end); |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
414 if (p == NULL) { |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
415 ngx_stream_proxy_finalize(s, NGX_ERROR); |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
416 return; |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
417 } |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
418 |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
419 u->downstream_buf.last = p; |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
420 u->proxy_protocol = 0; |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
421 } |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
422 |
6435
d1c791479bbb
Stream: post first read events from client and upstream.
Roman Arutyunyan <arut@nginx.com>
parents:
6393
diff
changeset
|
423 if (c->read->ready) { |
d1c791479bbb
Stream: post first read events from client and upstream.
Roman Arutyunyan <arut@nginx.com>
parents:
6393
diff
changeset
|
424 ngx_post_event(c->read, &ngx_posted_events); |
6115 | 425 } |
426 | |
427 ngx_stream_proxy_connect(s); | |
428 } | |
429 | |
430 | |
431 static void | |
432 ngx_stream_proxy_connect(ngx_stream_session_t *s) | |
433 { | |
434 ngx_int_t rc; | |
435 ngx_connection_t *c, *pc; | |
436 ngx_stream_upstream_t *u; | |
437 ngx_stream_proxy_srv_conf_t *pscf; | |
438 | |
439 c = s->connection; | |
440 | |
441 c->log->action = "connecting to upstream"; | |
442 | |
443 u = s->upstream; | |
444 | |
445 rc = ngx_event_connect_peer(&u->peer); | |
446 | |
447 ngx_log_debug1(NGX_LOG_DEBUG_STREAM, c->log, 0, "proxy connect: %i", rc); | |
448 | |
449 if (rc == NGX_ERROR) { | |
450 ngx_stream_proxy_finalize(s, NGX_ERROR); | |
451 return; | |
452 } | |
453 | |
454 if (rc == NGX_BUSY) { | |
455 ngx_log_error(NGX_LOG_ERR, c->log, 0, "no live upstreams"); | |
456 ngx_stream_proxy_finalize(s, NGX_DECLINED); | |
457 return; | |
458 } | |
459 | |
460 if (rc == NGX_DECLINED) { | |
461 ngx_stream_proxy_next_upstream(s); | |
462 return; | |
463 } | |
464 | |
465 /* rc == NGX_OK || rc == NGX_AGAIN || rc == NGX_DONE */ | |
466 | |
467 pc = u->peer.connection; | |
468 | |
469 pc->data = s; | |
470 pc->log = c->log; | |
471 pc->pool = c->pool; | |
472 pc->read->log = c->log; | |
473 pc->write->log = c->log; | |
474 | |
475 if (rc != NGX_AGAIN) { | |
476 ngx_stream_proxy_init_upstream(s); | |
477 return; | |
478 } | |
479 | |
480 pc->read->handler = ngx_stream_proxy_connect_handler; | |
481 pc->write->handler = ngx_stream_proxy_connect_handler; | |
482 | |
6393
70e6e1f12dee
Stream: initialize variable right before using it.
Roman Arutyunyan <arut@nginx.com>
parents:
6392
diff
changeset
|
483 pscf = ngx_stream_get_module_srv_conf(s, ngx_stream_proxy_module); |
70e6e1f12dee
Stream: initialize variable right before using it.
Roman Arutyunyan <arut@nginx.com>
parents:
6392
diff
changeset
|
484 |
6115 | 485 ngx_add_timer(pc->write, pscf->connect_timeout); |
486 } | |
487 | |
488 | |
489 static void | |
490 ngx_stream_proxy_init_upstream(ngx_stream_session_t *s) | |
491 { | |
6222 | 492 int tcp_nodelay; |
6115 | 493 u_char *p; |
494 ngx_connection_t *c, *pc; | |
495 ngx_log_handler_pt handler; | |
496 ngx_stream_upstream_t *u; | |
6221
7565e056fad6
Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6217
diff
changeset
|
497 ngx_stream_core_srv_conf_t *cscf; |
6115 | 498 ngx_stream_proxy_srv_conf_t *pscf; |
499 | |
6184
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
500 u = s->upstream; |
6221
7565e056fad6
Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6217
diff
changeset
|
501 pc = u->peer.connection; |
7565e056fad6
Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6217
diff
changeset
|
502 |
7565e056fad6
Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6217
diff
changeset
|
503 cscf = ngx_stream_get_module_srv_conf(s, ngx_stream_core_module); |
7565e056fad6
Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6217
diff
changeset
|
504 |
6436 | 505 if (pc->type == SOCK_STREAM |
506 && cscf->tcp_nodelay | |
507 && pc->tcp_nodelay == NGX_TCP_NODELAY_UNSET) | |
508 { | |
6221
7565e056fad6
Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6217
diff
changeset
|
509 ngx_log_debug0(NGX_LOG_DEBUG_STREAM, pc->log, 0, "tcp_nodelay"); |
7565e056fad6
Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6217
diff
changeset
|
510 |
7565e056fad6
Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6217
diff
changeset
|
511 tcp_nodelay = 1; |
7565e056fad6
Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6217
diff
changeset
|
512 |
7565e056fad6
Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6217
diff
changeset
|
513 if (setsockopt(pc->fd, IPPROTO_TCP, TCP_NODELAY, |
7565e056fad6
Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6217
diff
changeset
|
514 (const void *) &tcp_nodelay, sizeof(int)) == -1) |
7565e056fad6
Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6217
diff
changeset
|
515 { |
7565e056fad6
Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6217
diff
changeset
|
516 ngx_connection_error(pc, ngx_socket_errno, |
7565e056fad6
Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6217
diff
changeset
|
517 "setsockopt(TCP_NODELAY) failed"); |
7565e056fad6
Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6217
diff
changeset
|
518 ngx_stream_proxy_next_upstream(s); |
7565e056fad6
Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6217
diff
changeset
|
519 return; |
7565e056fad6
Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6217
diff
changeset
|
520 } |
7565e056fad6
Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6217
diff
changeset
|
521 |
7565e056fad6
Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6217
diff
changeset
|
522 pc->tcp_nodelay = NGX_TCP_NODELAY_SET; |
7565e056fad6
Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6217
diff
changeset
|
523 } |
6115 | 524 |
6184
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
525 if (u->proxy_protocol) { |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
526 if (ngx_stream_proxy_send_proxy_protocol(s) != NGX_OK) { |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
527 return; |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
528 } |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
529 |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
530 u->proxy_protocol = 0; |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
531 } |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
532 |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
533 pscf = ngx_stream_get_module_srv_conf(s, ngx_stream_proxy_module); |
6115 | 534 |
535 #if (NGX_STREAM_SSL) | |
6436 | 536 if (pc->type == SOCK_STREAM && pscf->ssl && pc->ssl == NULL) { |
6115 | 537 ngx_stream_proxy_ssl_init_connection(s); |
538 return; | |
539 } | |
540 #endif | |
541 | |
542 c = s->connection; | |
543 | |
544 if (c->log->log_level >= NGX_LOG_INFO) { | |
6230
2a621245f4cf
Win32: MSVC 2015 compatibility.
Maxim Dounin <mdounin@mdounin.ru>
parents:
6222
diff
changeset
|
545 ngx_str_t str; |
6115 | 546 u_char addr[NGX_SOCKADDR_STRLEN]; |
547 | |
6230
2a621245f4cf
Win32: MSVC 2015 compatibility.
Maxim Dounin <mdounin@mdounin.ru>
parents:
6222
diff
changeset
|
548 str.len = NGX_SOCKADDR_STRLEN; |
2a621245f4cf
Win32: MSVC 2015 compatibility.
Maxim Dounin <mdounin@mdounin.ru>
parents:
6222
diff
changeset
|
549 str.data = addr; |
6115 | 550 |
6230
2a621245f4cf
Win32: MSVC 2015 compatibility.
Maxim Dounin <mdounin@mdounin.ru>
parents:
6222
diff
changeset
|
551 if (ngx_connection_local_sockaddr(pc, &str, 1) == NGX_OK) { |
6115 | 552 handler = c->log->handler; |
553 c->log->handler = NULL; | |
554 | |
555 ngx_log_error(NGX_LOG_INFO, c->log, 0, "proxy %V connected to %V", | |
6230
2a621245f4cf
Win32: MSVC 2015 compatibility.
Maxim Dounin <mdounin@mdounin.ru>
parents:
6222
diff
changeset
|
556 &str, u->peer.name); |
6115 | 557 |
558 c->log->handler = handler; | |
559 } | |
560 } | |
561 | |
562 c->log->action = "proxying connection"; | |
563 | |
6436 | 564 if (u->upstream_buf.start == NULL) { |
565 p = ngx_pnalloc(c->pool, pscf->buffer_size); | |
566 if (p == NULL) { | |
567 ngx_stream_proxy_finalize(s, NGX_ERROR); | |
568 return; | |
569 } | |
570 | |
571 u->upstream_buf.start = p; | |
572 u->upstream_buf.end = p + pscf->buffer_size; | |
573 u->upstream_buf.pos = p; | |
574 u->upstream_buf.last = p; | |
6115 | 575 } |
576 | |
6436 | 577 if (c->type == SOCK_DGRAM) { |
578 s->received = c->buffer->last - c->buffer->pos; | |
579 u->downstream_buf = *c->buffer; | |
580 | |
581 if (pscf->responses == 0) { | |
582 pc->read->ready = 0; | |
583 pc->read->eof = 1; | |
584 } | |
585 } | |
6115 | 586 |
6202
6345822f0abb
Stream: upstream "connected" flag.
Roman Arutyunyan <arut@nginx.com>
parents:
6201
diff
changeset
|
587 u->connected = 1; |
6345822f0abb
Stream: upstream "connected" flag.
Roman Arutyunyan <arut@nginx.com>
parents:
6201
diff
changeset
|
588 |
6115 | 589 pc->read->handler = ngx_stream_proxy_upstream_handler; |
590 pc->write->handler = ngx_stream_proxy_upstream_handler; | |
591 | |
6436 | 592 if (pc->read->ready || pc->read->eof) { |
6435
d1c791479bbb
Stream: post first read events from client and upstream.
Roman Arutyunyan <arut@nginx.com>
parents:
6393
diff
changeset
|
593 ngx_post_event(pc->read, &ngx_posted_events); |
6115 | 594 } |
595 | |
596 ngx_stream_proxy_process(s, 0, 1); | |
597 } | |
598 | |
599 | |
6184
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
600 static ngx_int_t |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
601 ngx_stream_proxy_send_proxy_protocol(ngx_stream_session_t *s) |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
602 { |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
603 u_char *p; |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
604 ssize_t n, size; |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
605 ngx_connection_t *c, *pc; |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
606 ngx_stream_upstream_t *u; |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
607 ngx_stream_proxy_srv_conf_t *pscf; |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
608 u_char buf[NGX_PROXY_PROTOCOL_MAX_HEADER]; |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
609 |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
610 c = s->connection; |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
611 |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
612 ngx_log_debug0(NGX_LOG_DEBUG_STREAM, c->log, 0, |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
613 "stream proxy send PROXY protocol header"); |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
614 |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
615 p = ngx_proxy_protocol_write(c, buf, buf + NGX_PROXY_PROTOCOL_MAX_HEADER); |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
616 if (p == NULL) { |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
617 ngx_stream_proxy_finalize(s, NGX_ERROR); |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
618 return NGX_ERROR; |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
619 } |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
620 |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
621 u = s->upstream; |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
622 |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
623 pc = u->peer.connection; |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
624 |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
625 size = p - buf; |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
626 |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
627 n = pc->send(pc, buf, size); |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
628 |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
629 if (n == NGX_AGAIN) { |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
630 if (ngx_handle_write_event(pc->write, 0) != NGX_OK) { |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
631 ngx_stream_proxy_finalize(s, NGX_ERROR); |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
632 return NGX_ERROR; |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
633 } |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
634 |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
635 pscf = ngx_stream_get_module_srv_conf(s, ngx_stream_proxy_module); |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
636 |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
637 ngx_add_timer(pc->write, pscf->timeout); |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
638 |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
639 pc->write->handler = ngx_stream_proxy_connect_handler; |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
640 |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
641 return NGX_AGAIN; |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
642 } |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
643 |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
644 if (n == NGX_ERROR) { |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
645 ngx_stream_proxy_finalize(s, NGX_DECLINED); |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
646 return NGX_ERROR; |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
647 } |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
648 |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
649 if (n != size) { |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
650 |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
651 /* |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
652 * PROXY protocol specification: |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
653 * The sender must always ensure that the header |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
654 * is sent at once, so that the transport layer |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
655 * maintains atomicity along the path to the receiver. |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
656 */ |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
657 |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
658 ngx_log_error(NGX_LOG_ERR, c->log, 0, |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
659 "could not send PROXY protocol header at once"); |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
660 |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
661 ngx_stream_proxy_finalize(s, NGX_DECLINED); |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
662 |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
663 return NGX_ERROR; |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
664 } |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
665 |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
666 return NGX_OK; |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
667 } |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
668 |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
669 |
6115 | 670 #if (NGX_STREAM_SSL) |
671 | |
672 static char * | |
673 ngx_stream_proxy_ssl_password_file(ngx_conf_t *cf, ngx_command_t *cmd, | |
674 void *conf) | |
675 { | |
676 ngx_stream_proxy_srv_conf_t *pscf = conf; | |
677 | |
678 ngx_str_t *value; | |
679 | |
680 if (pscf->ssl_passwords != NGX_CONF_UNSET_PTR) { | |
681 return "is duplicate"; | |
682 } | |
683 | |
684 value = cf->args->elts; | |
685 | |
686 pscf->ssl_passwords = ngx_ssl_read_password_file(cf, &value[1]); | |
687 | |
688 if (pscf->ssl_passwords == NULL) { | |
689 return NGX_CONF_ERROR; | |
690 } | |
691 | |
692 return NGX_CONF_OK; | |
693 } | |
694 | |
695 | |
696 static void | |
697 ngx_stream_proxy_ssl_init_connection(ngx_stream_session_t *s) | |
698 { | |
699 ngx_int_t rc; | |
700 ngx_connection_t *pc; | |
701 ngx_stream_upstream_t *u; | |
702 ngx_stream_proxy_srv_conf_t *pscf; | |
703 | |
704 u = s->upstream; | |
705 | |
706 pc = u->peer.connection; | |
707 | |
708 pscf = ngx_stream_get_module_srv_conf(s, ngx_stream_proxy_module); | |
709 | |
710 if (ngx_ssl_create_connection(pscf->ssl, pc, NGX_SSL_BUFFER|NGX_SSL_CLIENT) | |
711 != NGX_OK) | |
712 { | |
713 ngx_stream_proxy_finalize(s, NGX_ERROR); | |
714 return; | |
715 } | |
716 | |
717 if (pscf->ssl_server_name || pscf->ssl_verify) { | |
718 if (ngx_stream_proxy_ssl_name(s) != NGX_OK) { | |
719 ngx_stream_proxy_finalize(s, NGX_ERROR); | |
720 return; | |
721 } | |
722 } | |
723 | |
724 if (pscf->ssl_session_reuse) { | |
725 if (u->peer.set_session(&u->peer, u->peer.data) != NGX_OK) { | |
726 ngx_stream_proxy_finalize(s, NGX_ERROR); | |
727 return; | |
728 } | |
729 } | |
730 | |
731 s->connection->log->action = "SSL handshaking to upstream"; | |
732 | |
733 rc = ngx_ssl_handshake(pc); | |
734 | |
735 if (rc == NGX_AGAIN) { | |
736 | |
737 if (!pc->write->timer_set) { | |
738 ngx_add_timer(pc->write, pscf->connect_timeout); | |
739 } | |
740 | |
741 pc->ssl->handler = ngx_stream_proxy_ssl_handshake; | |
742 return; | |
743 } | |
744 | |
745 ngx_stream_proxy_ssl_handshake(pc); | |
746 } | |
747 | |
748 | |
749 static void | |
750 ngx_stream_proxy_ssl_handshake(ngx_connection_t *pc) | |
751 { | |
752 long rc; | |
753 ngx_stream_session_t *s; | |
754 ngx_stream_upstream_t *u; | |
755 ngx_stream_proxy_srv_conf_t *pscf; | |
756 | |
757 s = pc->data; | |
758 | |
759 pscf = ngx_stream_get_module_srv_conf(s, ngx_stream_proxy_module); | |
760 | |
761 if (pc->ssl->handshaked) { | |
762 | |
763 if (pscf->ssl_verify) { | |
764 rc = SSL_get_verify_result(pc->ssl->connection); | |
765 | |
766 if (rc != X509_V_OK) { | |
767 ngx_log_error(NGX_LOG_ERR, pc->log, 0, | |
768 "upstream SSL certificate verify error: (%l:%s)", | |
769 rc, X509_verify_cert_error_string(rc)); | |
770 goto failed; | |
771 } | |
772 | |
773 u = s->upstream; | |
774 | |
775 if (ngx_ssl_check_host(pc, &u->ssl_name) != NGX_OK) { | |
776 ngx_log_error(NGX_LOG_ERR, pc->log, 0, | |
777 "upstream SSL certificate does not match \"%V\"", | |
778 &u->ssl_name); | |
779 goto failed; | |
780 } | |
781 } | |
782 | |
783 if (pscf->ssl_session_reuse) { | |
784 u = s->upstream; | |
785 u->peer.save_session(&u->peer, u->peer.data); | |
786 } | |
787 | |
6258
4b4aee40c508
Stream: delete proxy connection timer after SSL handshake.
Ruslan Ermilov <ru@nginx.com>
parents:
6230
diff
changeset
|
788 if (pc->write->timer_set) { |
4b4aee40c508
Stream: delete proxy connection timer after SSL handshake.
Ruslan Ermilov <ru@nginx.com>
parents:
6230
diff
changeset
|
789 ngx_del_timer(pc->write); |
4b4aee40c508
Stream: delete proxy connection timer after SSL handshake.
Ruslan Ermilov <ru@nginx.com>
parents:
6230
diff
changeset
|
790 } |
4b4aee40c508
Stream: delete proxy connection timer after SSL handshake.
Ruslan Ermilov <ru@nginx.com>
parents:
6230
diff
changeset
|
791 |
6115 | 792 ngx_stream_proxy_init_upstream(s); |
793 | |
794 return; | |
795 } | |
796 | |
797 failed: | |
798 | |
799 ngx_stream_proxy_next_upstream(s); | |
800 } | |
801 | |
802 | |
803 static ngx_int_t | |
804 ngx_stream_proxy_ssl_name(ngx_stream_session_t *s) | |
805 { | |
806 u_char *p, *last; | |
807 ngx_str_t name; | |
808 ngx_stream_upstream_t *u; | |
809 ngx_stream_proxy_srv_conf_t *pscf; | |
810 | |
811 pscf = ngx_stream_get_module_srv_conf(s, ngx_stream_proxy_module); | |
812 | |
813 u = s->upstream; | |
814 | |
815 name = pscf->ssl_name; | |
816 | |
817 if (name.len == 0) { | |
818 name = pscf->upstream->host; | |
819 } | |
820 | |
821 if (name.len == 0) { | |
822 goto done; | |
823 } | |
824 | |
825 /* | |
826 * ssl name here may contain port, strip it for compatibility | |
827 * with the http module | |
828 */ | |
829 | |
830 p = name.data; | |
831 last = name.data + name.len; | |
832 | |
833 if (*p == '[') { | |
834 p = ngx_strlchr(p, last, ']'); | |
835 | |
836 if (p == NULL) { | |
837 p = name.data; | |
838 } | |
839 } | |
840 | |
841 p = ngx_strlchr(p, last, ':'); | |
842 | |
843 if (p != NULL) { | |
844 name.len = p - name.data; | |
845 } | |
846 | |
847 if (!pscf->ssl_server_name) { | |
848 goto done; | |
849 } | |
850 | |
851 #ifdef SSL_CTRL_SET_TLSEXT_HOSTNAME | |
852 | |
853 /* as per RFC 6066, literal IPv4 and IPv6 addresses are not permitted */ | |
854 | |
855 if (name.len == 0 || *name.data == '[') { | |
856 goto done; | |
857 } | |
858 | |
859 if (ngx_inet_addr(name.data, name.len) != INADDR_NONE) { | |
860 goto done; | |
861 } | |
862 | |
863 /* | |
864 * SSL_set_tlsext_host_name() needs a null-terminated string, | |
865 * hence we explicitly null-terminate name here | |
866 */ | |
867 | |
868 p = ngx_pnalloc(s->connection->pool, name.len + 1); | |
869 if (p == NULL) { | |
870 return NGX_ERROR; | |
871 } | |
872 | |
873 (void) ngx_cpystrn(p, name.data, name.len + 1); | |
874 | |
875 name.data = p; | |
876 | |
877 ngx_log_debug1(NGX_LOG_DEBUG_STREAM, s->connection->log, 0, | |
878 "upstream SSL server name: \"%s\"", name.data); | |
879 | |
880 if (SSL_set_tlsext_host_name(u->peer.connection->ssl->connection, name.data) | |
881 == 0) | |
882 { | |
883 ngx_ssl_error(NGX_LOG_ERR, s->connection->log, 0, | |
884 "SSL_set_tlsext_host_name(\"%s\") failed", name.data); | |
885 return NGX_ERROR; | |
886 } | |
887 | |
888 #endif | |
889 | |
890 done: | |
891 | |
892 u->ssl_name = name; | |
893 | |
894 return NGX_OK; | |
895 } | |
896 | |
897 #endif | |
898 | |
899 | |
900 static void | |
901 ngx_stream_proxy_downstream_handler(ngx_event_t *ev) | |
902 { | |
6200
abee77018d3a
Stream: common handler for upstream and downstream.
Roman Arutyunyan <arut@nginx.com>
parents:
6184
diff
changeset
|
903 ngx_stream_proxy_process_connection(ev, ev->write); |
abee77018d3a
Stream: common handler for upstream and downstream.
Roman Arutyunyan <arut@nginx.com>
parents:
6184
diff
changeset
|
904 } |
abee77018d3a
Stream: common handler for upstream and downstream.
Roman Arutyunyan <arut@nginx.com>
parents:
6184
diff
changeset
|
905 |
abee77018d3a
Stream: common handler for upstream and downstream.
Roman Arutyunyan <arut@nginx.com>
parents:
6184
diff
changeset
|
906 |
abee77018d3a
Stream: common handler for upstream and downstream.
Roman Arutyunyan <arut@nginx.com>
parents:
6184
diff
changeset
|
907 static void |
abee77018d3a
Stream: common handler for upstream and downstream.
Roman Arutyunyan <arut@nginx.com>
parents:
6184
diff
changeset
|
908 ngx_stream_proxy_upstream_handler(ngx_event_t *ev) |
abee77018d3a
Stream: common handler for upstream and downstream.
Roman Arutyunyan <arut@nginx.com>
parents:
6184
diff
changeset
|
909 { |
abee77018d3a
Stream: common handler for upstream and downstream.
Roman Arutyunyan <arut@nginx.com>
parents:
6184
diff
changeset
|
910 ngx_stream_proxy_process_connection(ev, !ev->write); |
abee77018d3a
Stream: common handler for upstream and downstream.
Roman Arutyunyan <arut@nginx.com>
parents:
6184
diff
changeset
|
911 } |
abee77018d3a
Stream: common handler for upstream and downstream.
Roman Arutyunyan <arut@nginx.com>
parents:
6184
diff
changeset
|
912 |
abee77018d3a
Stream: common handler for upstream and downstream.
Roman Arutyunyan <arut@nginx.com>
parents:
6184
diff
changeset
|
913 |
abee77018d3a
Stream: common handler for upstream and downstream.
Roman Arutyunyan <arut@nginx.com>
parents:
6184
diff
changeset
|
914 static void |
abee77018d3a
Stream: common handler for upstream and downstream.
Roman Arutyunyan <arut@nginx.com>
parents:
6184
diff
changeset
|
915 ngx_stream_proxy_process_connection(ngx_event_t *ev, ngx_uint_t from_upstream) |
abee77018d3a
Stream: common handler for upstream and downstream.
Roman Arutyunyan <arut@nginx.com>
parents:
6184
diff
changeset
|
916 { |
6201
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
917 ngx_connection_t *c, *pc; |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
918 ngx_stream_session_t *s; |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
919 ngx_stream_upstream_t *u; |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
920 ngx_stream_proxy_srv_conf_t *pscf; |
6115 | 921 |
922 c = ev->data; | |
923 s = c->data; | |
6200
abee77018d3a
Stream: common handler for upstream and downstream.
Roman Arutyunyan <arut@nginx.com>
parents:
6184
diff
changeset
|
924 u = s->upstream; |
6115 | 925 |
6436 | 926 c = s->connection; |
927 pc = u->peer.connection; | |
928 | |
929 pscf = ngx_stream_get_module_srv_conf(s, ngx_stream_proxy_module); | |
930 | |
6115 | 931 if (ev->timedout) { |
6436 | 932 ev->timedout = 0; |
6201
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
933 |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
934 if (ev->delayed) { |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
935 ev->delayed = 0; |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
936 |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
937 if (!ev->ready) { |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
938 if (ngx_handle_read_event(ev, 0) != NGX_OK) { |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
939 ngx_stream_proxy_finalize(s, NGX_ERROR); |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
940 return; |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
941 } |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
942 |
6436 | 943 if (u->connected && !c->read->delayed && !pc->read->delayed) { |
944 ngx_add_timer(c->write, pscf->timeout); | |
6201
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
945 } |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
946 |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
947 return; |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
948 } |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
949 |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
950 } else { |
6436 | 951 if (s->connection->type == SOCK_DGRAM) { |
952 if (pscf->responses == NGX_MAX_INT32_VALUE) { | |
953 | |
954 /* | |
955 * successfully terminate timed out UDP session | |
956 * with unspecified number of responses | |
957 */ | |
958 | |
959 pc->read->ready = 0; | |
960 pc->read->eof = 1; | |
961 | |
962 ngx_stream_proxy_process(s, 1, 0); | |
963 return; | |
964 } | |
965 | |
966 if (u->received == 0) { | |
967 ngx_stream_proxy_next_upstream(s); | |
968 return; | |
969 } | |
970 } | |
971 | |
6201
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
972 ngx_connection_error(c, NGX_ETIMEDOUT, "connection timed out"); |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
973 ngx_stream_proxy_finalize(s, NGX_DECLINED); |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
974 return; |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
975 } |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
976 |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
977 } else if (ev->delayed) { |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
978 |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
979 ngx_log_debug0(NGX_LOG_DEBUG_STREAM, c->log, 0, |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
980 "stream connection delayed"); |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
981 |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
982 if (ngx_handle_read_event(ev, 0) != NGX_OK) { |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
983 ngx_stream_proxy_finalize(s, NGX_ERROR); |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
984 } |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
985 |
6115 | 986 return; |
987 } | |
988 | |
6202
6345822f0abb
Stream: upstream "connected" flag.
Roman Arutyunyan <arut@nginx.com>
parents:
6201
diff
changeset
|
989 if (from_upstream && !u->connected) { |
6200
abee77018d3a
Stream: common handler for upstream and downstream.
Roman Arutyunyan <arut@nginx.com>
parents:
6184
diff
changeset
|
990 return; |
6115 | 991 } |
992 | |
6200
abee77018d3a
Stream: common handler for upstream and downstream.
Roman Arutyunyan <arut@nginx.com>
parents:
6184
diff
changeset
|
993 ngx_stream_proxy_process(s, from_upstream, ev->write); |
6115 | 994 } |
995 | |
996 | |
997 static void | |
998 ngx_stream_proxy_connect_handler(ngx_event_t *ev) | |
999 { | |
1000 ngx_connection_t *c; | |
1001 ngx_stream_session_t *s; | |
1002 | |
1003 c = ev->data; | |
1004 s = c->data; | |
1005 | |
1006 if (ev->timedout) { | |
1007 ngx_log_error(NGX_LOG_ERR, c->log, NGX_ETIMEDOUT, "upstream timed out"); | |
1008 ngx_stream_proxy_next_upstream(s); | |
1009 return; | |
1010 } | |
1011 | |
1012 ngx_del_timer(c->write); | |
1013 | |
1014 ngx_log_debug0(NGX_LOG_DEBUG_STREAM, c->log, 0, | |
1015 "stream proxy connect upstream"); | |
1016 | |
1017 if (ngx_stream_proxy_test_connect(c) != NGX_OK) { | |
1018 ngx_stream_proxy_next_upstream(s); | |
1019 return; | |
1020 } | |
1021 | |
1022 ngx_stream_proxy_init_upstream(s); | |
1023 } | |
1024 | |
1025 | |
1026 static ngx_int_t | |
1027 ngx_stream_proxy_test_connect(ngx_connection_t *c) | |
1028 { | |
1029 int err; | |
1030 socklen_t len; | |
1031 | |
1032 #if (NGX_HAVE_KQUEUE) | |
1033 | |
1034 if (ngx_event_flags & NGX_USE_KQUEUE_EVENT) { | |
1035 err = c->write->kq_errno ? c->write->kq_errno : c->read->kq_errno; | |
1036 | |
1037 if (err) { | |
1038 (void) ngx_connection_error(c, err, | |
1039 "kevent() reported that connect() failed"); | |
1040 return NGX_ERROR; | |
1041 } | |
1042 | |
1043 } else | |
1044 #endif | |
1045 { | |
1046 err = 0; | |
1047 len = sizeof(int); | |
1048 | |
1049 /* | |
1050 * BSDs and Linux return 0 and set a pending error in err | |
1051 * Solaris returns -1 and sets errno | |
1052 */ | |
1053 | |
1054 if (getsockopt(c->fd, SOL_SOCKET, SO_ERROR, (void *) &err, &len) | |
1055 == -1) | |
1056 { | |
1057 err = ngx_socket_errno; | |
1058 } | |
1059 | |
1060 if (err) { | |
1061 (void) ngx_connection_error(c, err, "connect() failed"); | |
1062 return NGX_ERROR; | |
1063 } | |
1064 } | |
1065 | |
1066 return NGX_OK; | |
1067 } | |
1068 | |
1069 | |
6435
d1c791479bbb
Stream: post first read events from client and upstream.
Roman Arutyunyan <arut@nginx.com>
parents:
6393
diff
changeset
|
1070 static void |
6115 | 1071 ngx_stream_proxy_process(ngx_stream_session_t *s, ngx_uint_t from_upstream, |
1072 ngx_uint_t do_write) | |
1073 { | |
6201
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1074 off_t *received, limit; |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1075 size_t size, limit_rate; |
6115 | 1076 ssize_t n; |
1077 ngx_buf_t *b; | |
6124
f1f222db290b
Stream: prevent repeated event notifications after eof.
Roman Arutyunyan <arut@nginx.com>
parents:
6115
diff
changeset
|
1078 ngx_uint_t flags; |
6201
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1079 ngx_msec_t delay; |
6115 | 1080 ngx_connection_t *c, *pc, *src, *dst; |
1081 ngx_log_handler_pt handler; | |
1082 ngx_stream_upstream_t *u; | |
1083 ngx_stream_proxy_srv_conf_t *pscf; | |
1084 | |
1085 u = s->upstream; | |
1086 | |
1087 c = s->connection; | |
6202
6345822f0abb
Stream: upstream "connected" flag.
Roman Arutyunyan <arut@nginx.com>
parents:
6201
diff
changeset
|
1088 pc = u->connected ? u->peer.connection : NULL; |
6115 | 1089 |
6436 | 1090 if (c->type == SOCK_DGRAM && (ngx_terminate || ngx_exiting)) { |
1091 | |
1092 /* socket is already closed on worker shutdown */ | |
1093 | |
1094 handler = c->log->handler; | |
1095 c->log->handler = NULL; | |
1096 | |
1097 ngx_log_error(NGX_LOG_INFO, c->log, 0, "disconnected on shutdown"); | |
1098 | |
1099 c->log->handler = handler; | |
1100 | |
1101 ngx_stream_proxy_finalize(s, NGX_OK); | |
1102 return; | |
1103 } | |
1104 | |
6201
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1105 pscf = ngx_stream_get_module_srv_conf(s, ngx_stream_proxy_module); |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1106 |
6115 | 1107 if (from_upstream) { |
1108 src = pc; | |
1109 dst = c; | |
1110 b = &u->upstream_buf; | |
6208
7a14a0d754ad
Stream: renamed rate limiting directives.
Roman Arutyunyan <arut@nginx.com>
parents:
6204
diff
changeset
|
1111 limit_rate = pscf->download_rate; |
6201
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1112 received = &u->received; |
6115 | 1113 |
1114 } else { | |
1115 src = c; | |
1116 dst = pc; | |
1117 b = &u->downstream_buf; | |
6208
7a14a0d754ad
Stream: renamed rate limiting directives.
Roman Arutyunyan <arut@nginx.com>
parents:
6204
diff
changeset
|
1118 limit_rate = pscf->upload_rate; |
6201
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1119 received = &s->received; |
6115 | 1120 } |
1121 | |
1122 for ( ;; ) { | |
1123 | |
1124 if (do_write) { | |
1125 | |
1126 size = b->last - b->pos; | |
1127 | |
1128 if (size && dst && dst->write->ready) { | |
1129 | |
1130 n = dst->send(dst, b->pos, size); | |
1131 | |
6436 | 1132 if (n == NGX_AGAIN && dst->shared) { |
1133 /* cannot wait on a shared socket */ | |
1134 n = NGX_ERROR; | |
1135 } | |
1136 | |
6115 | 1137 if (n == NGX_ERROR) { |
6436 | 1138 if (c->type == SOCK_DGRAM && !from_upstream) { |
1139 ngx_stream_proxy_next_upstream(s); | |
1140 return; | |
1141 } | |
1142 | |
6115 | 1143 ngx_stream_proxy_finalize(s, NGX_DECLINED); |
6435
d1c791479bbb
Stream: post first read events from client and upstream.
Roman Arutyunyan <arut@nginx.com>
parents:
6393
diff
changeset
|
1144 return; |
6115 | 1145 } |
1146 | |
1147 if (n > 0) { | |
1148 b->pos += n; | |
1149 | |
1150 if (b->pos == b->last) { | |
1151 b->pos = b->start; | |
1152 b->last = b->start; | |
1153 } | |
1154 } | |
1155 } | |
1156 } | |
1157 | |
1158 size = b->end - b->last; | |
1159 | |
6201
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1160 if (size && src->read->ready && !src->read->delayed) { |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1161 |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1162 if (limit_rate) { |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1163 limit = (off_t) limit_rate * (ngx_time() - u->start_sec + 1) |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1164 - *received; |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1165 |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1166 if (limit <= 0) { |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1167 src->read->delayed = 1; |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1168 delay = (ngx_msec_t) (- limit * 1000 / limit_rate + 1); |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1169 ngx_add_timer(src->read, delay); |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1170 break; |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1171 } |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1172 |
6204
114d1f8cdcab
Stream: fixed possible integer overflow in rate limiting.
Valentin Bartenev <vbart@nginx.com>
parents:
6203
diff
changeset
|
1173 if ((off_t) size > limit) { |
6203
fdfdcad62875
Stream: fixed MSVC compilation warning.
Roman Arutyunyan <arut@nginx.com>
parents:
6202
diff
changeset
|
1174 size = (size_t) limit; |
6201
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1175 } |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1176 } |
6115 | 1177 |
1178 n = src->recv(src, b->last, size); | |
1179 | |
1180 if (n == NGX_AGAIN || n == 0) { | |
1181 break; | |
1182 } | |
1183 | |
1184 if (n > 0) { | |
6201
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1185 if (limit_rate) { |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1186 delay = (ngx_msec_t) (n * 1000 / limit_rate); |
6115 | 1187 |
6201
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1188 if (delay > 0) { |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1189 src->read->delayed = 1; |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1190 ngx_add_timer(src->read, delay); |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1191 } |
6115 | 1192 } |
1193 | |
6436 | 1194 if (c->type == SOCK_DGRAM && ++u->responses == pscf->responses) |
1195 { | |
1196 src->read->ready = 0; | |
1197 src->read->eof = 1; | |
1198 } | |
1199 | |
6201
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1200 *received += n; |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1201 b->last += n; |
6115 | 1202 do_write = 1; |
6201
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1203 |
6115 | 1204 continue; |
1205 } | |
1206 | |
1207 if (n == NGX_ERROR) { | |
6436 | 1208 if (c->type == SOCK_DGRAM && u->received == 0) { |
1209 ngx_stream_proxy_next_upstream(s); | |
1210 return; | |
1211 } | |
1212 | |
6115 | 1213 src->read->eof = 1; |
1214 } | |
1215 } | |
1216 | |
1217 break; | |
1218 } | |
1219 | |
1220 if (src->read->eof && (b->pos == b->last || (dst && dst->read->eof))) { | |
1221 handler = c->log->handler; | |
1222 c->log->handler = NULL; | |
1223 | |
1224 ngx_log_error(NGX_LOG_INFO, c->log, 0, | |
1225 "%s disconnected" | |
1226 ", bytes from/to client:%O/%O" | |
1227 ", bytes from/to upstream:%O/%O", | |
1228 from_upstream ? "upstream" : "client", | |
1229 s->received, c->sent, u->received, pc ? pc->sent : 0); | |
1230 | |
1231 c->log->handler = handler; | |
1232 | |
1233 ngx_stream_proxy_finalize(s, NGX_OK); | |
6435
d1c791479bbb
Stream: post first read events from client and upstream.
Roman Arutyunyan <arut@nginx.com>
parents:
6393
diff
changeset
|
1234 return; |
6115 | 1235 } |
1236 | |
6124
f1f222db290b
Stream: prevent repeated event notifications after eof.
Roman Arutyunyan <arut@nginx.com>
parents:
6115
diff
changeset
|
1237 flags = src->read->eof ? NGX_CLOSE_EVENT : 0; |
f1f222db290b
Stream: prevent repeated event notifications after eof.
Roman Arutyunyan <arut@nginx.com>
parents:
6115
diff
changeset
|
1238 |
6436 | 1239 if (!src->shared && ngx_handle_read_event(src->read, flags) != NGX_OK) { |
6115 | 1240 ngx_stream_proxy_finalize(s, NGX_ERROR); |
6435
d1c791479bbb
Stream: post first read events from client and upstream.
Roman Arutyunyan <arut@nginx.com>
parents:
6393
diff
changeset
|
1241 return; |
6115 | 1242 } |
1243 | |
1244 if (dst) { | |
6436 | 1245 if (!dst->shared && ngx_handle_write_event(dst->write, 0) != NGX_OK) { |
6115 | 1246 ngx_stream_proxy_finalize(s, NGX_ERROR); |
6435
d1c791479bbb
Stream: post first read events from client and upstream.
Roman Arutyunyan <arut@nginx.com>
parents:
6393
diff
changeset
|
1247 return; |
6115 | 1248 } |
1249 | |
6201
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1250 if (!c->read->delayed && !pc->read->delayed) { |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1251 ngx_add_timer(c->write, pscf->timeout); |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1252 |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1253 } else if (c->write->timer_set) { |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1254 ngx_del_timer(c->write); |
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1255 } |
6115 | 1256 } |
1257 } | |
1258 | |
1259 | |
1260 static void | |
1261 ngx_stream_proxy_next_upstream(ngx_stream_session_t *s) | |
1262 { | |
1263 ngx_msec_t timeout; | |
1264 ngx_connection_t *pc; | |
1265 ngx_stream_upstream_t *u; | |
1266 ngx_stream_proxy_srv_conf_t *pscf; | |
1267 | |
1268 ngx_log_debug0(NGX_LOG_DEBUG_STREAM, s->connection->log, 0, | |
1269 "stream proxy next upstream"); | |
1270 | |
1271 u = s->upstream; | |
1272 | |
1273 if (u->peer.sockaddr) { | |
1274 u->peer.free(&u->peer, u->peer.data, NGX_PEER_FAILED); | |
1275 u->peer.sockaddr = NULL; | |
1276 } | |
1277 | |
1278 pscf = ngx_stream_get_module_srv_conf(s, ngx_stream_proxy_module); | |
1279 | |
1280 timeout = pscf->next_upstream_timeout; | |
1281 | |
1282 if (u->peer.tries == 0 | |
1283 || !pscf->next_upstream | |
1284 || (timeout && ngx_current_msec - u->peer.start_time >= timeout)) | |
1285 { | |
1286 ngx_stream_proxy_finalize(s, NGX_DECLINED); | |
1287 return; | |
1288 } | |
1289 | |
1290 pc = u->peer.connection; | |
1291 | |
1292 if (pc) { | |
1293 ngx_log_debug1(NGX_LOG_DEBUG_STREAM, s->connection->log, 0, | |
1294 "close proxy upstream connection: %d", pc->fd); | |
1295 | |
1296 #if (NGX_STREAM_SSL) | |
1297 if (pc->ssl) { | |
1298 pc->ssl->no_wait_shutdown = 1; | |
1299 pc->ssl->no_send_shutdown = 1; | |
1300 | |
1301 (void) ngx_ssl_shutdown(pc); | |
1302 } | |
1303 #endif | |
1304 | |
1305 ngx_close_connection(pc); | |
1306 u->peer.connection = NULL; | |
1307 } | |
1308 | |
1309 ngx_stream_proxy_connect(s); | |
1310 } | |
1311 | |
1312 | |
1313 static void | |
1314 ngx_stream_proxy_finalize(ngx_stream_session_t *s, ngx_int_t rc) | |
1315 { | |
1316 ngx_connection_t *pc; | |
1317 ngx_stream_upstream_t *u; | |
1318 | |
1319 ngx_log_debug1(NGX_LOG_DEBUG_STREAM, s->connection->log, 0, | |
1320 "finalize stream proxy: %i", rc); | |
1321 | |
1322 u = s->upstream; | |
1323 | |
1324 if (u == NULL) { | |
1325 goto noupstream; | |
1326 } | |
1327 | |
1328 if (u->peer.free && u->peer.sockaddr) { | |
1329 u->peer.free(&u->peer, u->peer.data, 0); | |
1330 u->peer.sockaddr = NULL; | |
1331 } | |
1332 | |
1333 pc = u->peer.connection; | |
1334 | |
1335 if (pc) { | |
1336 ngx_log_debug1(NGX_LOG_DEBUG_STREAM, s->connection->log, 0, | |
1337 "close stream proxy upstream connection: %d", pc->fd); | |
1338 | |
1339 #if (NGX_STREAM_SSL) | |
1340 if (pc->ssl) { | |
1341 pc->ssl->no_wait_shutdown = 1; | |
1342 (void) ngx_ssl_shutdown(pc); | |
1343 } | |
1344 #endif | |
1345 | |
1346 ngx_close_connection(pc); | |
1347 u->peer.connection = NULL; | |
1348 } | |
1349 | |
1350 noupstream: | |
1351 | |
1352 ngx_stream_close_connection(s->connection); | |
1353 } | |
1354 | |
1355 | |
1356 static u_char * | |
1357 ngx_stream_proxy_log_error(ngx_log_t *log, u_char *buf, size_t len) | |
1358 { | |
1359 u_char *p; | |
1360 ngx_connection_t *pc; | |
1361 ngx_stream_session_t *s; | |
1362 ngx_stream_upstream_t *u; | |
1363 | |
1364 s = log->data; | |
1365 | |
1366 u = s->upstream; | |
1367 | |
1368 p = buf; | |
1369 | |
1370 if (u->peer.name) { | |
1371 p = ngx_snprintf(p, len, ", upstream: \"%V\"", u->peer.name); | |
1372 len -= p - buf; | |
1373 } | |
1374 | |
1375 pc = u->peer.connection; | |
1376 | |
1377 p = ngx_snprintf(p, len, | |
1378 ", bytes from/to client:%O/%O" | |
1379 ", bytes from/to upstream:%O/%O", | |
1380 s->received, s->connection->sent, | |
1381 u->received, pc ? pc->sent : 0); | |
1382 | |
1383 return p; | |
1384 } | |
1385 | |
1386 | |
1387 static void * | |
1388 ngx_stream_proxy_create_srv_conf(ngx_conf_t *cf) | |
1389 { | |
1390 ngx_stream_proxy_srv_conf_t *conf; | |
1391 | |
1392 conf = ngx_pcalloc(cf->pool, sizeof(ngx_stream_proxy_srv_conf_t)); | |
1393 if (conf == NULL) { | |
1394 return NULL; | |
1395 } | |
1396 | |
1397 /* | |
1398 * set by ngx_pcalloc(): | |
1399 * | |
1400 * conf->ssl_protocols = 0; | |
1401 * conf->ssl_ciphers = { 0, NULL }; | |
1402 * conf->ssl_name = { 0, NULL }; | |
1403 * conf->ssl_trusted_certificate = { 0, NULL }; | |
1404 * conf->ssl_crl = { 0, NULL }; | |
1405 * conf->ssl_certificate = { 0, NULL }; | |
1406 * conf->ssl_certificate_key = { 0, NULL }; | |
1407 * | |
1408 * conf->ssl = NULL; | |
1409 * conf->upstream = NULL; | |
1410 */ | |
1411 | |
1412 conf->connect_timeout = NGX_CONF_UNSET_MSEC; | |
1413 conf->timeout = NGX_CONF_UNSET_MSEC; | |
1414 conf->next_upstream_timeout = NGX_CONF_UNSET_MSEC; | |
6215
8ee6a08ea3eb
Stream: added proxy_buffer_size to set the size of data buffers.
Roman Arutyunyan <arut@nginx.com>
parents:
6208
diff
changeset
|
1415 conf->buffer_size = NGX_CONF_UNSET_SIZE; |
6208
7a14a0d754ad
Stream: renamed rate limiting directives.
Roman Arutyunyan <arut@nginx.com>
parents:
6204
diff
changeset
|
1416 conf->upload_rate = NGX_CONF_UNSET_SIZE; |
7a14a0d754ad
Stream: renamed rate limiting directives.
Roman Arutyunyan <arut@nginx.com>
parents:
6204
diff
changeset
|
1417 conf->download_rate = NGX_CONF_UNSET_SIZE; |
6436 | 1418 conf->responses = NGX_CONF_UNSET_UINT; |
6115 | 1419 conf->next_upstream_tries = NGX_CONF_UNSET_UINT; |
1420 conf->next_upstream = NGX_CONF_UNSET; | |
6184
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
1421 conf->proxy_protocol = NGX_CONF_UNSET; |
6183
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1422 conf->local = NGX_CONF_UNSET_PTR; |
6115 | 1423 |
1424 #if (NGX_STREAM_SSL) | |
1425 conf->ssl_enable = NGX_CONF_UNSET; | |
1426 conf->ssl_session_reuse = NGX_CONF_UNSET; | |
1427 conf->ssl_server_name = NGX_CONF_UNSET; | |
1428 conf->ssl_verify = NGX_CONF_UNSET; | |
1429 conf->ssl_verify_depth = NGX_CONF_UNSET_UINT; | |
1430 conf->ssl_passwords = NGX_CONF_UNSET_PTR; | |
1431 #endif | |
1432 | |
1433 return conf; | |
1434 } | |
1435 | |
1436 | |
1437 static char * | |
1438 ngx_stream_proxy_merge_srv_conf(ngx_conf_t *cf, void *parent, void *child) | |
1439 { | |
1440 ngx_stream_proxy_srv_conf_t *prev = parent; | |
1441 ngx_stream_proxy_srv_conf_t *conf = child; | |
1442 | |
1443 ngx_conf_merge_msec_value(conf->connect_timeout, | |
1444 prev->connect_timeout, 60000); | |
1445 | |
1446 ngx_conf_merge_msec_value(conf->timeout, | |
1447 prev->timeout, 10 * 60000); | |
1448 | |
1449 ngx_conf_merge_msec_value(conf->next_upstream_timeout, | |
1450 prev->next_upstream_timeout, 0); | |
1451 | |
6215
8ee6a08ea3eb
Stream: added proxy_buffer_size to set the size of data buffers.
Roman Arutyunyan <arut@nginx.com>
parents:
6208
diff
changeset
|
1452 ngx_conf_merge_size_value(conf->buffer_size, |
8ee6a08ea3eb
Stream: added proxy_buffer_size to set the size of data buffers.
Roman Arutyunyan <arut@nginx.com>
parents:
6208
diff
changeset
|
1453 prev->buffer_size, 16384); |
6115 | 1454 |
6208
7a14a0d754ad
Stream: renamed rate limiting directives.
Roman Arutyunyan <arut@nginx.com>
parents:
6204
diff
changeset
|
1455 ngx_conf_merge_size_value(conf->upload_rate, |
7a14a0d754ad
Stream: renamed rate limiting directives.
Roman Arutyunyan <arut@nginx.com>
parents:
6204
diff
changeset
|
1456 prev->upload_rate, 0); |
6201
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1457 |
6208
7a14a0d754ad
Stream: renamed rate limiting directives.
Roman Arutyunyan <arut@nginx.com>
parents:
6204
diff
changeset
|
1458 ngx_conf_merge_size_value(conf->download_rate, |
7a14a0d754ad
Stream: renamed rate limiting directives.
Roman Arutyunyan <arut@nginx.com>
parents:
6204
diff
changeset
|
1459 prev->download_rate, 0); |
6201
24488e6db782
Stream: upstream and downstream limit rates.
Roman Arutyunyan <arut@nginx.com>
parents:
6200
diff
changeset
|
1460 |
6436 | 1461 ngx_conf_merge_uint_value(conf->responses, |
1462 prev->responses, NGX_MAX_INT32_VALUE); | |
1463 | |
6115 | 1464 ngx_conf_merge_uint_value(conf->next_upstream_tries, |
1465 prev->next_upstream_tries, 0); | |
1466 | |
1467 ngx_conf_merge_value(conf->next_upstream, prev->next_upstream, 1); | |
1468 | |
6184
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
1469 ngx_conf_merge_value(conf->proxy_protocol, prev->proxy_protocol, 0); |
fa663739e115
Stream: client-side PROXY protocol.
Roman Arutyunyan <arut@nginx.com>
parents:
6183
diff
changeset
|
1470 |
6183
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1471 ngx_conf_merge_ptr_value(conf->local, prev->local, NULL); |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1472 |
6115 | 1473 #if (NGX_STREAM_SSL) |
1474 | |
1475 ngx_conf_merge_value(conf->ssl_enable, prev->ssl_enable, 0); | |
1476 | |
1477 ngx_conf_merge_value(conf->ssl_session_reuse, | |
1478 prev->ssl_session_reuse, 1); | |
1479 | |
1480 ngx_conf_merge_bitmask_value(conf->ssl_protocols, prev->ssl_protocols, | |
6157
b2899e7d0ef8
Disabled SSLv3 by default (ticket #653).
Maxim Dounin <mdounin@mdounin.ru>
parents:
6124
diff
changeset
|
1481 (NGX_CONF_BITMASK_SET|NGX_SSL_TLSv1 |
b2899e7d0ef8
Disabled SSLv3 by default (ticket #653).
Maxim Dounin <mdounin@mdounin.ru>
parents:
6124
diff
changeset
|
1482 |NGX_SSL_TLSv1_1|NGX_SSL_TLSv1_2)); |
6115 | 1483 |
1484 ngx_conf_merge_str_value(conf->ssl_ciphers, prev->ssl_ciphers, "DEFAULT"); | |
1485 | |
1486 ngx_conf_merge_str_value(conf->ssl_name, prev->ssl_name, ""); | |
1487 | |
1488 ngx_conf_merge_value(conf->ssl_server_name, prev->ssl_server_name, 0); | |
1489 | |
1490 ngx_conf_merge_value(conf->ssl_verify, prev->ssl_verify, 0); | |
1491 | |
1492 ngx_conf_merge_uint_value(conf->ssl_verify_depth, | |
1493 prev->ssl_verify_depth, 1); | |
1494 | |
1495 ngx_conf_merge_str_value(conf->ssl_trusted_certificate, | |
1496 prev->ssl_trusted_certificate, ""); | |
1497 | |
1498 ngx_conf_merge_str_value(conf->ssl_crl, prev->ssl_crl, ""); | |
1499 | |
1500 ngx_conf_merge_str_value(conf->ssl_certificate, | |
1501 prev->ssl_certificate, ""); | |
1502 | |
1503 ngx_conf_merge_str_value(conf->ssl_certificate_key, | |
1504 prev->ssl_certificate_key, ""); | |
1505 | |
1506 ngx_conf_merge_ptr_value(conf->ssl_passwords, prev->ssl_passwords, NULL); | |
1507 | |
1508 if (conf->ssl_enable && ngx_stream_proxy_set_ssl(cf, conf) != NGX_OK) { | |
1509 return NGX_CONF_ERROR; | |
1510 } | |
1511 | |
1512 #endif | |
1513 | |
1514 return NGX_CONF_OK; | |
1515 } | |
1516 | |
1517 | |
1518 #if (NGX_STREAM_SSL) | |
1519 | |
1520 static ngx_int_t | |
1521 ngx_stream_proxy_set_ssl(ngx_conf_t *cf, ngx_stream_proxy_srv_conf_t *pscf) | |
1522 { | |
1523 ngx_pool_cleanup_t *cln; | |
1524 | |
1525 pscf->ssl = ngx_pcalloc(cf->pool, sizeof(ngx_ssl_t)); | |
1526 if (pscf->ssl == NULL) { | |
1527 return NGX_ERROR; | |
1528 } | |
1529 | |
1530 pscf->ssl->log = cf->log; | |
1531 | |
1532 if (ngx_ssl_create(pscf->ssl, pscf->ssl_protocols, NULL) != NGX_OK) { | |
1533 return NGX_ERROR; | |
1534 } | |
1535 | |
1536 cln = ngx_pool_cleanup_add(cf->pool, 0); | |
1537 if (cln == NULL) { | |
1538 return NGX_ERROR; | |
1539 } | |
1540 | |
1541 cln->handler = ngx_ssl_cleanup_ctx; | |
1542 cln->data = pscf->ssl; | |
1543 | |
1544 if (pscf->ssl_certificate.len) { | |
1545 | |
1546 if (pscf->ssl_certificate_key.len == 0) { | |
1547 ngx_log_error(NGX_LOG_EMERG, cf->log, 0, | |
1548 "no \"proxy_ssl_certificate_key\" is defined " | |
1549 "for certificate \"%V\"", &pscf->ssl_certificate); | |
1550 return NGX_ERROR; | |
1551 } | |
1552 | |
1553 if (ngx_ssl_certificate(cf, pscf->ssl, &pscf->ssl_certificate, | |
1554 &pscf->ssl_certificate_key, pscf->ssl_passwords) | |
1555 != NGX_OK) | |
1556 { | |
1557 return NGX_ERROR; | |
1558 } | |
1559 } | |
1560 | |
1561 if (SSL_CTX_set_cipher_list(pscf->ssl->ctx, | |
1562 (const char *) pscf->ssl_ciphers.data) | |
1563 == 0) | |
1564 { | |
1565 ngx_ssl_error(NGX_LOG_EMERG, cf->log, 0, | |
1566 "SSL_CTX_set_cipher_list(\"%V\") failed", | |
1567 &pscf->ssl_ciphers); | |
1568 return NGX_ERROR; | |
1569 } | |
1570 | |
1571 if (pscf->ssl_verify) { | |
1572 if (pscf->ssl_trusted_certificate.len == 0) { | |
1573 ngx_log_error(NGX_LOG_EMERG, cf->log, 0, | |
1574 "no proxy_ssl_trusted_certificate for proxy_ssl_verify"); | |
1575 return NGX_ERROR; | |
1576 } | |
1577 | |
1578 if (ngx_ssl_trusted_certificate(cf, pscf->ssl, | |
1579 &pscf->ssl_trusted_certificate, | |
1580 pscf->ssl_verify_depth) | |
1581 != NGX_OK) | |
1582 { | |
1583 return NGX_ERROR; | |
1584 } | |
1585 | |
1586 if (ngx_ssl_crl(cf, pscf->ssl, &pscf->ssl_crl) != NGX_OK) { | |
1587 return NGX_ERROR; | |
1588 } | |
1589 } | |
1590 | |
1591 return NGX_OK; | |
1592 } | |
1593 | |
1594 #endif | |
1595 | |
1596 | |
1597 static char * | |
1598 ngx_stream_proxy_pass(ngx_conf_t *cf, ngx_command_t *cmd, void *conf) | |
1599 { | |
1600 ngx_stream_proxy_srv_conf_t *pscf = conf; | |
1601 | |
1602 ngx_url_t u; | |
1603 ngx_str_t *value, *url; | |
1604 ngx_stream_core_srv_conf_t *cscf; | |
1605 | |
1606 if (pscf->upstream) { | |
1607 return "is duplicate"; | |
1608 } | |
1609 | |
1610 cscf = ngx_stream_conf_get_module_srv_conf(cf, ngx_stream_core_module); | |
1611 | |
1612 cscf->handler = ngx_stream_proxy_handler; | |
1613 | |
1614 value = cf->args->elts; | |
1615 | |
1616 url = &value[1]; | |
1617 | |
1618 ngx_memzero(&u, sizeof(ngx_url_t)); | |
1619 | |
1620 u.url = *url; | |
1621 u.no_resolve = 1; | |
1622 | |
1623 pscf->upstream = ngx_stream_upstream_add(cf, &u, 0); | |
1624 if (pscf->upstream == NULL) { | |
1625 return NGX_CONF_ERROR; | |
1626 } | |
1627 | |
1628 return NGX_CONF_OK; | |
1629 } | |
6183
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1630 |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1631 |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1632 static char * |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1633 ngx_stream_proxy_bind(ngx_conf_t *cf, ngx_command_t *cmd, void *conf) |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1634 { |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1635 ngx_stream_proxy_srv_conf_t *pscf = conf; |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1636 |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1637 ngx_int_t rc; |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1638 ngx_str_t *value; |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1639 |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1640 if (pscf->local != NGX_CONF_UNSET_PTR) { |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1641 return "is duplicate"; |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1642 } |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1643 |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1644 value = cf->args->elts; |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1645 |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1646 if (ngx_strcmp(value[1].data, "off") == 0) { |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1647 pscf->local = NULL; |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1648 return NGX_CONF_OK; |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1649 } |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1650 |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1651 pscf->local = ngx_palloc(cf->pool, sizeof(ngx_addr_t)); |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1652 if (pscf->local == NULL) { |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1653 return NGX_CONF_ERROR; |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1654 } |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1655 |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1656 rc = ngx_parse_addr(cf->pool, pscf->local, value[1].data, value[1].len); |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1657 |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1658 switch (rc) { |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1659 case NGX_OK: |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1660 pscf->local->name = value[1]; |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1661 return NGX_CONF_OK; |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1662 |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1663 case NGX_DECLINED: |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1664 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0, |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1665 "invalid address \"%V\"", &value[1]); |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1666 /* fall through */ |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1667 |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1668 default: |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1669 return NGX_CONF_ERROR; |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1670 } |
4dcffe43a7ea
Stream: the "proxy_bind" directive.
Vladimir Homutov <vl@nginx.com>
parents:
6174
diff
changeset
|
1671 } |