[PATCH] Logging to file (was: Re: [PATCH] Logging to socket feature)

Juuso Alasuutari juuso.alasuutari at gmail.com
Wed Nov 14 03:55:46 PST 2007


On Tuesday 13 November 2007 16:55:24 Tollef Fog Heen wrote:
> * Juuso Alasuutari
>
> | It's been almost a year since I got this idea and suggested it on this
> | list [0]. As someone who does a lot of building from source, I've long
> | dreamed of a pkg-config feature to help identify missing dependencies. I
> | finally found time and energy to implement it myself and wrote a patch
> | which applies both against 0.22 and current development tree.
>
> Hi, sorry about completely forgetting about this.  Mea culpa, and I'll
> try to do better now.

No harm done, I'm persistent. :)

> Is there any particular reason you want to log to a socket rather than
> just logging to a file (which can be a FIFO)?

You're the second person to ask this, and after having a closer look at named 
pipes I can certainly understand why.

I'm not a terribly experienced coder, and a socket seemed to me like the most 
natural thing to use for a daemon that tracks pkg-config invocations. I've 
now changed the code to append to a file instead, and it's definitely more 
elegant that way. (I didn't update the example program yet, but the concept 
still applies.)

I'll attach a second revision of the patch. Please shoot holes in it if you 
find anything you don't like, and I'll do my best to fix them. (Something 
that I considered doing was making log_file static instead of a global, and 
making write_to_log_file() a function that accesses it instead of a macro, 
but I decided to avoid the varargs stuff. But I digress...)

Juuso


=== added file 'logfile.c'
--- logfile.c	1970-01-01 00:00:00 +0000
+++ logfile.c	2007-11-14 11:20:57 +0000
@@ -0,0 +1,44 @@
+/*
+ * Copyright (C) 2007 Juuso Alasuutari
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License as
+ * published by the Free Software Foundation; either version 2 of the
+ * License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
+ * 02111-1307, USA.
+ */
+
+#include "logfile.h"
+
+FILE *log_file = NULL;
+
+void
+open_log_file (const char *name)
+{
+  log_file = fopen (name, "a");
+  if (log_file)
+      debug_spew ("Opened log file '%s'\n", name);
+  else
+      debug_spew ("Failed to open log file '%s': %s\n", name, strerror 
(errno));
+}
+
+void
+close_log_file (void)
+{
+  if (log_file)
+    {
+      if (fclose (log_file) != EOF)
+        debug_spew ("Closed log file\n");
+      else
+        debug_spew ("Failed to close log file: %s\n", strerror (errno));
+    }
+}

=== added file 'logfile.h'
--- logfile.h	1970-01-01 00:00:00 +0000
+++ logfile.h	2007-11-14 11:20:57 +0000
@@ -0,0 +1,37 @@
+/*
+ * Copyright (C) 2007 Juuso Alasuutari
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License as
+ * published by the Free Software Foundation; either version 2 of the
+ * License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
+ * 02111-1307, USA.
+ */
+
+#ifndef PKG_CONFIG_LOGFILE_H
+#define PKG_CONFIG_LOGFILE_H
+
+#include <stdio.h>
+#include <errno.h>
+
+#define write_to_log_file(x, y...) \
+if (log_file) fprintf (log_file, x, ## y)
+
+extern FILE *log_file;
+
+void
+open_log_file (const char *name);
+
+void
+close_log_file (void);
+
+#endif

=== modified file 'Makefile.am'
--- Makefile.am	2007-02-25 10:05:01 +0000
+++ Makefile.am	2007-11-14 11:20:57 +0000
@@ -36,3 +36,6 @@
 	poptint.h \
 	poptparse.c
 
+if LOG_FILE
+pkg_config_SOURCES += logfile.c logfile.h
+endif

=== modified file 'configure.in'
--- configure.in	2007-06-18 21:31:42 +0000
+++ configure.in	2007-11-14 11:20:57 +0000
@@ -112,7 +112,18 @@
       fi
     fi
   ])
