Mercurial > hg > nginx-quic
annotate src/event/modules/ngx_eventport_module.c @ 4192:61e4af19df9f
Autoindex: escape '?' in file names.
For files with '?' in their names autoindex generated links with '?' not
escaped. This resulted in effectively truncated links as '?' indicates
query string start.
This is an updated version of the patch originally posted at [1]. It
introduces generic NGX_ESCAPE_URI_COMPONENT which escapes everything but
unreserved characters as per RFC 3986. This approach also renders unneeded
special colon processing (as colon is percent-encoded now), it's dropped
accordingly.
[1] http://nginx.org/pipermail/nginx-devel/2010-February/000112.html
Reported by Konstantin Leonov.
author | Maxim Dounin <mdounin@mdounin.ru> |
---|---|
date | Tue, 11 Oct 2011 17:56:51 +0000 |
parents | ab353d7dc182 |
children | d620f497c50f |
rev | line source |
---|---|
719 | 1 |
2 /* | |
3 * Copyright (C) Igor Sysoev | |
4 */ | |
5 | |
6 | |
7 #include <ngx_config.h> | |
8 #include <ngx_core.h> | |
9 #include <ngx_event.h> | |
10 | |
11 | |
12 #if (NGX_TEST_BUILD_EVENTPORT) | |
13 | |
14 #define ushort_t u_short | |
15 #define uint_t u_int | |
16 | |
17 /* Solaris declarations */ | |
18 | |
19 #define PORT_SOURCE_AIO 1 | |
20 #define PORT_SOURCE_TIMER 2 | |
21 #define PORT_SOURCE_USER 3 | |
22 #define PORT_SOURCE_FD 4 | |
23 #define PORT_SOURCE_ALERT 5 | |
24 #define PORT_SOURCE_MQ 6 | |
25 | |
26 #define ETIME 64 | |
27 | |
28 #define SIGEV_PORT 4 | |
29 | |
30 typedef struct { | |
31 int portev_events; /* event data is source specific */ | |
32 ushort_t portev_source; /* event source */ | |
33 ushort_t portev_pad; /* port internal use */ | |
34 uintptr_t portev_object; /* source specific object */ | |
35 void *portev_user; /* user cookie */ | |
36 } port_event_t; | |
37 | |
38 typedef struct port_notify { | |
39 int portnfy_port; /* bind request(s) to port */ | |
40 void *portnfy_user; /* user defined */ | |
41 } port_notify_t; | |
42 | |
1939
6e7daf852eec
restore building --test-build-rtsig and --test-build-eventport on FreeBSD 6
Igor Sysoev <igor@sysoev.ru>
parents:
1870
diff
changeset
|
43 #if (__FreeBSD_version < 700005) |
6e7daf852eec
restore building --test-build-rtsig and --test-build-eventport on FreeBSD 6
Igor Sysoev <igor@sysoev.ru>
parents:
1870
diff
changeset
|
44 |
6e7daf852eec
restore building --test-build-rtsig and --test-build-eventport on FreeBSD 6
Igor Sysoev <igor@sysoev.ru>
parents:
1870
diff
changeset
|
45 typedef struct itimerspec { /* definition per POSIX.4 */ |
6e7daf852eec
restore building --test-build-rtsig and --test-build-eventport on FreeBSD 6
Igor Sysoev <igor@sysoev.ru>
parents:
1870
diff
changeset
|
46 struct timespec it_interval;/* timer period */ |
6e7daf852eec
restore building --test-build-rtsig and --test-build-eventport on FreeBSD 6
Igor Sysoev <igor@sysoev.ru>
parents:
1870
diff
changeset
|
47 struct timespec it_value; /* timer expiration */ |
6e7daf852eec
restore building --test-build-rtsig and --test-build-eventport on FreeBSD 6
Igor Sysoev <igor@sysoev.ru>
parents:
1870
diff
changeset
|
48 } itimerspec_t; |
6e7daf852eec
restore building --test-build-rtsig and --test-build-eventport on FreeBSD 6
Igor Sysoev <igor@sysoev.ru>
parents:
1870
diff
changeset
|
49 |
6e7daf852eec
restore building --test-build-rtsig and --test-build-eventport on FreeBSD 6
Igor Sysoev <igor@sysoev.ru>
parents:
1870
diff
changeset
|
50 #endif |
6e7daf852eec
restore building --test-build-rtsig and --test-build-eventport on FreeBSD 6
Igor Sysoev <igor@sysoev.ru>
parents:
1870
diff
changeset
|
51 |
719 | 52 int port_create(void) |
53 { | |
54 return -1; | |
55 } | |
56 | |
57 int port_associate(int port, int source, uintptr_t object, int events, | |
58 void *user) | |
59 { | |
60 return -1; | |
61 } | |
62 | |
63 int port_dissociate(int port, int source, uintptr_t object) | |
64 { | |
65 return -1; | |
66 } | |
67 | |
68 int port_getn(int port, port_event_t list[], uint_t max, uint_t *nget, | |
69 struct timespec *timeout) | |
70 { | |
71 return -1; | |
72 } | |
73 | |
74 int timer_create(clockid_t clock_id, struct sigevent *evp, timer_t *timerid) | |
75 { | |
76 return -1; | |
77 } | |
78 | |
79 int timer_settime(timer_t timerid, int flags, const struct itimerspec *value, | |
80 struct itimerspec *ovalue) | |
81 { | |
82 return -1; | |
83 } | |
84 | |
85 int timer_delete(timer_t timerid) | |
86 { | |
87 return -1; | |
88 } | |
89 | |
90 #endif | |
91 | |
92 | |
93 typedef struct { | |
1354
f69d1aab6a0f
make 64-bit ngx_int_t on 64-bit platforms
Igor Sysoev <igor@sysoev.ru>
parents:
1287
diff
changeset
|
94 ngx_uint_t events; |
719 | 95 } ngx_eventport_conf_t; |
96 | |
97 | |
98 static ngx_int_t ngx_eventport_init(ngx_cycle_t *cycle, ngx_msec_t timer); | |
99 static void ngx_eventport_done(ngx_cycle_t *cycle); | |
1354
f69d1aab6a0f
make 64-bit ngx_int_t on 64-bit platforms
Igor Sysoev <igor@sysoev.ru>
parents:
1287
diff
changeset
|
100 static ngx_int_t ngx_eventport_add_event(ngx_event_t *ev, ngx_int_t event, |
f69d1aab6a0f
make 64-bit ngx_int_t on 64-bit platforms
Igor Sysoev <igor@sysoev.ru>
parents:
1287
diff
changeset
|
101 ngx_uint_t flags); |
f69d1aab6a0f
make 64-bit ngx_int_t on 64-bit platforms
Igor Sysoev <igor@sysoev.ru>
parents:
1287
diff
changeset
|
102 static ngx_int_t ngx_eventport_del_event(ngx_event_t *ev, ngx_int_t event, |
f69d1aab6a0f
make 64-bit ngx_int_t on 64-bit platforms
Igor Sysoev <igor@sysoev.ru>
parents:
1287
diff
changeset
|
103 ngx_uint_t flags); |
719 | 104 static ngx_int_t ngx_eventport_process_events(ngx_cycle_t *cycle, |
105 ngx_msec_t timer, ngx_uint_t flags); | |
106 | |
107 static void *ngx_eventport_create_conf(ngx_cycle_t *cycle); | |
108 static char *ngx_eventport_init_conf(ngx_cycle_t *cycle, void *conf); | |
109 | |
110 static int ep = -1; | |
111 static port_event_t *event_list; | |
1354
f69d1aab6a0f
make 64-bit ngx_int_t on 64-bit platforms
Igor Sysoev <igor@sysoev.ru>
parents:
1287
diff
changeset
|
112 static ngx_uint_t nevents; |
1870
a62fb6c156c5
fix building --test-build-rtsig and --test-build-eventport on FreeBSD 7
Igor Sysoev <igor@sysoev.ru>
parents:
1354
diff
changeset
|
113 static timer_t event_timer = (timer_t) -1; |
719 | 114 |
115 static ngx_str_t eventport_name = ngx_string("eventport"); | |
116 | |
117 | |
118 static ngx_command_t ngx_eventport_commands[] = { | |
119 | |
120 { ngx_string("eventport_events"), | |
121 NGX_EVENT_CONF|NGX_CONF_TAKE1, | |
122 ngx_conf_set_num_slot, | |
123 0, | |
124 offsetof(ngx_eventport_conf_t, events), | |
125 NULL }, | |
126 | |
127 ngx_null_command | |
128 }; | |
129 | |
130 | |
131 ngx_event_module_t ngx_eventport_module_ctx = { | |
132 &eventport_name, | |
133 ngx_eventport_create_conf, /* create configuration */ | |
134 ngx_eventport_init_conf, /* init configuration */ | |
135 | |
136 { | |
137 ngx_eventport_add_event, /* add an event */ | |
138 ngx_eventport_del_event, /* delete an event */ | |
139 ngx_eventport_add_event, /* enable an event */ | |
140 ngx_eventport_del_event, /* disable an event */ | |
141 NULL, /* add an connection */ | |
142 NULL, /* delete an connection */ | |
143 NULL, /* process the changes */ | |
144 ngx_eventport_process_events, /* process the events */ | |
145 ngx_eventport_init, /* init the events */ | |
146 ngx_eventport_done, /* done the events */ | |
147 } | |
148 | |
149 }; | |
150 | |
151 ngx_module_t ngx_eventport_module = { | |
152 NGX_MODULE_V1, | |
153 &ngx_eventport_module_ctx, /* module context */ | |
154 ngx_eventport_commands, /* module directives */ | |
155 NGX_EVENT_MODULE, /* module type */ | |
156 NULL, /* init master */ | |
157 NULL, /* init module */ | |
158 NULL, /* init process */ | |
159 NULL, /* init thread */ | |
160 NULL, /* exit thread */ | |
161 NULL, /* exit process */ | |
162 NULL, /* exit master */ | |
163 NGX_MODULE_V1_PADDING | |
164 }; | |
165 | |
166 | |
167 static ngx_int_t | |
168 ngx_eventport_init(ngx_cycle_t *cycle, ngx_msec_t timer) | |
169 { | |
170 port_notify_t pn; | |
171 struct itimerspec its; | |
172 struct sigevent sev; | |
173 ngx_eventport_conf_t *epcf; | |
174 | |
175 epcf = ngx_event_get_conf(cycle->conf_ctx, ngx_eventport_module); | |
176 | |
177 if (ep == -1) { | |
178 ep = port_create(); | |
179 | |
180 if (ep == -1) { | |
181 ngx_log_error(NGX_LOG_EMERG, cycle->log, ngx_errno, | |
182 "port_create() failed"); | |
183 return NGX_ERROR; | |
184 } | |
185 } | |
186 | |
187 if (nevents < epcf->events) { | |
188 if (event_list) { | |
189 ngx_free(event_list); | |
190 } | |
191 | |
192 event_list = ngx_alloc(sizeof(port_event_t) * epcf->events, | |
193 cycle->log); | |
194 if (event_list == NULL) { | |
195 return NGX_ERROR; | |
196 } | |
197 } | |
198 | |
199 ngx_event_flags = NGX_USE_EVENTPORT_EVENT; | |
200 | |
201 if (timer) { | |
202 ngx_memzero(&pn, sizeof(port_notify_t)); | |
203 pn.portnfy_port = ep; | |
204 | |
205 ngx_memzero(&sev, sizeof(struct sigevent)); | |
206 sev.sigev_notify = SIGEV_PORT; | |
207 #if !(NGX_TEST_BUILD_EVENTPORT) | |
208 sev.sigev_value.sival_ptr = &pn; | |
209 #endif | |
210 | |
211 if (timer_create(CLOCK_REALTIME, &sev, &event_timer) == -1) { | |
212 ngx_log_error(NGX_LOG_EMERG, cycle->log, ngx_errno, | |
213 "timer_create() failed"); | |
214 return NGX_ERROR; | |
215 } | |
216 | |
217 its.it_interval.tv_sec = timer / 1000; | |
218 its.it_interval.tv_nsec = (timer % 1000) * 1000000; | |
219 its.it_value.tv_sec = timer / 1000; | |
220 its.it_value.tv_nsec = (timer % 1000) * 1000000; | |
221 | |
222 if (timer_settime(event_timer, 0, &its, NULL) == -1) { | |
223 ngx_log_error(NGX_LOG_EMERG, cycle->log, ngx_errno, | |
224 "timer_settime() failed"); | |
225 return NGX_ERROR; | |
226 } | |
227 | |
228 ngx_event_flags |= NGX_USE_TIMER_EVENT; | |
229 } | |
230 | |
231 nevents = epcf->events; | |
232 | |
233 ngx_io = ngx_os_io; | |
234 | |
235 ngx_event_actions = ngx_eventport_module_ctx.actions; | |
236 | |
237 return NGX_OK; | |
238 } | |
239 | |
240 | |
241 static void | |
242 ngx_eventport_done(ngx_cycle_t *cycle) | |
243 { | |
1870
a62fb6c156c5
fix building --test-build-rtsig and --test-build-eventport on FreeBSD 7
Igor Sysoev <igor@sysoev.ru>
parents:
1354
diff
changeset
|
244 if (event_timer != (timer_t) -1) { |
719 | 245 if (timer_delete(event_timer) == -1) { |
246 ngx_log_error(NGX_LOG_ALERT, cycle->log, ngx_errno, | |
247 "timer_delete() failed"); | |
248 } | |
249 | |
1870
a62fb6c156c5
fix building --test-build-rtsig and --test-build-eventport on FreeBSD 7
Igor Sysoev <igor@sysoev.ru>
parents:
1354
diff
changeset
|
250 event_timer = (timer_t) -1; |
719 | 251 } |
252 | |
253 if (close(ep) == -1) { | |
254 ngx_log_error(NGX_LOG_ALERT, cycle->log, ngx_errno, | |
255 "close() event port failed"); | |
256 } | |
257 | |
258 ep = -1; | |
259 | |
260 ngx_free(event_list); | |
261 | |
262 event_list = NULL; | |
263 nevents = 0; | |
264 } | |
265 | |
266 | |
267 static ngx_int_t | |
1354
f69d1aab6a0f
make 64-bit ngx_int_t on 64-bit platforms
Igor Sysoev <igor@sysoev.ru>
parents:
1287
diff
changeset
|
268 ngx_eventport_add_event(ngx_event_t *ev, ngx_int_t event, ngx_uint_t flags) |
719 | 269 { |
1354
f69d1aab6a0f
make 64-bit ngx_int_t on 64-bit platforms
Igor Sysoev <igor@sysoev.ru>
parents:
1287
diff
changeset
|
270 ngx_int_t events, prev; |
719 | 271 ngx_event_t *e; |
272 ngx_connection_t *c; | |
273 | |
274 c = ev->data; | |
275 | |
276 events = event; | |
277 | |
278 if (event == NGX_READ_EVENT) { | |
279 e = c->write; | |
280 prev = POLLOUT; | |
281 #if (NGX_READ_EVENT != POLLIN) | |
282 events = POLLIN; | |
283 #endif | |
284 | |
285 } else { | |
286 e = c->read; | |
287 prev = POLLIN; | |
288 #if (NGX_WRITE_EVENT != POLLOUT) | |
289 events = POLLOUT; | |
290 #endif | |
291 } | |
292 | |
293 if (e->oneshot) { | |
294 events |= prev; | |
295 } | |
296 | |
297 ngx_log_debug2(NGX_LOG_DEBUG_EVENT, ev->log, 0, | |
1354
f69d1aab6a0f
make 64-bit ngx_int_t on 64-bit platforms
Igor Sysoev <igor@sysoev.ru>
parents:
1287
diff
changeset
|
298 "eventport add event: fd:%d ev:%04Xi", c->fd, events); |
719 | 299 |
300 if (port_associate(ep, PORT_SOURCE_FD, c->fd, events, | |
301 (void *) ((uintptr_t) ev | ev->instance)) | |
302 == -1) | |
303 { | |
304 ngx_log_error(NGX_LOG_ALERT, ev->log, ngx_errno, | |
305 "port_associate() failed"); | |
306 return NGX_ERROR; | |
307 } | |
308 | |
309 ev->active = 1; | |
310 ev->oneshot = 1; | |
311 | |
312 return NGX_OK; | |
313 } | |
314 | |
315 | |
316 static ngx_int_t | |
1354
f69d1aab6a0f
make 64-bit ngx_int_t on 64-bit platforms
Igor Sysoev <igor@sysoev.ru>
parents:
1287
diff
changeset
|
317 ngx_eventport_del_event(ngx_event_t *ev, ngx_int_t event, ngx_uint_t flags) |
719 | 318 { |
319 ngx_event_t *e; | |
320 ngx_connection_t *c; | |
321 | |
322 /* | |
323 * when the file descriptor is closed, the event port automatically | |
324 * dissociates it from the port, so we do not need to dissociate explicity | |
325 * the event before the closing the file descriptor | |
326 */ | |
327 | |
328 if (flags & NGX_CLOSE_EVENT) { | |
329 ev->active = 0; | |
330 ev->oneshot = 0; | |
331 return NGX_OK; | |
332 } | |
333 | |
334 c = ev->data; | |
335 | |
336 if (event == NGX_READ_EVENT) { | |
337 e = c->write; | |
338 event = POLLOUT; | |
339 | |
340 } else { | |
341 e = c->read; | |
342 event = POLLIN; | |
343 } | |
344 | |
345 if (e->oneshot) { | |
346 ngx_log_debug2(NGX_LOG_DEBUG_EVENT, ev->log, 0, | |
1354
f69d1aab6a0f
make 64-bit ngx_int_t on 64-bit platforms
Igor Sysoev <igor@sysoev.ru>
parents:
1287
diff
changeset
|
347 "eventport change event: fd:%d ev:%04Xi", c->fd, event); |
719 | 348 |
349 if (port_associate(ep, PORT_SOURCE_FD, c->fd, event, | |
350 (void *) ((uintptr_t) ev | ev->instance)) | |
351 == -1) | |
352 { | |
353 ngx_log_error(NGX_LOG_ALERT, ev->log, ngx_errno, | |
354 "port_associate() failed"); | |
355 return NGX_ERROR; | |
356 } | |
357 | |
358 } else { | |
359 ngx_log_debug1(NGX_LOG_DEBUG_EVENT, ev->log, 0, | |
360 "eventport del event: fd:%d", c->fd); | |
361 | |
362 if (port_dissociate(ep, PORT_SOURCE_FD, c->fd) == -1) { | |
363 ngx_log_error(NGX_LOG_ALERT, ev->log, ngx_errno, | |
364 "port_dissociate() failed"); | |
365 return NGX_ERROR; | |
366 } | |
367 } | |
368 | |
369 ev->active = 0; | |
370 ev->oneshot = 0; | |
371 | |
372 return NGX_OK; | |
373 } | |
374 | |
375 | |
376 ngx_int_t | |
377 ngx_eventport_process_events(ngx_cycle_t *cycle, ngx_msec_t timer, | |
378 ngx_uint_t flags) | |
379 { | |
380 int n, revents; | |
381 u_int events; | |
382 ngx_err_t err; | |
383 ngx_int_t instance; | |
384 ngx_uint_t i, level; | |
385 ngx_event_t *ev, *rev, *wev, **queue; | |
386 ngx_connection_t *c; | |
387 struct timespec ts, *tp; | |
388 | |
389 if (timer == NGX_TIMER_INFINITE) { | |
390 tp = NULL; | |
391 | |
392 } else { | |
393 ts.tv_sec = timer / 1000; | |
394 ts.tv_nsec = (timer % 1000) * 1000000; | |
395 tp = &ts; | |
396 } | |
397 | |
398 ngx_log_debug1(NGX_LOG_DEBUG_EVENT, cycle->log, 0, | |
399 "eventport timer: %M", timer); | |
400 | |
401 events = 1; | |
402 | |
1354
f69d1aab6a0f
make 64-bit ngx_int_t on 64-bit platforms
Igor Sysoev <igor@sysoev.ru>
parents:
1287
diff
changeset
|
403 n = port_getn(ep, event_list, (u_int) nevents, &events, tp); |
719 | 404 |
405 err = ngx_errno; | |
406 | |
407 if (flags & NGX_UPDATE_TIME) { | |
3475
ab353d7dc182
*) introduce ngx_time_sigsafe_update() to update the error log time only
Igor Sysoev <igor@sysoev.ru>
parents:
3474
diff
changeset
|
408 ngx_time_update(); |
719 | 409 } |
410 | |
411 if (n == -1) { | |
412 if (err == ETIME) { | |
413 if (timer != NGX_TIMER_INFINITE) { | |
414 return NGX_OK; | |
415 } | |
416 | |
417 ngx_log_error(NGX_LOG_ALERT, cycle->log, 0, | |
418 "port_getn() returned no events without timeout"); | |
419 return NGX_ERROR; | |
420 } | |
421 | |
422 level = (err == NGX_EINTR) ? NGX_LOG_INFO : NGX_LOG_ALERT; | |
423 ngx_log_error(level, cycle->log, err, "port_getn() failed"); | |
424 return NGX_ERROR; | |
425 } | |
426 | |
427 if (events == 0) { | |
428 if (timer != NGX_TIMER_INFINITE) { | |
429 return NGX_OK; | |
430 } | |
431 | |
432 ngx_log_error(NGX_LOG_ALERT, cycle->log, 0, | |
433 "port_getn() returned no events without timeout"); | |
434 return NGX_ERROR; | |
435 } | |
436 | |
437 ngx_mutex_lock(ngx_posted_events_mutex); | |
438 | |
439 for (i = 0; i < events; i++) { | |
440 | |
441 if (event_list[i].portev_source == PORT_SOURCE_TIMER) { | |
3475
ab353d7dc182
*) introduce ngx_time_sigsafe_update() to update the error log time only
Igor Sysoev <igor@sysoev.ru>
parents:
3474
diff
changeset
|
442 ngx_time_update(); |
719 | 443 continue; |
444 } | |
445 | |
446 ev = event_list[i].portev_user; | |
447 | |
448 switch (event_list[i].portev_source) { | |
449 | |
450 case PORT_SOURCE_FD: | |
451 | |
452 instance = (uintptr_t) ev & 1; | |
453 ev = (ngx_event_t *) ((uintptr_t) ev & (uintptr_t) ~1); | |
454 | |
455 if (ev->closed || ev->instance != instance) { | |
456 | |
457 /* | |
458 * the stale event from a file descriptor | |
459 * that was just closed in this iteration | |
460 */ | |
461 | |
462 ngx_log_debug1(NGX_LOG_DEBUG_EVENT, cycle->log, 0, | |
463 "eventport: stale event %p", ev); | |
464 continue; | |
465 } | |
466 | |
467 revents = event_list[i].portev_events; | |
468 | |
469 ngx_log_debug2(NGX_LOG_DEBUG_EVENT, cycle->log, 0, | |
470 "eventport: fd:%d, ev:%04Xd", | |
471 event_list[i].portev_object, revents); | |
472 | |
473 if (revents & (POLLERR|POLLHUP|POLLNVAL)) { | |
1128
06479b01caff
decrease log level from alert to debug for POLLERR|POLLHUP|POLLNVAL
Igor Sysoev <igor@sysoev.ru>
parents:
929
diff
changeset
|
474 ngx_log_debug2(NGX_LOG_DEBUG_EVENT, cycle->log, 0, |
06479b01caff
decrease log level from alert to debug for POLLERR|POLLHUP|POLLNVAL
Igor Sysoev <igor@sysoev.ru>
parents:
929
diff
changeset
|
475 "port_getn() error fd:%d ev:%04Xd", |
06479b01caff
decrease log level from alert to debug for POLLERR|POLLHUP|POLLNVAL
Igor Sysoev <igor@sysoev.ru>
parents:
929
diff
changeset
|
476 event_list[i].portev_object, revents); |
719 | 477 } |
478 | |
479 if (revents & ~(POLLIN|POLLOUT|POLLERR|POLLHUP|POLLNVAL)) { | |
480 ngx_log_error(NGX_LOG_ALERT, cycle->log, 0, | |
481 "strange port_getn() events fd:%d ev:%04Xd", | |
482 event_list[i].portev_object, revents); | |
483 } | |
484 | |
485 if ((revents & (POLLERR|POLLHUP|POLLNVAL)) | |
486 && (revents & (POLLIN|POLLOUT)) == 0) | |
487 { | |
488 /* | |
489 * if the error events were returned without POLLIN or POLLOUT, | |
490 * then add these flags to handle the events at least in one | |
491 * active handler | |
492 */ | |
493 | |
494 revents |= POLLIN|POLLOUT; | |
495 } | |
496 | |
497 c = ev->data; | |
498 rev = c->read; | |
499 wev = c->write; | |
500 | |
501 rev->active = 0; | |
502 wev->active = 0; | |
503 | |
504 if (revents & POLLIN) { | |
754
4ac89c5aa10d
style fix: remove trailing spaces
Igor Sysoev <igor@sysoev.ru>
parents:
719
diff
changeset
|
505 |
719 | 506 if ((flags & NGX_POST_THREAD_EVENTS) && !rev->accept) { |
507 rev->posted_ready = 1; | |
508 | |
509 } else { | |
510 rev->ready = 1; | |
511 } | |
512 | |
513 if (flags & NGX_POST_EVENTS) { | |
514 queue = (ngx_event_t **) (rev->accept ? | |
515 &ngx_posted_accept_events : &ngx_posted_events); | |
516 | |
517 ngx_locked_post_event(rev, queue); | |
518 | |
519 } else { | |
520 rev->handler(rev); | |
1287
3dd9883fa121
fix segfault when event port returns POLLERR without POLLIN or POLLOUT
Igor Sysoev <igor@sysoev.ru>
parents:
1128
diff
changeset
|
521 |
3dd9883fa121
fix segfault when event port returns POLLERR without POLLIN or POLLOUT
Igor Sysoev <igor@sysoev.ru>
parents:
1128
diff
changeset
|
522 if (ev->closed) { |
3dd9883fa121
fix segfault when event port returns POLLERR without POLLIN or POLLOUT
Igor Sysoev <igor@sysoev.ru>
parents:
1128
diff
changeset
|
523 continue; |
3dd9883fa121
fix segfault when event port returns POLLERR without POLLIN or POLLOUT
Igor Sysoev <igor@sysoev.ru>
parents:
1128
diff
changeset
|
524 } |
719 | 525 } |
526 | |
527 if (rev->accept) { | |
528 if (ngx_use_accept_mutex) { | |
529 ngx_accept_events = 1; | |
530 continue; | |
531 } | |
532 | |
533 if (port_associate(ep, PORT_SOURCE_FD, c->fd, POLLIN, | |
534 (void *) ((uintptr_t) ev | ev->instance)) | |
535 == -1) | |
536 { | |
537 ngx_log_error(NGX_LOG_ALERT, ev->log, ngx_errno, | |
538 "port_associate() failed"); | |
539 return NGX_ERROR; | |
540 } | |
541 } | |
542 } | |
543 | |
544 if (revents & POLLOUT) { | |
545 | |
546 if (flags & NGX_POST_THREAD_EVENTS) { | |
547 wev->posted_ready = 1; | |
548 | |
549 } else { | |
550 wev->ready = 1; | |
551 } | |
552 | |
553 if (flags & NGX_POST_EVENTS) { | |
554 ngx_locked_post_event(wev, &ngx_posted_events); | |
555 | |
556 } else { | |
557 wev->handler(wev); | |
558 } | |
559 } | |
560 | |
561 continue; | |
562 | |
563 default: | |
564 ngx_log_error(NGX_LOG_ALERT, cycle->log, 0, | |
565 "unexpected even_port object %d", | |
566 event_list[i].portev_object); | |
567 continue; | |
568 } | |
569 } | |
570 | |
571 ngx_mutex_unlock(ngx_posted_events_mutex); | |
572 | |
573 return NGX_OK; | |
574 } | |
575 | |
576 | |
577 static void * | |
578 ngx_eventport_create_conf(ngx_cycle_t *cycle) | |
579 { | |
580 ngx_eventport_conf_t *epcf; | |
581 | |
582 epcf = ngx_palloc(cycle->pool, sizeof(ngx_eventport_conf_t)); | |
583 if (epcf == NULL) { | |
2912
c7d57b539248
return NULL instead of NGX_CONF_ERROR on a create conf failure
Igor Sysoev <igor@sysoev.ru>
parents:
1939
diff
changeset
|
584 return NULL; |
719 | 585 } |
586 | |
587 epcf->events = NGX_CONF_UNSET; | |
588 | |
589 return epcf; | |
590 } | |
591 | |
592 | |
593 static char * | |
594 ngx_eventport_init_conf(ngx_cycle_t *cycle, void *conf) | |
595 { | |
596 ngx_eventport_conf_t *epcf = conf; | |
597 | |
598 ngx_conf_init_uint_value(epcf->events, 32); | |
599 | |
600 return NGX_CONF_OK; | |
601 } |