ah: require parsing complete before detach
Introduce helpers to force to detachable state and to test the ah is in a detachable state. Require not only the ah rx buffer is all used, but that the wsi has completed a full set of headers.
This commit is contained in:
parent
0b629d4037
commit
8f4f692945
7 changed files with 43 additions and 21 deletions
|
@ -402,8 +402,8 @@ lws_client_connect_2(struct lws *wsi)
|
|||
|
||||
oom4:
|
||||
/* we're closing, losing some rx is OK */
|
||||
if (wsi->u.hdr.ah)
|
||||
wsi->u.hdr.ah->rxpos = wsi->u.hdr.ah->rxlen;
|
||||
lws_header_table_force_to_detachable_state(wsi);
|
||||
|
||||
if (wsi->mode == LWSCM_HTTP_CLIENT ||
|
||||
wsi->mode == LWSCM_HTTP_CLIENT_ACCEPTED ||
|
||||
wsi->mode == LWSCM_WSCL_WAITING_CONNECT) {
|
||||
|
|
|
@ -583,7 +583,7 @@ lws_http_transaction_completed_client(struct lws *wsi)
|
|||
* we can drop the ah, if any
|
||||
*/
|
||||
if (wsi->u.hdr.ah) {
|
||||
wsi->u.hdr.ah->rxpos = wsi->u.hdr.ah->rxlen;
|
||||
lws_header_table_force_to_detachable_state(wsi);
|
||||
lws_header_table_detach(wsi, 0);
|
||||
}
|
||||
|
||||
|
@ -1258,7 +1258,7 @@ lws_generate_client_handshake(struct lws *wsi, char *pkt)
|
|||
wsi->user_space, NULL, 0))
|
||||
return NULL;
|
||||
|
||||
wsi->u.hdr.ah->rxpos = wsi->u.hdr.ah->rxlen;
|
||||
lws_header_table_force_to_detachable_state(wsi);
|
||||
lws_union_transition(wsi, LWSCM_RAW);
|
||||
lws_header_table_detach(wsi, 1);
|
||||
|
||||
|
|
|
@ -243,9 +243,8 @@ lws_close_free_wsi(struct lws *wsi, enum lws_close_status reason)
|
|||
}
|
||||
#endif
|
||||
|
||||
if (wsi->u.hdr.ah)
|
||||
/* we're closing, losing some rx is OK */
|
||||
wsi->u.hdr.ah->rxpos = wsi->u.hdr.ah->rxlen;
|
||||
/* we're closing, losing some rx is OK */
|
||||
lws_header_table_force_to_detachable_state(wsi);
|
||||
|
||||
context = wsi->context;
|
||||
pt = &context->pt[(int)wsi->tsi];
|
||||
|
@ -2552,7 +2551,7 @@ lws_cgi(struct lws *wsi, const char * const *exec_array, int script_uri_path_len
|
|||
* Actually having made the env, as a cgi we don't need the ah
|
||||
* any more
|
||||
*/
|
||||
if (wsi->u.hdr.ah->rxpos == wsi->u.hdr.ah->rxlen)
|
||||
if (lws_header_table_is_in_detachable_state(wsi))
|
||||
lws_header_table_detach(wsi, 0);
|
||||
|
||||
/* we are ready with the redirection pipes... run the thing */
|
||||
|
|
|
@ -215,6 +215,24 @@ bail:
|
|||
return 1;
|
||||
}
|
||||
|
||||
void
|
||||
lws_header_table_force_to_detachable_state(struct lws *wsi)
|
||||
{
|
||||
if (wsi->u.hdr.ah) {
|
||||
wsi->u.hdr.ah->rxpos = -1;
|
||||
wsi->u.hdr.ah->rxlen = -1;
|
||||
wsi->hdr_parsing_completed = 1;
|
||||
}
|
||||
}
|
||||
|
||||
int
|
||||
lws_header_table_is_in_detachable_state(struct lws *wsi)
|
||||
{
|
||||
struct allocated_headers *ah = wsi->u.hdr.ah;
|
||||
|
||||
return ah && ah->rxpos == ah->rxlen && wsi->hdr_parsing_completed;
|
||||
}
|
||||
|
||||
int lws_header_table_detach(struct lws *wsi, int autoservice)
|
||||
{
|
||||
struct lws_context *context = wsi->context;
|
||||
|
@ -224,6 +242,9 @@ int lws_header_table_detach(struct lws *wsi, int autoservice)
|
|||
struct lws **pwsi;
|
||||
time_t now;
|
||||
|
||||
if (!ah)
|
||||
return 0;
|
||||
|
||||
lwsl_info("%s: wsi %p: ah %p (tsi=%d, count = %d)\n", __func__,
|
||||
(void *)wsi, (void *)ah, wsi->tsi,
|
||||
pt->ah_count_in_use);
|
||||
|
@ -232,11 +253,9 @@ int lws_header_table_detach(struct lws *wsi, int autoservice)
|
|||
lws_free_set_NULL(wsi->u.hdr.preamble_rx);
|
||||
|
||||
/* may not be detached while he still has unprocessed rx */
|
||||
if (ah && ah->rxpos != ah->rxlen) {
|
||||
lwsl_err("%s: %p: CANNOT DETACH rxpos:%d, rxlen:%d\n", __func__, wsi,
|
||||
ah->rxpos, ah->rxlen);
|
||||
assert(ah->rxpos == ah->rxlen);
|
||||
|
||||
if (!lws_header_table_is_in_detachable_state(wsi)) {
|
||||
lwsl_err("%s: %p: CANNOT DETACH rxpos:%d, rxlen:%d, wsi->hdr_parsing_completed = %d\n", __func__, wsi,
|
||||
ah->rxpos, ah->rxlen, wsi->hdr_parsing_completed);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
|
@ -1904,6 +1904,11 @@ lws_header_table_reset(struct lws *wsi, int autoservice);
|
|||
void
|
||||
_lws_header_table_reset(struct allocated_headers *ah);
|
||||
|
||||
void
|
||||
lws_header_table_force_to_detachable_state(struct lws *wsi);
|
||||
int
|
||||
lws_header_table_is_in_detachable_state(struct lws *wsi);
|
||||
|
||||
LWS_EXTERN char * LWS_WARN_UNUSED_RESULT
|
||||
lws_hdr_simple_ptr(struct lws *wsi, enum lws_token_indexes h);
|
||||
|
||||
|
|
12
lib/server.c
12
lib/server.c
|
@ -1271,7 +1271,7 @@ deal_body:
|
|||
|
||||
bail_nuke_ah:
|
||||
/* we're closing, losing some rx is OK */
|
||||
wsi->u.hdr.ah->rxpos = wsi->u.hdr.ah->rxlen;
|
||||
lws_header_table_force_to_detachable_state(wsi);
|
||||
// lwsl_notice("%s: drop1\n", __func__);
|
||||
lws_header_table_detach(wsi, 1);
|
||||
|
||||
|
@ -1338,7 +1338,7 @@ raw_transition:
|
|||
wsi->user_space, NULL, 0))
|
||||
goto bail_nuke_ah;
|
||||
|
||||
wsi->u.hdr.ah->rxpos = wsi->u.hdr.ah->rxlen;
|
||||
lws_header_table_force_to_detachable_state(wsi);
|
||||
lws_union_transition(wsi, LWSCM_RAW);
|
||||
lws_header_table_detach(wsi, 1);
|
||||
|
||||
|
@ -1697,7 +1697,7 @@ upgrade_ws:
|
|||
|
||||
/* !!! drop ah unreservedly after ESTABLISHED */
|
||||
if (!wsi->more_rx_waiting) {
|
||||
wsi->u.hdr.ah->rxpos = wsi->u.hdr.ah->rxlen;
|
||||
lws_header_table_force_to_detachable_state(wsi);
|
||||
|
||||
//lwsl_notice("%p: dropping ah EST\n", wsi);
|
||||
lws_header_table_detach(wsi, 1);
|
||||
|
@ -1711,7 +1711,7 @@ upgrade_ws:
|
|||
bail_nuke_ah:
|
||||
/* drop the header info */
|
||||
/* we're closing, losing some rx is OK */
|
||||
wsi->u.hdr.ah->rxpos = wsi->u.hdr.ah->rxlen;
|
||||
lws_header_table_force_to_detachable_state(wsi);
|
||||
//lwsl_notice("%s: drop2\n", __func__);
|
||||
lws_header_table_detach(wsi, 1);
|
||||
|
||||
|
@ -1847,7 +1847,7 @@ lws_http_transaction_completed(struct lws *wsi)
|
|||
wsi->more_rx_waiting);
|
||||
|
||||
if (!wsi->more_rx_waiting) {
|
||||
wsi->u.hdr.ah->rxpos = wsi->u.hdr.ah->rxlen;
|
||||
lws_header_table_force_to_detachable_state(wsi);
|
||||
lws_header_table_detach(wsi, 1);
|
||||
#ifdef LWS_OPENSSL_SUPPORT
|
||||
/*
|
||||
|
@ -2260,7 +2260,7 @@ lws_server_socket_service(struct lws_context *context, struct lws *wsi,
|
|||
|
||||
lwsl_debug("%s: wsi %p: ah read rxpos %d, rxlen %d\n", __func__, wsi, wsi->u.hdr.ah->rxpos, wsi->u.hdr.ah->rxlen);
|
||||
|
||||
if (wsi->u.hdr.ah->rxpos == wsi->u.hdr.ah->rxlen &&
|
||||
if (lws_header_table_is_in_detachable_state(wsi) &&
|
||||
(wsi->mode != LWSCM_HTTP_SERVING &&
|
||||
wsi->mode != LWSCM_HTTP_SERVING_ACCEPTED &&
|
||||
wsi->mode != LWSCM_HTTP2_SERVING))
|
||||
|
|
|
@ -1257,8 +1257,7 @@ drain:
|
|||
if (wsi->u.hdr.ah) {
|
||||
lwsl_notice("%s: %p: detaching\n",
|
||||
__func__, wsi);
|
||||
/* show we used all the pending rx up */
|
||||
wsi->u.hdr.ah->rxpos = wsi->u.hdr.ah->rxlen;
|
||||
lws_header_table_force_to_detachable_state(wsi);
|
||||
/* we can run the normal ah detach flow despite
|
||||
* being in ws union mode, since all union members
|
||||
* start with hdr */
|
||||
|
|
Loading…
Add table
Reference in a new issue