-fi # !use_installed_glib
+
+  AC_ARG_ENABLE([log-file],
+    [  --enable-log-file       Enable logging to a file],
+    [enable_log_file=$enableval], [])
+
+  AM_CONDITIONAL(LOG_FILE, test x$enable_log_file = xyes)
+
+  if test x$enable_log_file = xyes; then
+    AC_DEFINE(LOG_FILE, 1, [Logging to a file])
+  fi
+
+fi # !native_win32
 
 AM_CONDITIONAL(USE_INSTALLED_GLIB, test x$use_installed_glib = xyes)
 
@@ -123,7 +134,7 @@
 
 else
   AC_CONFIG_SUBDIRS(glib-1.2.8)
-fi # !native_win32
+fi # !use_installed_glib
 
 AC_FUNC_ALLOCA
 

=== modified file 'main.c'
--- main.c	2006-08-16 17:57:14 +0000
+++ main.c	2007-11-14 11:20:57 +0000
@@ -24,6 +24,10 @@
 #include "pkg.h"
 #include "parse.h"
 
+#ifdef LOG_FILE
+#include "logfile.h"
+#endif
+
 #include "popt.h"
 #include <stdlib.h>
 #include <string.h>
@@ -375,6 +379,12 @@
       return 1;
     }
 
+#ifdef LOG_FILE
+  if (getenv ("PKG_CONFIG_LOG_FILE"))
+      open_log_file (getenv ("PKG_CONFIG_LOG_FILE"));
+  else
+      debug_spew ("PKG_CONFIG_LOG_FILE is not set\n");
+#endif
 
   /* Error printing is determined as follows:
    *     - for --cflags, --libs, etc. it's on by default
@@ -423,15 +433,32 @@
   if (want_my_version)
     {
       printf ("%s\n", VERSION);
+#ifdef LOG_FILE
+      close_log_file ();
+#endif
       return 0;
     }
 
   if (required_pkgconfig_version)
     {
       if (compare_versions (VERSION, required_pkgconfig_version) >= 0)
-        return 0;
+        {
+#ifdef LOG_FILE
+          write_to_log_file ("pkg-config >= %s\n",
+                             required_pkgconfig_version);
+          close_log_file ();
+#endif
+          return 0;
+        }
       else
-        return 1;
+        {
+#ifdef LOG_FILE
+          write_to_log_file ("! pkg-config >= %s\n",
+                             required_pkgconfig_version);
+          close_log_file ();
+#endif
+          return 1;
+        }
     }
 
   package_init ();
@@ -439,6 +466,9 @@
   if (want_list)
     {
       print_package_list ();
+#ifdef LOG_FILE
+      close_log_file ();
+#endif
       return 0;
     }
 
@@ -481,8 +511,18 @@
           {
             failed = TRUE;
             verbose_error ("No package '%s' found\n", ver->name);
+#ifdef LOG_FILE
+            write_to_log_file ("! %s\n", ver->name);
+#endif
             goto nextiter;
           }
+#ifdef LOG_FILE
+        else
+          {
+            req->req = ver;
+            write_to_log_file ("%s\n", ver->name);
+          }
+#endif
 
         if (!version_test (ver->comparison, req->version, ver->version))
           {
@@ -498,8 +538,23 @@
 	      verbose_error ("You may find new versions of %s at %s\n",
 			     req->name, req->url);
 
+#ifdef LOG_FILE
+            write_to_log_file ("! %s %s %s\n",
+                               ver->name,
+                               comparison_to_str (ver->comparison),
+                               ver->version);
+#endif
             goto nextiter;
           }
+#ifdef LOG_FILE
+        else if (ver->version)
+          {
+            write_to_log_file ("%s %s %s\n",
+                               ver->name,
+                               comparison_to_str (ver->comparison),
+                               ver->version);
+          }
+#endif
 
         packages = g_slist_prepend (packages, req);
 
@@ -507,9 +562,13 @@
         iter = g_slist_next (iter);
       }
 
-    if (failed) {
-      return 1;
-    }
+    if (failed)
+      {
+#ifdef LOG_FILE
+        close_log_file ();
+#endif
+        return 1;
+      }
 
   }
 
@@ -520,12 +579,19 @@
   if (packages == NULL)
     {
       fprintf (stderr, "Must specify package names on the command line\n");
-
+#ifdef LOG_FILE
+      close_log_file ();
+#endif
       exit (1);
     }
 
   if (want_exists)
-    return 0; /* if we got here, all the packages existed. */
+    {
+#ifdef LOG_FILE
+      close_log_file ();
+#endif
+      return 0; /* if we got here, all the packages existed. */
+    }
 
   if (want_uninstalled)
     {
@@ -537,11 +603,24 @@
           Package *pkg = tmp->data;
 
           if (pkg_uninstalled (pkg))
-            return 0;
+            {
+#ifdef LOG_FILE
+              write_to_log_file ("%s U\n", pkg->req->name);
+              close_log_file ();
+#endif
+              return 0;
+            }
+#ifdef LOG_FILE
+          else
+            write_to_log_file ("! %s U\n", pkg->req->name);
+#endif
 
           tmp = g_slist_next (tmp);
         }
 
