]> git.ipfire.org Git - thirdparty/elfutils.git/commitdiff
Add support for printing SDT elf notes.
authorMark Wielaard <mjw@redhat.com>
Sun, 24 Apr 2011 15:53:38 +0000 (17:53 +0200)
committerMark Wielaard <mjw@redhat.com>
Tue, 26 Apr 2011 12:15:27 +0000 (14:15 +0200)
libebl/
    * libebl.h (ebl_object_note_type_name): Add const char *name arg.
    * eblhooks.h (object_note_type_name): Likewise.
    * eblopenbackend.c (default_object_note_type_name): Likewise.
    * eblobjnotetypename.c (ebl_object_note_type_name): Likewise.
    And print version if name is "stapsdt".
    * eblobjnote.c (ebl_object_note): Add output for "stapsdt" notes.
src/
    * readelf.c (handle_notes_data): Call ebl_object_note_type_name
    with note name.

libebl/ChangeLog
libebl/ebl-hooks.h
libebl/eblobjnote.c
libebl/eblobjnotetypename.c
libebl/eblopenbackend.c
libebl/libebl.h
src/ChangeLog
src/readelf.c

index 97315f0084af7f27c3e4acac4b4d5f3f9b37d20c..ac2160de95ff6ef8b9f57f65b50fdffd96362334 100644 (file)
@@ -1,3 +1,12 @@
+2011-04-26  Mark Wielaard  <mjw@redhat.com>
+
+       * libebl.h (ebl_object_note_type_name): Add const char *name arg.
+       * eblhooks.h (object_note_type_name): Likewise.
+       * eblopenbackend.c (default_object_note_type_name): Likewise.
+       * eblobjnotetypename.c (ebl_object_note_type_name): Likewise.
+       And print version if name is "stapsdt".
+       * eblobjnote.c (ebl_object_note): Add output for "stapsdt" notes.
+
 2011-03-21  Marek Polacek  <mpolacek@redhat.com>
 
        * ebldynamictagname.c: Fix typo in TLSDESC_GOT.
index 82c6c6400e19c1e900debebbb94b5cf6619d46e6..a04b3db01db534f7e90b56462bfe41eabaae98f2 100644 (file)
@@ -111,7 +111,8 @@ const char *EBLHOOK(osabi_name) (int, char *, size_t);
 const char *EBLHOOK(core_note_type_name) (uint32_t, char *, size_t);
 
 /* Name of a note entry type for object files.  */
