#include "http.h" #include #include #include #include /* TODO: https://blog.netherlabs.nl/articles/2009/01/18/the-ultimate-so_linger-page-or-why-is-my-tcp-not-reliable */ int http_init(int port, int connection_amount) { int ret; int server_sock = socket(AF_INET, SOCK_STREAM, 0); if (server_sock == -1) { perror("Couldn't create socket"); return -1; } struct sockaddr_in server_addr; server_addr.sin_family = AF_INET; server_addr.sin_addr.s_addr = INADDR_ANY; server_addr.sin_port = htons(port); if (bind(server_sock, (struct sockaddr*)&server_addr, sizeof server_addr) == -1) { perror("Couldn't bind socket"); return -1; } if (listen(server_sock, connection_amount) == -1) { perror("Cannot listen on socket"); return -1; } return server_sock; } HTTP_Request* http_accept(int server) { int client_sock = accept(server, NULL, NULL); if (client_sock == -1) { perror("Couldn't connect to client"); return NULL; } HTTP_Request *request = malloc(sizeof(HTTP_Request)); request->client_sock = client_sock; /* TODO: Read entire message and parse into request struct */ ssize_t bytes_read; size_t bufsize = 4096; char buf[bufsize]; bytes_read = read(request->client_sock, buf, bufsize - 1); if (bytes_read == -1) { perror("Failed to read data"); } /* TODO: read tmp line by line */ char *tmp = strops_trim_left_string(buf, "\r\n"); size_t lines_count = 0; size_t lines_capacity = 10; char **lines = malloc(lines_capacity * sizeof (char*)); size_t i; while (strops_length(tmp) > 0) { char *line = malloc(strops_length(tmp)); memset(line, 0, strops_length(tmp)); for (i = 0; i < strops_length(tmp); i++) { if (tmp[i] == '\r' && tmp[i + 1] == '\n') { i += 2; break; } line[i] = tmp[i]; } for (; i > 0; i--) { strops_remove_at_pos_char_inplace(tmp, 0); } if (lines_count >= lines_capacity) { lines_capacity *= 2; lines = realloc(lines, lines_capacity * sizeof (char*)); } lines[lines_count] = line; lines_count++; } free(tmp); /* TODO: Parse lines */ /* TODO: find suitable data structure for field-lines */ /* request-line => method target version seperated by whitespace (SP) field-line => field-name:field-value seperated by a single colon => ':' field-value may have leading and trailing optionial whitespace (OWS) */ for (i = 0; i < lines_count; i++) { printf("%s\n", lines[i]); } /* TODO: remeber to delete this code after finishing parsing code */ for (i = lines_count; i > 0; i--) { free(lines[i]); } free(lines); return request; }