← Commit list

e0c6f4d4d6

Daniel Stenberg
Daniel Stenberg
2026-06-16
SUCCESS Duration: 189s

Subject

tool_writeout: fix %time{} output for %s

Binary

No binary (build failed)

Architecture & Compiler Flags

Architecture: x86_64-linux-gnu Compiler: gcc (Ubuntu 11.4.0-1ubuntu1~22.04.3) 11.4.0

—

Build Log

(log yok)

Commit Diff GitHub →

src/tool_writeout.c+29 -8
@@ -562,18 +562,39 @@ static const char *outtime(const char *ptr, /* %time{ ... */
vlen = end - ptr;
curlx_dyn_init(&format, 1024);
- /* insert sub-seconds for %f */
- /* insert +0000 for %z because it is otherwise not portable */
- /* insert UTC for %Z because it is otherwise not portable */
+ /* Insert:
+ - sub-seconds for %f
+ - epoch seconds for %s; strftime %s uses mktime() and assumes
+ local time, which breaks UTC output on non-UTC hosts
+ - +0000 for %z because it is otherwise not portable
+ - UTC for %Z because it is otherwise not portable
+ - Keep '%%' as-is so that strftime() makes a single % out of them
+ */
for(i = 0; !result && i < vlen; i++) {
- if((i < vlen - 1) && ptr[i] == '%' &&
- ((ptr[i + 1] == 'f') || ((ptr[i + 1] | 0x20) == 'z'))) {
- if(ptr[i + 1] == 'f')
+ if((i < vlen - 1) && ptr[i] == '%') {
+ switch(ptr[i + 1]) {
+ case 'f':
result = curlx_dyn_addf(&format, "%06u", usecs);
- else if(ptr[i + 1] == 'Z')
+ break;
+ case 's': {
+ /* time_t might be either 32 or 64 bits big */
+ curl_off_t tsecs = secs;
+ result = curlx_dyn_addf(&format, "%" CURL_FORMAT_CURL_OFF_T, tsecs);
+ break;
+ }
+ case 'Z':
result = curlx_dyn_addn(&format, "UTC", 3);
- else
+ break;
+ case 'z':
result = curlx_dyn_addn(&format, "+0000", 5);
+ break;
+ case '%':
+ result = curlx_dyn_addn(&format, "%%", 2);
+ break;
+ default:
+ result = curlx_dyn_addn(&format, &ptr[i], 1);
+ continue;
+ }
i++;
}
else
tests/data/test1981+2 -2
@@ -41,7 +41,7 @@ CURL_TIME=1754037103
LC_TIME=C
</setenv>
<command>
-http://%HOSTIP:%HTTPPORT/%TESTNUMBER --write-out='Time: %time{%d/%b/%Y %H:%M:%S.%f %z %Z}\n' -s -o %LOGDIR/dump
+http://%HOSTIP:%HTTPPORT/%TESTNUMBER --write-out='Time: %time{%d/%b/%Y %H:%M:%S.%f %z %Z%%s %s}\n' -s -o %LOGDIR/dump
</command>
</client>
@@ -55,7 +55,7 @@ Accept: */*
</protocol>
<stdout mode="text">
-Time: 01/Aug/2025 08:31:43.037103 +0000 UTC
+Time: 01/Aug/2025 08:31:43.037103 +0000 UTC%s 1754037103
</stdout>
</verify>
</testcase>