aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAndrey Uzunov <andrey.uzunov@gmail.com>2013-07-20 19:21:10 +0000
committerAndrey Uzunov <andrey.uzunov@gmail.com>2013-07-20 19:21:10 +0000
commit50735544c1caee405c3bdf0845bed78522b92f0c (patch)
tree6d9e28a11eed920e1b55137ab996931ed9ba9a84
parent84205b371f6f335e7a11ea37488c44086eb13d26 (diff)
downloadlibmicrohttpd-50735544c1caee405c3bdf0845bed78522b92f0c.tar.gz
libmicrohttpd-50735544c1caee405c3bdf0845bed78522b92f0c.zip
mhd2spdy: code formatting done and old code removed
-rw-r--r--src/examples/mhd2spdy.c82
-rw-r--r--src/examples/mhd2spdy_http.c178
-rw-r--r--src/examples/mhd2spdy_http.h9
-rw-r--r--src/examples/mhd2spdy_spdy.c329
-rw-r--r--src/examples/mhd2spdy_spdy.h71
-rw-r--r--src/examples/mhd2spdy_structures.c26
-rw-r--r--src/examples/mhd2spdy_structures.h72
7 files changed, 321 insertions, 446 deletions
diff --git a/src/examples/mhd2spdy.c b/src/examples/mhd2spdy.c
index d921aa27..0426a276 100644
--- a/src/examples/mhd2spdy.c
+++ b/src/examples/mhd2spdy.c
@@ -31,16 +31,20 @@
31#include "mhd2spdy_spdy.h" 31#include "mhd2spdy_spdy.h"
32#include "mhd2spdy_http.h" 32#include "mhd2spdy_http.h"
33 33
34
34static int run = 1; 35static int run = 1;
35//static int spdy_close = 0; 36//static int spdy_close = 0;
36 37
37static void catch_signal(int signal) 38
39static void
40catch_signal(int signal)
38{ 41{
39 (void)signal; 42 (void)signal;
40 //spdy_close = 1; 43 //spdy_close = 1;
41 run = 0; 44 run = 0;
42} 45}
43 46
47
44int 48int
45run_everything () 49run_everything ()
46{ 50{
@@ -54,10 +58,7 @@ run_everything ()
54 int maxfd_s = -1; 58 int maxfd_s = -1;
55 struct MHD_Daemon *daemon; 59 struct MHD_Daemon *daemon;
56 nfds_t spdy_npollfds = 1; 60 nfds_t spdy_npollfds = 1;
57 //struct pollfd spdy_pollfds[MAX_SPDY_CONNECTIONS];
58 struct URI * spdy2http_uri = NULL; 61 struct URI * spdy2http_uri = NULL;
59 //int spdy_nfds;
60 //int spdylay_timeout = 0;
61 struct SPDY_Connection *connection; 62 struct SPDY_Connection *connection;
62 struct SPDY_Connection *connections[MAX_SPDY_CONNECTIONS]; 63 struct SPDY_Connection *connections[MAX_SPDY_CONNECTIONS];
63 struct SPDY_Connection *connection_for_delete; 64 struct SPDY_Connection *connection_for_delete;
@@ -68,18 +69,15 @@ run_everything ()
68 if (signal(SIGINT, catch_signal) == SIG_ERR) 69 if (signal(SIGINT, catch_signal) == SIG_ERR)
69 PRINT_INFO("signal failed"); 70 PRINT_INFO("signal failed");
70 71
71 //spdy2http_url = argv[2];
72 glob_opt.streams_opened = 0; 72 glob_opt.streams_opened = 0;
73 glob_opt.responses_pending = 0; 73 glob_opt.responses_pending = 0;
74 glob_opt.global_memory = 0; 74 glob_opt.global_memory = 0;
75 //spdy_proto_version = 0;
76 75
77 srand(time(NULL)); 76 srand(time(NULL));
78 77
79 if(init_parse_uri(&glob_opt.uri_preg)) 78 if(init_parse_uri(&glob_opt.uri_preg))
80 DIE("Regexp compilation failed"); 79 DIE("Regexp compilation failed");
81 80
82
83 if(NULL != glob_opt.spdy2http_str) 81 if(NULL != glob_opt.spdy2http_str)
84 { 82 {
85 ret = parse_uri(&glob_opt.uri_preg, glob_opt.spdy2http_str, &spdy2http_uri); 83 ret = parse_uri(&glob_opt.uri_preg, glob_opt.spdy2http_str, &spdy2http_uri);
@@ -105,12 +103,10 @@ run_everything ()
105 if(NULL==daemon) 103 if(NULL==daemon)
106 DIE("MHD_start_daemon failed"); 104 DIE("MHD_start_daemon failed");
107 105
108
109 do 106 do
110 { 107 {
111 108 timeout.tv_sec = 0;
112 timeout.tv_sec = 0; 109 timeout.tv_usec = 0;
113 timeout.tv_usec = 0;
114 110
115 if(NULL == glob_opt.spdy_connection && NULL != glob_opt.spdy2http_str) 111 if(NULL == glob_opt.spdy_connection && NULL != glob_opt.spdy2http_str)
116 { 112 {
@@ -119,32 +115,19 @@ run_everything ()
119 PRINT_INFO("cannot connect to the proxy"); 115 PRINT_INFO("cannot connect to the proxy");
120 } 116 }
121 117
122 //PRINT_INFO("while1");
123 FD_ZERO(&rs); 118 FD_ZERO(&rs);
124 FD_ZERO(&ws); 119 FD_ZERO(&ws);
125 FD_ZERO(&es); 120 FD_ZERO(&es);
126 121
127 /*if(glob_opt.spdy_data_received) 122 ret = MHD_get_timeout(daemon, &timeoutlong);
128 { 123 if(MHD_NO == ret || timeoutlong > 5000)
129 timeout.tv_sec = 0; 124 timeout.tv_sec = 5;
130 timeout.tv_usec = 0;
131 glob_opt.spdy_data_received = false;
132}
133else{*/
134 /*if(glob_opt.responses_pending || glob_opt.streams_opened)// TODO only streams_opened true?
135 timeout.tv_usec = 0; //return immediately
136 else 125 else
137 {*/ 126 {
138 ret = MHD_get_timeout(daemon, &timeoutlong); 127 timeout.tv_sec = timeoutlong / 1000;
139 if(MHD_NO == ret || timeoutlong > 5000) 128 timeout.tv_usec = (timeoutlong % 1000) * 1000;
140 timeout.tv_sec = 5; 129 }
141 else 130
142 {
143 timeout.tv_sec = timeoutlong / 1000;
144 timeout.tv_usec = (timeoutlong % 1000) * 1000;
145 }
146 //}
147//}
148 if(MHD_NO == MHD_get_fdset (daemon, 131 if(MHD_NO == MHD_get_fdset (daemon,
149 &rs, 132 &rs,
150 &ws, 133 &ws,
@@ -160,12 +143,10 @@ else{*/
160 &ws, 143 &ws,
161 &es, 144 &es,
162 connections, MAX_SPDY_CONNECTIONS, &spdy_npollfds); 145 connections, MAX_SPDY_CONNECTIONS, &spdy_npollfds);
163 if(maxfd_s > maxfd) maxfd = maxfd_s; 146 if(maxfd_s > maxfd)
147 maxfd = maxfd_s;
164 148
165 PRINT_INFO2("MHD timeout %lld %lld", (unsigned long long)timeout.tv_sec, (unsigned long long)timeout.tv_usec); 149 PRINT_INFO2("MHD timeout %lld %lld", (unsigned long long)timeout.tv_sec, (unsigned long long)timeout.tv_usec);
166 //TODO
167 //timeout.tv_sec = 0;
168 //timeout.tv_usec = 0;
169 150
170 glob_opt.spdy_data_received = false; 151 glob_opt.spdy_data_received = false;
171 152
@@ -181,42 +162,20 @@ else{*/
181 break; 162 break;
182 default: 163 default:
183 PRINT_INFO("run"); 164 PRINT_INFO("run");
184 //MHD_run_from_select(daemon,&rs, &ws, &es); //not closing FDs 165 //MHD_run_from_select(daemon,&rs, &ws, &es); //not closing FDs at some time in past
185 MHD_run(daemon); 166 MHD_run(daemon);
186 spdy_run_select(&rs, &ws, &es, connections, spdy_npollfds); 167 spdy_run_select(&rs, &ws, &es, connections, spdy_npollfds);
187 if(glob_opt.spdy_data_received) 168 if(glob_opt.spdy_data_received)
188 { 169 {
189 PRINT_INFO("MHD run again"); 170 PRINT_INFO("MHD run again");
190 //MHD_run_from_select(daemon,&rs, &ws, &es); //not closing FDs 171 //MHD_run_from_select(daemon,&rs, &ws, &es); //not closing FDs at some time in past
191 MHD_run(daemon); 172 MHD_run(daemon);
192 } 173 }
193 break; 174 break;
194 } 175 }
195
196 /*
197 //if(glob_opt.streams_opened) spdylay_timeout = 500;
198 //if(glob_opt.responses_pending || glob_opt.streams_opened) spdylay_timeout = 0;
199 //else spdylay_timeout = 0;
200 //else spdylay_timeout = 0;
201
202 spdy_get_pollfdset(spdy_pollfds, connections, MAX_SPDY_CONNECTIONS, &spdy_npollfds);
203
204 //TODO
205 //spdylay_timeout = 0;
206
207 PRINT_INFO2("spdylay timeout %i", spdylay_timeout);
208 ret = poll(spdy_pollfds, spdy_npollfds, spdylay_timeout);
209 if(ret == -1)
210 DIE("poll");
211 if(ret > 0){
212 PRINT_INFO("spdy_run");
213 spdy_run(spdy_pollfds, connections, spdy_npollfds);
214 }*/
215 } 176 }
216 while(run); 177 while(run);
217 178
218 //TODO exit from loop and clean
219
220 MHD_stop_daemon (daemon); 179 MHD_stop_daemon (daemon);
221 180
222 //TODO SSL_free brakes 181 //TODO SSL_free brakes
@@ -246,6 +205,7 @@ else{*/
246 return 0; 205 return 0;
247} 206}
248 207
208
249void 209void
250display_usage() 210display_usage()
251{ 211{
diff --git a/src/examples/mhd2spdy_http.c b/src/examples/mhd2spdy_http.c
index 4761c086..7881d57a 100644
--- a/src/examples/mhd2spdy_http.c
+++ b/src/examples/mhd2spdy_http.c
@@ -26,7 +26,9 @@
26#include "mhd2spdy_spdy.h" 26#include "mhd2spdy_spdy.h"
27 27
28 28
29void * http_log_cb(void * cls, const char * uri) 29void *
30http_log_cb(void * cls,
31const char * uri)
30{ 32{
31 (void)cls; 33 (void)cls;
32 34
@@ -34,29 +36,18 @@ void * http_log_cb(void * cls, const char * uri)
34 36
35 PRINT_INFO2("log uri '%s'\n", uri); 37 PRINT_INFO2("log uri '%s'\n", uri);
36 38
37 //TODO free
38 if(NULL == (http_uri = au_malloc(sizeof(struct HTTP_URI )))) 39 if(NULL == (http_uri = au_malloc(sizeof(struct HTTP_URI ))))
39 DIE("no memory"); 40 DIE("no memory");
40 //memset(http_uri, 0 , sizeof(struct HTTP_URI));
41 http_uri->uri = strdup(uri); 41 http_uri->uri = strdup(uri);
42 return http_uri; 42 return http_uri;
43} 43}
44 44
45 45
46/*
47static int
48http_query_iterate_cb(void *cls,
49 enum MHD_ValueKind kind,
50 const char *name, const char *value)
51{
52
53}*/
54
55
56static int 46static int
57http_iterate_cb(void *cls, 47http_iterate_cb(void *cls,
58 enum MHD_ValueKind kind, 48 enum MHD_ValueKind kind,
59 const char *name, const char *value) 49 const char *name,
50 const char *value)
60{ 51{
61 (void)kind; 52 (void)kind;
62 53
@@ -85,9 +76,9 @@ http_iterate_cb(void *cls,
85 76
86static ssize_t 77static ssize_t
87http_response_callback (void *cls, 78http_response_callback (void *cls,
88 uint64_t pos, 79 uint64_t pos,
89 char *buffer, 80 char *buffer,
90 size_t max) 81 size_t max)
91{ 82{
92 (void)pos; 83 (void)pos;
93 84
@@ -96,15 +87,6 @@ http_response_callback (void *cls,
96 void *newbody; 87 void *newbody;
97 const union MHD_ConnectionInfo *info; 88 const union MHD_ConnectionInfo *info;
98 int val = 1; 89 int val = 1;
99
100 //max=16;
101
102 //PRINT_INFO2("response_callback, pos: %i, max is %i, len is %i",pos,max,proxy->length);
103
104 //assert(0 != proxy->length);
105
106 //if(MHD_CONTENT_READER_END_OF_STREAM == proxy->length)
107 // return MHD_CONTENT_READER_END_OF_STREAM;
108 90
109 PRINT_INFO2("http_response_callback for %s", proxy->url); 91 PRINT_INFO2("http_response_callback for %s", proxy->url);
110 92
@@ -116,7 +98,6 @@ http_response_callback (void *cls,
116 return MHD_CONTENT_READER_END_OF_STREAM; 98 return MHD_CONTENT_READER_END_OF_STREAM;
117 } 99 }
118 100
119 //*more = true;
120 if(!proxy->http_body_size)//nothing to write now 101 if(!proxy->http_body_size)//nothing to write now
121 { 102 {
122 //flush data 103 //flush data
@@ -154,13 +135,6 @@ http_response_callback (void *cls,
154 if(proxy->length >= 0) 135 if(proxy->length >= 0)
155 { 136 {
156 proxy->length -= ret; 137 proxy->length -= ret;
157 //printf("pr len %i", proxy->length);
158 /*if(proxy->length <= 0)
159 {
160 // *more = false;
161 //last frame
162 proxy->length = MHD_CONTENT_READER_END_OF_STREAM;
163 }*/
164 } 138 }
165 139
166 PRINT_INFO2("response_callback, size: %i",ret); 140 PRINT_INFO2("response_callback, size: %i",ret);
@@ -175,27 +149,7 @@ http_response_done_callback(void *cls)
175 struct Proxy *proxy = (struct Proxy *)cls; 149 struct Proxy *proxy = (struct Proxy *)cls;
176 150
177 PRINT_INFO2("http_response_done_callback for %s", proxy->url); 151 PRINT_INFO2("http_response_done_callback for %s", proxy->url);
178 //int ret; 152
179
180 //printf("response_done_callback\n");
181
182 //printf("answer for %s was sent\n", (char *)cls);
183
184 /*if(SPDY_RESPONSE_RESULT_SUCCESS != status)
185 {
186 printf("answer was NOT sent, %i\n",status);
187 }*/
188 /*if(CURLM_OK != (ret = curl_multi_remove_handle(multi_handle, proxy->curl_handle)))
189 {
190 PRINT_INFO2("curl_multi_remove_handle failed (%i)", ret);
191 }
192 curl_slist_free_all(proxy->curl_headers);
193 curl_easy_cleanup(proxy->curl_handle);
194 */
195 //SPDY_destroy_request(request);
196 //SPDY_destroy_response(response);
197 //if(!strcmp("/close",proxy->path)) run = 0;
198 //free(proxy->path);
199 if(proxy->spdy_active) 153 if(proxy->spdy_active)
200 proxy->http_active = false; 154 proxy->http_active = false;
201 else 155 else
@@ -219,12 +173,8 @@ http_cb_request (void *cls,
219 (void)upload_data; 173 (void)upload_data;
220 (void)upload_data_size; 174 (void)upload_data_size;
221 175
222 //struct MHD_Response *response;
223 int ret; 176 int ret;
224 struct Proxy *proxy; 177 struct Proxy *proxy;
225 //struct URI *spdy_uri;
226 //char **nv;
227 //int num_headers;
228 struct SPDY_Headers spdy_headers; 178 struct SPDY_Headers spdy_headers;
229 179
230 //PRINT_INFO2("request cb %i; %s", *ptr,url); 180 //PRINT_INFO2("request cb %i; %s", *ptr,url);
@@ -240,7 +190,7 @@ http_cb_request (void *cls,
240 free(http_uri->uri); 190 free(http_uri->uri);
241 free(http_uri); 191 free(http_uri);
242 PRINT_INFO2("unexpected method %s", method); 192 PRINT_INFO2("unexpected method %s", method);
243 return MHD_NO; /* unexpected method */ 193 return MHD_NO;
244 } 194 }
245 195
246 if(NULL == (proxy = au_malloc(sizeof(struct Proxy)))) 196 if(NULL == (proxy = au_malloc(sizeof(struct Proxy))))
@@ -250,17 +200,14 @@ http_cb_request (void *cls,
250 } 200 }
251 201
252 ++glob_opt.responses_pending; 202 ++glob_opt.responses_pending;
253 //memset(proxy, 0, sizeof(struct Proxy));
254 proxy->id = rand(); 203 proxy->id = rand();
255 proxy->http_active = true; 204 proxy->http_active = true;
256 //PRINT_INFO2("proxy obj with id %i created (%i)", proxy->id, proxy);
257 proxy->http_connection = connection; 205 proxy->http_connection = connection;
258 http_uri->proxy = proxy; 206 http_uri->proxy = proxy;
259 return MHD_YES; 207 return MHD_YES;
260 } 208 }
261 209
262 proxy = http_uri->proxy; 210 proxy = http_uri->proxy;
263 //*ptr = NULL; /* reset when done */
264 211
265 if(proxy->spdy_active) 212 if(proxy->spdy_active)
266 { 213 {
@@ -270,45 +217,15 @@ http_cb_request (void *cls,
270 } 217 }
271 218
272 PRINT_INFO2("received request for '%s %s %s'\n", method, http_uri->uri, version); 219 PRINT_INFO2("received request for '%s %s %s'\n", method, http_uri->uri, version);
273 /*
274 proxy->http_response = MHD_create_response_from_callback (MHD_SIZE_UNKNOWN,
275 8096,
276 &http_response_callback,
277 proxy,
278 &http_response_done_callback);
279
280 if (proxy->http_response == NULL)
281 DIE("no response");
282 */
283 220
284 proxy->url = http_uri->uri; 221 proxy->url = http_uri->uri;
285 //if(NULL == (proxy->url = strdup(http_uri->uri)))
286 // DIE("no memory");
287
288//TODO HTTP headers
289 /*MHD_get_connection_values (connection,
290 MHD_HEADER_KIND,
291 &http_iterate_cb,
292 proxy);
293 */
294 //proxy->url = strdup(url);
295 //if(NULL == (spdy_uri = au_malloc(sizeof(struct URI))))
296 // DIE("no memory");
297 222
298 ret = parse_uri(&glob_opt.uri_preg, proxy->url, &proxy->uri); 223 ret = parse_uri(&glob_opt.uri_preg, proxy->url, &proxy->uri);
299 if(ret != 0) 224 if(ret != 0)
300 DIE("parse_uri failed"); 225 DIE("parse_uri failed");
301 //proxy->uri = spdy_uri;
302 proxy->http_uri = http_uri; 226 proxy->http_uri = http_uri;
303 proxy->spdy_active = true; 227 proxy->spdy_active = true;
304 228
305 //proxy->spdy_request = au_malloc(sizeof(struct SPDY_Request));
306 //if(NULL == proxy->spdy_request)
307 // DIE("no memory");
308 //memset(proxy->spdy_request,0,sizeof(struct SPDY_Request));
309 //spdy_request_init(proxy->spdy_request, &spdy_uri);
310 //spdy_submit_request(spdy_connection, proxy);
311
312 spdy_headers.num = MHD_get_connection_values (connection, 229 spdy_headers.num = MHD_get_connection_values (connection,
313 MHD_HEADER_KIND, 230 MHD_HEADER_KIND,
314 NULL, 231 NULL,
@@ -331,16 +248,10 @@ http_cb_request (void *cls,
331 if(NULL == spdy_headers.nv[9]) 248 if(NULL == spdy_headers.nv[9])
332 spdy_headers.nv[9] = proxy->uri->host_and_port; 249 spdy_headers.nv[9] = proxy->uri->host_and_port;
333 250
334 /*int i;
335 for(i=0; i<spdy_headers.cnt; i+=2)
336 printf("%s: %s\n", spdy_headers.nv[i], spdy_headers.nv[i+1]);
337 */
338 if(0 != spdy_request(spdy_headers.nv, proxy)) 251 if(0 != spdy_request(spdy_headers.nv, proxy))
339 { 252 {
340 //--glob_opt.responses_pending;
341 free(spdy_headers.nv); 253 free(spdy_headers.nv);
342 //MHD_destroy_response (proxy->http_response); 254 free_proxy(proxy);
343 free_proxy(proxy);//TODO call it here or in done_callback
344 255
345 return MHD_NO; 256 return MHD_NO;
346 } 257 }
@@ -364,60 +275,20 @@ http_cb_request (void *cls,
364 if(MHD_NO == MHD_add_response_header (proxy->http_response, 275 if(MHD_NO == MHD_add_response_header (proxy->http_response,
365 "Keep-Alive", "timeout=5, max=100")) 276 "Keep-Alive", "timeout=5, max=100"))
366 PRINT_INFO("SPDY_name_value_add failed: "); 277 PRINT_INFO("SPDY_name_value_add failed: ");
367 /* 278
368 const union MHD_ConnectionInfo *info;
369 info = MHD_get_connection_info (connection,
370 MHD_CONNECTION_INFO_CONNECTION_FD);
371 int val = 1;
372 int rv;
373 rv = setsockopt(info->connect_fd, IPPROTO_TCP, TCP_NODELAY, &val, (socklen_t)sizeof(val));
374 if(rv == -1) {
375 DIE("setsockopt");
376 }*/
377 return MHD_YES; 279 return MHD_YES;
378} 280}
379 281
282
380void 283void
381http_create_response(struct Proxy* proxy, char **nv) 284http_create_response(struct Proxy* proxy,
285 char **nv)
382{ 286{
383 size_t i; 287 size_t i;
384 //uint64_t response_size=MHD_SIZE_UNKNOWN;
385
386 /*for(i = 0; nv[i]; i += 2) {
387 if(0 == strcmp("content-length", nv[i]))
388 {
389 response_size = atoi(nv[i+1]);
390 break;
391 }
392 }*/
393 /*
394 proxy->http_response = MHD_create_response_from_callback (MHD_SIZE_UNKNOWN,
395 4096,
396 &http_response_callback,
397 proxy,
398 &http_response_done_callback);
399
400 if (proxy->http_response == NULL)
401 DIE("no response");
402 288
403 if(MHD_NO == MHD_add_response_header (proxy->http_response,
404 "Proxy-Connection", "keep-alive"))
405 PRINT_INFO("SPDY_name_value_add failed: ");
406 if(MHD_NO == MHD_add_response_header (proxy->http_response,
407 "Connection", "Keep-Alive"))
408 PRINT_INFO("SPDY_name_value_add failed: ");
409 if(MHD_NO == MHD_add_response_header (proxy->http_response,
410 "Keep-Alive", "timeout=5, max=100"))
411 PRINT_INFO("SPDY_name_value_add failed: ");
412 */
413 for(i = 0; nv[i]; i += 2) { 289 for(i = 0; nv[i]; i += 2) {
414 //printf(" %s: %s\n", nv[i], nv[i+1]);
415 //int j;
416
417 if(0 == strcmp(":status", nv[i])) 290 if(0 == strcmp(":status", nv[i]))
418 { 291 {
419 //raise(SIGINT);
420 //proxy->status_msg = nv[i+1];
421 char tmp[4]; 292 char tmp[4];
422 memcpy(&tmp,nv[i+1],3); 293 memcpy(&tmp,nv[i+1],3);
423 tmp[3]=0; 294 tmp[3]=0;
@@ -431,35 +302,22 @@ http_create_response(struct Proxy* proxy, char **nv)
431 } 302 }
432 else if(0 == strcmp("content-length", nv[i])) 303 else if(0 == strcmp("content-length", nv[i]))
433 { 304 {
434 //proxy->length = atoi(nv[i+1]);
435 //response_size = atoi(nv[i+1]);
436 continue; 305 continue;
437 } 306 }
438 307
439 //for(j=0; j<strlen(nv[i]) && ':'==nv[i][j]; ++j);
440
441 char *header = *(nv+i); 308 char *header = *(nv+i);
442 //header[0] = toupper(header[0]);
443 if(MHD_NO == MHD_add_response_header (proxy->http_response, 309 if(MHD_NO == MHD_add_response_header (proxy->http_response,
444 header, nv[i+1])) 310 header, nv[i+1]))
445 { 311 {
446 PRINT_INFO2("SPDY_name_value_add failed: '%s' '%s'", header, nv[i+1]); 312 PRINT_INFO2("SPDY_name_value_add failed: '%s' '%s'", header, nv[i+1]);
447 //abort();
448 } 313 }
449 PRINT_INFO2("adding '%s: %s'",header, nv[i+1]); 314 PRINT_INFO2("adding '%s: %s'",header, nv[i+1]);
450 } 315 }
451 316
452 //PRINT_INFO2("%i", MHD_get_response_headers(proxy->http_response, NULL, NULL));
453 //PRINT_INFO2("state before %i", proxy->http_connection->state);
454 //PRINT_INFO2("loop before %i", proxy->http_connection->event_loop_info);
455 if(MHD_NO == MHD_queue_response (proxy->http_connection, proxy->status, proxy->http_response)){ 317 if(MHD_NO == MHD_queue_response (proxy->http_connection, proxy->status, proxy->http_response)){
456 PRINT_INFO("No queue"); 318 PRINT_INFO("No queue");
457 abort(); 319 abort();
458 } 320 }
459 //PRINT_INFO2("state after %i", proxy->http_connection->state); 321
460 //PRINT_INFO2("loop after %i", proxy->http_connection->event_loop_info); 322 MHD_destroy_response (proxy->http_response);
461 //MHD_destroy_response (proxy->http_response);
462 //PRINT_INFO2("state after %i", proxy->http_connection->state);
463 //PRINT_INFO2("loop after %i", proxy->http_connection->event_loop_info);
464 MHD_destroy_response (proxy->http_response);
465} 323}
diff --git a/src/examples/mhd2spdy_http.h b/src/examples/mhd2spdy_http.h
index 78685c69..240959cf 100644
--- a/src/examples/mhd2spdy_http.h
+++ b/src/examples/mhd2spdy_http.h
@@ -36,10 +36,13 @@ http_cb_request (void *cls,
36 const char *upload_data, 36 const char *upload_data,
37 size_t *upload_data_size, 37 size_t *upload_data_size,
38 void **ptr); 38 void **ptr);
39 39
40
40void * http_log_cb(void * cls, const char * uri); 41void * http_log_cb(void * cls, const char * uri);
41 42
43
42void 44void
43http_create_response(struct Proxy* proxy, char **nv); 45http_create_response(struct Proxy* proxy, char **nv);
44 46
47
45#endif 48#endif
diff --git a/src/examples/mhd2spdy_spdy.c b/src/examples/mhd2spdy_spdy.c
index 8640df35..413de7f3 100644
--- a/src/examples/mhd2spdy_spdy.c
+++ b/src/examples/mhd2spdy_spdy.c
@@ -35,29 +35,27 @@
35#include "mhd2spdy_spdy.h" 35#include "mhd2spdy_spdy.h"
36#include "mhd2spdy_http.h" 36#include "mhd2spdy_http.h"
37 37
38enum
39{
40 IO_NONE,
41 WANT_READ,
42 WANT_WRITE
43};
44
45 38
46/* 39/*
47 * Prints error containing the function name |func| and message |msg| 40 * Prints error containing the function name |func| and message |msg|
48 * and exit. 41 * and exit.
49 */ 42 */
50static void spdy_dief(const char *func, const char *msg) 43static void
44spdy_dief(const char *func,
45 const char *msg)
51{ 46{
52 fprintf(stderr, "FATAL: %s: %s\n", func, msg); 47 fprintf(stderr, "FATAL: %s: %s\n", func, msg);
53 exit(EXIT_FAILURE); 48 exit(EXIT_FAILURE);
54} 49}
55 50
51
56/* 52/*
57 * Prints error containing the function name |func| and error code 53 * Prints error containing the function name |func| and error code
58 * |error_code| and exit. 54 * |error_code| and exit.
59 */ 55 */
60void spdy_diec(const char *func, int error_code) 56void
57spdy_diec(const char *func,
58 int error_code)
61{ 59{
62 fprintf(stderr, "FATAL: %s: error_code=%d, msg=%s\n", func, error_code, 60 fprintf(stderr, "FATAL: %s: error_code=%d, msg=%s\n", func, error_code,
63 spdylay_strerror(error_code)); 61 spdylay_strerror(error_code));
@@ -71,11 +69,12 @@ void spdy_diec(const char *func, int error_code)
71 * bytes actually written. See the documentation of 69 * bytes actually written. See the documentation of
72 * spdylay_send_callback for the details. 70 * spdylay_send_callback for the details.
73 */ 71 */
74static ssize_t spdy_cb_send(spdylay_session *session, 72static ssize_t
75 const uint8_t *data, 73spdy_cb_send(spdylay_session *session,
76 size_t length, 74 const uint8_t *data,
77 int flags, 75 size_t length,
78 void *user_data) 76 int flags,
77 void *user_data)
79{ 78{
80 (void)session; 79 (void)session;
81 (void)flags; 80 (void)flags;
@@ -126,15 +125,19 @@ static ssize_t spdy_cb_send(spdylay_session *session,
126 return rv; 125 return rv;
127} 126}
128 127
128
129/* 129/*
130 * The implementation of spdylay_recv_callback type. Here we read data 130 * The implementation of spdylay_recv_callback type. Here we read data
131 * from the network and write them in |buf|. The capacity of |buf| is 131 * from the network and write them in |buf|. The capacity of |buf| is
132 * |length| bytes. Returns the number of bytes stored in |buf|. See 132 * |length| bytes. Returns the number of bytes stored in |buf|. See
133 * the documentation of spdylay_recv_callback for the details. 133 * the documentation of spdylay_recv_callback for the details.
134 */ 134 */
135static ssize_t spdy_cb_recv(spdylay_session *session, 135static ssize_t
136 uint8_t *buf, size_t length, int flags, 136spdy_cb_recv(spdylay_session *session,
137 void *user_data) 137 uint8_t *buf,
138 size_t length,
139 int flags,
140 void *user_data)
138{ 141{
139 (void)session; 142 (void)session;
140 (void)flags; 143 (void)flags;
@@ -191,63 +194,47 @@ static ssize_t spdy_cb_recv(spdylay_session *session,
191 return rv; 194 return rv;
192} 195}
193 196
194/*
195 * The implementation of spdylay_before_ctrl_send_callback type. We
196 * use this function to get stream ID of the request. This is because
197 * stream ID is not known when we submit the request
198 * (spdylay_spdy_submit_request).
199 */
200/*static void spdy_cb_before_ctrl_send(spdylay_session *session,
201 spdylay_frame_type type,
202 spdylay_frame *frame,
203 void *user_data)
204{
205}*/
206
207 197
208static void spdy_cb_on_ctrl_send(spdylay_session *session, 198static void
209 spdylay_frame_type type, 199spdy_cb_on_ctrl_send(spdylay_session *session,
210 spdylay_frame *frame, void *user_data) 200 spdylay_frame_type type,
201 spdylay_frame *frame,
202 void *user_data)
211{ 203{
212 (void)user_data; 204 (void)user_data;
213 205
214 //char **nv;
215 //const char *name = NULL;
216 int32_t stream_id; 206 int32_t stream_id;
217 //size_t i;
218 struct Proxy *proxy; 207 struct Proxy *proxy;
219 208
220 switch(type) { 209 switch(type) {
221 case SPDYLAY_SYN_STREAM: 210 case SPDYLAY_SYN_STREAM:
222 //nv = frame->syn_stream.nv; 211 stream_id = frame->syn_stream.stream_id;
223 //name = "SYN_STREAM"; 212 proxy = spdylay_session_get_stream_user_data(session, stream_id);
224 stream_id = frame->syn_stream.stream_id; 213 ++glob_opt.streams_opened;
225 proxy = spdylay_session_get_stream_user_data(session, stream_id); 214 ++proxy->spdy_connection->streams_opened;
226 ++glob_opt.streams_opened; 215 PRINT_INFO2("opening stream: str open %i; %s", glob_opt.streams_opened, proxy->url);
227 ++proxy->spdy_connection->streams_opened; 216 break;
228 PRINT_INFO2("opening stream: str open %i; %s", glob_opt.streams_opened, proxy->url); 217 default:
229 break; 218 break;
230 default:
231 break;
232 } 219 }
233} 220}
234 221
235void spdy_cb_on_ctrl_recv(spdylay_session *session, 222
236 spdylay_frame_type type, 223void
237 spdylay_frame *frame, void *user_data) 224spdy_cb_on_ctrl_recv(spdylay_session *session,
225 spdylay_frame_type type,
226 spdylay_frame *frame,
227 void *user_data)
238{ 228{
239 (void)user_data; 229 (void)user_data;
240 230
241 //struct SPDY_Request *req;
242 char **nv; 231 char **nv;
243 //const char *name = NULL;
244 int32_t stream_id; 232 int32_t stream_id;
245 struct Proxy * proxy; 233 struct Proxy * proxy;
246 234
247 switch(type) { 235 switch(type) {
248 case SPDYLAY_SYN_REPLY: 236 case SPDYLAY_SYN_REPLY:
249 nv = frame->syn_reply.nv; 237 nv = frame->syn_reply.nv;
250 //name = "SYN_REPLY";
251 stream_id = frame->syn_reply.stream_id; 238 stream_id = frame->syn_reply.stream_id;
252 break; 239 break;
253 case SPDYLAY_RST_STREAM: 240 case SPDYLAY_RST_STREAM:
@@ -255,7 +242,6 @@ void spdy_cb_on_ctrl_recv(spdylay_session *session,
255 break; 242 break;
256 case SPDYLAY_HEADERS: 243 case SPDYLAY_HEADERS:
257 nv = frame->headers.nv; 244 nv = frame->headers.nv;
258 //name = "HEADERS";
259 stream_id = frame->headers.stream_id; 245 stream_id = frame->headers.stream_id;
260 break; 246 break;
261 default: 247 default:
@@ -269,34 +255,37 @@ void spdy_cb_on_ctrl_recv(spdylay_session *session,
269 255
270 switch(type) { 256 switch(type) {
271 case SPDYLAY_SYN_REPLY: 257 case SPDYLAY_SYN_REPLY:
272 PRINT_INFO2("received headers for %s", proxy->url); 258 PRINT_INFO2("received headers for %s", proxy->url);
273 http_create_response(proxy, nv); 259 http_create_response(proxy, nv);
274 break; 260 break;
275 case SPDYLAY_RST_STREAM: 261 case SPDYLAY_RST_STREAM:
276 PRINT_INFO2("received reset stream for %s", proxy->url); 262 PRINT_INFO2("received reset stream for %s", proxy->url);
277 proxy->error = true; 263 proxy->error = true;
278 break; 264 break;
279 case SPDYLAY_HEADERS: 265 case SPDYLAY_HEADERS:
280 PRINT_INFO2("received headers for %s", proxy->url); 266 PRINT_INFO2("received headers for %s", proxy->url);
281 http_create_response(proxy, nv); 267 http_create_response(proxy, nv);
282 break; 268 break;
283 default: 269 default:
284 return; 270 return;
285 break; 271 break;
286 } 272 }
273
287 glob_opt.spdy_data_received = true; 274 glob_opt.spdy_data_received = true;
288} 275}
289 276
277
290/* 278/*
291 * The implementation of spdylay_on_stream_close_callback type. We use 279 * The implementation of spdylay_on_stream_close_callback type. We use
292 * this function to know the response is fully received. Since we just 280 * this function to know the response is fully received. Since we just
293 * fetch 1 resource in this program, after reception of the response, 281 * fetch 1 resource in this program, after reception of the response,
294 * we submit GOAWAY and close the session. 282 * we submit GOAWAY and close the session.
295 */ 283 */
296static void spdy_cb_on_stream_close(spdylay_session *session, 284static void
297 int32_t stream_id, 285spdy_cb_on_stream_close(spdylay_session *session,
298 spdylay_status_code status_code, 286 int32_t stream_id,
299 void *user_data) 287 spdylay_status_code status_code,
288 void *user_data)
300{ 289{
301 (void)status_code; 290 (void)status_code;
302 (void)user_data; 291 (void)user_data;
@@ -315,24 +304,24 @@ static void spdy_cb_on_stream_close(spdylay_session *session,
315 proxy->spdy_active = false; 304 proxy->spdy_active = false;
316 else 305 else
317 free_proxy(proxy); 306 free_proxy(proxy);
318 return;
319} 307}
320 308
321#define SPDY_MAX_OUTLEN 4096
322 309
323/* 310/*
324 * The implementation of spdylay_on_data_chunk_recv_callback type. We 311 * The implementation of spdylay_on_data_chunk_recv_callback type. We
325 * use this function to print the received response body. 312 * use this function to print the received response body.
326 */ 313 */
327static void spdy_cb_on_data_chunk_recv(spdylay_session *session, uint8_t flags, 314static void
328 int32_t stream_id, 315spdy_cb_on_data_chunk_recv(spdylay_session *session,
329 const uint8_t *data, size_t len, 316 uint8_t flags,
330 void *user_data) 317 int32_t stream_id,
318 const uint8_t *data,
319 size_t len,
320 void *user_data)
331{ 321{
332 (void)flags; 322 (void)flags;
333 (void)user_data; 323 (void)user_data;
334 324
335 //struct SPDY_Request *req;
336 struct Proxy *proxy; 325 struct Proxy *proxy;
337 proxy = spdylay_session_get_stream_user_data(session, stream_id); 326 proxy = spdylay_session_get_stream_user_data(session, stream_id);
338 327
@@ -348,12 +337,17 @@ static void spdy_cb_on_data_chunk_recv(spdylay_session *session, uint8_t flags,
348 337
349 memcpy(proxy->http_body + proxy->http_body_size, data, len); 338 memcpy(proxy->http_body + proxy->http_body_size, data, len);
350 proxy->http_body_size += len; 339 proxy->http_body_size += len;
351 PRINT_INFO2("received data for %s; %zu bytes", proxy->url, len); 340 PRINT_INFO2("received data for %s; %zu bytes", proxy->url, len);
352 glob_opt.spdy_data_received = true; 341 glob_opt.spdy_data_received = true;
353} 342}
354 343
355static void spdy_cb_on_data_recv(spdylay_session *session, 344
356 uint8_t flags, int32_t stream_id, int32_t length, void *user_data) 345static void
346spdy_cb_on_data_recv(spdylay_session *session,
347 uint8_t flags,
348 int32_t stream_id,
349 int32_t length,
350 void *user_data)
357{ 351{
358 (void)length; 352 (void)length;
359 (void)user_data; 353 (void)user_data;
@@ -367,18 +361,19 @@ static void spdy_cb_on_data_recv(spdylay_session *session,
367 } 361 }
368} 362}
369 363
364
370/* 365/*
371 * Setup callback functions. Spdylay API offers many callback 366 * Setup callback functions. Spdylay API offers many callback
372 * functions, but most of them are optional. The send_callback is 367 * functions, but most of them are optional. The send_callback is
373 * always required. Since we use spdylay_session_recv(), the 368 * always required. Since we use spdylay_session_recv(), the
374 * recv_callback is also required. 369 * recv_callback is also required.
375 */ 370 */
376static void spdy_setup_spdylay_callbacks(spdylay_session_callbacks *callbacks) 371static void
372spdy_setup_spdylay_callbacks(spdylay_session_callbacks *callbacks)
377{ 373{
378 memset(callbacks, 0, sizeof(spdylay_session_callbacks)); 374 memset(callbacks, 0, sizeof(spdylay_session_callbacks));
379 callbacks->send_callback = spdy_cb_send; 375 callbacks->send_callback = spdy_cb_send;
380 callbacks->recv_callback = spdy_cb_recv; 376 callbacks->recv_callback = spdy_cb_recv;
381 //callbacks->before_ctrl_send_callback = spdy_cb_before_ctrl_send;
382 callbacks->on_ctrl_send_callback = spdy_cb_on_ctrl_send; 377 callbacks->on_ctrl_send_callback = spdy_cb_on_ctrl_send;
383 callbacks->on_ctrl_recv_callback = spdy_cb_on_ctrl_recv; 378 callbacks->on_ctrl_recv_callback = spdy_cb_on_ctrl_recv;
384 callbacks->on_stream_close_callback = spdy_cb_on_stream_close; 379 callbacks->on_stream_close_callback = spdy_cb_on_stream_close;
@@ -386,21 +381,25 @@ static void spdy_setup_spdylay_callbacks(spdylay_session_callbacks *callbacks)
386 callbacks->on_data_recv_callback = spdy_cb_on_data_recv; 381 callbacks->on_data_recv_callback = spdy_cb_on_data_recv;
387} 382}
388 383
384
389/* 385/*
390 * Callback function for SSL/TLS NPN. Since this program only supports 386 * Callback function for SSL/TLS NPN. Since this program only supports
391 * SPDY protocol, if server does not offer SPDY protocol the Spdylay 387 * SPDY protocol, if server does not offer SPDY protocol the Spdylay
392 * library supports, we terminate program. 388 * library supports, we terminate program.
393 */ 389 */
394static int spdy_cb_ssl_select_next_proto(SSL* ssl, 390static int
395 unsigned char **out, unsigned char *outlen, 391spdy_cb_ssl_select_next_proto(SSL* ssl,
396 const unsigned char *in, unsigned int inlen, 392 unsigned char **out,
393 unsigned char *outlen,
394 const unsigned char *in,
395 unsigned int inlen,
397 void *arg) 396 void *arg)
398{ 397{
399 (void)ssl; 398 (void)ssl;
400 399
401 //PRINT_INFO("spdy_cb_ssl_select_next_proto");
402 int rv; 400 int rv;
403 uint16_t *spdy_proto_version; 401 uint16_t *spdy_proto_version;
402
404 /* spdylay_select_next_protocol() selects SPDY protocol version the 403 /* spdylay_select_next_protocol() selects SPDY protocol version the
405 Spdylay library supports. */ 404 Spdylay library supports. */
406 rv = spdylay_select_next_protocol(out, outlen, in, inlen); 405 rv = spdylay_select_next_protocol(out, outlen, in, inlen);
@@ -413,11 +412,14 @@ static int spdy_cb_ssl_select_next_proto(SSL* ssl,
413 return SSL_TLSEXT_ERR_OK; 412 return SSL_TLSEXT_ERR_OK;
414} 413}
415 414
415
416/* 416/*
417 * Setup SSL context. We pass |spdy_proto_version| to get negotiated 417 * Setup SSL context. We pass |spdy_proto_version| to get negotiated
418 * SPDY protocol version in NPN callback. 418 * SPDY protocol version in NPN callback.
419 */ 419 */
420void spdy_ssl_init_ssl_ctx(SSL_CTX *ssl_ctx, uint16_t *spdy_proto_version) 420void
421spdy_ssl_init_ssl_ctx(SSL_CTX *ssl_ctx,
422 uint16_t *spdy_proto_version)
421{ 423{
422 /* Disable SSLv2 and enable all workarounds for buggy servers */ 424 /* Disable SSLv2 and enable all workarounds for buggy servers */
423 SSL_CTX_set_options(ssl_ctx, SSL_OP_ALL|SSL_OP_NO_SSLv2 | SSL_OP_NO_COMPRESSION); 425 SSL_CTX_set_options(ssl_ctx, SSL_OP_ALL|SSL_OP_NO_SSLv2 | SSL_OP_NO_COMPRESSION);
@@ -428,153 +430,184 @@ void spdy_ssl_init_ssl_ctx(SSL_CTX *ssl_ctx, uint16_t *spdy_proto_version)
428 spdy_proto_version); 430 spdy_proto_version);
429} 431}
430 432
431static int spdy_ssl_handshake(SSL *ssl, int fd) 433
434static int
435spdy_ssl_handshake(SSL *ssl,
436 int fd)
432{ 437{
433 int rv; 438 int rv;
434 if(SSL_set_fd(ssl, fd) == 0) { 439
440 if(SSL_set_fd(ssl, fd) == 0)
435 spdy_dief("SSL_set_fd", ERR_error_string(ERR_get_error(), NULL)); 441 spdy_dief("SSL_set_fd", ERR_error_string(ERR_get_error(), NULL));
436 } 442
437 ERR_clear_error(); 443 ERR_clear_error();
438 rv = SSL_connect(ssl); 444 rv = SSL_connect(ssl);
439 if(rv <= 0) { 445 if(rv <= 0)
440 PRINT_INFO2("SSL_connect %s", ERR_error_string(ERR_get_error(), NULL)); 446 PRINT_INFO2("SSL_connect %s", ERR_error_string(ERR_get_error(), NULL));
441 }
442 447
443 return rv; 448 return rv;
444} 449}
445 450
451
446/* 452/*
447 * Connects to the host |host| and port |port|. This function returns 453 * Connects to the host |host| and port |port|. This function returns
448 * the file descriptor of the client socket. 454 * the file descriptor of the client socket.
449 */ 455 */
450static int spdy_socket_connect_to(const char *host, uint16_t port) 456static int
457spdy_socket_connect_to(const char *host,
458 uint16_t port)
451{ 459{
452 struct addrinfo hints; 460 struct addrinfo hints;
453 int fd = -1; 461 int fd = -1;
454 int rv; 462 int rv;
455 char service[NI_MAXSERV]; 463 char service[NI_MAXSERV];
456 struct addrinfo *res, *rp; 464 struct addrinfo *res, *rp;
465
466 //TODO checks
457 snprintf(service, sizeof(service), "%u", port); 467 snprintf(service, sizeof(service), "%u", port);
458 memset(&hints, 0, sizeof(struct addrinfo)); 468 memset(&hints, 0, sizeof(struct addrinfo));
459 hints.ai_family = AF_UNSPEC; 469 hints.ai_family = AF_UNSPEC;
460 hints.ai_socktype = SOCK_STREAM; 470 hints.ai_socktype = SOCK_STREAM;
461 rv = getaddrinfo(host, service, &hints, &res); 471 rv = getaddrinfo(host, service, &hints, &res);
462 if(rv != 0) { 472 if(rv != 0)
473 {
463 printf("%s\n",host); 474 printf("%s\n",host);
464 spdy_dief("getaddrinfo", gai_strerror(rv)); 475 spdy_dief("getaddrinfo", gai_strerror(rv));
465 } 476 }
466 for(rp = res; rp; rp = rp->ai_next) { 477 for(rp = res; rp; rp = rp->ai_next)
478 {
467 fd = socket(rp->ai_family, rp->ai_socktype, rp->ai_protocol); 479 fd = socket(rp->ai_family, rp->ai_socktype, rp->ai_protocol);
468 if(fd == -1) { 480 if(fd == -1)
469 continue; 481 continue;
470 }
471 while((rv = connect(fd, rp->ai_addr, rp->ai_addrlen)) == -1 && 482 while((rv = connect(fd, rp->ai_addr, rp->ai_addrlen)) == -1 &&
472 errno == EINTR); 483 errno == EINTR);
473 if(rv == 0) { 484 if(rv == 0)
474 break; 485 break;
475 }
476 close(fd); 486 close(fd);
477 fd = -1; 487 fd = -1;
478 } 488 }
479 freeaddrinfo(res); 489 freeaddrinfo(res);
490
480 return fd; 491 return fd;
481} 492}
482 493
483static void spdy_socket_make_non_block(int fd) 494
495static void
496spdy_socket_make_non_block(int fd)
484{ 497{
485 int flags, rv; 498 int flags;
499 int rv;
500
486 while((flags = fcntl(fd, F_GETFL, 0)) == -1 && errno == EINTR); 501 while((flags = fcntl(fd, F_GETFL, 0)) == -1 && errno == EINTR);
487 if(flags == -1) { 502
503 if(flags == -1)
488 spdy_dief("fcntl", strerror(errno)); 504 spdy_dief("fcntl", strerror(errno));
489 } 505
490 while((rv = fcntl(fd, F_SETFL, flags | O_NONBLOCK)) == -1 && errno == EINTR); 506 while((rv = fcntl(fd, F_SETFL, flags | O_NONBLOCK)) == -1 && errno == EINTR);
491 if(rv == -1) { 507
508 if(rv == -1)
492 spdy_dief("fcntl", strerror(errno)); 509 spdy_dief("fcntl", strerror(errno));
493 }
494} 510}
495 511
512
496/* 513/*
497 * Setting TCP_NODELAY is not mandatory for the SPDY protocol. 514 * Setting TCP_NODELAY is not mandatory for the SPDY protocol.
498 */ 515 */
499static void spdy_socket_set_tcp_nodelay(int fd) 516static void
517spdy_socket_set_tcp_nodelay(int fd)
500{ 518{
501 int val = 1; 519 int val = 1;
502 int rv; 520 int rv;
521
503 rv = setsockopt(fd, IPPROTO_TCP, TCP_NODELAY, &val, (socklen_t)sizeof(val)); 522 rv = setsockopt(fd, IPPROTO_TCP, TCP_NODELAY, &val, (socklen_t)sizeof(val));
504 if(rv == -1) { 523 if(rv == -1)
505 spdy_dief("setsockopt", strerror(errno)); 524 spdy_dief("setsockopt", strerror(errno));
506 }
507} 525}
508 526
509/* 527/*
510 * Update |pollfd| based on the state of |connection|. 528 * Update |pollfd| based on the state of |connection|.
511 */ 529 */
512void spdy_ctl_poll(struct pollfd *pollfd, struct SPDY_Connection *connection) 530void
531spdy_ctl_poll(struct pollfd *pollfd,
532 struct SPDY_Connection *connection)
513{ 533{
514 pollfd->events = 0; 534 pollfd->events = 0;
515 if(spdylay_session_want_read(connection->session) || 535 if(spdylay_session_want_read(connection->session) ||
516 connection->want_io == WANT_READ) { 536 connection->want_io == WANT_READ)
537 {
517 pollfd->events |= POLLIN; 538 pollfd->events |= POLLIN;
518 } 539 }
519 if(spdylay_session_want_write(connection->session) || 540 if(spdylay_session_want_write(connection->session) ||
520 connection->want_io == WANT_WRITE) { 541 connection->want_io == WANT_WRITE)
542 {
521 pollfd->events |= POLLOUT; 543 pollfd->events |= POLLOUT;
522 } 544 }
523} 545}
524 546
547
525/* 548/*
526 * Update |selectfd| based on the state of |connection|. 549 * Update |selectfd| based on the state of |connection|.
527 */ 550 */
528bool spdy_ctl_select(fd_set * read_fd_set, 551bool
529 fd_set * write_fd_set, 552spdy_ctl_select(fd_set * read_fd_set,
530 fd_set * except_fd_set, 553 fd_set * write_fd_set,
531 struct SPDY_Connection *connection) 554 fd_set * except_fd_set,
555 struct SPDY_Connection *connection)
532{ 556{
533 (void)except_fd_set; 557 (void)except_fd_set;
534 558
535 bool ret = false; 559 bool ret = false;
536 560
537 if(spdylay_session_want_read(connection->session) || 561 if(spdylay_session_want_read(connection->session) ||
538 connection->want_io == WANT_READ) { 562 connection->want_io == WANT_READ)
563 {
539 FD_SET(connection->fd, read_fd_set); 564 FD_SET(connection->fd, read_fd_set);
540 ret = true; 565 ret = true;
541 } 566 }
542 if(spdylay_session_want_write(connection->session) || 567 if(spdylay_session_want_write(connection->session) ||
543 connection->want_io == WANT_WRITE) { 568 connection->want_io == WANT_WRITE)
569 {
544 FD_SET(connection->fd, write_fd_set); 570 FD_SET(connection->fd, write_fd_set);
545 ret = true; 571 ret = true;
546 } 572 }
573
547 return ret; 574 return ret;
548} 575}
549 576
577
550/* 578/*
551 * Performs the network I/O. 579 * Performs the network I/O.
552 */ 580 */
553int spdy_exec_io(struct SPDY_Connection *connection) 581int
582spdy_exec_io(struct SPDY_Connection *connection)
554{ 583{
555 int rv; 584 int rv;
585
556 rv = spdylay_session_recv(connection->session); 586 rv = spdylay_session_recv(connection->session);
557 if(rv != 0) { 587 if(rv != 0)
588 {
558 PRINT_INFO2("spdylay_session_recv %i", rv); 589 PRINT_INFO2("spdylay_session_recv %i", rv);
559 return rv; 590 return rv;
560 } 591 }
561 rv = spdylay_session_send(connection->session); 592 rv = spdylay_session_send(connection->session);
562 if(rv != 0) { 593 if(rv != 0)
563 PRINT_INFO2("spdylay_session_send %i", rv); 594 PRINT_INFO2("spdylay_session_send %i", rv);
564 } 595
565 return rv; 596 return rv;
566} 597}
567 598
599
568/* 600/*
569 * Fetches the resource denoted by |uri|. 601 * Fetches the resource denoted by |uri|.
570 */ 602 */
571struct SPDY_Connection * spdy_connect(const struct URI *uri, uint16_t port, bool is_tls) 603struct SPDY_Connection *
604spdy_connect(const struct URI *uri,
605 uint16_t port,
606 bool is_tls)
572{ 607{
573 spdylay_session_callbacks callbacks; 608 spdylay_session_callbacks callbacks;
574 int fd; 609 int fd;
575 //SSL_CTX *ssl_ctx;
576 SSL *ssl=NULL; 610 SSL *ssl=NULL;
577 //struct SPDY_Request req;
578 struct SPDY_Connection * connection; 611 struct SPDY_Connection * connection;
579 int rv; 612 int rv;
580 613
@@ -583,19 +616,14 @@ struct SPDY_Connection * spdy_connect(const struct URI *uri, uint16_t port, bool
583 /* Establish connection and setup SSL */ 616 /* Establish connection and setup SSL */
584 PRINT_INFO2("connecting to %s:%i", uri->host, port); 617 PRINT_INFO2("connecting to %s:%i", uri->host, port);
585 fd = spdy_socket_connect_to(uri->host, port); 618 fd = spdy_socket_connect_to(uri->host, port);
586 if(fd == -1) { 619 if(fd == -1)
620 {
587 PRINT_INFO("Could not open file descriptor"); 621 PRINT_INFO("Could not open file descriptor");
588 return NULL;//glob_opt.spdy_connection; 622 return NULL;
589 } 623 }
590 624
591 if(is_tls) 625 if(is_tls)
592 { 626 {
593 /*ssl_ctx = SSL_CTX_new(SSLv23_client_method());
594 if(ssl_ctx == NULL) {
595 spdy_dief("SSL_CTX_new", ERR_error_string(ERR_get_error(), NULL));
596 }
597 spdy_ssl_init_ssl_ctx(ssl_ctx, &spdy_proto_version);
598 */
599 ssl = SSL_new(glob_opt.ssl_ctx); 627 ssl = SSL_new(glob_opt.ssl_ctx);
600 if(ssl == NULL) { 628 if(ssl == NULL) {
601 spdy_dief("SSL_new", ERR_error_string(ERR_get_error(), NULL)); 629 spdy_dief("SSL_new", ERR_error_string(ERR_get_error(), NULL));
@@ -624,7 +652,6 @@ struct SPDY_Connection * spdy_connect(const struct URI *uri, uint16_t port, bool
624 652
625 if(NULL == (connection = au_malloc(sizeof(struct SPDY_Connection)))) 653 if(NULL == (connection = au_malloc(sizeof(struct SPDY_Connection))))
626 return NULL; 654 return NULL;
627 //memset(connection, 0 , sizeof(struct SPDY_Connection));
628 655
629 connection->is_tls = is_tls; 656 connection->is_tls = is_tls;
630 connection->ssl = ssl; 657 connection->ssl = ssl;
@@ -647,6 +674,7 @@ struct SPDY_Connection * spdy_connect(const struct URI *uri, uint16_t port, bool
647 return connection; 674 return connection;
648} 675}
649 676
677
650void 678void
651spdy_free_connection(struct SPDY_Connection * connection) 679spdy_free_connection(struct SPDY_Connection * connection)
652{ 680{
@@ -659,8 +687,10 @@ spdy_free_connection(struct SPDY_Connection * connection)
659 } 687 }
660} 688}
661 689
690
662int 691int
663spdy_request(const char **nv, struct Proxy *proxy) 692spdy_request(const char **nv,
693 struct Proxy *proxy)
664{ 694{
665 int ret; 695 int ret;
666 uint16_t port; 696 uint16_t port;
@@ -714,13 +744,18 @@ spdy_request(const char **nv, struct Proxy *proxy)
714 744
715 745
716void 746void
717spdy_get_pollfdset(struct pollfd fds[], struct SPDY_Connection *connections[], unsigned int max_size, nfds_t *real_size) 747spdy_get_pollfdset(struct pollfd fds[],
748 struct SPDY_Connection *connections[],
749 unsigned int max_size,
750 nfds_t *real_size)
718{ 751{
719 struct SPDY_Connection *connection; 752 struct SPDY_Connection *connection;
720 struct Proxy *proxy; 753 struct Proxy *proxy;
721 754
722 *real_size = 0; 755 *real_size = 0;
723 if(max_size<1) return; 756 if(max_size<1)
757 return;
758
724 if(NULL != glob_opt.spdy_connection) 759 if(NULL != glob_opt.spdy_connection)
725 { 760 {
726 spdy_ctl_poll(&(fds[*real_size]), glob_opt.spdy_connection); 761 spdy_ctl_poll(&(fds[*real_size]), glob_opt.spdy_connection);
@@ -781,9 +816,11 @@ spdy_get_pollfdset(struct pollfd fds[], struct SPDY_Connection *connections[], u
781 816
782int 817int
783spdy_get_selectfdset(fd_set * read_fd_set, 818spdy_get_selectfdset(fd_set * read_fd_set,
784 fd_set * write_fd_set, 819 fd_set * write_fd_set,
785 fd_set * except_fd_set, 820 fd_set * except_fd_set,
786 struct SPDY_Connection *connections[], unsigned int max_size, nfds_t *real_size) 821 struct SPDY_Connection *connections[],
822 unsigned int max_size,
823 nfds_t *real_size)
787{ 824{
788 struct SPDY_Connection *connection; 825 struct SPDY_Connection *connection;
789 struct Proxy *proxy; 826 struct Proxy *proxy;
@@ -791,7 +828,9 @@ spdy_get_selectfdset(fd_set * read_fd_set,
791 int maxfd = 0; 828 int maxfd = 0;
792 829
793 *real_size = 0; 830 *real_size = 0;
794 if(max_size<1) return 0; 831 if(max_size<1)
832 return 0;
833
795 if(NULL != glob_opt.spdy_connection) 834 if(NULL != glob_opt.spdy_connection)
796 { 835 {
797 ret = spdy_ctl_select(read_fd_set, 836 ret = spdy_ctl_select(read_fd_set,
@@ -857,12 +896,13 @@ spdy_get_selectfdset(fd_set * read_fd_set,
857 896
858 897
859void 898void
860spdy_run(struct pollfd fds[], struct SPDY_Connection *connections[], int size) 899spdy_run(struct pollfd fds[],
900 struct SPDY_Connection *connections[],
901 int size)
861{ 902{
862 int i; 903 int i;
863 int ret; 904 int ret;
864 struct Proxy *proxy; 905 struct Proxy *proxy;
865 //PRINT_INFO2("size is %i", size);
866 906
867 for(i=0; i<size; ++i) 907 for(i=0; i<size; ++i)
868 { 908 {
@@ -898,21 +938,20 @@ spdy_run(struct pollfd fds[], struct SPDY_Connection *connections[], int size)
898 } 938 }
899 } 939 }
900 else 940 else
901 {
902 PRINT_INFO("not called"); 941 PRINT_INFO("not called");
903 }
904 } 942 }
905} 943}
906 944
907void 945void
908spdy_run_select(fd_set * read_fd_set, 946spdy_run_select(fd_set * read_fd_set,
909 fd_set * write_fd_set, 947 fd_set * write_fd_set,
910 fd_set * except_fd_set, struct SPDY_Connection *connections[], int size) 948 fd_set * except_fd_set,
949 struct SPDY_Connection *connections[],
950 int size)
911{ 951{
912 int i; 952 int i;
913 int ret; 953 int ret;
914 struct Proxy *proxy; 954 struct Proxy *proxy;
915 //PRINT_INFO2("size is %i", size);
916 955
917 for(i=0; i<size; ++i) 956 for(i=0; i<size; ++i)
918 { 957 {
@@ -920,12 +959,6 @@ spdy_run_select(fd_set * read_fd_set,
920 if(FD_ISSET(connections[i]->fd, read_fd_set) || FD_ISSET(connections[i]->fd, write_fd_set) || FD_ISSET(connections[i]->fd, except_fd_set)) 959 if(FD_ISSET(connections[i]->fd, read_fd_set) || FD_ISSET(connections[i]->fd, write_fd_set) || FD_ISSET(connections[i]->fd, except_fd_set))
921 { 960 {
922 ret = spdy_exec_io(connections[i]); 961 ret = spdy_exec_io(connections[i]);
923 //PRINT_INFO2("%i",ret);
924 //if((spdy_pollfds[i].revents & POLLHUP) || (spdy_pollfds[0].revents & POLLERR))
925 // PRINT_INFO("SPDY SPDY_Connection error");
926
927 //TODO POLLRDHUP
928 // always close on ret != 0?
929 962
930 if(0 != ret) 963 if(0 != ret)
931 { 964 {
@@ -948,8 +981,6 @@ spdy_run_select(fd_set * read_fd_set,
948 } 981 }
949 } 982 }
950 else 983 else
951 {
952 PRINT_INFO("not called"); 984 PRINT_INFO("not called");
953 }
954 } 985 }
955} 986}
diff --git a/src/examples/mhd2spdy_spdy.h b/src/examples/mhd2spdy_spdy.h
index fa27e7f6..980ee1d1 100644
--- a/src/examples/mhd2spdy_spdy.h
+++ b/src/examples/mhd2spdy_spdy.h
@@ -26,43 +26,76 @@
26 26
27#include "mhd2spdy_structures.h" 27#include "mhd2spdy_structures.h"
28 28
29struct SPDY_Connection * spdy_connect(const struct URI *uri, uint16_t port, bool is_tls);
30 29
31void spdy_ctl_poll(struct pollfd *pollfd, struct SPDY_Connection *connection); 30struct SPDY_Connection *
31spdy_connect(const struct URI *uri,
32 uint16_t port,
33 bool is_tls);
32 34
33bool spdy_ctl_select(fd_set * read_fd_set,
34 fd_set * write_fd_set,
35 fd_set * except_fd_set,
36 struct SPDY_Connection *connection);
37 35
38int spdy_exec_io(struct SPDY_Connection *connection); 36void
37spdy_ctl_poll(struct pollfd *pollfd,
38 struct SPDY_Connection *connection);
39
40
41bool
42spdy_ctl_select(fd_set * read_fd_set,
43 fd_set * write_fd_set,
44 fd_set * except_fd_set,
45 struct SPDY_Connection *connection);
46
47
48int
49spdy_exec_io(struct SPDY_Connection *connection);
50
51
52void
53spdy_diec(const char *func,
54 int error_code);
39 55
40void spdy_diec(const char *func, int error_code);
41 56
42int 57int
43spdy_request(const char **nv, struct Proxy *proxy); 58spdy_request(const char **nv,
59 struct Proxy *proxy);
60
61
62void
63spdy_ssl_init_ssl_ctx(SSL_CTX *ssl_ctx,
64 uint16_t *spdy_proto_version);
44 65
45void spdy_ssl_init_ssl_ctx(SSL_CTX *ssl_ctx, uint16_t *spdy_proto_version);
46 66
47void 67void
48spdy_free_connection(struct SPDY_Connection * connection); 68spdy_free_connection(struct SPDY_Connection * connection);
49 69
70
50void 71void
51spdy_get_pollfdset(struct pollfd fds[], struct SPDY_Connection *connections[], unsigned int max_size, nfds_t *real_size); 72spdy_get_pollfdset(struct pollfd fds[],
73 struct SPDY_Connection *connections[],
74 unsigned int max_size,
75 nfds_t *real_size);
52 76
53 77
54int 78int
55spdy_get_selectfdset(fd_set * read_fd_set, 79spdy_get_selectfdset(fd_set * read_fd_set,
56 fd_set * write_fd_set, 80 fd_set * write_fd_set,
57 fd_set * except_fd_set, 81 fd_set * except_fd_set,
58 struct SPDY_Connection *connections[], unsigned int max_size, nfds_t *real_size); 82 struct SPDY_Connection *connections[],
59 83 unsigned int max_size,
84 nfds_t *real_size);
85
86
60void 87void
61spdy_run(struct pollfd fds[], struct SPDY_Connection *connections[], int size); 88spdy_run(struct pollfd fds[],
89 struct SPDY_Connection *connections[],
90 int size);
91
62 92
63void 93void
64spdy_run_select(fd_set * read_fd_set, 94spdy_run_select(fd_set * read_fd_set,
65 fd_set * write_fd_set, 95 fd_set * write_fd_set,
66 fd_set * except_fd_set, struct SPDY_Connection *connections[], int size); 96 fd_set * except_fd_set,
67 97 struct SPDY_Connection *connections[],
98 int size);
99
100
68#endif 101#endif
diff --git a/src/examples/mhd2spdy_structures.c b/src/examples/mhd2spdy_structures.c
index da29581c..2982b2a4 100644
--- a/src/examples/mhd2spdy_structures.c
+++ b/src/examples/mhd2spdy_structures.c
@@ -32,7 +32,6 @@ free_uri(struct URI * uri)
32 free(uri->full_uri); 32 free(uri->full_uri);
33 free(uri->scheme); 33 free(uri->scheme);
34 free(uri->host_and_port); 34 free(uri->host_and_port);
35 //free(uri->host_and_port_for_connecting);
36 free(uri->host); 35 free(uri->host);
37 free(uri->path); 36 free(uri->path);
38 free(uri->path_and_more); 37 free(uri->path_and_more);
@@ -43,6 +42,7 @@ free_uri(struct URI * uri)
43 } 42 }
44} 43}
45 44
45
46int 46int
47init_parse_uri(regex_t * preg) 47init_parse_uri(regex_t * preg)
48{ 48{
@@ -66,7 +66,9 @@ deinit_parse_uri(regex_t * preg)
66} 66}
67 67
68int 68int
69parse_uri(regex_t * preg, char * full_uri, struct URI ** uri) 69parse_uri(regex_t * preg,
70 char * full_uri,
71 struct URI ** uri)
70{ 72{
71 int ret; 73 int ret;
72 char *colon; 74 char *colon;
@@ -94,22 +96,8 @@ parse_uri(regex_t * preg, char * full_uri, struct URI ** uri)
94 if(NULL == colon) 96 if(NULL == colon)
95 { 97 {
96 (*uri)->host = strdup((*uri)->host_and_port); 98 (*uri)->host = strdup((*uri)->host_and_port);
97 /*if(0 == strcasecmp("http", uri->scheme)) 99 (*uri)->port = 0;
98 { 100
99 uri->port = 80;
100 asprintf(&(uri->host_and_port_for_connecting), "%s:80", uri->host_and_port);
101 }
102 else if(0 == strcasecmp("https", uri->scheme))
103 {
104 uri->port = 443;
105 asprintf(&(uri->host_and_port_for_connecting), "%s:443", uri->host_and_port);
106 }
107 else
108 {
109 PRINT_INFO("no standard scheme!");
110 */(*uri)->port = 0;
111 /*uri->host_and_port_for_connecting = strdup(uri->host_and_port);
112 }*/
113 return 0; 101 return 0;
114 } 102 }
115 103
@@ -125,6 +113,7 @@ parse_uri(regex_t * preg, char * full_uri, struct URI ** uri)
125 return 0; 113 return 0;
126} 114}
127 115
116
128void 117void
129free_proxy(struct Proxy *proxy) 118free_proxy(struct Proxy *proxy)
130{ 119{
@@ -136,6 +125,7 @@ free_proxy(struct Proxy *proxy)
136 free(proxy); 125 free(proxy);
137} 126}
138 127
128//TODO remove this
139void *au_malloc(size_t size) 129void *au_malloc(size_t size)
140{ 130{
141 void *new_memory; 131 void *new_memory;
diff --git a/src/examples/mhd2spdy_structures.h b/src/examples/mhd2spdy_structures.h
index 6d6d9769..88c28c64 100644
--- a/src/examples/mhd2spdy_structures.h
+++ b/src/examples/mhd2spdy_structures.h
@@ -49,23 +49,32 @@
49#include <spdylay/spdylay.h> 49#include <spdylay/spdylay.h>
50#include <getopt.h> 50#include <getopt.h>
51 51
52
53/* WANT_READ if SSL connection needs more input; or WANT_WRITE if it
54 needs more output; or IO_NONE. This is necessary because SSL/TLS
55 re-negotiation is possible at any time. Spdylay API offers
56 similar functions like spdylay_session_want_read() and
57 spdylay_session_want_write() but they do not take into account
58 SSL connection. */
59enum
60{
61 IO_NONE,
62 WANT_READ,
63 WANT_WRITE
64};
65
66
52struct Proxy; 67struct Proxy;
53 68
69
54struct SPDY_Connection { 70struct SPDY_Connection {
55 SSL *ssl; 71 SSL *ssl;
56 //SSL_CTX *ssl_ctx;
57 spdylay_session *session; 72 spdylay_session *session;
58 struct SPDY_Connection *prev; 73 struct SPDY_Connection *prev;
59 struct SPDY_Connection *next; 74 struct SPDY_Connection *next;
60 struct Proxy *proxies_head; 75 struct Proxy *proxies_head;
61 struct Proxy *proxies_tail; 76 struct Proxy *proxies_tail;
62 char *host; 77 char *host;
63 /* WANT_READ if SSL connection needs more input; or WANT_WRITE if it
64 needs more output; or IO_NONE. This is necessary because SSL/TLS
65 re-negotiation is possible at any time. Spdylay API offers
66 similar functions like spdylay_session_want_read() and
67 spdylay_session_want_write() but they do not take into account
68 SSL connection. */
69 int fd; 78 int fd;
70 int want_io; 79 int want_io;
71 uint counter; 80 uint counter;
@@ -79,7 +88,6 @@ struct URI
79 char * full_uri; 88 char * full_uri;
80 char * scheme; 89 char * scheme;
81 char * host_and_port; 90 char * host_and_port;
82 //char * host_and_port_for_connecting;
83 char * host; 91 char * host;
84 char * path; 92 char * path;
85 char * path_and_more; 93 char * path_and_more;
@@ -88,26 +96,21 @@ struct URI
88 uint16_t port; 96 uint16_t port;
89}; 97};
90 98
99
91struct HTTP_URI; 100struct HTTP_URI;
92 101
102
93struct Proxy 103struct Proxy
94{ 104{
95 struct MHD_Connection *http_connection; 105 struct MHD_Connection *http_connection;
96 struct MHD_Response *http_response; 106 struct MHD_Response *http_response;
97 struct URI *uri; 107 struct URI *uri;
98 struct HTTP_URI *http_uri; //TODO remove me 108 struct HTTP_URI *http_uri;
99 struct SPDY_Connection *spdy_connection; 109 struct SPDY_Connection *spdy_connection;
100 struct Proxy *next; 110 struct Proxy *next;
101 struct Proxy *prev; 111 struct Proxy *prev;
102 //char *path;
103 char *url; 112 char *url;
104 //struct SPDY_Request *request;
105 //struct SPDY_Response *response;
106 //CURL *curl_handle;
107 //struct curl_slist *curl_headers;
108 //struct SPDY_NameValue *headers;
109 char *version; 113 char *version;
110 //char *status_msg;
111 void *http_body; 114 void *http_body;
112 size_t http_body_size; 115 size_t http_body_size;
113 ssize_t length; 116 ssize_t length;
@@ -126,6 +129,7 @@ struct HTTP_URI
126 struct Proxy * proxy; 129 struct Proxy * proxy;
127}; 130};
128 131
132
129struct SPDY_Headers 133struct SPDY_Headers
130{ 134{
131 const char **nv; 135 const char **nv;
@@ -133,6 +137,7 @@ struct SPDY_Headers
133 int cnt; 137 int cnt;
134}; 138};
135 139
140
136struct global_options 141struct global_options
137{ 142{
138 char *spdy2http_str; 143 char *spdy2http_str;
@@ -150,24 +155,9 @@ struct global_options
150 bool verbose; 155 bool verbose;
151 bool only_proxy; 156 bool only_proxy;
152 bool spdy_data_received; 157 bool spdy_data_received;
153} glob_opt; 158}
154 159glob_opt;
155/*
156
157#define SOCK_ADDR_IN_PTR(sa) ((struct sockaddr_in *)(sa))
158#define SOCK_ADDR_IN_FAMILY(sa) SOCK_ADDR_IN_PTR(sa)->sin_family
159#define SOCK_ADDR_IN_PORT(sa) SOCK_ADDR_IN_PTR(sa)->sin_port
160#define SOCK_ADDR_IN_ADDR(sa) SOCK_ADDR_IN_PTR(sa)->sin_addr
161 160
162#ifdef HAS_IPV6
163
164#define SOCK_ADDR_IN6_PTR(sa) ((struct sockaddr_in6 *)(sa))
165#define SOCK_ADDR_IN6_FAMILY(sa) SOCK_ADDR_IN6_PTR(sa)->sin6_family
166#define SOCK_ADDR_IN6_PORT(sa) SOCK_ADDR_IN6_PTR(sa)->sin6_port
167#define SOCK_ADDR_IN6_ADDR(sa) SOCK_ADDR_IN6_PTR(sa)->sin6_addr
168
169#endif
170*/
171 161
172//forbidden headers 162//forbidden headers
173#define SPDY_HTTP_HEADER_TRANSFER_ENCODING "transfer-encoding" 163#define SPDY_HTTP_HEADER_TRANSFER_ENCODING "transfer-encoding"
@@ -177,6 +167,7 @@ struct global_options
177 167
178#define MAX_SPDY_CONNECTIONS 100 168#define MAX_SPDY_CONNECTIONS 100
179 169
170#define SPDY_MAX_OUTLEN 4096
180 171
181/** 172/**
182 * Insert an element at the head of a DLL. Assumes that head, tail and 173 * Insert an element at the head of a DLL. Assumes that head, tail and
@@ -251,18 +242,27 @@ struct global_options
251void 242void
252free_uri(struct URI * uri); 243free_uri(struct URI * uri);
253 244
245
254int 246int
255init_parse_uri(regex_t * preg); 247init_parse_uri(regex_t * preg);
256 248
249
257void 250void
258deinit_parse_uri(regex_t * preg); 251deinit_parse_uri(regex_t * preg);
259 252
253
260int 254int
261parse_uri(regex_t * preg, char * full_uri, struct URI ** uri); 255parse_uri(regex_t * preg,
256 char * full_uri,
257 struct URI ** uri);
258
262 259
263void 260void
264free_proxy(struct Proxy *proxy); 261free_proxy(struct Proxy *proxy);
265 262
266void *au_malloc(size_t size); 263
264void *
265au_malloc(size_t size);
266
267 267
268#endif 268#endif