Package: valgrind
Version: 1:3.15.0-1
Followup-For: Bug #940516

Dear Maintainer,

The patch email didn't seem to work properly. Some of the headers are
part of the message somehow. I'm still new to Git, so I guess I didn't
send it properly (Gnus did mention something about fixing the headers or
something like that). Should've used git send-email I guess... Anyway,
I'll just attach the patch to this message below.
From 8b3719c3a8eb16802c58b1625c6551987def0477 Mon Sep 17 00:00:00 2001
From: Asher Gordon <asd...@posteo.net>
Date: Thu, 19 Sep 2019 20:11:46 -0400
Subject: [PATCH] Allow loading suppression directories recursively.
To: Debian Bug Tracking System <940...@bugs.debian.org>

Also, load the $prefix/lib/valgrind directory recursively by default
instead of $prefix/lib/valgrind/default.supp.

Fixes 93376.
---
 NEWS                        |  5 +++
 coregrind/m_errormgr.c      | 80 +++++++++++++++++++++++++++++++++++--
 coregrind/m_libcfile.c      |  5 +++
 coregrind/m_main.c          |  7 +---
 include/pub_tool_libcfile.h |  8 ++++
 5 files changed, 95 insertions(+), 10 deletions(-)

diff --git a/NEWS b/NEWS
index 2fde3c7cd..fe696c060 100644
--- a/NEWS
+++ b/NEWS
@@ -25,6 +25,10 @@ support for X86/macOS 10.13 and AMD64/macOS 10.13.
   Your program can also change the dynamically changeable options using
   the client request VALGRIND_CLO_CHANGE(option).
 
+* Directories are now loaded recursively when passed to
+  --suppressions. A default directory, $prefix/lib/valgrind is loaded
+  by default instead of $prefix/lib/valgrind/default.supp.
+
 * ==================== TOOL CHANGES ====================
 
 * DHAT:
@@ -62,6 +66,7 @@ To see details of a given bug, visit
   https://bugs.kde.org/show_bug.cgi?id=XXXXXX
 where XXXXXX is the bug number as listed below.
 
+93376   Suppressions directory
 400593  In Coregrind, use statx for some internal syscalls if [f]stat[64] fail
 406561  mcinfcallWSRU gdbserver_test fails on ppc64
 406824  Unsupported baseline
diff --git a/coregrind/m_errormgr.c b/coregrind/m_errormgr.c
index 52505ba5b..2b01a2f21 100644
--- a/coregrind/m_errormgr.c
+++ b/coregrind/m_errormgr.c
@@ -1481,10 +1481,82 @@ static void load_one_suppressions_file ( Int clo_suppressions_i )
 
 void VG_(add_suppression_file)(const HChar *filename)
 {
-   HChar *f = VG_(strdup)("errormgr.addsup", filename);
-   VG_(addToXA)(VG_(clo_suppressions), &f);
-   if (load_suppressions_called)
-      load_one_suppressions_file( VG_(sizeXA)(VG_(clo_suppressions)) - 1 );
+   // Check if it's a directory.
+   if (VG_(is_dir)( filename )) {
+      SysRes sres;
+      Int fd;
+
+      // Open the directory.
+      sres = VG_(open)( filename, VKI_O_RDONLY, 0 );
+      if (sr_isError(sres)) {
+         if (VG_(clo_xml))
+            VG_(printf_xml)("</valgrindoutput>\n");
+         VG_(umsg)("FATAL: can't open suppressions directory \"%s\"\n", filename );
+         VG_(exit)(1);
+      }
+      fd = sr_Res(sres);
+
+      // Read each entry and add it recursively.
+      while (True) {
+         Int nRead, pos = 0;
+         HChar buf[1024];
+
+         sres = VG_(getdents)( fd, (struct vg_dirent *)buf, sizeof(buf) );
+         if (sr_isError(sres)) {
+            if (VG_(clo_xml))
+               VG_(printf_xml)("</valgrindoutput>\n");
+            VG_(umsg)("FATAL: can't read suppressions directory \"%s\"\n", filename );
+            VG_(exit)(1);
+         }
+         nRead = sr_Res(sres);
+
+         vg_assert(nRead >= 0);
+
+         if (nRead == 0) {
+            // We're at the end of the directory.
+            break;
+         }
+
+         // Add the entries.
+         while (pos < nRead) {
+            struct vg_dirent *entry = (struct vg_dirent *)(buf + pos);
+            HChar *fullpath;
+            SizeT nameSize = VG_(strlen)(entry->name);
+
+            // Skip dotfiles and files which don't end in ".supp".
+            if (entry->name[0] == '.' || nameSize < 5 ||
+                !VG_STREQ(entry->name + nameSize - 5, ".supp")) {
+               pos += entry->reclen;
+               continue;
+            }
+
+            // Get the full path including the directory name.
+            fullpath = VG_(malloc)("errormgr.addsup",
+                                   VG_(strlen)(filename) +
+                                   VG_(strlen)(entry->name) + 2);
+            VG_(strcpy)(fullpath, filename);
+            VG_(strcat)(fullpath, "/");
+            VG_(strcat)(fullpath, entry->name);
+
+            // Add the entry.
+            VG_(add_suppression_file)( fullpath );
+
+            VG_(free)(fullpath);
+
+            // Go to the next entry.
+            pos += entry->reclen;
+         }
+      }
+
+      VG_(close)(fd);
+   }
+   else {
+      // It's not a directory.
+      HChar *f = VG_(strdup)("errormgr.addsup", filename);
+      VG_(addToXA)(VG_(clo_suppressions), &f);
+      if (load_suppressions_called)
+         load_one_suppressions_file( VG_(sizeXA)(VG_(clo_suppressions)) - 1 );
+   }
 }
 
 void VG_(load_suppressions) ( void )
