diff options
author | Andrey Uzunov <andrey.uzunov@gmail.com> | 2013-08-11 19:35:43 +0000 |
---|---|---|
committer | Andrey Uzunov <andrey.uzunov@gmail.com> | 2013-08-11 19:35:43 +0000 |
commit | e421dc4c64105540b24ee732e8887ee26c40276a (patch) | |
tree | 6d6674c83330ecaf6ff2fd94edcde343971ba3c2 /src/microspdy | |
parent | 62f53d643f796ad3a32d8eabfdceb985245ec15f (diff) | |
download | libmicrohttpd-e421dc4c64105540b24ee732e8887ee26c40276a.tar.gz libmicrohttpd-e421dc4c64105540b24ee732e8887ee26c40276a.zip |
spdy: simple POST support implemented; API changes; fixed warnings in spdy tests
Diffstat (limited to 'src/microspdy')
-rw-r--r-- | src/microspdy/applicationlayer.c | 25 | ||||
-rw-r--r-- | src/microspdy/daemon.c | 6 | ||||
-rw-r--r-- | src/microspdy/daemon.h | 3 | ||||
-rw-r--r-- | src/microspdy/session.c | 45 | ||||
-rw-r--r-- | src/microspdy/stream.c | 19 | ||||
-rw-r--r-- | src/microspdy/stream.h | 13 | ||||
-rw-r--r-- | src/microspdy/structures.h | 36 |
7 files changed, 131 insertions, 16 deletions
diff --git a/src/microspdy/applicationlayer.c b/src/microspdy/applicationlayer.c index efcf2b3d..17a00289 100644 --- a/src/microspdy/applicationlayer.c +++ b/src/microspdy/applicationlayer.c | |||
@@ -157,7 +157,7 @@ spdy_handler_new_stream (void *cls, | |||
157 | } | 157 | } |
158 | 158 | ||
159 | //ignore everything but GET | 159 | //ignore everything but GET |
160 | if(strcasecmp("GET",method)) | 160 | if(strcasecmp("GET",method) && strcasecmp("POST",method)) |
161 | { | 161 | { |
162 | SPDYF_DEBUG("received method '%s'", method); | 162 | SPDYF_DEBUG("received method '%s'", method); |
163 | static char * html = "Method not implemented. libmicrospdy supports now only GET."; | 163 | static char * html = "Method not implemented. libmicrospdy supports now only GET."; |
@@ -187,7 +187,10 @@ spdy_handler_new_stream (void *cls, | |||
187 | version, | 187 | version, |
188 | host, | 188 | host, |
189 | scheme, | 189 | scheme, |
190 | headers); | 190 | headers, |
191 | !stream->is_in_closed); | ||
192 | |||
193 | stream->cls = request; | ||
191 | 194 | ||
192 | return SPDY_YES; | 195 | return SPDY_YES; |
193 | 196 | ||
@@ -200,6 +203,21 @@ spdy_handler_new_stream (void *cls, | |||
200 | 203 | ||
201 | 204 | ||
202 | /** | 205 | /** |
206 | * TODO | ||
207 | */ | ||
208 | static int | ||
209 | spdy_handler_new_data (void * cls, | ||
210 | struct SPDYF_Stream *stream, | ||
211 | const void * buf, | ||
212 | size_t size, | ||
213 | bool more) | ||
214 | { | ||
215 | return stream->session->daemon->received_data_cb(cls, stream->cls, buf, size, more); | ||
216 | } | ||
217 | |||
218 | |||
219 | |||
220 | /** | ||
203 | * Callback to be called when the response queue object was handled and | 221 | * Callback to be called when the response queue object was handled and |
204 | * the data was already sent or discarded. | 222 | * the data was already sent or discarded. |
205 | * | 223 | * |
@@ -332,7 +350,7 @@ SPDY_start_daemon (uint16_t port, | |||
332 | SPDY_NewSessionCallback nscb, | 350 | SPDY_NewSessionCallback nscb, |
333 | SPDY_SessionClosedCallback sccb, | 351 | SPDY_SessionClosedCallback sccb, |
334 | SPDY_NewRequestCallback nrcb, | 352 | SPDY_NewRequestCallback nrcb, |
335 | SPDY_NewPOSTDataCallback npdcb, | 353 | SPDY_NewDataCallback npdcb, |
336 | void * cls, | 354 | void * cls, |
337 | ...) | 355 | ...) |
338 | { | 356 | { |
@@ -367,6 +385,7 @@ SPDY_start_daemon (uint16_t port, | |||
367 | nrcb, | 385 | nrcb, |
368 | npdcb, | 386 | npdcb, |
369 | &spdy_handler_new_stream, | 387 | &spdy_handler_new_stream, |
388 | &spdy_handler_new_data, | ||
370 | cls, | 389 | cls, |
371 | NULL, | 390 | NULL, |
372 | valist | 391 | valist |
diff --git a/src/microspdy/daemon.c b/src/microspdy/daemon.c index a8bea83b..77129894 100644 --- a/src/microspdy/daemon.c +++ b/src/microspdy/daemon.c | |||
@@ -173,8 +173,9 @@ SPDYF_start_daemon_va (uint16_t port, | |||
173 | SPDY_NewSessionCallback nscb, | 173 | SPDY_NewSessionCallback nscb, |
174 | SPDY_SessionClosedCallback sccb, | 174 | SPDY_SessionClosedCallback sccb, |
175 | SPDY_NewRequestCallback nrcb, | 175 | SPDY_NewRequestCallback nrcb, |
176 | SPDY_NewPOSTDataCallback npdcb, | 176 | SPDY_NewDataCallback npdcb, |
177 | SPDYF_NewStreamCallback fnscb, | 177 | SPDYF_NewStreamCallback fnscb, |
178 | SPDYF_NewDataCallback fndcb, | ||
178 | void * cls, | 179 | void * cls, |
179 | void * fcls, | 180 | void * fcls, |
180 | va_list valist) | 181 | va_list valist) |
@@ -237,10 +238,11 @@ SPDYF_start_daemon_va (uint16_t port, | |||
237 | daemon->new_session_cb = nscb; | 238 | daemon->new_session_cb = nscb; |
238 | daemon->session_closed_cb = sccb; | 239 | daemon->session_closed_cb = sccb; |
239 | daemon->new_request_cb = nrcb; | 240 | daemon->new_request_cb = nrcb; |
240 | daemon->new_post_data_cb = npdcb; | 241 | daemon->received_data_cb = npdcb; |
241 | daemon->cls = cls; | 242 | daemon->cls = cls; |
242 | daemon->fcls = fcls; | 243 | daemon->fcls = fcls; |
243 | daemon->fnew_stream_cb = fnscb; | 244 | daemon->fnew_stream_cb = fnscb; |
245 | daemon->freceived_data_cb = fndcb; | ||
244 | 246 | ||
245 | #if HAVE_INET6 | 247 | #if HAVE_INET6 |
246 | //handling IPv6 | 248 | //handling IPv6 |
diff --git a/src/microspdy/daemon.h b/src/microspdy/daemon.h index 03e322b5..0dbc5ab1 100644 --- a/src/microspdy/daemon.h +++ b/src/microspdy/daemon.h | |||
@@ -62,8 +62,9 @@ SPDYF_start_daemon_va (uint16_t port, | |||
62 | SPDY_NewSessionCallback nscb, | 62 | SPDY_NewSessionCallback nscb, |
63 | SPDY_SessionClosedCallback sccb, | 63 | SPDY_SessionClosedCallback sccb, |
64 | SPDY_NewRequestCallback nrcb, | 64 | SPDY_NewRequestCallback nrcb, |
65 | SPDY_NewPOSTDataCallback npdcb, | 65 | SPDY_NewDataCallback npdcb, |
66 | SPDYF_NewStreamCallback fnscb, | 66 | SPDYF_NewStreamCallback fnscb, |
67 | SPDYF_NewDataCallback fndcb, | ||
67 | void * cls, | 68 | void * cls, |
68 | void * fcls, | 69 | void * fcls, |
69 | va_list valist); | 70 | va_list valist); |
diff --git a/src/microspdy/session.c b/src/microspdy/session.c index 856bed85..7edebaba 100644 --- a/src/microspdy/session.c +++ b/src/microspdy/session.c | |||
@@ -325,14 +325,15 @@ spdyf_handler_read_rst_stream (struct SPDY_Session *session) | |||
325 | static void | 325 | static void |
326 | spdyf_handler_read_data (struct SPDY_Session *session) | 326 | spdyf_handler_read_data (struct SPDY_Session *session) |
327 | { | 327 | { |
328 | //just ignore the whole frame for now | 328 | int ret; |
329 | struct SPDYF_Data_Frame * frame; | 329 | struct SPDYF_Data_Frame * frame; |
330 | struct SPDYF_Stream * stream; | ||
330 | 331 | ||
331 | SPDYF_ASSERT(SPDY_SESSION_STATUS_WAIT_FOR_SUBHEADER == session->status | 332 | SPDYF_ASSERT(SPDY_SESSION_STATUS_WAIT_FOR_SUBHEADER == session->status |
332 | || SPDY_SESSION_STATUS_WAIT_FOR_BODY == session->status, | 333 | || SPDY_SESSION_STATUS_WAIT_FOR_BODY == session->status, |
333 | "the function is called wrong"); | 334 | "the function is called wrong"); |
334 | 335 | ||
335 | SPDYF_DEBUG("DATA frame received (POST?). Ignoring"); | 336 | //SPDYF_DEBUG("DATA frame received (POST?). Ignoring"); |
336 | 337 | ||
337 | //SPDYF_SIGINT(""); | 338 | //SPDYF_SIGINT(""); |
338 | 339 | ||
@@ -355,9 +356,41 @@ spdyf_handler_read_data (struct SPDY_Session *session) | |||
355 | if(session->read_buffer_offset - session->read_buffer_beginning | 356 | if(session->read_buffer_offset - session->read_buffer_beginning |
356 | >= frame->length) | 357 | >= frame->length) |
357 | { | 358 | { |
358 | session->read_buffer_beginning += frame->length; | 359 | stream = SPDYF_stream_find(frame->stream_id, session); |
359 | session->status = SPDY_SESSION_STATUS_WAIT_FOR_HEADER; | 360 | |
360 | free(frame); | 361 | if(NULL == stream || stream->is_in_closed || NULL == session->daemon->received_data_cb) |
362 | { | ||
363 | if(NULL == session->daemon->received_data_cb) | ||
364 | SPDYF_DEBUG("No callback for DATA frame set"); | ||
365 | |||
366 | SPDYF_DEBUG("Ignoring DATA frame!"); | ||
367 | |||
368 | //TODO send error? | ||
369 | |||
370 | //TODO for now ignore frame | ||
371 | session->read_buffer_beginning += frame->length; | ||
372 | session->status = SPDY_SESSION_STATUS_WAIT_FOR_HEADER; | ||
373 | free(frame); | ||
374 | return; | ||
375 | } | ||
376 | |||
377 | ret = session->daemon->freceived_data_cb(session->daemon->cls, | ||
378 | stream, | ||
379 | session->read_buffer + session->read_buffer_beginning, | ||
380 | frame->length, | ||
381 | 0 == (SPDY_DATA_FLAG_FIN & frame->flags)); | ||
382 | |||
383 | session->read_buffer_beginning += frame->length; | ||
384 | |||
385 | //TODO close in and send rst maybe | ||
386 | SPDYF_ASSERT(SPDY_YES == ret, "Cancel POST data is not yet implemented"); | ||
387 | |||
388 | if(SPDY_DATA_FLAG_FIN & frame->flags) | ||
389 | { | ||
390 | stream->is_in_closed = true; | ||
391 | } | ||
392 | session->status = SPDY_SESSION_STATUS_WAIT_FOR_HEADER; | ||
393 | free(frame); | ||
361 | } | 394 | } |
362 | } | 395 | } |
363 | 396 | ||
@@ -1020,7 +1053,7 @@ SPDYF_session_write (struct SPDY_Session *session, bool only_one_frame) | |||
1020 | } | 1053 | } |
1021 | 1054 | ||
1022 | //set stream to closed if the frame's fin flag is set | 1055 | //set stream to closed if the frame's fin flag is set |
1023 | SPDYF_stream_set_flags(queue_head); | 1056 | SPDYF_stream_set_flags_on_write(queue_head); |
1024 | 1057 | ||
1025 | if(NULL != queue_head->frqcb) | 1058 | if(NULL != queue_head->frqcb) |
1026 | { | 1059 | { |
diff --git a/src/microspdy/stream.c b/src/microspdy/stream.c index 97fdd6c8..336672ac 100644 --- a/src/microspdy/stream.c +++ b/src/microspdy/stream.c | |||
@@ -122,7 +122,7 @@ SPDYF_stream_destroy(struct SPDYF_Stream *stream) | |||
122 | 122 | ||
123 | 123 | ||
124 | void | 124 | void |
125 | SPDYF_stream_set_flags(struct SPDYF_Response_Queue *response_queue) | 125 | SPDYF_stream_set_flags_on_write(struct SPDYF_Response_Queue *response_queue) |
126 | { | 126 | { |
127 | struct SPDYF_Stream * stream = response_queue->stream; | 127 | struct SPDYF_Stream * stream = response_queue->stream; |
128 | 128 | ||
@@ -149,3 +149,20 @@ SPDYF_stream_set_flags(struct SPDYF_Response_Queue *response_queue) | |||
149 | } | 149 | } |
150 | } | 150 | } |
151 | } | 151 | } |
152 | |||
153 | |||
154 | //TODO add function *on_read | ||
155 | |||
156 | |||
157 | struct SPDYF_Stream * | ||
158 | SPDYF_stream_find(uint32_t stream_id, struct SPDY_Session * session) | ||
159 | { | ||
160 | struct SPDYF_Stream * stream = session->streams_head; | ||
161 | |||
162 | while(NULL != stream && stream_id != stream->stream_id) | ||
163 | { | ||
164 | stream = stream->next; | ||
165 | } | ||
166 | |||
167 | return stream; | ||
168 | } | ||
diff --git a/src/microspdy/stream.h b/src/microspdy/stream.h index a795ad28..de51077a 100644 --- a/src/microspdy/stream.h +++ b/src/microspdy/stream.h | |||
@@ -60,6 +60,17 @@ SPDYF_stream_destroy(struct SPDYF_Stream *stream); | |||
60 | * @param response_queue sent for this stream | 60 | * @param response_queue sent for this stream |
61 | */ | 61 | */ |
62 | void | 62 | void |
63 | SPDYF_stream_set_flags(struct SPDYF_Response_Queue *response_queue); | 63 | SPDYF_stream_set_flags_on_write(struct SPDYF_Response_Queue *response_queue); |
64 | |||
65 | |||
66 | /** | ||
67 | * Find and return a session's stream, based on stream's ID. | ||
68 | * | ||
69 | * @param stream_id to search for | ||
70 | * @param session whose streams are considered | ||
71 | * @return SPDY_Stream with the desired ID. Can be NULL. | ||
72 | */ | ||
73 | struct SPDYF_Stream * | ||
74 | SPDYF_stream_find(uint32_t stream_id, struct SPDY_Session * session); | ||
64 | 75 | ||
65 | #endif | 76 | #endif |
diff --git a/src/microspdy/structures.h b/src/microspdy/structures.h index ff4c47ff..1c2a0aaf 100644 --- a/src/microspdy/structures.h +++ b/src/microspdy/structures.h | |||
@@ -317,6 +317,28 @@ struct SPDYF_Stream; | |||
317 | 317 | ||
318 | struct SPDYF_Response_Queue; | 318 | struct SPDYF_Response_Queue; |
319 | 319 | ||
320 | |||
321 | /** | ||
322 | * Callback for received new data chunk. | ||
323 | * | ||
324 | * @param cls client-defined closure | ||
325 | * @param stream handler | ||
326 | * @param buf data chunk from the data | ||
327 | * @param size the size of the data chunk 'buf' in bytes | ||
328 | * @param more false if this is the last frame received on this stream. Note: | ||
329 | * true does not mean that more data will come, exceptional | ||
330 | * situation is possible | ||
331 | * @return SPDY_YES to continue calling the function, | ||
332 | * SPDY_NO to stop calling the function for this stream | ||
333 | */ | ||
334 | typedef int | ||
335 | (*SPDYF_NewDataCallback) (void * cls, | ||
336 | struct SPDYF_Stream *stream, | ||
337 | const void * buf, | ||
338 | size_t size, | ||
339 | bool more); | ||
340 | |||
341 | |||
320 | /** | 342 | /** |
321 | * Callback for new stream. To be used in the application layer of the | 343 | * Callback for new stream. To be used in the application layer of the |
322 | * lib. | 344 | * lib. |
@@ -515,6 +537,11 @@ struct SPDYF_Stream | |||
515 | * Name value pairs, sent within the frame which created the stream. | 537 | * Name value pairs, sent within the frame which created the stream. |
516 | */ | 538 | */ |
517 | struct SPDY_NameValue *headers; | 539 | struct SPDY_NameValue *headers; |
540 | |||
541 | /** | ||
542 | * Any object to be used by the application layer. | ||
543 | */ | ||
544 | void *cls; | ||
518 | 545 | ||
519 | /** | 546 | /** |
520 | * This stream's ID. | 547 | * This stream's ID. |
@@ -888,9 +915,14 @@ struct SPDY_Daemon | |||
888 | 915 | ||
889 | /** | 916 | /** |
890 | * Callback called when HTTP POST params are received | 917 | * Callback called when HTTP POST params are received |
891 | * after request | 918 | * after request. To be used by the application layer |
919 | */ | ||
920 | SPDY_NewDataCallback received_data_cb; | ||
921 | |||
922 | /** | ||
923 | * Callback called when DATA frame is received. | ||
892 | */ | 924 | */ |
893 | SPDY_NewPOSTDataCallback new_post_data_cb; | 925 | SPDYF_NewDataCallback freceived_data_cb; |
894 | 926 | ||
895 | /** | 927 | /** |
896 | * Closure argument for all the callbacks that can be used by the client. | 928 | * Closure argument for all the callbacks that can be used by the client. |