diff --git a/include/http/request_parser.h b/include/http/request_parser.h index 354ca9f..0681002 100644 --- a/include/http/request_parser.h +++ b/include/http/request_parser.h @@ -8,7 +8,8 @@ #define HTTP_REQUEST_PARSER_READ_CHUNK 1024 typedef enum e_HttpRequestState { - HTTP_REQUEST_START=0, + HTTP_REQUEST_GARBAGE=0, + HTTP_REQUEST_START, HTTP_REQUEST_REQEUST_LINE_DONE, HTTP_REQUEST_HEADERS_DONE, HTTP_REQUEST_DONE @@ -18,6 +19,7 @@ typedef enum e_HttpRequestState { CLASS(HttpRequestParser) { char * buffer; size_t buffer_used; + size_t buffer_size; //HttpRequestQueue request_queue; HttpRequestState state; diff --git a/src/http/request.c b/src/http/request.c index aa7b218..662f8a4 100644 --- a/src/http/request.c +++ b/src/http/request.c @@ -1,11 +1,10 @@ #include -#include "cclass.h" +#include "class.h" #include "http/request.h" -INIT_CLASS(HTTP_REQUEST); - -static void +static +void _free(void ** data) { if (NULL != *data) { @@ -13,9 +12,9 @@ _free(void ** data) } } -__construct(LOGGER) {} - -__destruct(LOGGER) +static +void +dtor(void * _this) { int i; @@ -31,8 +30,7 @@ __destruct(LOGGER) _free(&(this->body)); } -__jsonConst(LOGGER) {} -__toJson(LOGGER) {} -__clear(LOGGER) {} +INIT_IFACE(Class, NULL, dtor, NULL); +CREATE_CLASS(HttpRequest, IFACE(Class)); // vim: set ts=4 sw=4: diff --git a/src/http/request_parser.c b/src/http/request_parser.c index 04f1e92..04f71e5 100644 --- a/src/http/request_parser.c +++ b/src/http/request_parser.c @@ -3,6 +3,7 @@ #include #include #include +#include #include #include "class.h" @@ -14,7 +15,7 @@ static void -httpRequestParserParse(char * data, size_t * size); +httpRequestParserParse(HttpRequestParser); static void @@ -25,6 +26,7 @@ ctor(void * _this, va_list * params) //this->request_queue = va_arg(*params, HttpRequestQueue); this->buffer = malloc(HTTP_REQUEST_PARSER_READ_CHUNK); + this->buffer[0] = 0; } static @@ -78,15 +80,16 @@ get_data(void * _this, int fd) */ chunks++; - if (size > remaining) { + if (size >= remaining) { this->buffer = realloc(this->buffer, chunks * HTTP_REQUEST_PARSER_READ_CHUNK); } memcpy(this->buffer + this->buffer_used, buffer, size); this->buffer_used += size; + this->buffer[this->buffer_used] = 0; - httpRequestParserParse(this->buffer, &this->buffer_used); + httpRequestParserParse(this); } return size; @@ -97,12 +100,121 @@ INIT_IFACE(StreamReader, get_data); CREATE_CLASS(HttpRequestParser, NULL, IFACE(Class), IFACE(StreamReader)); static +inline +int +httpRequestLineGet(HttpRequestParser this, char ** line) +{ + char * line_end = strstr(this->buffer, "\r\n"); + + if (NULL == line_end) { + *line = NULL; + return -1; + } + + *line_end = 0; + *line = malloc(strlen(this->buffer) + 1); + strcpy(*line, this->buffer); + + line_end+=2; + + memmove(this->buffer, + line_end, + this->buffer_used - (line_end-this->buffer) + 1); + + this->buffer_used -= line_end-this->buffer; + + return line_end-this->buffer-2; +} + +static +inline void -httpRequestParserParse(char * data, size_t * size) +httpRequestSkip(HttpRequestParser this) { - data[*size] = 0; - printf("%s", data); - *size = 0; + size_t skip; + + for (skip = 0; + 0 != this->buffer[skip] + && ! isalpha(this->buffer[skip]) + && this->buffer_used > skip; + skip++); + + memmove(this->buffer, + &this->buffer[skip], + this->buffer_used - skip + 1); + + this->buffer_used -= skip; +} + +static +void +httpRequestParserParse(HttpRequestParser this) +{ + //static HttpRequest request = NULL; + char * line; + int cont = 1; + int length; + + //if(NULL == HttpRequest) { + // request = new(HttpRequest); + //} + + while(cont) { + switch(this->state) { + case HTTP_REQUEST_GARBAGE: + puts("==skip garbage=="); + httpRequestSkip(this); + + this->state = HTTP_REQUEST_START; + break; + + case HTTP_REQUEST_START: + puts("==request line=="); + if (-1 == httpRequestLineGet(this, &line)) { + cont = 0; + break; + } + + printf("%s\n", line); + free(line); + this->state = HTTP_REQUEST_REQEUST_LINE_DONE; + break; + + case HTTP_REQUEST_REQEUST_LINE_DONE: + puts("==read header=="); + if (-1 == (length = httpRequestLineGet(this, &line))) { + cont = 0; + break; + } + + if (0 == length) { + free(line); + this->state = HTTP_REQUEST_HEADERS_DONE; + break; + } + + printf("%s\n", line); + free(line); + break; + + case HTTP_REQUEST_HEADERS_DONE: + puts("==headers done=="); + this->state = HTTP_REQUEST_DONE; + break; + + case HTTP_REQUEST_DONE: + puts("==request done=="); + + if (0 == this->buffer_used) { + cont = 0; + } + + break; + + default: + break; + } + } } // vim: set ts=4 sw=4: