diff --git a/dist/Debug/GNU-Linux-x86/khttp b/dist/Debug/GNU-Linux-x86/khttp
deleted file mode 100755
index 923439d..0000000
Binary files a/dist/Debug/GNU-Linux-x86/khttp and /dev/null differ
diff --git a/nbproject/private/configurations.xml b/nbproject/private/configurations.xml
index a0dea49..daa4a74 100644
--- a/nbproject/private/configurations.xml
+++ b/nbproject/private/configurations.xml
@@ -13,6 +13,8 @@
+
+
diff --git a/src/http/http.c b/src/http/http.c
index 203f949..557d6f0 100644
--- a/src/http/http.c
+++ b/src/http/http.c
@@ -3,6 +3,7 @@
#include
#include
#include "http.h"
+#include "../main.h"
/*
* METHOD_GET, METHOD_POST, METHOD_HEAD, METHOD_PUT,
@@ -32,7 +33,7 @@ http_method http_method_fromstring(const char* method) {
METHOD_CONNECT};
size_t count = sizeof(methods) / sizeof(http_method);
- for(int i; i < count; i++) {
+ for(int i=0; i < count; i++) {
if (strcmp(http_method_getstring(methods[i],NULL), method) == 0) {
return methods[i];
}
@@ -42,6 +43,9 @@ http_method http_method_fromstring(const char* method) {
http_request_line *http_request_line_new(http_method method, const char* other) {
http_request_line *req = calloc(1, sizeof(http_request_line));
+ if (req == NULL) {
+ fatal("calloc failed");
+ }
req->method = method;
if (req->method == METHOD_OTHER) {
req->method_other = calloc(strlen(other)+1, sizeof(char));
@@ -59,6 +63,9 @@ void http_request_line_delete(http_request_line *req) {
http_response_line *http_response_line_new(uint16_t code) {
http_response_line *resp = calloc(1, sizeof(http_response_line));
+ if (resp == NULL) {
+ fatal("calloc failed");
+ }
resp->code = code;
resp->version = HTTP11;
return resp;
@@ -117,7 +124,9 @@ void http_reponse_line_delete(http_response_line *resp) {
http_header *http_header_new(const char* name) {
http_header *header = calloc(1, sizeof(http_header));
-
+ if (header == NULL) {
+ fatal("calloc failed");
+ }
header->name = calloc(strlen(name)+1, sizeof(char));
strcpy(header->name, name);
@@ -126,10 +135,16 @@ http_header *http_header_new(const char* name) {
void http_header_append_content(http_header *header, const char* content) {
if (header->content == NULL) {
header->content = calloc(strlen(content)+1, sizeof(char));
+ if (header->content == NULL) {
+ fatal("calloc failed");
+ }
strcpy(header->content, content);
} else {
uint32_t newlen = strlen(header->content) + strlen(content) + 1;
header->content = realloc(header->content, newlen);
+ if (header->content == NULL) {
+ fatal("calloc failed");
+ }
strcat(header->content, content);
}
}
@@ -141,13 +156,20 @@ void http_header_delete(http_header *header) {
http_request *http_request_new() {
http_request *req = calloc(1, sizeof(http_request));
+ if (req == NULL) {
+ fatal("calloc failed");
+ }
req->header_count = 0;
req->body = NULL;
+ req->parsestatus = PARSE_REQUESTLINE;
return req;
}
void http_request_add_header(http_request *req, http_header *header) {
req->header_count++;
req->headers = realloc(req->headers, req->header_count * sizeof(http_header*));
+ if (req->headers == NULL) {
+ fatal("calloc failed");
+ }
req->headers[req->header_count-1] = header;
}
void http_request_apppend_body(http_request *req, const char* body) {
@@ -157,6 +179,9 @@ void http_request_apppend_body(http_request *req, const char* body) {
}
bodylen += strlen(body) + 1;
req->body = realloc(req->body, bodylen * sizeof(char));
+ if (req->body == NULL) {
+ fatal("calloc failed");
+ }
strcat(req->body, body);
}
void http_request_delete(http_request *req) {
diff --git a/src/http/http.h b/src/http/http.h
index 1ca2ec7..9fef224 100644
--- a/src/http/http.h
+++ b/src/http/http.h
@@ -13,7 +13,6 @@ extern "C" {
#endif
#include
-#include "request.h"
typedef enum http_method {
METHOD_GET, METHOD_POST, METHOD_HEAD, METHOD_PUT,
@@ -43,13 +42,19 @@ extern "C" {
char* content;
} http_header;
+ typedef enum http_request_parsestatus {
+ PARSE_REQUESTLINE, PARSE_HEADERS, PARSE_BODY, PARSE_DONE, PARSE_FAIL
+ } http_request_parsestatus;
+
typedef struct http_request {
http_request_line *req;
+ http_request_parsestatus parsestatus;
http_header **headers;
uint32_t header_count;
char *body;
} http_request;
+
char* http_method_getstring(http_method method, char* method_other);
http_method http_method_fromstring(const char* method);
diff --git a/src/http/request.c b/src/http/request.c
index aded04b..45ed0ad 100644
--- a/src/http/request.c
+++ b/src/http/request.c
@@ -1,6 +1,66 @@
#include
#include
#include
+#include
+#include "../main.h"
#include "http.h"
-
+char* parse_request(http_request *req, char *input) {
+ size_t line_count;
+ char** lines = str_splitlines(input, &line_count);
+
+ switch(req->parsestatus) {
+ case PARSE_REQUESTLINE:
+ if (line_count == 0) {
+ break;
+ }
+
+ char* requestStr = lines[0];
+
+ char methodStr[20] = {0};
+ char uriStr[1024] = {0};
+ char versionStr[16] = {0};
+
+ int count = sscanf(requestStr, "%19s%*[ \t]%1023s%*[ \t]%15s", methodStr, uriStr, versionStr);
+ if (count < 3) {
+ req->parsestatus = PARSE_FAIL;
+ break;
+ }
+
+ http_method method = http_method_fromstring(methodStr);
+ if (method == METHOD_INVALID) {
+ req->parsestatus = PARSE_FAIL;
+ break;
+ }
+
+ http_version version;
+ if (strcasecmp(versionStr, "HTTP/1.0") == 0) { version = HTTP10; }
+ if (strcasecmp(versionStr, "HTTP/1.1") == 0) { version = HTTP11; }
+
+ http_request_line *request_line = http_request_line_new(method, NULL);
+ request_line->version = version;
+ request_line->uri = calloc(strlen(uriStr)+1, sizeof(char));
+ if (request_line->uri == NULL) {
+ fatal("calloc failed");
+ }
+ strcpy(request_line->uri, uriStr);
+ req->req = request_line;
+ req->parsestatus = PARSE_HEADERS;
+
+ break;
+ case PARSE_HEADERS:
+ break;
+ case PARSE_BODY:
+ break;
+ case PARSE_DONE:
+ case PARSE_FAIL:
+ break;
+ }
+
+ for(size_t i=0; i < line_count; i++) {
+ free(lines[i]);
+ free(lines);
+ }
+
+ return NULL;
+}
\ No newline at end of file
diff --git a/src/http/request.h b/src/http/request.h
index bde8df1..79dcb5c 100644
--- a/src/http/request.h
+++ b/src/http/request.h
@@ -12,9 +12,10 @@
extern "C" {
#endif
+#include "../ut/utstring.h"
#include "http.h"
-
+ char* parse_request(http_request *req, char *input);
#ifdef __cplusplus
diff --git a/src/main.c b/src/main.c
index 26f0e13..c0e3456 100644
--- a/src/main.c
+++ b/src/main.c
@@ -12,16 +12,26 @@
#include
#include "ut/utlist.h"
+#include "ut/utarray.h"
#include "main.h"
#include "socket.h"
+#include "http/http.h"
+#include "http/request.h"
int serverfd = 0;
+char* teststr = "GET /testing/123 HTTP/1.1\r\n";
/*
*
*/
int main(int argc, char** argv) {
+ /*char *test = calloc(strlen(teststr)+1, sizeof(char));
+ strcpy(test, teststr);
+ http_request *req = http_request_new();
+ parse_request(req, test);
+
+ return 0;*/
skt_elem *connections = NULL;
serverfd = svr_create();
@@ -38,6 +48,7 @@ int main(int argc, char** argv) {
if (info != NULL) {
skt_elem* newconn = calloc(1, sizeof(skt_elem));
newconn->info = info;
+ newconn->current_request = http_request_new();
LL_APPEND(connections, newconn);
}
}
@@ -90,6 +101,9 @@ int main(int argc, char** argv) {
if (elem->info->closed) {
LL_DELETE(connections, elem);
skt_delete(elem->info);
+ if (elem->current_request != NULL) {
+ http_request_delete(elem->current_request);
+ }
free(elem);
}
}
@@ -124,4 +138,46 @@ void info(char* msg, ...) {
vfprintf(stdout, msg, va);
fputc('\n', stdout);
va_end(va);
+}
+
+char** str_splitlines(char *str, size_t *line_count) {
+ char **result;
+ *line_count = 0;
+ char *tmp = str;
+
+ while(*tmp) {
+ if (*tmp == '\n') {
+ (*line_count)++;
+ }
+ tmp++;
+ }
+ if (*line_count == 0) {
+ result = calloc(1, sizeof(char*));
+ result[0] = calloc(strlen(str), sizeof(char));
+ strcpy(result[0], str);
+ return result;
+ }
+ result = calloc(*line_count, sizeof(char*));
+ if (result == NULL) {
+ fatal("calloc failed");
+ }
+
+ size_t i=0, linelen = 0;
+ char *line = strtok(str, "\n");
+ while(line) {
+ linelen = strlen(line);
+ result[i] = calloc(linelen+1, sizeof(char));
+ if (result[i] == NULL) {
+ fatal("calloc failed");
+ }
+ strcpy(result[i], line);
+ if (result[i][linelen-1] == '\r') {
+ result[i][linelen-1] = '\0';
+ result[i] = realloc(result[i], linelen);
+ }
+ line = strtok(NULL, "\n");
+ i++;
+ }
+
+ return result;
}
\ No newline at end of file
diff --git a/src/main.h b/src/main.h
index f5146a4..2299e58 100644
--- a/src/main.h
+++ b/src/main.h
@@ -20,6 +20,8 @@ void fatal(char* msg);
void warning(char* msg, bool showPError);
void info(char* msg, ...);
+char** str_splitlines(char *str, size_t *line_count);
+
#ifdef __cplusplus
}
diff --git a/src/socket.h b/src/socket.h
index e6cfb4b..f161c65 100644
--- a/src/socket.h
+++ b/src/socket.h
@@ -17,8 +17,9 @@ extern "C" {
#include
#include
#include
+#include "http/http.h"
#include "ut/utstring.h"
-
+
typedef struct skt_info skt_info;
struct skt_info {
@@ -36,6 +37,7 @@ extern "C" {
typedef struct skt_elem {
skt_info* info;
+ http_request *current_request;
struct skt_elem *next;
} skt_elem;
diff --git a/src/ut/utarray.h b/src/ut/utarray.h
index dcddd72..a6f70dd 100644
--- a/src/ut/utarray.h
+++ b/src/ut/utarray.h
@@ -218,7 +218,12 @@ typedef struct {
/* last we pre-define a few icd for common utarrays of ints and strings */
static void utarray_str_cpy(void *dst, const void *src) {
char **_src = (char**)src, **_dst = (char**)dst;
- *_dst = (*_src == NULL) ? NULL : strdup(*_src);
+ if (*_src != NULL) {
+ *_dst = calloc(strlen(*_src)+1, sizeof(char));
+ if (*_dst != NULL) {
+ strcpy(*_dst, *_src);
+ }
+ }
}
static void utarray_str_dtor(void *elt) {
char **eltc = (char**)elt;