lib: move 'done' parameter to SingleRequests

A transfer may do several `SingleRequest`s for its success. This happens
regularly for authentication, follows and retries on failed connections.
The "readwrite()" calls and functions connected to those carried a `bool
*done` parameter to indicate that the current `SingleRequest` is over.
This may happen before `upload_done` or `download_done` bits of
`SingleRequest` are set.

The problem with that is now `write_resp()` protocol handlers are
invoked in places where the `bool *done` cannot be passed up to the
caller. Instead of being a bool in the call chain, it needs to become a
member of `SingleRequest`, reflecting its state.

This removes the `bool *done` parameter and adds the `done` bit to
`SingleRequest` instead. It adds `Curl_req_soft_reset()` for using a
`SingleRequest` in a follow up, clearing `done` and other
flags/counters.

Closes #13096
This commit is contained in:
Stefan Eissing 2024-03-11 12:35:07 +01:00 committed by Daniel Stenberg
parent 6aeb729b5c
commit 4e4e8af1f6
No known key found for this signature in database
GPG key ID: 5CC908FDB71E12C2
16 changed files with 96 additions and 100 deletions

View file

@ -209,7 +209,7 @@ static ssize_t Curl_xfer_recv_resp(struct Curl_easy *data,
*/
static CURLcode readwrite_data(struct Curl_easy *data,
struct SingleRequest *k,
int *didwhat, bool *done)
int *didwhat)
{
struct connectdata *conn = data->conn;
CURLcode result = CURLE_OK;
@ -219,8 +219,6 @@ static CURLcode readwrite_data(struct Curl_easy *data,
curl_off_t total_received = 0;
bool is_multiplex = FALSE;
*done = FALSE;
result = Curl_multi_xfer_buf_borrow(data, &xfer_buf, &xfer_blen);
if(result)
goto out;
@ -281,8 +279,8 @@ static CURLcode readwrite_data(struct Curl_easy *data,
}
total_received += blen;
result = Curl_xfer_write_resp(data, buf, blen, is_eos, done);
if(result || *done)
result = Curl_xfer_write_resp(data, buf, blen, is_eos);
if(result || data->req.done)
goto out;
/* if we are done, we stop receiving. On multiplexed connections,
@ -403,8 +401,7 @@ static int select_bits_paused(struct Curl_easy *data, int select_bits)
* Curl_readwrite() is the low-level function to be called when data is to
* be read and written to/from the connection.
*/
CURLcode Curl_readwrite(struct Curl_easy *data,
bool *done)
CURLcode Curl_readwrite(struct Curl_easy *data)
{
struct connectdata *conn = data->conn;
struct SingleRequest *k = &data->req;
@ -450,8 +447,8 @@ CURLcode Curl_readwrite(struct Curl_easy *data,
#ifdef USE_HYPER
if(conn->datastream) {
result = conn->datastream(data, conn, &didwhat, done, select_bits);
if(result || *done)
result = conn->datastream(data, conn, &didwhat, select_bits);
if(result || data->req.done)
goto out;
}
else {
@ -460,8 +457,8 @@ CURLcode Curl_readwrite(struct Curl_easy *data,
the stream was rewound (in which case we have data in a
buffer) */
if((k->keepon & KEEP_RECV) && (select_bits & CURL_CSELECT_IN)) {
result = readwrite_data(data, k, &didwhat, done);
if(result || *done)
result = readwrite_data(data, k, &didwhat);
if(result || data->req.done)
goto out;
}
@ -561,8 +558,10 @@ CURLcode Curl_readwrite(struct Curl_easy *data,
}
}
/* Now update the "done" boolean we return */
*done = (0 == (k->keepon&(KEEP_RECVBITS|KEEP_SENDBITS))) ? TRUE : FALSE;
/* If there is nothing more to send/recv, the request is done */
if(0 == (k->keepon&(KEEP_RECVBITS|KEEP_SENDBITS)))
data->req.done = TRUE;
out:
if(result)
DEBUGF(infof(data, "Curl_readwrite() -> %d", result));
@ -937,7 +936,7 @@ CURLcode Curl_follow(struct Curl_easy *data,
data->state.url = newurl;
data->state.url_alloc = TRUE;
Curl_req_soft_reset(&data->req, data);
infof(data, "Issue another request to this URL: '%s'", data->state.url);
/*
@ -1209,14 +1208,14 @@ void Curl_xfer_setup(
CURLcode Curl_xfer_write_resp(struct Curl_easy *data,
char *buf, size_t blen,
bool is_eos, bool *done)
bool is_eos)
{
CURLcode result = CURLE_OK;
if(data->conn->handler->write_resp) {
/* protocol handlers offering this function take full responsibility
* for writing all received download data to the client. */
result = data->conn->handler->write_resp(data, buf, blen, is_eos, done);
result = data->conn->handler->write_resp(data, buf, blen, is_eos);
}
else {
/* No special handling by protocol handler, write all received data