aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDag-Erling Smørgrav <des@FreeBSD.org>2025-09-01 06:33:28 +0000
committerDag-Erling Smørgrav <des@FreeBSD.org>2025-09-01 06:33:47 +0000
commitca89e15355097e9b57bf4e17a50506e081fe04b3 (patch)
treebba856541fcb802e9a355b7a3d823ccabf36ad14
parent004ce88ad1efd42a1d7d5692849b4aa6906178fc (diff)
tzcode: Don't treat TZDEFAULT as tainted
tzset() calls zoneinit() with the FROMENV flag set unconditionally, so if TZ is unset and we use TZDEFAULT instead, we were still treating it as if it came from the environment. Unset the FROMENV flag if name is null and we switch to TZDEFAULT, or if, after skipping the optional leading colon, we find that name is identical to TZDEFAULT. This incorporates upstream change d0e0b00f846c ("Avoid unnecessary access, stat calls"). Fixes: b6ea2513f776 ("tzcode: Limit TZ for setugid programs") Event: Oslo Hackathon 202508 Reviewed by: philip Differential Revision: https://reviews.freebsd.org/D52240
-rw-r--r--contrib/tzcode/localtime.c10
1 files changed, 6 insertions, 4 deletions
diff --git a/contrib/tzcode/localtime.c b/contrib/tzcode/localtime.c
index a80d422f2955..15afeeecb6d0 100644
--- a/contrib/tzcode/localtime.c
+++ b/contrib/tzcode/localtime.c
@@ -615,6 +615,7 @@ tzloadbody(char const *name, struct state *sp, char tzloadflags,
name = TZDEFAULT;
if (! name)
return EINVAL;
+ tzloadflags &= ~TZLOAD_FROMENV;
}
if (name[0] == ':')
@@ -670,11 +671,13 @@ tzloadbody(char const *name, struct state *sp, char tzloadflags,
fid = _open(name, (O_RDONLY | O_BINARY | O_CLOEXEC | O_CLOFORK
| O_IGNORE_CTTY | O_NOCTTY));
#else /* __FreeBSD__ */
+ if ((tzloadflags & TZLOAD_FROMENV) && strcmp(name, TZDEFAULT) == 0)
+ tzloadflags &= ~TZLOAD_FROMENV;
relname = name;
if (strncmp(relname, TZDIR "/", strlen(TZDIR) + 1) == 0)
relname += strlen(TZDIR) + 1;
dd = _open(TZDIR, O_DIRECTORY | O_RDONLY);
- if (issetugid() && (tzloadflags & TZLOAD_FROMENV)) {
+ if ((tzloadflags & TZLOAD_FROMENV) && issetugid()) {
if (dd < 0)
return errno;
if (fstatat(dd, name, &sb, AT_RESOLVE_BENEATH) < 0) {
@@ -1624,14 +1627,13 @@ zoneinit(struct state *sp, char const *name, char tzloadflags)
static void
tzset_unlocked(void)
{
+ char const *name = getenv("TZ");
#ifdef __FreeBSD__
- tzset_unlocked_name(getenv("TZ"));
+ tzset_unlocked_name(name);
}
static void
tzset_unlocked_name(char const *name)
{
-#else
- char const *name = getenv("TZ");
#endif
struct state *sp = lclptr;
int lcl = name ? strlen(name) < sizeof lcl_TZname : -1;