http2: improved upload eos handling

- replace the counting of upload lengths with the new eos send flag
- improve frequency of stream draining to happen less on events where it
  is not needed
- this PR is based on #14220

http2, cf-h2-proxy: fix EAGAINed out buffer
- in adjust pollset and shutdown handling, a non-empty `ctx->outbufq`
  must trigger send polling, irregardless of http/2 flow control
- in http2, fix retry handling of blocked GOAWAY frame

test case improvement:
- let client 'upload-pausing' handle http versions

Closes #14253
This commit is contained in:
Stefan Eissing 2024-08-04 09:51:26 +02:00 committed by Daniel Stenberg
parent 344ba8c883
commit 35bf766280
No known key found for this signature in database
GPG key ID: 5CC908FDB71E12C2
10 changed files with 302 additions and 190 deletions

View file

@ -184,6 +184,30 @@ static bool xfer_recv_shutdown_started(struct Curl_easy *data)
return Curl_shutdown_started(data, sockindex);
}
CURLcode Curl_xfer_send_shutdown(struct Curl_easy *data, bool *done)
{
int sockindex;
if(!data || !data->conn)
return CURLE_FAILED_INIT;
if(data->conn->writesockfd == CURL_SOCKET_BAD)
return CURLE_FAILED_INIT;
sockindex = (data->conn->writesockfd == data->conn->sock[SECONDARYSOCKET]);
return Curl_conn_shutdown(data, sockindex, done);
}
static bool xfer_send_shutdown_started(struct Curl_easy *data)
{
int sockindex;
if(!data || !data->conn)
return CURLE_FAILED_INIT;
if(data->conn->writesockfd == CURL_SOCKET_BAD)
return CURLE_FAILED_INIT;
sockindex = (data->conn->writesockfd == data->conn->sock[SECONDARYSOCKET]);
return Curl_shutdown_started(data, sockindex);
}
/**
* Receive raw response data for the transfer.
* @param data the transfer
@ -420,6 +444,16 @@ CURLcode Curl_readwrite(struct Curl_easy *data)
select_bits = data->state.select_bits;
data->state.select_bits = 0;
}
else if(((k->keepon & KEEP_RECVBITS) == KEEP_RECV) &&
xfer_recv_shutdown_started(data)) {
DEBUGF(infof(data, "readwrite, recv for finishing shutdown"));
select_bits = CURL_CSELECT_IN;
}
else if(((k->keepon & KEEP_SENDBITS) == KEEP_SEND) &&
xfer_send_shutdown_started(data)) {
DEBUGF(infof(data, "readwrite, send for finishing shutdown"));
select_bits = CURL_CSELECT_OUT;
}
else {
curl_socket_t fd_read;
curl_socket_t fd_write;
@ -1303,18 +1337,6 @@ CURLcode Curl_xfer_send_close(struct Curl_easy *data)
return CURLE_OK;
}
CURLcode Curl_xfer_send_shutdown(struct Curl_easy *data, bool *done)
{
int sockindex;
if(!data || !data->conn)
return CURLE_FAILED_INIT;
if(data->conn->writesockfd == CURL_SOCKET_BAD)
return CURLE_FAILED_INIT;
sockindex = (data->conn->writesockfd == data->conn->sock[SECONDARYSOCKET]);
return Curl_conn_shutdown(data, sockindex, done);
}
bool Curl_xfer_is_blocked(struct Curl_easy *data)
{
bool want_send = ((data)->req.keepon & KEEP_SEND);