annotate src/stream/ngx_stream_handler.c @ 6679:40e8ce405859

Stream: postpone session initialization under accept mutex. Previously, it was possible that some system calls could be invoked while holding the accept mutex. This is clearly wrong as it prevents incoming connections from being accepted as quickly as possible.
author Dmitry Volyntsev <xeioex@nginx.com>
date Tue, 06 Sep 2016 21:28:13 +0300
parents 0125b151c9a5
children 7357abd1fa8c
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
6115
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
1
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
2 /*
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
3 * Copyright (C) Roman Arutyunyan
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
4 * Copyright (C) Nginx, Inc.
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
5 */
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
6
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
7
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
8 #include <ngx_config.h>
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
9 #include <ngx_core.h>
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
10 #include <ngx_event.h>
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
11 #include <ngx_stream.h>
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
12
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
13
6674
38143d1abdec Stream: the $status variable.
Roman Arutyunyan <arut@nginx.com>
parents: 6669
diff changeset
14 static void ngx_stream_close_connection(ngx_connection_t *c);
6115
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
15 static u_char *ngx_stream_log_error(ngx_log_t *log, u_char *buf, size_t len);
6679
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
16 static void ngx_stream_init_session_handler(ngx_event_t *rev);
6115
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
17 static void ngx_stream_init_session(ngx_connection_t *c);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
18
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
19 #if (NGX_STREAM_SSL)
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
20 static void ngx_stream_ssl_init_connection(ngx_ssl_t *ssl, ngx_connection_t *c);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
21 static void ngx_stream_ssl_handshake_handler(ngx_connection_t *c);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
22 #endif
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
23
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
24
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
25 void
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
26 ngx_stream_init_connection(ngx_connection_t *c)
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
27 {
6175
8807a2369b1a Stream: access module.
Vladimir Homutov <vl@nginx.com>
parents: 6129
diff changeset
28 u_char text[NGX_SOCKADDR_STRLEN];
8807a2369b1a Stream: access module.
Vladimir Homutov <vl@nginx.com>
parents: 6129
diff changeset
29 size_t len;
8807a2369b1a Stream: access module.
Vladimir Homutov <vl@nginx.com>
parents: 6129
diff changeset
30 ngx_uint_t i;
6669
164a0824ce20 Stream: the $session_time variable.
Vladimir Homutov <vl@nginx.com>
parents: 6607
diff changeset
31 ngx_time_t *tp;
6679
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
32 ngx_event_t *rev;
6175
8807a2369b1a Stream: access module.
Vladimir Homutov <vl@nginx.com>
parents: 6129
diff changeset
33 struct sockaddr *sa;
8807a2369b1a Stream: access module.
Vladimir Homutov <vl@nginx.com>
parents: 6129
diff changeset
34 ngx_stream_port_t *port;
8807a2369b1a Stream: access module.
Vladimir Homutov <vl@nginx.com>
parents: 6129
diff changeset
35 struct sockaddr_in *sin;
8807a2369b1a Stream: access module.
Vladimir Homutov <vl@nginx.com>
parents: 6129
diff changeset
36 ngx_stream_in_addr_t *addr;
8807a2369b1a Stream: access module.
Vladimir Homutov <vl@nginx.com>
parents: 6129
diff changeset
37 ngx_stream_session_t *s;
8807a2369b1a Stream: access module.
Vladimir Homutov <vl@nginx.com>
parents: 6129
diff changeset
38 ngx_stream_addr_conf_t *addr_conf;
6115
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
39 #if (NGX_HAVE_INET6)
6175
8807a2369b1a Stream: access module.
Vladimir Homutov <vl@nginx.com>
parents: 6129
diff changeset
40 struct sockaddr_in6 *sin6;
8807a2369b1a Stream: access module.
Vladimir Homutov <vl@nginx.com>
parents: 6129
diff changeset
41 ngx_stream_in6_addr_t *addr6;
6115
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
42 #endif
6175
8807a2369b1a Stream: access module.
Vladimir Homutov <vl@nginx.com>
parents: 6129
diff changeset
43 ngx_stream_core_srv_conf_t *cscf;
8807a2369b1a Stream: access module.
Vladimir Homutov <vl@nginx.com>
parents: 6129
diff changeset
44 ngx_stream_core_main_conf_t *cmcf;
6115
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
45
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
46 /* find the server configuration for the address:port */
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
47
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
48 port = c->listening->servers;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
49
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
50 if (port->naddrs > 1) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
51
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
52 /*
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
53 * There are several addresses on this port and one of them
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
54 * is the "*:port" wildcard so getsockname() is needed to determine
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
55 * the server address.
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
56 *
6436
8f038068f4bc Stream: UDP proxy.
Roman Arutyunyan <arut@nginx.com>
parents: 6223
diff changeset
57 * AcceptEx() and recvmsg() already gave this address.
6115
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
58 */
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
59
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
60 if (ngx_connection_local_sockaddr(c, NULL, 0) != NGX_OK) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
61 ngx_stream_close_connection(c);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
62 return;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
63 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
64
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
65 sa = c->local_sockaddr;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
66
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
67 switch (sa->sa_family) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
68
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
69 #if (NGX_HAVE_INET6)
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
70 case AF_INET6:
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
71 sin6 = (struct sockaddr_in6 *) sa;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
72
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
73 addr6 = port->addrs;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
74
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
75 /* the last address is "*" */
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
76
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
77 for (i = 0; i < port->naddrs - 1; i++) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
78 if (ngx_memcmp(&addr6[i].addr6, &sin6->sin6_addr, 16) == 0) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
79 break;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
80 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
81 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
82
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
83 addr_conf = &addr6[i].conf;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
84
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
85 break;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
86 #endif
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
87
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
88 default: /* AF_INET */
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
89 sin = (struct sockaddr_in *) sa;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
90
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
91 addr = port->addrs;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
92
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
93 /* the last address is "*" */
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
94
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
95 for (i = 0; i < port->naddrs - 1; i++) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
96 if (addr[i].addr == sin->sin_addr.s_addr) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
97 break;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
98 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
99 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
100
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
101 addr_conf = &addr[i].conf;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
102
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
103 break;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
104 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
105
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
106 } else {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
107 switch (c->local_sockaddr->sa_family) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
108
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
109 #if (NGX_HAVE_INET6)
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
110 case AF_INET6:
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
111 addr6 = port->addrs;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
112 addr_conf = &addr6[0].conf;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
113 break;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
114 #endif
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
115
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
116 default: /* AF_INET */
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
117 addr = port->addrs;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
118 addr_conf = &addr[0].conf;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
119 break;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
120 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
121 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
122
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
123 s = ngx_pcalloc(c->pool, sizeof(ngx_stream_session_t));
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
124 if (s == NULL) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
125 ngx_stream_close_connection(c);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
126 return;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
127 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
128
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
129 s->signature = NGX_STREAM_MODULE;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
130 s->main_conf = addr_conf->ctx->main_conf;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
131 s->srv_conf = addr_conf->ctx->srv_conf;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
132
6679
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
133 #if (NGX_STREAM_SSL)
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
134 s->ssl = addr_conf->ssl;
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
135 #endif
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
136
6115
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
137 s->connection = c;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
138 c->data = s;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
139
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
140 cscf = ngx_stream_get_module_srv_conf(s, ngx_stream_core_module);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
141
6129
187aa751ad62 Core: the ngx_set_connection_log() macro.
Vladimir Homutov <vl@nginx.com>
parents: 6115
diff changeset
142 ngx_set_connection_log(c, cscf->error_log);
6115
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
143
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
144 len = ngx_sock_ntop(c->sockaddr, c->socklen, text, NGX_SOCKADDR_STRLEN, 1);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
145
6461
a01e315b3a78 Stream: additional logging for UDP.
Vladimir Homutov <vl@nginx.com>
parents: 6436
diff changeset
146 ngx_log_error(NGX_LOG_INFO, c->log, 0, "*%uA %sclient %*s connected to %V",
a01e315b3a78 Stream: additional logging for UDP.
Vladimir Homutov <vl@nginx.com>
parents: 6436
diff changeset
147 c->number, c->type == SOCK_DGRAM ? "udp " : "",
a01e315b3a78 Stream: additional logging for UDP.
Vladimir Homutov <vl@nginx.com>
parents: 6436
diff changeset
148 len, text, &addr_conf->addr_text);
6115
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
149
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
150 c->log->connection = c->number;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
151 c->log->handler = ngx_stream_log_error;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
152 c->log->data = s;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
153 c->log->action = "initializing connection";
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
154 c->log_error = NGX_ERROR_INFO;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
155
6175
8807a2369b1a Stream: access module.
Vladimir Homutov <vl@nginx.com>
parents: 6129
diff changeset
156 cmcf = ngx_stream_get_module_main_conf(s, ngx_stream_core_module);
8807a2369b1a Stream: access module.
Vladimir Homutov <vl@nginx.com>
parents: 6129
diff changeset
157
6607
c70b7f4537e1 Stream: variables and script.
Vladimir Homutov <vl@nginx.com>
parents: 6461
diff changeset
158 s->variables = ngx_pcalloc(s->connection->pool,
c70b7f4537e1 Stream: variables and script.
Vladimir Homutov <vl@nginx.com>
parents: 6461
diff changeset
159 cmcf->variables.nelts
c70b7f4537e1 Stream: variables and script.
Vladimir Homutov <vl@nginx.com>
parents: 6461
diff changeset
160 * sizeof(ngx_stream_variable_value_t));
c70b7f4537e1 Stream: variables and script.
Vladimir Homutov <vl@nginx.com>
parents: 6461
diff changeset
161
c70b7f4537e1 Stream: variables and script.
Vladimir Homutov <vl@nginx.com>
parents: 6461
diff changeset
162 if (s->variables == NULL) {
c70b7f4537e1 Stream: variables and script.
Vladimir Homutov <vl@nginx.com>
parents: 6461
diff changeset
163 ngx_stream_close_connection(c);
c70b7f4537e1 Stream: variables and script.
Vladimir Homutov <vl@nginx.com>
parents: 6461
diff changeset
164 return;
c70b7f4537e1 Stream: variables and script.
Vladimir Homutov <vl@nginx.com>
parents: 6461
diff changeset
165 }
c70b7f4537e1 Stream: variables and script.
Vladimir Homutov <vl@nginx.com>
parents: 6461
diff changeset
166
6669
164a0824ce20 Stream: the $session_time variable.
Vladimir Homutov <vl@nginx.com>
parents: 6607
diff changeset
167 tp = ngx_timeofday();
164a0824ce20 Stream: the $session_time variable.
Vladimir Homutov <vl@nginx.com>
parents: 6607
diff changeset
168 s->start_sec = tp->sec;
164a0824ce20 Stream: the $session_time variable.
Vladimir Homutov <vl@nginx.com>
parents: 6607
diff changeset
169 s->start_msec = tp->msec;
164a0824ce20 Stream: the $session_time variable.
Vladimir Homutov <vl@nginx.com>
parents: 6607
diff changeset
170
6679
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
171 rev = c->read;
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
172 rev->handler = ngx_stream_init_session_handler;
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
173
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
174 if (ngx_use_accept_mutex) {
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
175 ngx_post_event(rev, &ngx_posted_events);
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
176 return;
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
177 }
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
178
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
179 rev->handler(rev);
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
180 }
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
181
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
182
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
183 static void
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
184 ngx_stream_init_session_handler(ngx_event_t *rev)
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
185 {
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
186 int tcp_nodelay;
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
187 ngx_int_t rc;
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
188 ngx_connection_t *c;
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
189 ngx_stream_session_t *s;
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
190 ngx_stream_core_srv_conf_t *cscf;
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
191 ngx_stream_core_main_conf_t *cmcf;
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
192
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
193 c = rev->data;
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
194 s = c->data;
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
195
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
196 c->log->action = "initializing session";
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
197
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
198 cmcf = ngx_stream_get_module_main_conf(s, ngx_stream_core_module);
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
199
6197
0dcef374b8bb Stream: connection limiting module.
Vladimir Homutov <vl@nginx.com>
parents: 6175
diff changeset
200 if (cmcf->limit_conn_handler) {
0dcef374b8bb Stream: connection limiting module.
Vladimir Homutov <vl@nginx.com>
parents: 6175
diff changeset
201 rc = cmcf->limit_conn_handler(s);
0dcef374b8bb Stream: connection limiting module.
Vladimir Homutov <vl@nginx.com>
parents: 6175
diff changeset
202
6674
38143d1abdec Stream: the $status variable.
Roman Arutyunyan <arut@nginx.com>
parents: 6669
diff changeset
203 if (rc == NGX_ERROR) {
38143d1abdec Stream: the $status variable.
Roman Arutyunyan <arut@nginx.com>
parents: 6669
diff changeset
204 ngx_stream_finalize_session(s, NGX_STREAM_INTERNAL_SERVER_ERROR);
38143d1abdec Stream: the $status variable.
Roman Arutyunyan <arut@nginx.com>
parents: 6669
diff changeset
205 return;
38143d1abdec Stream: the $status variable.
Roman Arutyunyan <arut@nginx.com>
parents: 6669
diff changeset
206 }
38143d1abdec Stream: the $status variable.
Roman Arutyunyan <arut@nginx.com>
parents: 6669
diff changeset
207
38143d1abdec Stream: the $status variable.
Roman Arutyunyan <arut@nginx.com>
parents: 6669
diff changeset
208 if (rc == NGX_ABORT) {
38143d1abdec Stream: the $status variable.
Roman Arutyunyan <arut@nginx.com>
parents: 6669
diff changeset
209 ngx_stream_finalize_session(s, NGX_STREAM_SERVICE_UNAVAILABLE);
6197
0dcef374b8bb Stream: connection limiting module.
Vladimir Homutov <vl@nginx.com>
parents: 6175
diff changeset
210 return;
0dcef374b8bb Stream: connection limiting module.
Vladimir Homutov <vl@nginx.com>
parents: 6175
diff changeset
211 }
0dcef374b8bb Stream: connection limiting module.
Vladimir Homutov <vl@nginx.com>
parents: 6175
diff changeset
212 }
0dcef374b8bb Stream: connection limiting module.
Vladimir Homutov <vl@nginx.com>
parents: 6175
diff changeset
213
6175
8807a2369b1a Stream: access module.
Vladimir Homutov <vl@nginx.com>
parents: 6129
diff changeset
214 if (cmcf->access_handler) {
8807a2369b1a Stream: access module.
Vladimir Homutov <vl@nginx.com>
parents: 6129
diff changeset
215 rc = cmcf->access_handler(s);
8807a2369b1a Stream: access module.
Vladimir Homutov <vl@nginx.com>
parents: 6129
diff changeset
216
6674
38143d1abdec Stream: the $status variable.
Roman Arutyunyan <arut@nginx.com>
parents: 6669
diff changeset
217 if (rc == NGX_ERROR) {
38143d1abdec Stream: the $status variable.
Roman Arutyunyan <arut@nginx.com>
parents: 6669
diff changeset
218 ngx_stream_finalize_session(s, NGX_STREAM_INTERNAL_SERVER_ERROR);
38143d1abdec Stream: the $status variable.
Roman Arutyunyan <arut@nginx.com>
parents: 6669
diff changeset
219 return;
38143d1abdec Stream: the $status variable.
Roman Arutyunyan <arut@nginx.com>
parents: 6669
diff changeset
220 }
38143d1abdec Stream: the $status variable.
Roman Arutyunyan <arut@nginx.com>
parents: 6669
diff changeset
221
38143d1abdec Stream: the $status variable.
Roman Arutyunyan <arut@nginx.com>
parents: 6669
diff changeset
222 if (rc == NGX_ABORT) {
38143d1abdec Stream: the $status variable.
Roman Arutyunyan <arut@nginx.com>
parents: 6669
diff changeset
223 ngx_stream_finalize_session(s, NGX_STREAM_FORBIDDEN);
6175
8807a2369b1a Stream: access module.
Vladimir Homutov <vl@nginx.com>
parents: 6129
diff changeset
224 return;
8807a2369b1a Stream: access module.
Vladimir Homutov <vl@nginx.com>
parents: 6129
diff changeset
225 }
8807a2369b1a Stream: access module.
Vladimir Homutov <vl@nginx.com>
parents: 6129
diff changeset
226 }
8807a2369b1a Stream: access module.
Vladimir Homutov <vl@nginx.com>
parents: 6129
diff changeset
227
6679
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
228 cscf = ngx_stream_get_module_srv_conf(s, ngx_stream_core_module);
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
229
6436
8f038068f4bc Stream: UDP proxy.
Roman Arutyunyan <arut@nginx.com>
parents: 6223
diff changeset
230 if (c->type == SOCK_STREAM
8f038068f4bc Stream: UDP proxy.
Roman Arutyunyan <arut@nginx.com>
parents: 6223
diff changeset
231 && cscf->tcp_nodelay
8f038068f4bc Stream: UDP proxy.
Roman Arutyunyan <arut@nginx.com>
parents: 6223
diff changeset
232 && c->tcp_nodelay == NGX_TCP_NODELAY_UNSET)
8f038068f4bc Stream: UDP proxy.
Roman Arutyunyan <arut@nginx.com>
parents: 6223
diff changeset
233 {
6221
7565e056fad6 Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents: 6197
diff changeset
234 ngx_log_debug0(NGX_LOG_DEBUG_STREAM, c->log, 0, "tcp_nodelay");
7565e056fad6 Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents: 6197
diff changeset
235
7565e056fad6 Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents: 6197
diff changeset
236 tcp_nodelay = 1;
7565e056fad6 Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents: 6197
diff changeset
237
7565e056fad6 Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents: 6197
diff changeset
238 if (setsockopt(c->fd, IPPROTO_TCP, TCP_NODELAY,
7565e056fad6 Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents: 6197
diff changeset
239 (const void *) &tcp_nodelay, sizeof(int)) == -1)
7565e056fad6 Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents: 6197
diff changeset
240 {
7565e056fad6 Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents: 6197
diff changeset
241 ngx_connection_error(c, ngx_socket_errno,
7565e056fad6 Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents: 6197
diff changeset
242 "setsockopt(TCP_NODELAY) failed");
6674
38143d1abdec Stream: the $status variable.
Roman Arutyunyan <arut@nginx.com>
parents: 6669
diff changeset
243 ngx_stream_finalize_session(s, NGX_STREAM_INTERNAL_SERVER_ERROR);
6221
7565e056fad6 Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents: 6197
diff changeset
244 return;
7565e056fad6 Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents: 6197
diff changeset
245 }
7565e056fad6 Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents: 6197
diff changeset
246
7565e056fad6 Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents: 6197
diff changeset
247 c->tcp_nodelay = NGX_TCP_NODELAY_SET;
7565e056fad6 Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents: 6197
diff changeset
248 }
7565e056fad6 Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents: 6197
diff changeset
249
7565e056fad6 Stream: the "tcp_nodelay" directive.
Vladimir Homutov <vl@nginx.com>
parents: 6197
diff changeset
250
6115
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
251 #if (NGX_STREAM_SSL)
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
252 {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
253 ngx_stream_ssl_conf_t *sslcf;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
254
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
255 sslcf = ngx_stream_get_module_srv_conf(s, ngx_stream_ssl_module);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
256
6679
40e8ce405859 Stream: postpone session initialization under accept mutex.
Dmitry Volyntsev <xeioex@nginx.com>
parents: 6678
diff changeset
257 if (s->ssl) {
6115
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
258 c->log->action = "SSL handshaking";
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
259
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
260 if (sslcf->ssl.ctx == NULL) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
261 ngx_log_error(NGX_LOG_ERR, c->log, 0,
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
262 "no \"ssl_certificate\" is defined "
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
263 "in server listening on SSL port");
6674
38143d1abdec Stream: the $status variable.
Roman Arutyunyan <arut@nginx.com>
parents: 6669
diff changeset
264 ngx_stream_finalize_session(s, NGX_STREAM_INTERNAL_SERVER_ERROR);
6115
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
265 return;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
266 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
267
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
268 ngx_stream_ssl_init_connection(&sslcf->ssl, c);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
269 return;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
270 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
271 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
272 #endif
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
273
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
274 ngx_stream_init_session(c);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
275 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
276
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
277
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
278 static void
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
279 ngx_stream_init_session(ngx_connection_t *c)
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
280 {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
281 ngx_stream_session_t *s;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
282 ngx_stream_core_srv_conf_t *cscf;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
283
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
284 s = c->data;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
285 c->log->action = "handling client connection";
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
286
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
287 cscf = ngx_stream_get_module_srv_conf(s, ngx_stream_core_module);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
288
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
289 s->ctx = ngx_pcalloc(c->pool, sizeof(void *) * ngx_stream_max_module);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
290 if (s->ctx == NULL) {
6674
38143d1abdec Stream: the $status variable.
Roman Arutyunyan <arut@nginx.com>
parents: 6669
diff changeset
291 ngx_stream_finalize_session(s, NGX_STREAM_INTERNAL_SERVER_ERROR);
6115
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
292 return;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
293 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
294
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
295 cscf->handler(s);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
296 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
297
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
298
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
299 #if (NGX_STREAM_SSL)
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
300
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
301 static void
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
302 ngx_stream_ssl_init_connection(ngx_ssl_t *ssl, ngx_connection_t *c)
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
303 {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
304 ngx_stream_session_t *s;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
305 ngx_stream_ssl_conf_t *sslcf;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
306
6674
38143d1abdec Stream: the $status variable.
Roman Arutyunyan <arut@nginx.com>
parents: 6669
diff changeset
307 s = c->data;
38143d1abdec Stream: the $status variable.
Roman Arutyunyan <arut@nginx.com>
parents: 6669
diff changeset
308
6115
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
309 if (ngx_ssl_create_connection(ssl, c, 0) == NGX_ERROR) {
6674
38143d1abdec Stream: the $status variable.
Roman Arutyunyan <arut@nginx.com>
parents: 6669
diff changeset
310 ngx_stream_finalize_session(s, NGX_STREAM_INTERNAL_SERVER_ERROR);
6115
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
311 return;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
312 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
313
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
314 if (ngx_ssl_handshake(c) == NGX_AGAIN) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
315 sslcf = ngx_stream_get_module_srv_conf(s, ngx_stream_ssl_module);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
316
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
317 ngx_add_timer(c->read, sslcf->handshake_timeout);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
318
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
319 c->ssl->handler = ngx_stream_ssl_handshake_handler;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
320
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
321 return;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
322 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
323
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
324 ngx_stream_ssl_handshake_handler(c);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
325 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
326
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
327
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
328 static void
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
329 ngx_stream_ssl_handshake_handler(ngx_connection_t *c)
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
330 {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
331 if (!c->ssl->handshaked) {
6674
38143d1abdec Stream: the $status variable.
Roman Arutyunyan <arut@nginx.com>
parents: 6669
diff changeset
332 ngx_stream_finalize_session(c->data, NGX_STREAM_INTERNAL_SERVER_ERROR);
6115
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
333 return;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
334 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
335
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
336 if (c->read->timer_set) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
337 ngx_del_timer(c->read);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
338 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
339
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
340 ngx_stream_init_session(c);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
341 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
342
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
343 #endif
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
344
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
345
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
346 void
6674
38143d1abdec Stream: the $status variable.
Roman Arutyunyan <arut@nginx.com>
parents: 6669
diff changeset
347 ngx_stream_finalize_session(ngx_stream_session_t *s, ngx_uint_t rc)
38143d1abdec Stream: the $status variable.
Roman Arutyunyan <arut@nginx.com>
parents: 6669
diff changeset
348 {
6678
0125b151c9a5 Stream: log module.
Vladimir Homutov <vl@nginx.com>
parents: 6674
diff changeset
349 ngx_stream_core_main_conf_t *cmcf;
0125b151c9a5 Stream: log module.
Vladimir Homutov <vl@nginx.com>
parents: 6674
diff changeset
350
6674
38143d1abdec Stream: the $status variable.
Roman Arutyunyan <arut@nginx.com>
parents: 6669
diff changeset
351 ngx_log_debug1(NGX_LOG_DEBUG_STREAM, s->connection->log, 0,
38143d1abdec Stream: the $status variable.
Roman Arutyunyan <arut@nginx.com>
parents: 6669
diff changeset
352 "finalize stream session: %i", rc);
38143d1abdec Stream: the $status variable.
Roman Arutyunyan <arut@nginx.com>
parents: 6669
diff changeset
353
38143d1abdec Stream: the $status variable.
Roman Arutyunyan <arut@nginx.com>
parents: 6669
diff changeset
354 s->status = rc;
38143d1abdec Stream: the $status variable.
Roman Arutyunyan <arut@nginx.com>
parents: 6669
diff changeset
355
6678
0125b151c9a5 Stream: log module.
Vladimir Homutov <vl@nginx.com>
parents: 6674
diff changeset
356 cmcf = ngx_stream_get_module_main_conf(s, ngx_stream_core_module);
0125b151c9a5 Stream: log module.
Vladimir Homutov <vl@nginx.com>
parents: 6674
diff changeset
357
0125b151c9a5 Stream: log module.
Vladimir Homutov <vl@nginx.com>
parents: 6674
diff changeset
358 if (cmcf->access_log_handler) {
0125b151c9a5 Stream: log module.
Vladimir Homutov <vl@nginx.com>
parents: 6674
diff changeset
359 (void) cmcf->access_log_handler(s);
0125b151c9a5 Stream: log module.
Vladimir Homutov <vl@nginx.com>
parents: 6674
diff changeset
360 }
0125b151c9a5 Stream: log module.
Vladimir Homutov <vl@nginx.com>
parents: 6674
diff changeset
361
6674
38143d1abdec Stream: the $status variable.
Roman Arutyunyan <arut@nginx.com>
parents: 6669
diff changeset
362 ngx_stream_close_connection(s->connection);
38143d1abdec Stream: the $status variable.
Roman Arutyunyan <arut@nginx.com>
parents: 6669
diff changeset
363 }
38143d1abdec Stream: the $status variable.
Roman Arutyunyan <arut@nginx.com>
parents: 6669
diff changeset
364
38143d1abdec Stream: the $status variable.
Roman Arutyunyan <arut@nginx.com>
parents: 6669
diff changeset
365
38143d1abdec Stream: the $status variable.
Roman Arutyunyan <arut@nginx.com>
parents: 6669
diff changeset
366 static void
6115
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
367 ngx_stream_close_connection(ngx_connection_t *c)
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
368 {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
369 ngx_pool_t *pool;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
370
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
371 ngx_log_debug1(NGX_LOG_DEBUG_STREAM, c->log, 0,
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
372 "close stream connection: %d", c->fd);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
373
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
374 #if (NGX_STREAM_SSL)
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
375
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
376 if (c->ssl) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
377 if (ngx_ssl_shutdown(c) == NGX_AGAIN) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
378 c->ssl->handler = ngx_stream_close_connection;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
379 return;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
380 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
381 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
382
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
383 #endif
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
384
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
385 #if (NGX_STAT_STUB)
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
386 (void) ngx_atomic_fetch_add(ngx_stat_active, -1);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
387 #endif
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
388
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
389 pool = c->pool;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
390
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
391 ngx_close_connection(c);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
392
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
393 ngx_destroy_pool(pool);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
394 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
395
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
396
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
397 static u_char *
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
398 ngx_stream_log_error(ngx_log_t *log, u_char *buf, size_t len)
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
399 {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
400 u_char *p;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
401 ngx_stream_session_t *s;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
402
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
403 if (log->action) {
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
404 p = ngx_snprintf(buf, len, " while %s", log->action);
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
405 len -= p - buf;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
406 buf = p;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
407 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
408
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
409 s = log->data;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
410
6461
a01e315b3a78 Stream: additional logging for UDP.
Vladimir Homutov <vl@nginx.com>
parents: 6436
diff changeset
411 p = ngx_snprintf(buf, len, ", %sclient: %V, server: %V",
a01e315b3a78 Stream: additional logging for UDP.
Vladimir Homutov <vl@nginx.com>
parents: 6436
diff changeset
412 s->connection->type == SOCK_DGRAM ? "udp " : "",
6115
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
413 &s->connection->addr_text,
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
414 &s->connection->listening->addr_text);
6223
d1f94042c29c Stream: fixed potential error log buffer overrun.
Vladimir Homutov <vl@nginx.com>
parents: 6221
diff changeset
415 len -= p - buf;
d1f94042c29c Stream: fixed potential error log buffer overrun.
Vladimir Homutov <vl@nginx.com>
parents: 6221
diff changeset
416 buf = p;
6115
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
417
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
418 if (s->log_handler) {
6223
d1f94042c29c Stream: fixed potential error log buffer overrun.
Vladimir Homutov <vl@nginx.com>
parents: 6221
diff changeset
419 p = s->log_handler(log, buf, len);
6115
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
420 }
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
421
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
422 return p;
61d7ae76647d Stream: port from NGINX+.
Ruslan Ermilov <ru@nginx.com>
parents:
diff changeset
423 }