-const char *EBLHOOK(object_note_type_name) (uint32_t, char *, size_t);
+const char *EBLHOOK(object_note_type_name) (const char *, uint32_t,
+                                           char *, size_t);
 
 /* Describe core note format.  */
 int EBLHOOK(core_note) (const GElf_Nhdr *, const char *,
index b56c6cbc0e5ea8cf345bfb63de22e24e2f2e5eb5..ec5bb7daff587d5123a1d3f5e6030e4c6d9c2a30 100644 (file)
@@ -1,5 +1,5 @@
 /* Print contents of object file note.
-   Copyright (C) 2002, 2007, 2009 Red Hat, Inc.
+   Copyright (C) 2002, 2007, 2009, 2011 Red Hat, Inc.
    This file is part of Red Hat elfutils.
    Written by Ulrich Drepper <drepper@redhat.com>, 2002.
 
@@ -68,6 +68,94 @@ ebl_object_note (ebl, name, type, descsz, desc)
 {
   if (! ebl->object_note (name, type, descsz, desc))
     /* The machine specific function did not know this type.  */
+
+    if (strcmp ("stapsdt", name) == 0)
+      {
+       if (type != 3)
+         {
+           printf (gettext ("unknown SDT version %u\n"), type);
+           return;
+         }
+
+       /* Descriptor starts with three addresses, pc, base ref and
+          semaphore.  Then three zero terminated strings provider,
+          name and arguments.  */
+
+       union
+       {
+         Elf64_Addr a64[3];
+         Elf32_Addr a32[3];
+       } addrs;
+
+       size_t addrs_size = gelf_fsize (ebl->elf, ELF_T_ADDR, 3, EV_CURRENT);
+       if (descsz < addrs_size + 3)
+         {
+         invalid_sdt:
+           printf (gettext ("invalid SDT probe descriptor\n"));
+           return;
+         }
+
+       Elf_Data src =
+         {
+           .d_type = ELF_T_ADDR, .d_version = EV_CURRENT,
+           .d_buf = (void *) desc, .d_size = addrs_size
+         };
+
+       Elf_Data dst =
+         {
+           .d_type = ELF_T_ADDR, .d_version = EV_CURRENT,
+           .d_buf = &addrs, .d_size = addrs_size
+         };
+
+       if (gelf_xlatetom (ebl->elf, &dst, &src,
+                          elf_getident (ebl->elf, NULL)[EI_DATA]) == NULL)
+         {
+           printf ("%s\n", elf_errmsg (-1));
+           return;
+         }
+
+       const char *provider = desc + addrs_size;
+       const char *pname = memchr (provider, '\0', desc + descsz - provider);
+       if (pname == NULL)
+         goto invalid_sdt;
+
+       ++pname;
+       const char *args = memchr (pname, '\0', desc + descsz - pname);
+       if (args == NULL ||
+           memchr (++args, '\0', desc + descsz - pname) != desc + descsz - 1)
+         goto invalid_sdt;
+
+       GElf_Addr pc;
+       GElf_Addr base;
+       GElf_Addr sem;
+       if (gelf_getclass (ebl->elf) == ELFCLASS32)
+         {
+           pc = addrs.a32[0];
+           base = addrs.a32[1];
+           sem = addrs.a32[2];
+         }
+       else
+         {
+           pc = addrs.a64[0];
+           base = addrs.a64[1];
+           sem = addrs.a64[2];
+         }
+
+       printf (gettext ("    PC: "));
+       printf ("%#" PRIx64 ",", pc);
+       printf (gettext (" Base: "));
+       printf ("%#" PRIx64 ",", base);
+       printf (gettext (" Semaphore: "));
+       printf ("%#" PRIx64 "\n", sem);
+       printf (gettext ("    Provider: "));
+       printf ("%s,", provider);
+       printf (gettext (" Name: "));
+       printf ("%s,", pname);
+       printf (gettext (" Args: "));
+       printf ("'%s'\n", args);
+       return;
+      }
+
     switch (type)
       {
       case NT_GNU_BUILD_ID:
index 8e99dbb41b4f5d3977a4a60d4970764d097bfee5..0ceb5a87ad0ccfd209bef34b0de65704c64ba500 100644 (file)
@@ -1,5 +1,5 @@
 /* Return note type name.
-   Copyright (C) 2002, 2007, 2009 Red Hat, Inc.
+   Copyright (C) 2002, 2007, 2009, 2011 Red Hat, Inc.
    This file is part of Red Hat elfutils.
    Written by Ulrich Drepper <drepper@redhat.com>, 2002.
 
 
 #include <inttypes.h>
 #include <stdio.h>
+#include <string.h>
 #include <libeblP.h>
 
 
 const char *
-ebl_object_note_type_name (ebl, type, buf, len)
+ebl_object_note_type_name (ebl, name, type, buf, len)
      Ebl *ebl;
+     const char *name;
      uint32_t type;
      char *buf;
      size_t len;
 {
-  const char *res = ebl->object_note_type_name (type, buf, len);
+  const char *res = ebl->object_note_type_name (name, type, buf, len);
 
   if (res == NULL)
     {
+      if (strcmp (name, "stapsdt") == 0)
+       {
+         snprintf (buf, len, "Version: %" PRIu32, type);
+         return buf;
+       }
+
       static const char *knowntypes[] =
        {
 #define KNOWNSTYPE(name) [NT_##name] = #name
index 24f472ce34941571864af8b5da584eb44cc8a3d6..60e7f84a5406d280f92f1fc5f5fa042061fd9b66 100644 (file)
@@ -184,8 +184,8 @@ static const char *default_osabi_name (int ignore, char *buf, size_t len);
 static void default_destr (struct ebl *ignore);
 static const char *default_core_note_type_name (uint32_t, char *buf,
                                                size_t len);
-static const char *default_object_note_type_name (uint32_t, char *buf,
-                                                 size_t len);
+static const char *default_object_note_type_name (const char *name, uint32_t,
+                                                 char *buf, size_t len);
 static int default_core_note (const GElf_Nhdr *nhdr, const char *name,
                              GElf_Word *regs_offset, size_t *nregloc,
                              const Ebl_Register_Location **reglocs,
@@ -619,7 +619,8 @@ default_core_note (const GElf_Nhdr *nhdr __attribute__ ((unused)),
 }
 
 static const char *
-default_object_note_type_name (uint32_t ignore __attribute__ ((unused)),
+default_object_note_type_name (const char *name __attribute__ ((unused)),
+                              uint32_t ignore __attribute__ ((unused)),
                               char *buf __attribute__ ((unused)),
                               size_t len __attribute__ ((unused)))
 {
index b4307282db51ae49a5bb5928ea652182fb8c1b2c..3a33402424e2e289a28a38f97c8b197fd862870f 100644 (file)
@@ -184,8 +184,9 @@ extern const char *ebl_core_note_type_name (Ebl *ebl, uint32_t type, char *buf,
                                            size_t len);
 
 /* Return name of the note section type for an object file.  */
-extern const char *ebl_object_note_type_name (Ebl *ebl, uint32_t type,
-                                             char *buf, size_t len);
+extern const char *ebl_object_note_type_name (Ebl *ebl, const char *name,
+                                             uint32_t type, char *buf,
+                                             size_t len);
 
 /* Print information about object note if available.  */
 extern void ebl_object_note (Ebl *ebl, const char *name, uint32_t type,
index 956cce2a5b37b93338b7a43bc9634747ae3972ae..290bf1296387b9fd80babade4772b5274e96efcb 100644 (file)
@@ -1,3 +1,8 @@
+2011-04-26  Mark Wielaard  <mjw@redhat.com>
+
+       * readelf.c (handle_notes_data): Call ebl_object_note_type_name
+       with note name.
+
 2011-03-24  Petr Machata  <pmachata@redhat.com>
 
        * readelf.c (print_debug_line_section): Emit initial space for all
index f2c48007f3538a1d5827050fc8868588f0dbdb22..efc3571c533ff667f52aefba853b8404c9c20d8d 100644 (file)
@@ -7904,7 +7904,7 @@ handle_notes_data (Ebl *ebl, const GElf_Ehdr *ehdr,
              ehdr->e_type == ET_CORE
              ? ebl_core_note_type_name (ebl, nhdr.n_type,
                                         buf, sizeof (buf))
-             : ebl_object_note_type_name (ebl, nhdr.n_type,
+             : ebl_object_note_type_name (ebl, name, nhdr.n_type,
                                           buf2, sizeof (buf2)));
 
       /* Filter out invalid entries.  */