This is the mail archive of the elfutils-devel@sourceware.org mailing list for the elfutils project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

Re: [PATCH] Add --core-pattern option to eu-stack


On Thu, 2014-10-30 at 22:55 +0100, Mark Wielaard wrote:
> I did have to lookup how to use this though. And I couldn't make it work
> without adding an -o option to eu-stack to explicitly redirect output
> since it seems you cannot use normal shell redirections
> in /proc/sys/kernel/core_pattern. So I had to use something like
> --output=/proc/%p/cwd/%i.stack. Where does the stdout of the
> core_pattern end up otherwise?

For reference. Attached is the cleaned up -o support patch I added.
It is a little paranoid setting umask and using O_EXCL explicitly.
But I think that is correct behavior when used in cases where normal
shell redirection doesn't work.

Cheers,

Mark
From 6e06c911e1d2a0f9cbd07a6bcaa6f76d6d7648b4 Mon Sep 17 00:00:00 2001
From: Mark Wielaard <mjw@redhat.com>
Date: Mon, 3 Nov 2014 14:16:57 +0100
Subject: [PATCH] stack: Add --output, -o option.

-o, --output=FILE Place output into FILE. FILE should not yet exists and
                  will be created.

Signed-off-by: Mark Wielaard <mjw@redhat.com>
---
 src/ChangeLog | 10 ++++++++++
 src/stack.c   | 56 ++++++++++++++++++++++++++++++++++++--------------------
 2 files changed, 46 insertions(+), 20 deletions(-)

diff --git a/src/ChangeLog b/src/ChangeLog
index a252cdc..70d6325 100644
--- a/src/ChangeLog
+++ b/src/ChangeLog
@@ -1,3 +1,13 @@
+2014-19-03  Mark Wielaard  <mjw@redhat.com>
+
+	* stack.c (fout): New static variable.
+	(module_callback): fprintf to fout.
+	(print_frame): Likewise.
+	(print_frames): Likewise.
+	(parse_opt): Handle 'o'.
+	(main): Add --output, -o to options. Set fout to stdout.
+	fprintf to fout.
+
 2014-09-14  Petr Machata  <pmachata@redhat.com>
 
 	* readelf.c (handle_relocs_rela): Typo fix, test DESTSHDR properly.
diff --git a/src/stack.c b/src/stack.c
index c277dfd..0b1d235 100644
--- a/src/stack.c
+++ b/src/stack.c
@@ -26,6 +26,8 @@
 #include <string.h>
 #include <locale.h>
 #include <fcntl.h>
+#include <sys/stat.h>
+#include <sys/types.h>
 #include ELFUTILS_HEADER(dwfl)
 
 #include <dwarf.h>
@@ -97,6 +99,9 @@ static char *demangle_buffer = NULL;
 /* Whether any frames have been shown at all.  Determines exit status.  */
 static bool frames_shown = false;
 
