comparison src/event/modules/ngx_iocp_module.c @ 102:7e86d028d8f0

nginx-0.0.1-2003-06-06-18:59:20 import
author Igor Sysoev <igor@sysoev.ru>
date Fri, 06 Jun 2003 14:59:20 +0000
parents 19cc647ecd91
children 6dfda4cf5200
comparison
equal deleted inserted replaced
101:2e069b6e6920 102:7e86d028d8f0
1
2 /*
3 * Copyright (C) 2002-2003 Igor Sysoev, http://sysoev.ru
4 */
5
1 6
2 #include <ngx_config.h> 7 #include <ngx_config.h>
3
4 #include <ngx_core.h> 8 #include <ngx_core.h>
5 #include <ngx_log.h>
6 #include <ngx_errno.h>
7 #include <ngx_time.h>
8 #include <ngx_connection.h>
9 #include <ngx_event.h> 9 #include <ngx_event.h>
10 #include <ngx_event_timer.h> 10
11 11
12 #include <ngx_iocp_module.h> 12 typedef struct {
13 13 int threads;
14 14 } ngx_iocp_conf_t;
15 int ngx_iocp_threads = 0;; 15
16 16
17 17 static int ngx_iocp_init(ngx_log_t *log);
18 static HANDLE iocp; 18 static void ngx_iocp_done(ngx_log_t *log);
19 static ngx_event_t *timer_queue; 19 static int ngx_iocp_add_event(ngx_event_t *ev, int event, u_int key);
20 20 static int ngx_iocp_process_events(ngx_log_t *log);
21 21 static void *ngx_iocp_create_conf(ngx_pool_t *pool);
22 int ngx_iocp_init(int max_connections, ngx_log_t *log) 22 static char *ngx_iocp_init_conf(ngx_pool_t *pool, void *conf);
23 { 23
24 iocp = CreateIoCompletionPort(INVALID_HANDLE_VALUE, 24
25 NULL, 0, ngx_iocp_threads); 25 static ngx_str_t iocp_name = ngx_string("iocp");
26
27 static ngx_command_t ngx_iocp_commands[] = {
28
29 {ngx_string("iocp_threads"),
30 NGX_EVENT_CONF|NGX_CONF_TAKE1,
31 ngx_conf_set_num_slot,
32 0,
33 offsetof(ngx_iocp_conf_t, threads),
34 NULL},
35
36 ngx_null_command
37 };
38
39
40 ngx_event_module_t ngx_iocp_module_ctx = {
41 &iocp_name,
42 ngx_iocp_create_conf, /* create configuration */
43 ngx_iocp_init_conf, /* init configuration */
44
45 {
46 ngx_iocp_add_event, /* add an event */
47 NULL, /* delete an event */
48 NULL, /* enable an event */
49 NULL, /* disable an event */
50 NULL, /* add an connection */
51 NULL, /* delete an connection */
52 ngx_iocp_process_events, /* process the events */
53 ngx_iocp_init, /* init the events */
54 ngx_iocp_done /* done the events */
55 }
56
57 };
58
59 ngx_module_t ngx_iocp_module = {
60 NGX_MODULE,
61 &ngx_iocp_module_ctx, /* module context */
62 ngx_iocp_commands, /* module directives */
63 NGX_EVENT_MODULE, /* module type */
64 NULL /* init module */
65 };
66
67
68 static HANDLE iocp;
69
70
71 static int ngx_iocp_init(ngx_log_t *log)
72 {
73 ngx_iocp_conf_t *cf;
74
75 cf = ngx_event_get_conf(ngx_iocp_module);
76
77 iocp = CreateIoCompletionPort(INVALID_HANDLE_VALUE, NULL, 0, cf->threads);
26 78
27 if (iocp == NULL) { 79 if (iocp == NULL) {
28 ngx_log_error(NGX_LOG_EMERG, log, ngx_errno, 80 ngx_log_error(NGX_LOG_EMERG, log, ngx_errno,
29 "CreateIoCompletionPort() failed"); 81 "CreateIoCompletionPort() failed");
30 return NGX_ERROR; 82 return NGX_ERROR;
31 } 83 }
32 84
33 timer_queue = ngx_event_init_timer(log); 85 if (ngx_event_timer_init(log) == NGX_ERROR) {
34 if (timer_queue == NULL) {
35 return NGX_ERROR; 86 return NGX_ERROR;
36 } 87 }
37 88
38 ngx_event_actions.process = ngx_iocp_process_events; 89 ngx_event_actions = ngx_iocp_module_ctx.actions;
39 90
40 ngx_event_flags = NGX_HAVE_AIO_EVENT|NGX_HAVE_IOCP_EVENT; 91 ngx_event_flags = NGX_HAVE_AIO_EVENT|NGX_HAVE_IOCP_EVENT;
41 92
42 return NGX_OK; 93 return NGX_OK;
43 } 94 }
44 95
45 96
46 int ngx_iocp_add_event(ngx_event_t *ev) 97 static void ngx_iocp_done(ngx_log_t *log)
98 {
99 if (CloseHandle(iocp) == -1) {
100 ngx_log_error(NGX_LOG_ALERT, log, ngx_errno,
101 "iocp CloseHandle() failed");
102 }
103
104 ngx_event_timer_done(log);
105 }
106
107
108 static int ngx_iocp_add_event(ngx_event_t *ev, int event, u_int key)
47 { 109 {
48 ngx_connection_t *c; 110 ngx_connection_t *c;
49 111
50 c = (ngx_connection_t *) ev->data; 112 c = (ngx_connection_t *) ev->data;
51 113
52 ngx_log_debug(ev->log, "iocp: %d, %08x:%08x" _ c->fd _ ev _ &ev->ovlp); 114 ngx_log_debug(ev->log, "iocp add: %d, %08x:%08x" _ c->fd _ key _ &ev->ovlp);
53 115
54 if (CreateIoCompletionPort((HANDLE) c->fd, iocp, (DWORD) ev, 0) == NULL) { 116 if (CreateIoCompletionPort((HANDLE) c->fd, iocp, key, 0) == NULL) {
55 ngx_log_error(NGX_LOG_ALERT, ev->log, ngx_errno, 117 ngx_log_error(NGX_LOG_ALERT, ev->log, ngx_errno,
56 "CreateIoCompletionPort() failed"); 118 "CreateIoCompletionPort() failed");
57 return NGX_ERROR; 119 return NGX_ERROR;
58 } 120 }
59 121
60 return NGX_OK; 122 return NGX_OK;
61 } 123 }
62 124
63 125
64 int ngx_iocp_process_events(ngx_log_t *log) 126 static int ngx_iocp_process_events(ngx_log_t *log)
65 { 127 {
66 int rc; 128 int rc;
129 u_int key;
67 size_t bytes; 130 size_t bytes;
68 ngx_err_t err; 131 ngx_err_t err;
69 ngx_msec_t timer, delta; 132 ngx_msec_t timer, delta;
70 ngx_event_t *ev, *e; 133 ngx_event_t *ev;
71 ngx_event_ovlp_t *ovlp; 134 ngx_event_ovlp_t *ovlp;
72
73 ngx_log_debug(log, "iocp");
74 135
75 timer = ngx_event_find_timer(); 136 timer = ngx_event_find_timer();
76 137
77 if (timer) { 138 if (timer) {
78 delta = ngx_msec(); 139 delta = ngx_msec();
82 delta = 0; 143 delta = 0;
83 } 144 }
84 145
85 ngx_log_debug(log, "iocp timer: %d" _ timer); 146 ngx_log_debug(log, "iocp timer: %d" _ timer);
86 147
87 #if 1 148 rc = GetQueuedCompletionStatus(iocp, &bytes, (LPDWORD) &key,
88 rc = GetQueuedCompletionStatus(iocp, &bytes, (LPDWORD) &e,
89 (LPOVERLAPPED *) &ovlp, timer); 149 (LPOVERLAPPED *) &ovlp, timer);
90 ngx_log_debug(log, "iocp: %d, %d:%08x:%08x" _ rc _ bytes _ e _ ovlp); 150
151 ngx_log_debug(log, "iocp: %d, %d:%08x:%08x" _ rc _ bytes _ key _ ovlp);
152
91 if (rc == 0) { 153 if (rc == 0) {
92 #else
93 if (GetQueuedCompletionStatus(iocp, &bytes, (LPDWORD) &e,
94 (LPOVERLAPPED *) &ovlp, timer) == 0) {
95 #endif
96 err = ngx_errno; 154 err = ngx_errno;
97 155
98 if (ovlp == NULL) { 156 if (ovlp == NULL) {
99 if (err != WAIT_TIMEOUT) { 157 if (err != WAIT_TIMEOUT) {
100 ngx_log_error(NGX_LOG_ALERT, log, err, 158 ngx_log_error(NGX_LOG_ALERT, log, err,
116 if (ovlp) { 174 if (ovlp) {
117 ev = ovlp->event; 175 ev = ovlp->event;
118 176
119 ngx_log_debug(log, "iocp ev: %08x" _ ev); 177 ngx_log_debug(log, "iocp ev: %08x" _ ev);
120 178
121 if (ev == e) { 179 switch (key) {
122 /* it's not AcceptEx() completion */ 180 case NGX_IOCP_IO:
123 ev->ready = 1; 181 ev->ready = 1;
124 ev->available = bytes; 182 ev->available = bytes;
183 break;
184
185 case NGX_IOCP_ACCEPT:
186 break;
125 } 187 }
126 188
127 ngx_log_debug(log, "iocp ev: %08x" _ ev->event_handler); 189 ngx_log_debug(log, "iocp ev handler: %08x" _ ev->event_handler);
128 190
129 ev->event_handler(ev); 191 ev->event_handler(ev);
130 } 192 }
131 193
132 return NGX_OK; 194 return NGX_OK;
133 } 195 }
196
197
198 static void *ngx_iocp_create_conf(ngx_pool_t *pool)
199 {
200 ngx_iocp_conf_t *cf;
201
202 ngx_test_null(cf, ngx_palloc(pool, sizeof(ngx_iocp_conf_t)),
203 NGX_CONF_ERROR);
204
205 cf->threads = NGX_CONF_UNSET;
206
207 return cf;
208 }
209
210
211 static char *ngx_iocp_init_conf(ngx_pool_t *pool, void *conf)
212 {
213 ngx_iocp_conf_t *cf = conf;
214
215 ngx_conf_init_value(cf->threads, 0);
216
217 return NGX_CONF_OK;
218 }