Parse and store HTTP request headers, handle Content-Length of post content

master
teknomunk 1 year ago
parent 1aed804578
commit e31b804fdc

@ -52,6 +52,7 @@ struct http_request
struct buffered_write* response_body_buffer;
struct header* response_headers;
bool sent_response_headers;
size_t unread_post_content;
// Memory holds
char* first_line;
@ -115,22 +116,31 @@ static void request_fiber_entry()
req->levels_to_root = depth;
int length;
int content_length = 0;
do {
n = 0;
getline_stripped( &ptr, &n, f );
length = strlen(ptr);
if( length > 0 ) {
/*
struct header* h = (struct header*)malloc(sizeof(struct header));
h->next = NULL;
int pos = index( ptr, ':' )
*/
char* value;
char* key = strtok_r( ptr, ":", &value );
while( *value == ' ' ) { ++value; }
printf( "Header: '%s' (%d)\n", ptr, length );
struct header* h = (struct header*)malloc(sizeof(struct header));
h->next = req->request_headers;
h->key = key;
h->value = value;
printf( "Header: %s: %s\n", h->key, h->value );
req->request_headers = h;
if( 0 == strcmp("Content-Length", key ) ) {
sscanf( value, "%u", &content_length );
}
}
free(ptr);
} while( length > 0 );
req->unread_post_content = content_length;
req->handler( req, req->handler_data );
fflush( req->response_body );
@ -212,6 +222,16 @@ static ssize_t http_request_read( void* cookie, char* buf, size_t size )
{
struct http_request* req = (struct http_request*)cookie;
if( req->unread_post_content == -1 ) {
size = 1;
} else if( req->unread_post_content == 0 ) {
return 0;
} else {
if( size > req->unread_post_content ) {
size = req->unread_post_content;
}
}
struct io_bytes_args args;
args.fd = req->sock;
args.failed = false;
@ -231,6 +251,10 @@ static ssize_t http_request_read( void* cookie, char* buf, size_t size )
http_request_call_nonblock( ready, NULL );
}
if( req->unread_post_content != -1 ) {
req->unread_post_content -= args.size_read;
}
return args.size_read;
}
static ssize_t http_request_write_body( struct http_request* req, const char* buf, size_t size )
@ -316,10 +340,15 @@ static ssize_t http_request_body_write( void* cookie, const char* buf, size_t si
static int http_request_body_close( void* cookie )
{}
static int http_request_seek( void* cookie, off64_t*, int )
{
return 0;
}
static cookie_io_functions_t http_response_functions = {
.read = http_request_read,
.write = http_request_body_write,
.seek = NULL,
.seek = http_request_seek,
.close = http_request_body_close,
};
@ -343,6 +372,7 @@ struct http_request* http_request_new( ucontext_t* main, int sock, const char* r
req->sent_response_headers = false;
req->chunked_body = false;
req->response_size = -1;
req->unread_post_content = -1;
req->response_body = fopencookie( (void*)req, "w+", http_response_functions );
@ -374,6 +404,14 @@ void http_request_release( struct http_request* req )
{
printf( "closing socket %d\n", req->sock );
close( req->sock );
for( struct header* iter = req->request_headers; iter; ) {
struct header* next = iter->next;
free(iter->key);
free(iter);
iter = next;
}
free( req->first_line );
free( req->context.uc_stack.ss_sp );
free( req->remote_addr );

Loading…
Cancel
Save