[compiler-rt] [sanitizer] Fix sanitizing glob_t when flags contain GLOB_DOOFFS (PR #166468)

Samuel Thibault via llvm-commits llvm-commits at lists.llvm.org
Tue Nov 4 15:48:31 PST 2025


https://github.com/sthibaul updated https://github.com/llvm/llvm-project/pull/166468

>From 8a63aff3c27eca9fa3f9c01b25716020c6ec5f8d Mon Sep 17 00:00:00 2001
From: Samuel Thibault <samuel.thibault at ens-lyon.org>
Date: Mon, 27 Jan 2025 00:11:00 +0100
Subject: [PATCH] [sanitizer] Fix sanitizing glob_t when flags contain
 GLOB_DOOFFS

e.g.

  glob_t g;
  memset(&g, 0, sizeof(g);
  g.gl_offs = 1;
  glob("*", GLOB_DOOFFS, NULL, &g);

will reserve one NULL entry at the beginning of g.gl_pathv, in addition to
the gl.gl_pathc results.
---
 .../sanitizer_common_interceptors.inc         | 21 +++++++++++++------
 1 file changed, 15 insertions(+), 6 deletions(-)

diff --git a/compiler-rt/lib/sanitizer_common/sanitizer_common_interceptors.inc b/compiler-rt/lib/sanitizer_common/sanitizer_common_interceptors.inc
index b10ce7fa44afc..12d45c47c2b28 100644
--- a/compiler-rt/lib/sanitizer_common/sanitizer_common_interceptors.inc
+++ b/compiler-rt/lib/sanitizer_common/sanitizer_common_interceptors.inc
@@ -2468,13 +2468,19 @@ INTERCEPTOR(int, timespec_get, struct __sanitizer_timespec *ts, int base) {
 #endif
 
 #if SANITIZER_INTERCEPT_GLOB
-static void unpoison_glob_t(void *ctx, __sanitizer_glob_t *pglob) {
+static void unpoison_glob_t(void *ctx, int flags, __sanitizer_glob_t* pglob) {
+  SIZE_T offs;
   COMMON_INTERCEPTOR_WRITE_RANGE(ctx, pglob, sizeof(*pglob));
+  if (flags & GLOB_DOOFFS)
+    offs = pglob->gl_offs;
+  else
+    offs = 0;
   // +1 for NULL pointer at the end.
   if (pglob->gl_pathv)
     COMMON_INTERCEPTOR_WRITE_RANGE(
-        ctx, pglob->gl_pathv, (pglob->gl_pathc + 1) * sizeof(*pglob->gl_pathv));
-  for (SIZE_T i = 0; i < pglob->gl_pathc; ++i) {
+        ctx, pglob->gl_pathv,
+	(offs + pglob->gl_pathc + 1) * sizeof(*pglob->gl_pathv));
+  for (SIZE_T i = offs; i < offs + pglob->gl_pathc; ++i) {
     char *p = pglob->gl_pathv[i];
     COMMON_INTERCEPTOR_WRITE_RANGE(ctx, p, internal_strlen(p) + 1);
   }
@@ -2488,7 +2494,8 @@ INTERCEPTOR(int, glob, const char *pattern, int flags,
   COMMON_INTERCEPTOR_ENTER(ctx, glob, pattern, flags, errfunc, pglob);
   COMMON_INTERCEPTOR_READ_STRING(ctx, pattern, 0);
   int res = REAL(glob)(pattern, flags, errfunc, pglob);
-  if ((!res || res == glob_nomatch) && pglob) unpoison_glob_t(ctx, pglob);
+  if ((!res || res == glob_nomatch) && pglob)
+    unpoison_glob_t(ctx, flags, pglob);
   return res;
 }
 #else
@@ -2552,7 +2559,8 @@ INTERCEPTOR(int, glob, const char *pattern, int flags,
     Swap(pglob->gl_stat, glob_copy.gl_stat);
   }
   pglob_copy = 0;
-  if ((!res || res == glob_nomatch) && pglob) unpoison_glob_t(ctx, pglob);
+  if ((!res || res == glob_nomatch) && pglob)
+    unpoison_glob_t(ctx, flags, pglob);
   return res;
 }
 #endif  // SANITIZER_SOLARIS
@@ -2588,7 +2596,8 @@ INTERCEPTOR(int, glob64, const char *pattern, int flags,
     Swap(pglob->gl_stat, glob_copy.gl_stat);
   }
   pglob_copy = 0;
-  if ((!res || res == glob_nomatch) && pglob) unpoison_glob_t(ctx, pglob);
+  if ((!res || res == glob_nomatch) && pglob)
+    unpoison_glob_t(ctx, flags, pglob);
   return res;
 }
 #define INIT_GLOB64                \



More information about the llvm-commits mailing list