From: Daniel Stenberg Date: Wed, 27 Dec 2023 08:28:48 +0000 (+0100) Subject: getinfo: CURLINFO_QUEUE_TIME_T X-Git-Tag: curl-8_6_0~171 X-Git-Url: http://git.ipfire.org/?a=commitdiff_plain;h=68f96fc9bfce90c264d4d95b91135f3ef945eea8;p=thirdparty%2Fcurl.git getinfo: CURLINFO_QUEUE_TIME_T Returns the time, in microseconds, during which this transfer was held in a waiting queue before it started "for real". A transfer might be put in a queue if after getting started, it cannot create a new connection etc due to set conditions and limits imposed by the application. Ref: #12293 Closes #12368 --- diff --git a/docs/libcurl/curl_easy_getinfo.3 b/docs/libcurl/curl_easy_getinfo.3 index f3c9f946ce..153551f10a 100644 --- a/docs/libcurl/curl_easy_getinfo.3 +++ b/docs/libcurl/curl_easy_getinfo.3 @@ -95,6 +95,9 @@ See \fICURLINFO_PRETRANSFER_TIME(3)\fP .IP CURLINFO_PRETRANSFER_TIME_T Time from start until just before the transfer begins. See \fICURLINFO_PRETRANSFER_TIME_T(3)\fP +.IP CURLINFO_QUEUE_TIME_T +Time during which this transfer was held in a waiting queue. +See \fICURLINFO_QUEUE_TIME_T(3\fP .IP CURLINFO_STARTTRANSFER_TIME Time from start until just when the first byte is received. See \fICURLINFO_STARTTRANSFER_TIME(3)\fP @@ -259,14 +262,18 @@ An overview of the six time values available from \fIcurl_easy_getinfo(3)\fP curl_easy_perform() | - |--NAMELOOKUP - |--|--CONNECT - |--|--|--APPCONNECT - |--|--|--|--PRETRANSFER - |--|--|--|--|--STARTTRANSFER - |--|--|--|--|--|--TOTAL - |--|--|--|--|--|--REDIRECT + |--QUEUE_TIME + |--|--NAMELOOKUP + |--|--|--CONNECT + |--|--|--|--APPCONNECT + |--|--|--|--|--PRETRANSFER + |--|--|--|--|--|--STARTTRANSFER + |--|--|--|--|--|--|--TOTAL + |--|--|--|--|--|--|--REDIRECT .fi +.IP "QUEUE_TIME" +\fICURLINFO_QUEUE_TIME_T(3\fP. The time during which the transfer was held in +a waiting queue before it could start for real. (Added in 8.6.0) .IP NAMELOOKUP \fICURLINFO_NAMELOOKUP_TIME(3)\fP and \fICURLINFO_NAMELOOKUP_TIME_T(3)\fP. The time it took from the start until the name resolving was completed. diff --git a/docs/libcurl/opts/CURLINFO_QUEUE_TIME_T.3 b/docs/libcurl/opts/CURLINFO_QUEUE_TIME_T.3 new file mode 100644 index 0000000000..5ccd7c48a7 --- /dev/null +++ b/docs/libcurl/opts/CURLINFO_QUEUE_TIME_T.3 @@ -0,0 +1,74 @@ +.\" ************************************************************************** +.\" * _ _ ____ _ +.\" * Project ___| | | | _ \| | +.\" * / __| | | | |_) | | +.\" * | (__| |_| | _ <| |___ +.\" * \___|\___/|_| \_\_____| +.\" * +.\" * Copyright (C) Daniel Stenberg, , et al. +.\" * +.\" * This software is licensed as described in the file COPYING, which +.\" * you should have received as part of this distribution. The terms +.\" * are also available at https://curl.se/docs/copyright.html. +.\" * +.\" * You may opt to use, copy, modify, merge, publish, distribute and/or sell +.\" * copies of the Software, and permit persons to whom the Software is +.\" * furnished to do so, under the terms of the COPYING file. +.\" * +.\" * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY +.\" * KIND, either express or implied. +.\" * +.\" * SPDX-License-Identifier: curl +.\" * +.\" ************************************************************************** +.\" +.TH CURLINFO_QUEUE_TIME_T 3 "28 Apr 2018" libcurl libcurl +.SH NAME +CURLINFO_QUEUE_TIME_T \- time this transfer was queued +.SH SYNOPSIS +.nf +#include + +CURLcode curl_easy_getinfo(CURL *handle, CURLINFO_QUEUE_TIME_T, + curl_off_t *timep); +.fi +.SH DESCRIPTION +Pass a pointer to a curl_off_t to receive the time, in microseconds, this +transfer was held in a waiting queue before it started "for real". A transfer +might be put in a queue if after getting started, it cannot create a new +connection etc due to set conditions and limits imposed by the application. + +See also the TIMES overview in the \fIcurl_easy_getinfo(3)\fP man page. +.SH PROTOCOLS +All +.SH EXAMPLE +.nf +int main(void) +{ + CURL *curl = curl_easy_init(); + if(curl) { + CURLcode res; + curl_off_t queue; + curl_easy_setopt(curl, CURLOPT_URL, "https://example.com"); + res = curl_easy_perform(curl); + if(CURLE_OK == res) { + res = curl_easy_getinfo(curl, CURLINFO_QUEUE_TIME_T, &queue); + if(CURLE_OK == res) { + printf("Queued: %" CURL_FORMAT_CURL_OFF_T ".%06ld us", queue / 1000000, + (long)(queue % 1000000)); + } + } + /* always cleanup */ + curl_easy_cleanup(curl); + } +} +.fi +.SH AVAILABILITY +Added in 8.6.0 +.SH RETURN VALUE +Returns CURLE_OK if the option is supported, and CURLE_UNKNOWN_OPTION if not. +.SH "SEE ALSO" +.BR curl_easy_getinfo (3), +.BR curl_easy_setopt (3), +.BR CURLINFO_STARTTRANSFER_TIME_T (3), +.BR CURLOPT_TIMEOUT (3) diff --git a/docs/libcurl/opts/Makefile.inc b/docs/libcurl/opts/Makefile.inc index 4b581c5be4..be7035bf00 100644 --- a/docs/libcurl/opts/Makefile.inc +++ b/docs/libcurl/opts/Makefile.inc @@ -65,6 +65,7 @@ man_MANS = \ CURLINFO_PROXY_ERROR.3 \ CURLINFO_PROXY_SSL_VERIFYRESULT.3 \ CURLINFO_PROXYAUTH_AVAIL.3 \ + CURLINFO_QUEUE_TIME_T.3 \ CURLINFO_REDIRECT_COUNT.3 \ CURLINFO_REDIRECT_TIME.3 \ CURLINFO_REDIRECT_TIME_T.3 \ diff --git a/docs/libcurl/symbols-in-versions b/docs/libcurl/symbols-in-versions index a77a525502..c20008a731 100644 --- a/docs/libcurl/symbols-in-versions +++ b/docs/libcurl/symbols-in-versions @@ -469,6 +469,7 @@ CURLINFO_PROXY_ERROR 7.73.0 CURLINFO_PROXY_SSL_VERIFYRESULT 7.52.0 CURLINFO_PROXYAUTH_AVAIL 7.10.8 CURLINFO_PTR 7.54.1 +CURLINFO_QUEUE_TIME_T 8.6.0 CURLINFO_REDIRECT_COUNT 7.9.7 CURLINFO_REDIRECT_TIME 7.9.7 CURLINFO_REDIRECT_TIME_T 7.61.0 diff --git a/include/curl/curl.h b/include/curl/curl.h index a5b59e0268..b35ac95553 100644 --- a/include/curl/curl.h +++ b/include/curl/curl.h @@ -2936,7 +2936,8 @@ typedef enum { CURLINFO_CAPATH = CURLINFO_STRING + 62, CURLINFO_XFER_ID = CURLINFO_OFF_T + 63, CURLINFO_CONN_ID = CURLINFO_OFF_T + 64, - CURLINFO_LASTONE = 64 + CURLINFO_QUEUE_TIME_T = CURLINFO_OFF_T + 65, + CURLINFO_LASTONE = 65 } CURLINFO; /* CURLINFO_RESPONSE_CODE is the new name for the option previously known as diff --git a/lib/getinfo.c b/lib/getinfo.c index f1574e097b..2f74629e1e 100644 --- a/lib/getinfo.c +++ b/lib/getinfo.c @@ -409,6 +409,9 @@ static CURLcode getinfo_offt(struct Curl_easy *data, CURLINFO info, case CURLINFO_STARTTRANSFER_TIME_T: *param_offt = data->progress.t_starttransfer; break; + case CURLINFO_QUEUE_TIME_T: + *param_offt = data->progress.t_postqueue; + break; case CURLINFO_REDIRECT_TIME_T: *param_offt = data->progress.t_redirect; break; @@ -420,7 +423,7 @@ static CURLcode getinfo_offt(struct Curl_easy *data, CURLINFO info, break; case CURLINFO_CONN_ID: *param_offt = data->conn? - data->conn->connection_id : data->state.recent_conn_id; + data->conn->connection_id : data->state.recent_conn_id; break; default: return CURLE_UNKNOWN_OPTION; diff --git a/lib/multi.c b/lib/multi.c index 89a02680a5..9c7cde8f16 100644 --- a/lib/multi.c +++ b/lib/multi.c @@ -1943,6 +1943,7 @@ static CURLMcode multi_runsingle(struct Curl_multi *multi, } if(!result) { + *nowp = Curl_pgrsTime(data, TIMER_POSTQUEUE); if(async) /* We're now waiting for an asynchronous name lookup */ multistate(data, MSTATE_RESOLVING); diff --git a/lib/progress.c b/lib/progress.c index e96cbf7af4..d05fcc3ebd 100644 --- a/lib/progress.c +++ b/lib/progress.c @@ -174,10 +174,18 @@ void Curl_pgrsTimeWas(struct Curl_easy *data, timerid timer, data->progress.t_startop = timestamp; break; case TIMER_STARTSINGLE: - /* This is set at the start of each single fetch */ + /* This is set at the start of each single transfer */ data->progress.t_startsingle = timestamp; data->progress.is_t_startransfer_set = false; break; + case TIMER_POSTQUEUE: + /* Set when the transfer starts (after potentially having been brought + back from the waiting queue). It needs to count from t_startop and not + t_startsingle since the latter is reset when a connection is brought + back from the pending queue. */ + data->progress.t_postqueue = + Curl_timediff_us(timestamp, data->progress.t_startop); + break; case TIMER_STARTACCEPT: data->progress.t_acceptdata = timestamp; break; diff --git a/lib/progress.h b/lib/progress.h index fc39e34d20..73749419ad 100644 --- a/lib/progress.h +++ b/lib/progress.h @@ -30,7 +30,8 @@ typedef enum { TIMER_NONE, TIMER_STARTOP, - TIMER_STARTSINGLE, + TIMER_STARTSINGLE, /* start of transfer, might get queued */ + TIMER_POSTQUEUE, /* start, immediately after dequeue */ TIMER_NAMELOOKUP, TIMER_CONNECT, TIMER_APPCONNECT, diff --git a/lib/urldata.h b/lib/urldata.h index be9158325b..210fca76c4 100644 --- a/lib/urldata.h +++ b/lib/urldata.h @@ -1189,6 +1189,7 @@ struct Progress { curl_off_t dlspeed; curl_off_t ulspeed; + timediff_t t_postqueue; timediff_t t_nslookup; timediff_t t_connect; timediff_t t_appconnect;