feat(lnm): more request processing code
All checks were successful
ci/woodpecker/push/build Pipeline was successful
All checks were successful
ci/woodpecker/push/build Pipeline was successful
This commit is contained in:
parent
8c21ccf58b
commit
77b62825a6
5 changed files with 120 additions and 19 deletions
|
|
@ -1,12 +1,18 @@
|
|||
#include <stdbool.h>
|
||||
#include <string.h>
|
||||
|
||||
#include "lnm/http/consts.h"
|
||||
#include "lnm/http/loop.h"
|
||||
#include "lnm/http/loop_internal.h"
|
||||
#include "lnm/http/req.h"
|
||||
#include "lnm/loop.h"
|
||||
#include "lnm/loop_internal.h"
|
||||
|
||||
/* static const lnm_http_loop_state lnm_http_loop_state_first_req =
|
||||
* lnm_http_loop_state_parse_req; */
|
||||
static const lnm_http_loop_state lnm_http_loop_state_first_res =
|
||||
lnm_http_loop_state_write_headers;
|
||||
|
||||
void lnm_http_loop_process_parse_req(lnm_http_conn *conn) {
|
||||
lnm_http_loop_ctx *ctx = conn->ctx;
|
||||
|
||||
|
|
@ -16,7 +22,7 @@ void lnm_http_loop_process_parse_req(lnm_http_conn *conn) {
|
|||
switch (res) {
|
||||
case lnm_http_parse_err_ok:
|
||||
conn->r.read += ctx->req.len;
|
||||
ctx->state = lnm_http_loop_state_steps;
|
||||
ctx->state = lnm_http_loop_state_route;
|
||||
break;
|
||||
case lnm_http_parse_err_incomplete:
|
||||
// If the request is already the size of the read buffer, we close the
|
||||
|
|
@ -29,8 +35,8 @@ void lnm_http_loop_process_parse_req(lnm_http_conn *conn) {
|
|||
conn->state = lnm_loop_state_end;
|
||||
break;
|
||||
case lnm_http_parse_err_unknown_method:
|
||||
// TODO set status code here
|
||||
conn->state = lnm_loop_state_end;
|
||||
ctx->res.status = lnm_http_status_method_not_implemented;
|
||||
ctx->state = lnm_http_loop_state_first_res;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
|
@ -65,31 +71,80 @@ void lnm_http_loop_process_route(lnm_http_conn *conn) {
|
|||
match_level = match_level < new_match_level ? new_match_level : match_level;
|
||||
}
|
||||
|
||||
ctx->route = match_level == 2 ? route : NULL;
|
||||
switch (match_level) {
|
||||
case 0:
|
||||
ctx->res.status = lnm_http_status_not_found;
|
||||
ctx->state = lnm_http_loop_state_first_res;
|
||||
break;
|
||||
case 1:
|
||||
ctx->res.status = lnm_http_status_method_not_allowed;
|
||||
ctx->state = lnm_http_loop_state_first_res;
|
||||
break;
|
||||
case 2:
|
||||
ctx->route = route;
|
||||
ctx->cur_step = route->step;
|
||||
ctx->state = lnm_http_loop_state_parse_headers;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
void lnm_http_loop_process_parse_headers(lnm_http_conn *conn) {
|
||||
lnm_http_loop_ctx *ctx = conn->ctx;
|
||||
|
||||
// TODO
|
||||
|
||||
ctx->state = lnm_http_loop_state_steps;
|
||||
}
|
||||
|
||||
void lnm_http_loop_process_steps(lnm_http_conn *conn) {
|
||||
/* lnm_http_loop_ctx *ctx = conn->ctx; */
|
||||
lnm_http_loop_ctx *ctx = conn->ctx;
|
||||
lnm_http_step *step;
|
||||
|
||||
/* while () */
|
||||
do {
|
||||
step = ctx->cur_step;
|
||||
|
||||
switch (step->fn(conn)) {
|
||||
case lnm_http_step_err_done:
|
||||
ctx->cur_step = ctx->cur_step->next;
|
||||
break;
|
||||
case lnm_http_step_err_io_needed:
|
||||
break;
|
||||
case lnm_http_step_err_close:
|
||||
conn->state = lnm_loop_state_end;
|
||||
break;
|
||||
case lnm_http_step_err_res:
|
||||
ctx->state = lnm_http_loop_state_first_res;
|
||||
break;
|
||||
}
|
||||
} while ((step != ctx->cur_step) && (ctx->cur_step != NULL));
|
||||
|
||||
if (ctx->cur_step == NULL) {
|
||||
ctx->state = lnm_http_loop_state_write_headers;
|
||||
}
|
||||
}
|
||||
|
||||
void (*process_fns[])(lnm_http_conn *conn) = {
|
||||
lnm_http_loop_process_parse_req,
|
||||
lnm_http_loop_process_route,
|
||||
lnm_http_loop_process_parse_headers,
|
||||
lnm_http_loop_process_steps,
|
||||
};
|
||||
|
||||
void lnm_http_loop_process(lnm_http_conn *conn) {
|
||||
lnm_http_loop_ctx *ctx = conn->ctx;
|
||||
|
||||
lnm_http_loop_state cur_state;
|
||||
lnm_http_loop_state http_loop_state;
|
||||
lnm_loop_state loop_state;
|
||||
|
||||
// As long as the processing is able to advance to a next state, we keep
|
||||
// progressing
|
||||
// We stop processing if:
|
||||
// - the event loop state has changed, as we need to switch to the other I/O
|
||||
// loop
|
||||
// - the process fn returned without changing the HTTP loop state, indicating
|
||||
// it's waiting for I/O
|
||||
do {
|
||||
cur_state = ctx->state;
|
||||
http_loop_state = ctx->state;
|
||||
loop_state = conn->state;
|
||||
|
||||
process_fns[cur_state](conn);
|
||||
} while (conn->state == lnm_loop_state_req && cur_state != ctx->state);
|
||||
process_fns[http_loop_state](conn);
|
||||
} while ((conn->state == loop_state) && (http_loop_state != ctx->state));
|
||||
}
|
||||
Loading…
Add table
Add a link
Reference in a new issue