+#ifdef LOG_FILE
+      close_log_file ();
+#endif
       return 1;
     }
 
@@ -564,27 +643,75 @@
       Package *pkg = packages->data;
 
       if (compare_versions (pkg->version, required_exact_version) == 0)
-        return 0;
+        {
+#ifdef LOG_FILE
+          write_to_log_file ("%s = %s\n",
+                             pkg->req->name,
+                             required_exact_version);
+          close_log_file ();
+#endif
+          return 0;
+        }
       else
-        return 1;
+        {
+#ifdef LOG_FILE
+          write_to_log_file ("! %s = %s\n",
+                             pkg->req->name,
+                             required_exact_version);
+          close_log_file ();
+#endif
+          return 1;
+        }
     }
   else if (required_atleast_version)
     {
       Package *pkg = packages->data;
 
       if (compare_versions (pkg->version, required_atleast_version) >= 0)
-        return 0;
+        {
+#ifdef LOG_FILE
+          write_to_log_file ("%s >= %s\n",
+                             pkg->req->name,
+                             required_atleast_version);
+          close_log_file ();
+#endif
+          return 0;
+        }
       else
-        return 1;
+        {
+#ifdef LOG_FILE
+          write_to_log_file ("! %s >= %s\n",
+                             pkg->req->name,
+                             required_atleast_version);
+          close_log_file ();
+#endif
+          return 1;
+        }
     }
   else if (required_max_version)
     {
       Package *pkg = packages->data;
 
       if (compare_versions (pkg->version, required_max_version) <= 0)
-        return 0;
+        {
+#ifdef LOG_FILE
+          write_to_log_file ("%s <= %s\n",
+                             pkg->req->name,
+                             required_max_version);
+          close_log_file ();
+#endif
+          return 0;
+        }
       else
-        return 1;
+        {
+#ifdef LOG_FILE
+          write_to_log_file ("! %s <= %s\n",
+                             pkg->req->name,
+                             required_max_version);
+          close_log_file ();
+#endif
+          return 1;
+        }
     }
 
   /* Print all flags; then print a newline at the end. */
@@ -652,5 +779,8 @@
   if (need_newline)
     printf ("\n");
 
+#ifdef LOG_FILE
+  close_log_file ();
+#endif
   return 0;
 }

=== modified file 'pkg.h'
--- pkg.h	2005-10-16 17:31:41 +0000
+++ pkg.h	2007-11-14 11:20:57 +0000
@@ -75,6 +75,9 @@
   int path_position; /* used to order packages by position in path of 
their .pc file, lower number means earlier in path */
   int libs_num; /* Number of times the "Libs" header has been seen */
   int libs_private_num;  /* Number of times the "Libs.private" header has 
been seen */
+#ifdef LOG_FILE
+  RequiredVersion *req;  /* Pointer to package's required version data */
+#endif
 };
 
 Package *get_package               (const char *name);



More information about the pkg-config mailing list