>Synopsis: localtime(3) always returns UTC
>Category: library
>Environment:
System : OpenBSD 7.9
Details : OpenBSD 7.9-current (GENERIC.MP) #476: Fri May 15
03:34:47 UTC 2026
[email protected]:/usr/src/sys/arch/amd64/compile/GENERIC.MP
Architecture: OpenBSD.amd64
Machine : amd64
>Description:
Since today's sysupgrade -s, all my clocks are in UTC. After taking a
second look, this seems to be localtime(3)'s fault.
Please consider the following short C program as an example.
#include <err.h>
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
int
main(int argc, char *argv[])
{
struct tm *tp;
time_t tval;
char buf[1024];
if (time(&tval) == 1)
err(1, "time");
tp = localtime(&tval);
if (!tp)
err(1, "localtime");
strftime(buf, sizeof(buf), "%a %b %e %H:%M:%S %Z %Y",
tp);
printf("%s\n", buf);
return EXIT_SUCCESS;
}
On an OpenBSD 7.8, OpenBSD 7.8 GENERIC.MP#7 amd64, the output matched
/etc/localtime and honored TZ.
$ ./a.out
Fri May 15 14:02:06 CEST 2026
$ TZ=UTC ./a.out
Fri May 15 12:02:11 UTC 2026
$ TZ=Europe/London ./a.out
Fri May 15 13:02:19 BST 2026
However, on my -current system, it's UTC all the way.
$ ./a.out
Fri May 15 12:04:37 UTC 2026
$ TZ=UTC ./a.out
Fri May 15 12:04:43 UTC 2026
$ TZ=Europe/London ./a.out
Fri May 15 12:04:48 UTC 2026
There was a really recent change from deraadt to
lib/libc/time/localtime.c,
which goes in this direction but I am uncertain how much it is related.
- https://marc.info/?l=openbsd-cvs&m=177881228902319&w=2
-
https://cvsweb.openbsd.org/diff/src/lib/libc/time/localtime.c,v?rev=1.78&prev=1.77
>How-To-Repeat:
Upgrade a current OpenBSD to "OpenBSD 7.9 GENERIC.MP#476 amd64" and
either
try the C code above or just use date(1).