diff --git a/coregrind/m_libcfile.c b/coregrind/m_libcfile.c
index 3a8fed85d..7e6ffe2e8 100644
--- a/coregrind/m_libcfile.c
+++ b/coregrind/m_libcfile.c
@@ -215,6 +215,11 @@ Int VG_(read) ( Int fd, void* buf, Int count)
    return ret;
 }
 
+SysRes VG_(getdents) ( UInt fd, struct vg_dirent *dirp, UInt count ) {
+   SysRes res = VG_(do_syscall3)(__NR_getdents, fd, (UWord)dirp, count);
+   return res;
+}
+
 Int VG_(write) ( Int fd, const void* buf, Int count)
 {
    Int    ret;
diff --git a/coregrind/m_main.c b/coregrind/m_main.c
index 6ad1b93d1..ae1d11e4a 100644
--- a/coregrind/m_main.c
+++ b/coregrind/m_main.c
@@ -1097,12 +1097,7 @@ void main_process_cmd_line_options( void )
    if (VG_(clo_default_supp) &&
        (VG_(needs).core_errors || VG_(needs).tool_errors)) {
       /* If loading default is enabled, add it to the supp list. */
-      static const HChar default_supp[] = "default.supp";
-      Int len = VG_(strlen)(VG_(libdir)) + 1 + sizeof(default_supp);
-      HChar *buf = VG_(malloc)("main.mpclo.3", len);
-      VG_(sprintf)(buf, "%s/%s", VG_(libdir), default_supp);
-      VG_(add_suppression_file)(buf);
-      VG_(free)(buf);
+      VG_(add_suppression_file)(VG_(libdir));
    }
 }
 
diff --git a/include/pub_tool_libcfile.h b/include/pub_tool_libcfile.h
index c42f1b8d4..e9643ca83 100644
--- a/include/pub_tool_libcfile.h
+++ b/include/pub_tool_libcfile.h
@@ -69,6 +69,13 @@ struct vg_stat {
    ULong   ctime_nsec;
 };
 
+struct vg_dirent {
+   ULong ino;
+   ULong off;
+   UShort reclen;
+   HChar name[];
+};
+
 extern SysRes VG_(mknod)  ( const HChar* pathname, Int mode, UWord dev );
 extern SysRes VG_(open)   ( const HChar* pathname, Int flags, Int mode );
 /* fd_open words like the open(2) system call: 
@@ -76,6 +83,7 @@ extern SysRes VG_(open)   ( const HChar* pathname, Int flags, Int mode );
 extern Int VG_(fd_open)  (const HChar* pathname, Int flags, Int mode);
 extern void   VG_(close)  ( Int fd );
 extern Int    VG_(read)   ( Int fd, void* buf, Int count);
+extern SysRes VG_(getdents) ( UInt fd, struct vg_dirent* dirp, UInt count );
 extern Int    VG_(write)  ( Int fd, const void* buf, Int count);
 extern Int    VG_(pipe)   ( Int fd[2] );
 extern Off64T VG_(lseek)  ( Int fd, Off64T offset, Int whence );
-- 
2.23.0

Also, I tried to add a "patch" tag to this bug (with "Tags: patch"), but
it didn't seem to work. What am I doing wrong?

Sorry for the inconvenience,
Asher

-- 
By necessity, by proclivity, and by delight, we all quote.  In fact, it is as
difficult to appropriate the thoughts of others as it is to invent.
                -- R. Emerson
                -- Quoted from a fortune cookie program
                (whose author claims, "Actually, stealing IS easier.")
                [to which I reply, "You think it's easy for me to
                misconstrue all these misquotations?!?"  Ed.]

Attachment: signature.asc
Description: PGP signature

Reply via email to