+/* Where --output/-o goes to (stdout by default).  */
+static FILE *fout;
+
 /* Program exit codes. All frames shown without any errors is GOOD.
    Some frames shown with some non-fatal errors is an ERROR.  A fatal
    error or no frames shown at all is BAD.  A command line USAGE exit
@@ -147,7 +152,7 @@ module_callback (Dwfl_Module *mod, void **userdata __attribute__((unused)),
   assert (strcmp (modname, name) == 0);
 
   int width = get_addr_width (mod);
-  printf ("0x%0*" PRIx64 "-0x%0*" PRIx64 " %s\n",
+  fprintf (fout, "0x%0*" PRIx64 "-0x%0*" PRIx64 " %s\n",
 	  width, start, width, end, basename (name));
 
   const unsigned char *id;
@@ -155,17 +160,17 @@ module_callback (Dwfl_Module *mod, void **userdata __attribute__((unused)),
   int id_len = dwfl_module_build_id (mod, &id, &id_vaddr);
   if (id_len > 0)
     {
-      printf ("  [");
+      fprintf (fout, "  [");
       do
-	printf ("%02" PRIx8, *id++);
+	fprintf (fout, "%02" PRIx8, *id++);
       while (--id_len > 0);
-      printf ("]\n");
+      fprintf (fout, "]\n");
     }
 
   if (elf != NULL)
-    printf ("  %s\n", mainfile != NULL ? mainfile : "-");
+    fprintf (fout, "  %s\n", mainfile != NULL ? mainfile : "-");
   if (dwarf != NULL)
-    printf ("  %s\n", debugfile != NULL ? debugfile : "-");
+    fprintf (fout, "  %s\n", debugfile != NULL ? debugfile : "-");
 
   return DWARF_CB_OK;
 }
@@ -219,10 +224,10 @@ print_frame (int nr, Dwarf_Addr pc, bool isactivation,
 	     Dwarf_Die *die)
 {
   int width = get_addr_width (mod);
-  printf ("#%-2u 0x%0*" PRIx64, nr, width, (uint64_t) pc);
+  fprintf (fout, "#%-2u 0x%0*" PRIx64, nr, width, (uint64_t) pc);
 
   if (show_activation)
-    printf ("%4s", ! isactivation ? "- 1" : "");
+    fprintf (fout, "%4s", ! isactivation ? "- 1" : "");
 
   if (symname != NULL)
     {
@@ -237,7 +242,7 @@ print_frame (int nr, Dwarf_Addr pc, bool isactivation,
 	    symname = demangle_buffer = dsymname;
 	}
 #endif
-      printf (" %s", symname);
+      fprintf (fout, " %s", symname);
     }
 
   const char* fname;
@@ -247,7 +252,7 @@ print_frame (int nr, Dwarf_Addr pc, bool isactivation,
   if (show_module)
     {
       if (fname != NULL)
-	printf (" - %s", fname);
+	fprintf (fout, " - %s", fname);
     }
 
   if (show_build_id)
@@ -257,11 +262,11 @@ print_frame (int nr, Dwarf_Addr pc, bool isactivation,
       int id_len = dwfl_module_build_id (mod, &id, &id_vaddr);
       if (id_len > 0)
 	{
-	  printf ("\n    [");
+	  fprintf (fout, "\n    [");
 	  do
-	    printf ("%02" PRIx8, *id++);
+	    fprintf (fout, "%02" PRIx8, *id++);
 	  while (--id_len > 0);
-	  printf ("]@0x%0" PRIx64 "+0x%" PRIx64,
+	  fprintf (fout, "]@0x%0" PRIx64 "+0x%" PRIx64,
 		  start, pc_adjusted - start);
 	}
     }
@@ -303,16 +308,16 @@ print_frame (int nr, Dwarf_Addr pc, bool isactivation,
 
       if (sname != NULL)
 	{
-	  printf ("\n    %s", sname);
+	  fprintf (fout, "\n    %s", sname);
 	  if (line > 0)
 	    {
-	      printf (":%d", line);
+	      fprintf (fout, ":%d", line);
 	      if (col > 0)
-		printf (":%d", col);
+		fprintf (fout, ":%d", col);
 	    }
 	}
     }
-  printf ("\n");
+  fprintf (fout, "\n");
 }
 
 static void
@@ -362,7 +367,7 @@ print_frames (struct frames *frames, pid_t tid, int dwflerr, const char *what)
   if (frames->frames > 0)
     frames_shown = true;
 
-  printf ("TID %d:\n", tid);
+  fprintf (fout, "TID %d:\n", tid);
   int frame_nr = 0;
   for (int nr = 0; nr < frames->frames && (maxframes == 0
 					   || frame_nr < maxframes); nr++)
@@ -560,6 +565,14 @@ parse_opt (int key, char *arg __attribute__ ((unused)),
       show_modules = true;
       break;
 
+    case 'o':
+      umask (S_IWGRP | S_IWOTH);
+      fout = fopen (arg, "wx");
+      if (fout == NULL)
+	error (EXIT_BAD, errno,
+	       N_("Cannot create and exclusively open output file '%s'"), arg);
+      break;
+
     case ARGP_KEY_END:
       if (core == NULL && exec != NULL)
 	argp_error (state,
@@ -658,6 +671,8 @@ main (int argc, char **argv)
 	N_("Additionally show inlined function frames using DWARF debuginfo if available (implies -d)"), 0 },
       { "module",  'm', NULL, 0,
 	N_("Additionally show module file information"), 0 },
+      { "output",  'o', "FILE", 0,
+	N_("Place output into FILE. FILE should not yet exists and will be created."), 0 },
       { "source",  's', NULL, 0,
 	N_("Additionally show source file information"), 0 },
       { "verbose", 'v', NULL, 0,
@@ -690,11 +705,12 @@ occured the program exits with return code 2.  If the program was \
 invoked with bad or missing arguments it will exit with return code 64.")
     };
 
+  fout = stdout;
   argp_parse (&argp, argc, argv, 0, NULL, NULL);
 
   if (show_modules)
     {
-      printf ("PID %d - %s module memory map\n", dwfl_pid (dwfl),
+      fprintf (fout, "PID %d - %s module memory map\n", dwfl_pid (dwfl),
 	      pid != 0 ? "process" : "core");
       if (dwfl_getmodules (dwfl, module_callback, NULL, 0) != 0)
 	error (EXIT_BAD, 0, "dwfl_getmodules: %s", dwfl_errmsg (-1));
@@ -727,7 +743,7 @@ invoked with bad or missing arguments it will exit with return code 64.")
     }
   else
     {
-      printf ("PID %d - %s\n", dwfl_pid (dwfl), pid != 0 ? "process" : "core");
+      fprintf (fout, "PID %d - %s\n", dwfl_pid (dwfl), pid != 0 ? "process" : "core");
       switch (dwfl_getthreads (dwfl, thread_callback, &frames))
 	{
 	case DWARF_CB_OK:
-- 
1.8.3.1


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]