minor improvements
This commit is contained in:
@@ -9,15 +9,14 @@
|
||||
#include "utils/config.h"
|
||||
|
||||
/* Clients max queue */
|
||||
#define CWS_SERVER_BACKLOG 10
|
||||
#define CWS_SERVER_BACKLOG 128
|
||||
|
||||
/* Size of the epoll_event array */
|
||||
#define CWS_SERVER_EPOLL_MAXEVENTS 10
|
||||
#define CWS_SERVER_EPOLL_MAXEVENTS 64
|
||||
|
||||
/* Wait forever (epoll_wait()) */
|
||||
#define CWS_SERVER_EPOLL_TIMEOUT -1
|
||||
#define CWS_SERVER_EPOLL_TIMEOUT 1000
|
||||
|
||||
#define CWS_SERVER_MAX_REQUEST_SIZE (64 * 1024) /* 64 KB */
|
||||
#define CWS_SERVER_MAX_REQUEST_SIZE (16 * 1024) /* 16KB */
|
||||
|
||||
/* Main server loop */
|
||||
extern volatile sig_atomic_t cws_server_run;
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
#include "http/http.h"
|
||||
|
||||
#include <errno.h>
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
@@ -207,14 +208,16 @@ int cws_http_send_resource(cws_http *request) {
|
||||
FILE *file = fopen(mcl_string_cstr(request->location_path), "rb");
|
||||
if (file == NULL) {
|
||||
cws_http_send_response(request, CWS_HTTP_NOT_FOUND);
|
||||
return -1;
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Retrieve correct Content-Type */
|
||||
char content_type[1024];
|
||||
int ret = cws_http_get_content_type(request, content_type);
|
||||
if (ret < 0) {
|
||||
fclose(file);
|
||||
cws_http_send_response(request, CWS_HTTP_NOT_FOUND);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Retrieve file size */
|
||||
@@ -227,20 +230,21 @@ int cws_http_send_resource(cws_http *request) {
|
||||
if (file_data == NULL) {
|
||||
fclose(file);
|
||||
CWS_LOG_ERROR("Unable to allocate file data");
|
||||
return -1;
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Read 1 byte until content_length from file and put in file_data */
|
||||
/* Read file data */
|
||||
size_t read_bytes = fread(file_data, 1, content_length, file);
|
||||
fclose(file);
|
||||
|
||||
if (read_bytes != content_length) {
|
||||
free(file_data);
|
||||
CWS_LOG_ERROR("Partial read from file");
|
||||
return -1;
|
||||
return 0;
|
||||
}
|
||||
|
||||
char conn[32];
|
||||
/* Check for keep-alive connection */
|
||||
char conn[32] = "close";
|
||||
mcl_bucket *connection = mcl_hm_get(request->headers, "Connection");
|
||||
if (connection && strcmp((char *)connection->value, "keep-alive") == 0) {
|
||||
strcpy(conn, "keep-alive");
|
||||
@@ -250,12 +254,23 @@ int cws_http_send_resource(cws_http *request) {
|
||||
char *response = NULL;
|
||||
size_t response_len = cws_http_response_builder(&response, "HTTP/1.1", CWS_HTTP_OK, content_type, conn, file_data, content_length);
|
||||
|
||||
/* Send response in chunks to avoid blocking */
|
||||
size_t bytes_sent = 0;
|
||||
size_t sent;
|
||||
do {
|
||||
sent = send(request->sockfd, response + bytes_sent, response_len, 0);
|
||||
ssize_t sent;
|
||||
const size_t chunk_size = 8192;
|
||||
|
||||
while (bytes_sent < response_len) {
|
||||
size_t to_send = (response_len - bytes_sent > chunk_size) ? chunk_size : (response_len - bytes_sent);
|
||||
sent = send(request->sockfd, response + bytes_sent, to_send, MSG_NOSIGNAL);
|
||||
|
||||
if (sent <= 0) {
|
||||
if (errno == EAGAIN || errno == EWOULDBLOCK) {
|
||||
continue;
|
||||
}
|
||||
break;
|
||||
}
|
||||
bytes_sent += sent;
|
||||
} while (bytes_sent < response_len && sent != 0);
|
||||
}
|
||||
|
||||
free(response);
|
||||
free(file_data);
|
||||
@@ -300,17 +315,24 @@ void cws_http_send_simple_html(cws_http *request, cws_http_status status, char *
|
||||
"</body>"
|
||||
"</html>",
|
||||
title, description);
|
||||
size_t body_len = strlen(body) * sizeof(char);
|
||||
size_t body_len = strlen(body);
|
||||
|
||||
char conn[32] = "close";
|
||||
mcl_bucket *connection = mcl_hm_get(request->headers, "Connection");
|
||||
if (connection) {
|
||||
strncpy(conn, (char *)connection->value, sizeof(conn));
|
||||
strncpy(conn, (char *)connection->value, sizeof(conn) - 1);
|
||||
conn[sizeof(conn) - 1] = '\0';
|
||||
}
|
||||
|
||||
char *response = NULL;
|
||||
size_t response_len = cws_http_response_builder(&response, "HTTP/1.1", status, "text/html", conn, body, body_len);
|
||||
send(request->sockfd, response, response_len, 0);
|
||||
|
||||
/* Send response with error handling */
|
||||
ssize_t sent = send(request->sockfd, response, response_len, MSG_NOSIGNAL);
|
||||
if (sent < 0) {
|
||||
CWS_LOG_ERROR("Failed to send response: %s", strerror(errno));
|
||||
}
|
||||
|
||||
free(response);
|
||||
}
|
||||
|
||||
|
||||
@@ -119,7 +119,6 @@ cws_server_ret cws_server_loop(int sockfd, cws_config *config) {
|
||||
int nfds = epoll_wait(epfd, revents, CWS_SERVER_EPOLL_MAXEVENTS, CWS_SERVER_EPOLL_TIMEOUT);
|
||||
|
||||
if (nfds == 0) {
|
||||
CWS_LOG_INFO("epoll timeout, continue...");
|
||||
continue;
|
||||
}
|
||||
|
||||
@@ -167,10 +166,10 @@ cws_server_ret cws_server_handle_new_client(int sockfd, int epfd, mcl_hashmap *c
|
||||
}
|
||||
|
||||
cws_server_ret cws_server_handle_client_data(int client_fd, int epfd, mcl_hashmap *clients, cws_config *config) {
|
||||
char tmp_data[4096];
|
||||
char tmp_data[1024];
|
||||
memset(tmp_data, 0, sizeof(tmp_data));
|
||||
char ip[INET_ADDRSTRLEN] = {0};
|
||||
mcl_string *data = mcl_string_new("", 4096);
|
||||
mcl_string *data = mcl_string_new("", 1024);
|
||||
|
||||
/* Incoming data */
|
||||
ssize_t total_bytes = 0;
|
||||
@@ -184,6 +183,7 @@ cws_server_ret cws_server_handle_client_data(int client_fd, int epfd, mcl_hashma
|
||||
return CWS_SERVER_REQUEST_TOO_LARGE;
|
||||
}
|
||||
mcl_string_append(data, tmp_data);
|
||||
memset(tmp_data, 0, sizeof(tmp_data));
|
||||
}
|
||||
|
||||
if (bytes_read < 0 && errno != EAGAIN && errno != EWOULDBLOCK) {
|
||||
@@ -199,6 +199,7 @@ cws_server_ret cws_server_handle_client_data(int client_fd, int epfd, mcl_hashma
|
||||
mcl_bucket *client = mcl_hm_get(clients, &client_fd);
|
||||
if (!client) {
|
||||
CWS_LOG_ERROR("Client fd %d not found in hashmap", client_fd);
|
||||
mcl_string_free(data);
|
||||
cws_epoll_del(epfd, client_fd);
|
||||
close(client_fd);
|
||||
|
||||
@@ -229,7 +230,9 @@ cws_server_ret cws_server_handle_client_data(int client_fd, int epfd, mcl_hashma
|
||||
|
||||
int keepalive = cws_http_send_resource(request);
|
||||
cws_http_free(request);
|
||||
if (!keepalive) {
|
||||
|
||||
/* Only close connection if not keep-alive */
|
||||
if (keepalive <= 0) {
|
||||
cws_server_close_client(epfd, client_fd, clients);
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user