* [PATCH/RFC 01/02 v2] Refactor PRPSINFO handling on Binutils @ 2012-12-17 3:10 Sergio Durigan Junior 2012-12-17 15:43 ` H.J. Lu 2012-12-18 17:38 ` Jan Kratochvil 0 siblings, 2 replies; 21+ messages in thread From: Sergio Durigan Junior @ 2012-12-17 3:10 UTC (permalink / raw) To: Binutils Development; +Cc: GDB Patches, Pedro Alves, H.J. Lu Hi, This is a follow-up on: <http://sourceware.org/ml/binutils/2012-11/msg00240.html> Sorry for the delay on this. I addressed Pedro's and H.J.'s comments, and took some time to test the patch on different architectures. It also took me some time to decide the best way to handle several little issues that I was facing: different declarations for PPC needed, different declarations for PRPSINFO structures, etc. Anyway, I hope I managed to solve these problems, but I would really appreciate some comments (if you have, of course) about the code. The idea was to simplify the handling of PRPSINFO, so: 1) I created elf_{internal,external}_prpsinfo* structures, organized differently according to their purposes. 2) I created the new PRPSINFO*_COPY_FIELDS macros, which take care of (duh) copying the fields from the internal to the external structures, obeying bitness and such. 3) I also took the liberty to implement the i386 version of the *_write_core_note. 4) I removed some dependency on the CORE_HEADER macro (suggested by Pedro). Not sure if everything is correct, though. Anyway, I guess those are the main changes. Please let me know if you have some question about the patch. Thanks. -- Sergio 2012-12-17 Sergio Durigan Junior <sergiodj@redhat.com> * Makefile.in (BUILD_CFILES): Add `elf-psinfo.h'. * elf-bfd.h (elf_internal_prpsinfo): Forward declaration for structure. (elfcore_write_prpsinfo): Change prototype, accepting `elf_internal_prpsinfo' as argument. * elf-psinfo.h: New file. * elf.c: Include `elf-psinfo.h'. (elfcore_psinfo_t, elfcore_psinfo32_t): Remove declarations. (elfcore_grok_psinfo): Refactor the #ifdef's to not consider `HAVE_PRPSINFO*' defines. (elfcore_write_prpsinfo): Change prototype, accepting `elf_internal_prpsinfo' as argument. Rewrite parts of the code to make use of the new argument. * elf32-arm.c: Include `elf-psinfo.h'. (elf32_arm_nabi_write_core_note): Refactor `NT_PRPSINFO' case. * elf32-i386.c: Include `elf-bfd.h', `elf-psinfo.h' and `stdarg.h'. Include `CORE_HEADER' if defined. (elf_i386_write_core_note): New function. * elf32-ppc.c: Include `elf-psinfo.h'. (ppc_elf_write_core_note): Refactor `NT_PRPSINFO' case. * elf64-ppc.c: Include `elf-psinfo.h'. (ppc64_elf_write_core_note): Refactor `NT_PRPSINFO' case. * elf64-x86-64.c: Include `elf-psinfo.h'. Include `stdarg.h' unconditionally. (elf_x86_64_write_core_note): Remove `#ifdef CORE_HEADER', making the function unconditionally available. Refactor `NT_PRPSINFO' case. * hosts/x86-64linux.h (HAVE_PRPSINFO32_T, HAVE_PRPSINFO32_T_PR_PID, elf_prpsinfo32, elf_prpsinfo64, prpsinfo32_t, prpsinfo64_t): Remove definitions, moving some of them to `elf-psinfo.h'. --- bfd/Makefile.in | 2 +- bfd/elf-bfd.h | 6 +- bfd/elf-psinfo.h | 215 +++++++++++++++++++++++++++++++++++++++++++++++ bfd/elf.c | 38 ++++----- bfd/elf32-arm.c | 13 ++- bfd/elf32-i386.c | 70 +++++++++++++++ bfd/elf32-ppc.c | 14 ++- bfd/elf64-ppc.c | 14 ++- bfd/elf64-x86-64.c | 36 ++++---- bfd/hosts/x86-64linux.h | 37 -------- 10 files changed, 353 insertions(+), 92 deletions(-) create mode 100644 bfd/elf-psinfo.h diff --git a/bfd/Makefile.in b/bfd/Makefile.in index 92d9d08..e12deb5 100644 --- a/bfd/Makefile.in +++ b/bfd/Makefile.in @@ -1050,7 +1050,7 @@ BUILD_CFILES = \ CFILES = $(SOURCE_CFILES) $(BUILD_CFILES) SOURCE_HFILES = \ aout-target.h aoutf1.h aoutx.h coffcode.h coffswap.h ecoffswap.h \ - elf-bfd.h elf-hppa.h elf32-hppa.h \ + elf-bfd.h elf-psinfo.h elf-hppa.h elf32-hppa.h \ elf64-hppa.h elfcode.h elfcore.h \ freebsd.h genlink.h go32stub.h \ libaout.h libbfd.h libcoff.h libecoff.h libhppa.h libieee.h \ diff --git a/bfd/elf-bfd.h b/bfd/elf-bfd.h index b8d82b1..d314291 100644 --- a/bfd/elf-bfd.h +++ b/bfd/elf-bfd.h @@ -2234,11 +2234,15 @@ extern bfd_boolean bfd_elf_lookup_section_flags extern Elf_Internal_Phdr * _bfd_elf_find_segment_containing_section (bfd * abfd, asection * section); +/* Forward declaration of prpsinfo. See `elf-psinfo.h' for more details. */ + +struct elf_internal_prpsinfo; + /* Exported interface for writing elf corefile notes. */ extern char *elfcore_write_note (bfd *, char *, int *, const char *, int, const void *, int); extern char *elfcore_write_prpsinfo - (bfd *, char *, int *, const char *, const char *); + (bfd *, char *, int *, const struct elf_internal_prpsinfo *); extern char *elfcore_write_prstatus (bfd *, char *, int *, long, int, const void *); extern char * elfcore_write_pstatus diff --git a/bfd/elf-psinfo.h b/bfd/elf-psinfo.h new file mode 100644 index 0000000..61b38e1 --- /dev/null +++ b/bfd/elf-psinfo.h @@ -0,0 +1,215 @@ +/* Declarations for PRPSINFO structures under ELF on GNU/Linux. + Copyright 2012 Free Software Foundation, Inc. + + This file is part of BFD, the Binary File Descriptor library. + + 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 3 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., 51 Franklin Street - Fifth Floor, Boston, + MA 02110-1301, USA. */ + +#undef HAVE_PRPSINFO32_T +#define HAVE_PRPSINFO32_T +#undef HAVE_PRPSINFO32_T_PR_PID +#define HAVE_PRPSINFO32_T_PR_PID + +/* Maximum size of the arguments that can be stored in a PRPSINFO + structure. */ + +#define ELF_PRARGSZ (80) + +/* Internal structure which holds information to be included in the + PRPSINFO section of the corefile. + + This is an "internal" structure in the sense that it should be used to + pass information to BFD (via the `elfcore_write_prpsinfo', for example), + so things like endianess shouldn't be an issue. This structure will + eventually be converted in one of the `elf_external_*' structures + below. */ + +struct elf_internal_prpsinfo + { + char pr_state; /* Numeric process state. */ + char pr_sname; /* Char for pr_state. */ + char pr_zomb; /* Zombie. */ + char pr_nice; /* Nice val. */ + unsigned long pr_flag; /* Flags. */ + unsigned int pr_uid; + unsigned int pr_gid; + int pr_pid, pr_ppid, pr_pgrp, pr_sid; + /* Lots missing */ + char pr_fname[16]; /* Filename of executable. */ + char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ + }; + +/* External 32-bit structure for PRPSINFO. This structure is ABI-defined, + thus we choose to use char arrays here in order to avoid dealing with + different types in different architectures. + + This structure will ultimately be written in the corefile's note section, + as the PRPSINFO. */ + +struct elf_external_prpsinfo32 + { + char pr_state; /* Numeric process state. */ + char pr_sname; /* Char for pr_state. */ + char pr_zomb; /* Zombie. */ + char pr_nice; /* Nice val. */ + char pr_flag[4]; /* Flags. */ + char pr_uid[2]; + char pr_gid[2]; + char pr_pid[4]; + char pr_ppid[4]; + char pr_pgrp[4]; + char pr_sid[4]; + /* Lots missing */ + char pr_fname[16]; /* Filename of executable. */ + char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ + }; + +/* External 32-bit PPC structure for PRPSINFO. This structure is ABI-defined, + thus we choose to use char arrays here in order to avoid dealing with + different types in different architectures. + + The reason why we have a different structure only for PPC is because + on this architecture (and *only* here!) the size of 32-bit structure + changes. This is due to the different sizes of `pr_uid' and `pr_gid', + which on non-PPC architectures are declared as `short int' and on PPC + architectures are declared as `int'. + + This structure will ultimately be written in the corefile's note section, + as the PRPSINFO. */ + +struct elf_external_ppc_prpsinfo32 + { + char pr_state; /* Numeric process state. */ + char pr_sname; /* Char for pr_state. */ + char pr_zomb; /* Zombie. */ + char pr_nice; /* Nice val. */ + char pr_flag[4]; /* Flags. */ + char pr_uid[4]; + char pr_gid[4]; + char pr_pid[4]; + char pr_ppid[4]; + char pr_pgrp[4]; + char pr_sid[4]; + /* Lots missing */ + char pr_fname[16]; /* Filename of executable. */ + char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ + }; + +/* Helper macro to copy (properly handling endianess) things from the + `elf_internal_prpsinfo' structure to the `elf_external_prpsinfo32' + structure. + + Note that FROM should be a pointer, and TO should be the explicit type. */ + +#define PRPSINFO32_COPY_FIELDS(abfd, from, to) \ + do \ + { \ + H_PUT_8 (abfd, from->pr_state, &to.pr_state); \ + H_PUT_8 (abfd, from->pr_sname, &to.pr_sname); \ + H_PUT_8 (abfd, from->pr_zomb, &to.pr_zomb); \ + H_PUT_8 (abfd, from->pr_nice, &to.pr_nice); \ + H_PUT_32 (abfd, from->pr_flag, to.pr_flag); \ + H_PUT_16 (abfd, from->pr_uid, to.pr_uid); \ + H_PUT_16 (abfd, from->pr_gid, to.pr_gid); \ + H_PUT_32 (abfd, from->pr_pid, to.pr_pid); \ + H_PUT_32 (abfd, from->pr_ppid, to.pr_ppid); \ + H_PUT_32 (abfd, from->pr_pgrp, to.pr_pgrp); \ + H_PUT_32 (abfd, from->pr_sid, to.pr_sid); \ + strncpy (to.pr_fname, from->pr_fname, sizeof (to.pr_fname)); \ + strncpy (to.pr_psargs, from->pr_psargs, sizeof (to.pr_psargs)); \ + } while (0) + +/* Helper macro to copy (properly handling endianess) things from the + `elf_internal_prpsinfo' structure to the `elf_external_ppc_prpsinfo32' + structure. + + Note that FROM should be a pointer, and TO should be the explicit type. */ + +#define PRPSINFO32_PPC_COPY_FIELDS(abfd, from, to) \ + do \ + { \ + H_PUT_8 (abfd, from->pr_state, &to.pr_state); \ + H_PUT_8 (abfd, from->pr_sname, &to.pr_sname); \ + H_PUT_8 (abfd, from->pr_zomb, &to.pr_zomb); \ + H_PUT_8 (abfd, from->pr_nice, &to.pr_nice); \ + H_PUT_32 (abfd, from->pr_flag, to.pr_flag); \ + H_PUT_32 (abfd, from->pr_uid, to.pr_uid); \ + H_PUT_32 (abfd, from->pr_gid, to.pr_gid); \ + H_PUT_32 (abfd, from->pr_pid, to.pr_pid); \ + H_PUT_32 (abfd, from->pr_ppid, to.pr_ppid); \ + H_PUT_32 (abfd, from->pr_pgrp, to.pr_pgrp); \ + H_PUT_32 (abfd, from->pr_sid, to.pr_sid); \ + strncpy (to.pr_fname, from->pr_fname, sizeof (to.pr_fname)); \ + strncpy (to.pr_psargs, from->pr_psargs, sizeof (to.pr_psargs)); \ + } while (0) + +/* External 64-bit structure for PRPSINFO. This structure is ABI-defined, + thus we choose to use char arrays here in order to avoid dealing with + different types in different architectures. + + Differently from the 32-bit version, the PowerPC guys made our lives better + and used the same size as the other architectures. + + This structure will ultimately be written in the corefile's note section, + as the PRPSINFO. */ + +struct elf_external_prpsinfo64 + { + char pr_state; /* Numeric process state. */ + char pr_sname; /* Char for pr_state. */ + char pr_zomb; /* Zombie. */ + char pr_nice; /* Nice val. */ + char pr_flag[8]; /* Flags. */ + char gap[4]; + char pr_uid[4]; + char pr_gid[4]; + char pr_pid[4]; + char pr_ppid[4]; + char pr_pgrp[4]; + char pr_sid[4]; + /* Lots missing */ + char pr_fname[16]; /* Filename of executable. */ + char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ + }; + +/* Helper macro to copy (properly handling endianess) things from the + `elf_internal_prpsinfo' structure to the `elf_external_prpsinfo64' + structure. + + Note that FROM should be a pointer, and TO should be the explicit type. */ + +#define PRPSINFO64_COPY_FIELDS(abfd, from, to) \ + do \ + { \ + H_PUT_8 (abfd, from->pr_state, &to.pr_state); \ + H_PUT_8 (abfd, from->pr_sname, &to.pr_sname); \ + H_PUT_8 (abfd, from->pr_zomb, &to.pr_zomb); \ + H_PUT_8 (abfd, from->pr_nice, &to.pr_nice); \ + H_PUT_64 (abfd, from->pr_flag, to.pr_flag); \ + H_PUT_32 (abfd, from->pr_uid, to.pr_uid); \ + H_PUT_32 (abfd, from->pr_gid, to.pr_gid); \ + H_PUT_32 (abfd, from->pr_pid, to.pr_pid); \ + H_PUT_32 (abfd, from->pr_ppid, to.pr_ppid); \ + H_PUT_32 (abfd, from->pr_pgrp, to.pr_pgrp); \ + H_PUT_32 (abfd, from->pr_sid, to.pr_sid); \ + strncpy (to.pr_fname, from->pr_fname, sizeof (to.pr_fname)); \ + strncpy (to.pr_psargs, from->pr_psargs, sizeof (to.pr_psargs)); \ + } while (0) + +/* Process info. In the end we do provide typedefs for them. */ + +typedef struct elf_external_prpsinfo32 prpsinfo32_t; +typedef struct elf_external_prpsinfo64 prpsinfo64_t; diff --git a/bfd/elf.c b/bfd/elf.c index a92dd5d..a39b88c 100644 --- a/bfd/elf.c +++ b/bfd/elf.c @@ -44,6 +44,7 @@ SECTION #include "elf-bfd.h" #include "libiberty.h" #include "safe-ctype.h" +#include "elf-psinfo.h" #ifdef CORE_HEADER #include CORE_HEADER @@ -8161,13 +8162,6 @@ elfcore_grok_arm_vfp (bfd *abfd, Elf_Internal_Note *note) return elfcore_make_note_pseudosection (abfd, ".reg-arm-vfp", note); } -#if defined (HAVE_PRPSINFO_T) -typedef prpsinfo_t elfcore_psinfo_t; -#if defined (HAVE_PRPSINFO32_T) /* Sparc64 cross Sparc32 */ -typedef prpsinfo32_t elfcore_psinfo32_t; -#endif -#endif - #if defined (HAVE_PSINFO_T) typedef psinfo_t elfcore_psinfo_t; #if defined (HAVE_PSINFO32_T) /* Sparc64 cross Sparc32 */ @@ -8201,17 +8195,17 @@ _bfd_elfcore_strndup (bfd *abfd, char *start, size_t max) return dups; } -#if defined (HAVE_PRPSINFO_T) || defined (HAVE_PSINFO_T) static bfd_boolean elfcore_grok_psinfo (bfd *abfd, Elf_Internal_Note *note) { +#if defined (HAVE_PSINFO_T) if (note->descsz == sizeof (elfcore_psinfo_t)) { elfcore_psinfo_t psinfo; memcpy (&psinfo, note->descdata, sizeof (psinfo)); -#if defined (HAVE_PSINFO_T_PR_PID) || defined (HAVE_PRPSINFO_T_PR_PID) +#if defined (HAVE_PSINFO_T_PR_PID) elf_tdata (abfd)->core_pid = psinfo.pr_pid; #endif elf_tdata (abfd)->core_program @@ -8222,7 +8216,7 @@ elfcore_grok_psinfo (bfd *abfd, Elf_Internal_Note *note) = _bfd_elfcore_strndup (abfd, psinfo.pr_psargs, sizeof (psinfo.pr_psargs)); } -#if defined (HAVE_PRPSINFO32_T) || defined (HAVE_PSINFO32_T) +#if defined (HAVE_PSINFO32_T) else if (note->descsz == sizeof (elfcore_psinfo32_t)) { /* 64-bit host, 32-bit corefile */ @@ -8230,7 +8224,7 @@ elfcore_grok_psinfo (bfd *abfd, Elf_Internal_Note *note) memcpy (&psinfo, note->descdata, sizeof (psinfo)); -#if defined (HAVE_PSINFO32_T_PR_PID) || defined (HAVE_PRPSINFO32_T_PR_PID) +#if defined (HAVE_PSINFO32_T_PR_PID) elf_tdata (abfd)->core_pid = psinfo.pr_pid; #endif elf_tdata (abfd)->core_program @@ -8261,10 +8255,14 @@ elfcore_grok_psinfo (bfd *abfd, Elf_Internal_Note *note) if (0 < n && command[n - 1] == ' ') command[n - 1] = '\0'; } +#else /* defined (HAVE_PSINFO_T) */ + /* Avoid compiler warning about "unused variables". */ + (void) abfd; + (void) note; return TRUE; +#endif } -#endif /* defined (HAVE_PRPSINFO_T) || defined (HAVE_PSINFO_T) */ #if defined (HAVE_PSTATUS_T) static bfd_boolean @@ -9062,16 +9060,16 @@ char * elfcore_write_prpsinfo (bfd *abfd, char *buf, int *bufsiz, - const char *fname, - const char *psargs) + const struct elf_internal_prpsinfo *input) { const struct elf_backend_data *bed = get_elf_backend_data (abfd); if (bed->elf_backend_write_core_note != NULL) { char *ret; + ret = (*bed->elf_backend_write_core_note) (abfd, buf, bufsiz, - NT_PRPSINFO, fname, psargs); + NT_PRPSINFO, input); if (ret != NULL) return ret; } @@ -9089,8 +9087,8 @@ elfcore_write_prpsinfo (bfd *abfd, #endif memset (&data, 0, sizeof (data)); - strncpy (data.pr_fname, fname, sizeof (data.pr_fname)); - strncpy (data.pr_psargs, psargs, sizeof (data.pr_psargs)); + strncpy (data.pr_fname, input->pr_fname, sizeof (data.pr_fname)); + strncpy (data.pr_psargs, input->pr_psargs, sizeof (data.pr_psargs)); return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, &data, sizeof (data)); } @@ -9101,13 +9099,13 @@ elfcore_write_prpsinfo (bfd *abfd, psinfo_t data; int note_type = NT_PSINFO; #else - prpsinfo_t data; + prpsinfo64_t data; int note_type = NT_PRPSINFO; #endif memset (&data, 0, sizeof (data)); - strncpy (data.pr_fname, fname, sizeof (data.pr_fname)); - strncpy (data.pr_psargs, psargs, sizeof (data.pr_psargs)); + strncpy (data.pr_fname, input->pr_fname, sizeof (data.pr_fname)); + strncpy (data.pr_psargs, input->pr_psargs, sizeof (data.pr_psargs)); return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, &data, sizeof (data)); } diff --git a/bfd/elf32-arm.c b/bfd/elf32-arm.c index fd7d26a..cacc895 100644 --- a/bfd/elf32-arm.c +++ b/bfd/elf32-arm.c @@ -30,6 +30,7 @@ #include "elf-nacl.h" #include "elf-vxworks.h" #include "elf/arm.h" +#include "elf-psinfo.h" /* Return the relocation section associated with NAME. HTAB is the bfd's elf32_arm_link_hash_entry. */ @@ -2004,17 +2005,19 @@ elf32_arm_nabi_write_core_note (bfd *abfd, char *buf, int *bufsiz, case NT_PRPSINFO: { - char data[124]; + const struct elf_internal_prpsinfo *prpsinfo; + struct elf_external_prpsinfo32 data; va_list ap; va_start (ap, note_type); - memset (data, 0, sizeof (data)); - strncpy (data + 28, va_arg (ap, const char *), 16); - strncpy (data + 44, va_arg (ap, const char *), 80); + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); va_end (ap); + memset (&data, 0, sizeof (data)); + PRPSINFO32_COPY_FIELDS (abfd, prpsinfo, data); + return elfcore_write_note (abfd, buf, bufsiz, - "CORE", note_type, data, sizeof (data)); + "CORE", note_type, &data, sizeof (data)); } case NT_PRSTATUS: diff --git a/bfd/elf32-i386.c b/bfd/elf32-i386.c index a188cec..5b81baa 100644 --- a/bfd/elf32-i386.c +++ b/bfd/elf32-i386.c @@ -31,12 +31,20 @@ #include "objalloc.h" #include "hashtab.h" #include "dwarf2.h" +#include "elf-bfd.h" +#include "elf-psinfo.h" + +#include <stdarg.h> /* 386 uses REL relocations instead of RELA. */ #define USE_REL 1 #include "elf/i386.h" +#ifdef CORE_HEADER +#include CORE_HEADER +#endif + static reloc_howto_type elf_howto_table[]= { HOWTO(R_386_NONE, 0, 0, 0, FALSE, 0, complain_overflow_bitfield, @@ -500,6 +508,67 @@ elf_i386_grok_psinfo (bfd *abfd, Elf_Internal_Note *note) return TRUE; } + +static char * +elf_i386_write_core_note (bfd *abfd, char *buf, int *bufsiz, + int note_type, ...) +{ + const struct elf_backend_data *bed = get_elf_backend_data (abfd); + va_list ap; + const struct elf_internal_prpsinfo *prpsinfo; + long pid; + int cursig; + const void *gregs; + struct elf_external_prpsinfo32 data; + + switch (note_type) + { + default: + return NULL; + + case NT_PRPSINFO: + va_start (ap, note_type); + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); + va_end (ap); + + memset (&data, 0, sizeof (data)); + PRPSINFO32_COPY_FIELDS (abfd, prpsinfo, data); + + return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, + &data, sizeof (data)); + /* NOTREACHED */ + + case NT_PRSTATUS: + va_start (ap, note_type); + pid = va_arg (ap, long); + cursig = va_arg (ap, int); + gregs = va_arg (ap, const void *); + va_end (ap); + + if (bed->elf_machine_code == EM_X86_64) + { + prstatusx32_t prstat; + memset (&prstat, 0, sizeof (prstat)); + prstat.pr_pid = pid; + prstat.pr_cursig = cursig; + memcpy (&prstat.pr_reg, gregs, sizeof (prstat.pr_reg)); + return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, + &prstat, sizeof (prstat)); + } + else + { + prstatus32_t prstat; + memset (&prstat, 0, sizeof (prstat)); + prstat.pr_pid = pid; + prstat.pr_cursig = cursig; + memcpy (&prstat.pr_reg, gregs, sizeof (prstat.pr_reg)); + return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, + &prstat, sizeof (prstat)); + } + } + /* NOTREACHED */ +} + \f /* Functions for the i386 ELF linker. @@ -5140,6 +5209,7 @@ elf_i386_add_symbol_hook (bfd * abfd, #define elf_backend_gc_sweep_hook elf_i386_gc_sweep_hook #define elf_backend_grok_prstatus elf_i386_grok_prstatus #define elf_backend_grok_psinfo elf_i386_grok_psinfo +#define elf_backend_write_core_note elf_i386_write_core_note #define elf_backend_reloc_type_class elf_i386_reloc_type_class #define elf_backend_relocate_section elf_i386_relocate_section #define elf_backend_size_dynamic_sections elf_i386_size_dynamic_sections diff --git a/bfd/elf32-ppc.c b/bfd/elf32-ppc.c index 5241926..2869663 100644 --- a/bfd/elf32-ppc.c +++ b/bfd/elf32-ppc.c @@ -37,6 +37,7 @@ #include "elf32-ppc.h" #include "elf-vxworks.h" #include "dwarf2.h" +#include "elf-psinfo.h" typedef enum split16_format_type { @@ -2222,16 +2223,19 @@ ppc_elf_write_core_note (bfd *abfd, char *buf, int *bufsiz, int note_type, ...) case NT_PRPSINFO: { - char data[128]; + const struct elf_internal_prpsinfo *prpsinfo; + struct elf_external_ppc_prpsinfo32 data; va_list ap; va_start (ap, note_type); - memset (data, 0, sizeof (data)); - strncpy (data + 32, va_arg (ap, const char *), 16); - strncpy (data + 48, va_arg (ap, const char *), 80); + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); va_end (ap); + + memset (&data, 0, sizeof (data)); + PRPSINFO32_PPC_COPY_FIELDS (abfd, prpsinfo, data); + return elfcore_write_note (abfd, buf, bufsiz, - "CORE", note_type, data, sizeof (data)); + "CORE", note_type, &data, sizeof (data)); } case NT_PRSTATUS: diff --git a/bfd/elf64-ppc.c b/bfd/elf64-ppc.c index 10b6f9d..4eda989 100644 --- a/bfd/elf64-ppc.c +++ b/bfd/elf64-ppc.c @@ -34,6 +34,7 @@ #include "elf-bfd.h" #include "elf/ppc64.h" #include "elf64-ppc.h" +#include "elf-psinfo.h" #include "dwarf2.h" static bfd_reloc_status_type ppc64_elf_ha_reloc @@ -2718,16 +2719,19 @@ ppc64_elf_write_core_note (bfd *abfd, char *buf, int *bufsiz, int note_type, case NT_PRPSINFO: { - char data[136]; + const struct elf_internal_prpsinfo *prpsinfo; + struct elf_external_prpsinfo64 data; va_list ap; va_start (ap, note_type); - memset (data, 0, sizeof (data)); - strncpy (data + 40, va_arg (ap, const char *), 16); - strncpy (data + 56, va_arg (ap, const char *), 80); + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); va_end (ap); + + memset (&data, 0, sizeof (data)); + PRPSINFO64_COPY_FIELDS (abfd, prpsinfo, data); + return elfcore_write_note (abfd, buf, bufsiz, - "CORE", note_type, data, sizeof (data)); + "CORE", note_type, &data, sizeof (data)); } case NT_PRSTATUS: diff --git a/bfd/elf64-x86-64.c b/bfd/elf64-x86-64.c index 283681c..2c9939d 100644 --- a/bfd/elf64-x86-64.c +++ b/bfd/elf64-x86-64.c @@ -32,11 +32,13 @@ #include "hashtab.h" #include "dwarf2.h" #include "libiberty.h" +#include "elf-psinfo.h" + +#include <stdarg.h> #include "elf/x86-64.h" #ifdef CORE_HEADER -#include <stdarg.h> #include CORE_HEADER #endif @@ -415,14 +417,13 @@ elf_x86_64_grok_psinfo (bfd *abfd, Elf_Internal_Note *note) return TRUE; } -#ifdef CORE_HEADER static char * elf_x86_64_write_core_note (bfd *abfd, char *buf, int *bufsiz, int note_type, ...) { const struct elf_backend_data *bed = get_elf_backend_data (abfd); va_list ap; - const char *fname, *psargs; + const struct elf_internal_prpsinfo *prpsinfo; long pid; int cursig; const void *gregs; @@ -434,27 +435,28 @@ elf_x86_64_write_core_note (bfd *abfd, char *buf, int *bufsiz, case NT_PRPSINFO: va_start (ap, note_type); - fname = va_arg (ap, const char *); - psargs = va_arg (ap, const char *); + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); va_end (ap); if (bed->s->elfclass == ELFCLASS32) { - prpsinfo32_t data; - memset (&data, 0, sizeof (data)); - strncpy (data.pr_fname, fname, sizeof (data.pr_fname)); - strncpy (data.pr_psargs, psargs, sizeof (data.pr_psargs)); + struct elf_external_prpsinfo32 data32; + + memset (&data32, 0, sizeof (data32)); + PRPSINFO32_COPY_FIELDS (abfd, prpsinfo, data32); + return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, - &data, sizeof (data)); + &data32, sizeof (data32)); } else { - prpsinfo64_t data; - memset (&data, 0, sizeof (data)); - strncpy (data.pr_fname, fname, sizeof (data.pr_fname)); - strncpy (data.pr_psargs, psargs, sizeof (data.pr_psargs)); + struct elf_external_prpsinfo64 data64; + + memset (&data64, 0, sizeof (data64)); + PRPSINFO64_COPY_FIELDS (abfd, prpsinfo, data64); + return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, - &data, sizeof (data)); + &data64, sizeof (data64)); } /* NOTREACHED */ @@ -501,7 +503,7 @@ elf_x86_64_write_core_note (bfd *abfd, char *buf, int *bufsiz, } /* NOTREACHED */ } -#endif + \f /* Functions for the x86-64 ELF linker. */ @@ -5225,9 +5227,7 @@ static const struct bfd_elf_special_section #define elf_backend_gc_sweep_hook elf_x86_64_gc_sweep_hook #define elf_backend_grok_prstatus elf_x86_64_grok_prstatus #define elf_backend_grok_psinfo elf_x86_64_grok_psinfo -#ifdef CORE_HEADER #define elf_backend_write_core_note elf_x86_64_write_core_note -#endif #define elf_backend_reloc_type_class elf_x86_64_reloc_type_class #define elf_backend_relocate_section elf_x86_64_relocate_section #define elf_backend_size_dynamic_sections elf_x86_64_size_dynamic_sections diff --git a/bfd/hosts/x86-64linux.h b/bfd/hosts/x86-64linux.h index 78be09a..6070978 100644 --- a/bfd/hosts/x86-64linux.h +++ b/bfd/hosts/x86-64linux.h @@ -43,11 +43,6 @@ typedef unsigned long long int uint64_t; /* Unsigned 64-bit integer aligned to 8 bytes. */ typedef uint64_t __attribute__ ((__aligned__ (8))) a8_uint64_t; -#undef HAVE_PRPSINFO32_T -#define HAVE_PRPSINFO32_T -#undef HAVE_PRPSINFO32_T_PR_PID -#define HAVE_PRPSINFO32_T_PR_PID - #undef HAVE_PRSTATUS32_T #define HAVE_PRSTATUS32_T @@ -191,36 +186,6 @@ struct elf_prstatus64 int pr_fpvalid; /* True if math copro being used. */ }; -struct elf_prpsinfo32 - { - char pr_state; /* Numeric process state. */ - char pr_sname; /* Char for pr_state. */ - char pr_zomb; /* Zombie. */ - char pr_nice; /* Nice val. */ - unsigned int pr_flag; /* Flags. */ - unsigned short int pr_uid; - unsigned short int pr_gid; - int pr_pid, pr_ppid, pr_pgrp, pr_sid; - /* Lots missing */ - char pr_fname[16]; /* Filename of executable. */ - char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ - }; - -struct elf_prpsinfo64 - { - char pr_state; /* Numeric process state. */ - char pr_sname; /* Char for pr_state. */ - char pr_zomb; /* Zombie. */ - char pr_nice; /* Nice val. */ - a8_uint64_t pr_flag; /* Flags. */ - unsigned int pr_uid; - unsigned int pr_gid; - int pr_pid, pr_ppid, pr_pgrp, pr_sid; - /* Lots missing */ - char pr_fname[16]; /* Filename of executable. */ - char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ - }; - /* The rest of this file provides the types for emulation of the Solaris <proc_service.h> interfaces that should be implemented by users of libthread_db. */ @@ -229,5 +194,3 @@ struct elf_prpsinfo64 typedef struct elf_prstatus32 prstatus32_t; typedef struct elf_prstatusx32 prstatusx32_t; typedef struct elf_prstatus64 prstatus64_t; -typedef struct elf_prpsinfo32 prpsinfo32_t; -typedef struct elf_prpsinfo64 prpsinfo64_t; -- 1.7.7.6 ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: [PATCH/RFC 01/02 v2] Refactor PRPSINFO handling on Binutils 2012-12-17 3:10 [PATCH/RFC 01/02 v2] Refactor PRPSINFO handling on Binutils Sergio Durigan Junior @ 2012-12-17 15:43 ` H.J. Lu 2012-12-17 17:41 ` Sergio Durigan Junior 2012-12-18 17:38 ` Jan Kratochvil 1 sibling, 1 reply; 21+ messages in thread From: H.J. Lu @ 2012-12-17 15:43 UTC (permalink / raw) To: Sergio Durigan Junior; +Cc: Binutils Development, GDB Patches, Pedro Alves On Sun, Dec 16, 2012 at 7:09 PM, Sergio Durigan Junior <sergiodj@redhat.com> wrote: > Hi, > > This is a follow-up on: > <http://sourceware.org/ml/binutils/2012-11/msg00240.html> > > Sorry for the delay on this. I addressed Pedro's and H.J.'s comments, > and took some time to test the patch on different architectures. > > It also took me some time to decide the best way to handle several > little issues that I was facing: different declarations for PPC needed, > different declarations for PRPSINFO structures, etc. > > Anyway, I hope I managed to solve these problems, but I would really > appreciate some comments (if you have, of course) about the code. The > idea was to simplify the handling of PRPSINFO, so: > > 1) I created elf_{internal,external}_prpsinfo* structures, organized > differently according to their purposes. > > 2) I created the new PRPSINFO*_COPY_FIELDS macros, which take care of > (duh) copying the fields from the internal to the external structures, > obeying bitness and such. > > 3) I also took the liberty to implement the i386 version of the > *_write_core_note. > > 4) I removed some dependency on the CORE_HEADER macro (suggested by > Pedro). Not sure if everything is correct, though. > > Anyway, I guess those are the main changes. Please let me know if you > have some question about the patch. Thanks. > > + > +static char * > +elf_i386_write_core_note (bfd *abfd, char *buf, int *bufsiz, > + int note_type, ...) > +{ > + const struct elf_backend_data *bed = get_elf_backend_data (abfd); > + va_list ap; > + const struct elf_internal_prpsinfo *prpsinfo; > + long pid; > + int cursig; > + const void *gregs; > + struct elf_external_prpsinfo32 data; > + > + switch (note_type) > + { > + default: > + return NULL; > + > + case NT_PRPSINFO: > + va_start (ap, note_type); > + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); > + va_end (ap); > + > + memset (&data, 0, sizeof (data)); > + PRPSINFO32_COPY_FIELDS (abfd, prpsinfo, data); > + > + return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, > + &data, sizeof (data)); > + /* NOTREACHED */ > + > + case NT_PRSTATUS: > + va_start (ap, note_type); > + pid = va_arg (ap, long); > + cursig = va_arg (ap, int); > + gregs = va_arg (ap, const void *); > + va_end (ap); > + > + if (bed->elf_machine_code == EM_X86_64) > + { > + prstatusx32_t prstat; > + memset (&prstat, 0, sizeof (prstat)); > + prstat.pr_pid = pid; > + prstat.pr_cursig = cursig; > + memcpy (&prstat.pr_reg, gregs, sizeof (prstat.pr_reg)); > + return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, > + &prstat, sizeof (prstat)); > + } > + else When will elf_i386_write_core_note be called for x32 process? -- H.J. ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: [PATCH/RFC 01/02 v2] Refactor PRPSINFO handling on Binutils 2012-12-17 15:43 ` H.J. Lu @ 2012-12-17 17:41 ` Sergio Durigan Junior 2012-12-17 17:44 ` H.J. Lu 0 siblings, 1 reply; 21+ messages in thread From: Sergio Durigan Junior @ 2012-12-17 17:41 UTC (permalink / raw) To: H.J. Lu; +Cc: Binutils Development, GDB Patches, Pedro Alves On Monday, December 17 2012, H. J. Lu wrote: > On Sun, Dec 16, 2012 at 7:09 PM, Sergio Durigan Junior > <sergiodj@redhat.com> wrote: >> + if (bed->elf_machine_code == EM_X86_64) >> + { >> + prstatusx32_t prstat; >> + memset (&prstat, 0, sizeof (prstat)); >> + prstat.pr_pid = pid; >> + prstat.pr_cursig = cursig; >> + memcpy (&prstat.pr_reg, gregs, sizeof (prstat.pr_reg)); >> + return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, >> + &prstat, sizeof (prstat)); >> + } >> + else > > When will elf_i386_write_core_note be called for > x32 process? Ops, sorry, that code sneaked in apparently. Here's the new version of the patch. -- Sergio --- bfd/Makefile.in | 2 +- bfd/elf-bfd.h | 6 +- bfd/elf-psinfo.h | 215 +++++++++++++++++++++++++++++++++++++++++++++++ bfd/elf.c | 38 ++++----- bfd/elf32-arm.c | 13 ++- bfd/elf32-i386.c | 62 ++++++++++++++ bfd/elf32-ppc.c | 14 ++- bfd/elf64-ppc.c | 14 ++- bfd/elf64-x86-64.c | 36 ++++---- bfd/hosts/x86-64linux.h | 37 -------- 10 files changed, 345 insertions(+), 92 deletions(-) create mode 100644 bfd/elf-psinfo.h diff --git a/bfd/Makefile.in b/bfd/Makefile.in index 92d9d08..e12deb5 100644 --- a/bfd/Makefile.in +++ b/bfd/Makefile.in @@ -1050,7 +1050,7 @@ BUILD_CFILES = \ CFILES = $(SOURCE_CFILES) $(BUILD_CFILES) SOURCE_HFILES = \ aout-target.h aoutf1.h aoutx.h coffcode.h coffswap.h ecoffswap.h \ - elf-bfd.h elf-hppa.h elf32-hppa.h \ + elf-bfd.h elf-psinfo.h elf-hppa.h elf32-hppa.h \ elf64-hppa.h elfcode.h elfcore.h \ freebsd.h genlink.h go32stub.h \ libaout.h libbfd.h libcoff.h libecoff.h libhppa.h libieee.h \ diff --git a/bfd/elf-bfd.h b/bfd/elf-bfd.h index b8d82b1..d314291 100644 --- a/bfd/elf-bfd.h +++ b/bfd/elf-bfd.h @@ -2234,11 +2234,15 @@ extern bfd_boolean bfd_elf_lookup_section_flags extern Elf_Internal_Phdr * _bfd_elf_find_segment_containing_section (bfd * abfd, asection * section); +/* Forward declaration of prpsinfo. See `elf-psinfo.h' for more details. */ + +struct elf_internal_prpsinfo; + /* Exported interface for writing elf corefile notes. */ extern char *elfcore_write_note (bfd *, char *, int *, const char *, int, const void *, int); extern char *elfcore_write_prpsinfo - (bfd *, char *, int *, const char *, const char *); + (bfd *, char *, int *, const struct elf_internal_prpsinfo *); extern char *elfcore_write_prstatus (bfd *, char *, int *, long, int, const void *); extern char * elfcore_write_pstatus diff --git a/bfd/elf-psinfo.h b/bfd/elf-psinfo.h new file mode 100644 index 0000000..61b38e1 --- /dev/null +++ b/bfd/elf-psinfo.h @@ -0,0 +1,215 @@ +/* Declarations for PRPSINFO structures under ELF on GNU/Linux. + Copyright 2012 Free Software Foundation, Inc. + + This file is part of BFD, the Binary File Descriptor library. + + 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 3 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., 51 Franklin Street - Fifth Floor, Boston, + MA 02110-1301, USA. */ + +#undef HAVE_PRPSINFO32_T +#define HAVE_PRPSINFO32_T +#undef HAVE_PRPSINFO32_T_PR_PID +#define HAVE_PRPSINFO32_T_PR_PID + +/* Maximum size of the arguments that can be stored in a PRPSINFO + structure. */ + +#define ELF_PRARGSZ (80) + +/* Internal structure which holds information to be included in the + PRPSINFO section of the corefile. + + This is an "internal" structure in the sense that it should be used to + pass information to BFD (via the `elfcore_write_prpsinfo', for example), + so things like endianess shouldn't be an issue. This structure will + eventually be converted in one of the `elf_external_*' structures + below. */ + +struct elf_internal_prpsinfo + { + char pr_state; /* Numeric process state. */ + char pr_sname; /* Char for pr_state. */ + char pr_zomb; /* Zombie. */ + char pr_nice; /* Nice val. */ + unsigned long pr_flag; /* Flags. */ + unsigned int pr_uid; + unsigned int pr_gid; + int pr_pid, pr_ppid, pr_pgrp, pr_sid; + /* Lots missing */ + char pr_fname[16]; /* Filename of executable. */ + char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ + }; + +/* External 32-bit structure for PRPSINFO. This structure is ABI-defined, + thus we choose to use char arrays here in order to avoid dealing with + different types in different architectures. + + This structure will ultimately be written in the corefile's note section, + as the PRPSINFO. */ + +struct elf_external_prpsinfo32 + { + char pr_state; /* Numeric process state. */ + char pr_sname; /* Char for pr_state. */ + char pr_zomb; /* Zombie. */ + char pr_nice; /* Nice val. */ + char pr_flag[4]; /* Flags. */ + char pr_uid[2]; + char pr_gid[2]; + char pr_pid[4]; + char pr_ppid[4]; + char pr_pgrp[4]; + char pr_sid[4]; + /* Lots missing */ + char pr_fname[16]; /* Filename of executable. */ + char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ + }; + +/* External 32-bit PPC structure for PRPSINFO. This structure is ABI-defined, + thus we choose to use char arrays here in order to avoid dealing with + different types in different architectures. + + The reason why we have a different structure only for PPC is because + on this architecture (and *only* here!) the size of 32-bit structure + changes. This is due to the different sizes of `pr_uid' and `pr_gid', + which on non-PPC architectures are declared as `short int' and on PPC + architectures are declared as `int'. + + This structure will ultimately be written in the corefile's note section, + as the PRPSINFO. */ + +struct elf_external_ppc_prpsinfo32 + { + char pr_state; /* Numeric process state. */ + char pr_sname; /* Char for pr_state. */ + char pr_zomb; /* Zombie. */ + char pr_nice; /* Nice val. */ + char pr_flag[4]; /* Flags. */ + char pr_uid[4]; + char pr_gid[4]; + char pr_pid[4]; + char pr_ppid[4]; + char pr_pgrp[4]; + char pr_sid[4]; + /* Lots missing */ + char pr_fname[16]; /* Filename of executable. */ + char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ + }; + +/* Helper macro to copy (properly handling endianess) things from the + `elf_internal_prpsinfo' structure to the `elf_external_prpsinfo32' + structure. + + Note that FROM should be a pointer, and TO should be the explicit type. */ + +#define PRPSINFO32_COPY_FIELDS(abfd, from, to) \ + do \ + { \ + H_PUT_8 (abfd, from->pr_state, &to.pr_state); \ + H_PUT_8 (abfd, from->pr_sname, &to.pr_sname); \ + H_PUT_8 (abfd, from->pr_zomb, &to.pr_zomb); \ + H_PUT_8 (abfd, from->pr_nice, &to.pr_nice); \ + H_PUT_32 (abfd, from->pr_flag, to.pr_flag); \ + H_PUT_16 (abfd, from->pr_uid, to.pr_uid); \ + H_PUT_16 (abfd, from->pr_gid, to.pr_gid); \ + H_PUT_32 (abfd, from->pr_pid, to.pr_pid); \ + H_PUT_32 (abfd, from->pr_ppid, to.pr_ppid); \ + H_PUT_32 (abfd, from->pr_pgrp, to.pr_pgrp); \ + H_PUT_32 (abfd, from->pr_sid, to.pr_sid); \ + strncpy (to.pr_fname, from->pr_fname, sizeof (to.pr_fname)); \ + strncpy (to.pr_psargs, from->pr_psargs, sizeof (to.pr_psargs)); \ + } while (0) + +/* Helper macro to copy (properly handling endianess) things from the + `elf_internal_prpsinfo' structure to the `elf_external_ppc_prpsinfo32' + structure. + + Note that FROM should be a pointer, and TO should be the explicit type. */ + +#define PRPSINFO32_PPC_COPY_FIELDS(abfd, from, to) \ + do \ + { \ + H_PUT_8 (abfd, from->pr_state, &to.pr_state); \ + H_PUT_8 (abfd, from->pr_sname, &to.pr_sname); \ + H_PUT_8 (abfd, from->pr_zomb, &to.pr_zomb); \ + H_PUT_8 (abfd, from->pr_nice, &to.pr_nice); \ + H_PUT_32 (abfd, from->pr_flag, to.pr_flag); \ + H_PUT_32 (abfd, from->pr_uid, to.pr_uid); \ + H_PUT_32 (abfd, from->pr_gid, to.pr_gid); \ + H_PUT_32 (abfd, from->pr_pid, to.pr_pid); \ + H_PUT_32 (abfd, from->pr_ppid, to.pr_ppid); \ + H_PUT_32 (abfd, from->pr_pgrp, to.pr_pgrp); \ + H_PUT_32 (abfd, from->pr_sid, to.pr_sid); \ + strncpy (to.pr_fname, from->pr_fname, sizeof (to.pr_fname)); \ + strncpy (to.pr_psargs, from->pr_psargs, sizeof (to.pr_psargs)); \ + } while (0) + +/* External 64-bit structure for PRPSINFO. This structure is ABI-defined, + thus we choose to use char arrays here in order to avoid dealing with + different types in different architectures. + + Differently from the 32-bit version, the PowerPC guys made our lives better + and used the same size as the other architectures. + + This structure will ultimately be written in the corefile's note section, + as the PRPSINFO. */ + +struct elf_external_prpsinfo64 + { + char pr_state; /* Numeric process state. */ + char pr_sname; /* Char for pr_state. */ + char pr_zomb; /* Zombie. */ + char pr_nice; /* Nice val. */ + char pr_flag[8]; /* Flags. */ + char gap[4]; + char pr_uid[4]; + char pr_gid[4]; + char pr_pid[4]; + char pr_ppid[4]; + char pr_pgrp[4]; + char pr_sid[4]; + /* Lots missing */ + char pr_fname[16]; /* Filename of executable. */ + char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ + }; + +/* Helper macro to copy (properly handling endianess) things from the + `elf_internal_prpsinfo' structure to the `elf_external_prpsinfo64' + structure. + + Note that FROM should be a pointer, and TO should be the explicit type. */ + +#define PRPSINFO64_COPY_FIELDS(abfd, from, to) \ + do \ + { \ + H_PUT_8 (abfd, from->pr_state, &to.pr_state); \ + H_PUT_8 (abfd, from->pr_sname, &to.pr_sname); \ + H_PUT_8 (abfd, from->pr_zomb, &to.pr_zomb); \ + H_PUT_8 (abfd, from->pr_nice, &to.pr_nice); \ + H_PUT_64 (abfd, from->pr_flag, to.pr_flag); \ + H_PUT_32 (abfd, from->pr_uid, to.pr_uid); \ + H_PUT_32 (abfd, from->pr_gid, to.pr_gid); \ + H_PUT_32 (abfd, from->pr_pid, to.pr_pid); \ + H_PUT_32 (abfd, from->pr_ppid, to.pr_ppid); \ + H_PUT_32 (abfd, from->pr_pgrp, to.pr_pgrp); \ + H_PUT_32 (abfd, from->pr_sid, to.pr_sid); \ + strncpy (to.pr_fname, from->pr_fname, sizeof (to.pr_fname)); \ + strncpy (to.pr_psargs, from->pr_psargs, sizeof (to.pr_psargs)); \ + } while (0) + +/* Process info. In the end we do provide typedefs for them. */ + +typedef struct elf_external_prpsinfo32 prpsinfo32_t; +typedef struct elf_external_prpsinfo64 prpsinfo64_t; diff --git a/bfd/elf.c b/bfd/elf.c index a92dd5d..a39b88c 100644 --- a/bfd/elf.c +++ b/bfd/elf.c @@ -44,6 +44,7 @@ SECTION #include "elf-bfd.h" #include "libiberty.h" #include "safe-ctype.h" +#include "elf-psinfo.h" #ifdef CORE_HEADER #include CORE_HEADER @@ -8161,13 +8162,6 @@ elfcore_grok_arm_vfp (bfd *abfd, Elf_Internal_Note *note) return elfcore_make_note_pseudosection (abfd, ".reg-arm-vfp", note); } -#if defined (HAVE_PRPSINFO_T) -typedef prpsinfo_t elfcore_psinfo_t; -#if defined (HAVE_PRPSINFO32_T) /* Sparc64 cross Sparc32 */ -typedef prpsinfo32_t elfcore_psinfo32_t; -#endif -#endif - #if defined (HAVE_PSINFO_T) typedef psinfo_t elfcore_psinfo_t; #if defined (HAVE_PSINFO32_T) /* Sparc64 cross Sparc32 */ @@ -8201,17 +8195,17 @@ _bfd_elfcore_strndup (bfd *abfd, char *start, size_t max) return dups; } -#if defined (HAVE_PRPSINFO_T) || defined (HAVE_PSINFO_T) static bfd_boolean elfcore_grok_psinfo (bfd *abfd, Elf_Internal_Note *note) { +#if defined (HAVE_PSINFO_T) if (note->descsz == sizeof (elfcore_psinfo_t)) { elfcore_psinfo_t psinfo; memcpy (&psinfo, note->descdata, sizeof (psinfo)); -#if defined (HAVE_PSINFO_T_PR_PID) || defined (HAVE_PRPSINFO_T_PR_PID) +#if defined (HAVE_PSINFO_T_PR_PID) elf_tdata (abfd)->core_pid = psinfo.pr_pid; #endif elf_tdata (abfd)->core_program @@ -8222,7 +8216,7 @@ elfcore_grok_psinfo (bfd *abfd, Elf_Internal_Note *note) = _bfd_elfcore_strndup (abfd, psinfo.pr_psargs, sizeof (psinfo.pr_psargs)); } -#if defined (HAVE_PRPSINFO32_T) || defined (HAVE_PSINFO32_T) +#if defined (HAVE_PSINFO32_T) else if (note->descsz == sizeof (elfcore_psinfo32_t)) { /* 64-bit host, 32-bit corefile */ @@ -8230,7 +8224,7 @@ elfcore_grok_psinfo (bfd *abfd, Elf_Internal_Note *note) memcpy (&psinfo, note->descdata, sizeof (psinfo)); -#if defined (HAVE_PSINFO32_T_PR_PID) || defined (HAVE_PRPSINFO32_T_PR_PID) +#if defined (HAVE_PSINFO32_T_PR_PID) elf_tdata (abfd)->core_pid = psinfo.pr_pid; #endif elf_tdata (abfd)->core_program @@ -8261,10 +8255,14 @@ elfcore_grok_psinfo (bfd *abfd, Elf_Internal_Note *note) if (0 < n && command[n - 1] == ' ') command[n - 1] = '\0'; } +#else /* defined (HAVE_PSINFO_T) */ + /* Avoid compiler warning about "unused variables". */ + (void) abfd; + (void) note; return TRUE; +#endif } -#endif /* defined (HAVE_PRPSINFO_T) || defined (HAVE_PSINFO_T) */ #if defined (HAVE_PSTATUS_T) static bfd_boolean @@ -9062,16 +9060,16 @@ char * elfcore_write_prpsinfo (bfd *abfd, char *buf, int *bufsiz, - const char *fname, - const char *psargs) + const struct elf_internal_prpsinfo *input) { const struct elf_backend_data *bed = get_elf_backend_data (abfd); if (bed->elf_backend_write_core_note != NULL) { char *ret; + ret = (*bed->elf_backend_write_core_note) (abfd, buf, bufsiz, - NT_PRPSINFO, fname, psargs); + NT_PRPSINFO, input); if (ret != NULL) return ret; } @@ -9089,8 +9087,8 @@ elfcore_write_prpsinfo (bfd *abfd, #endif memset (&data, 0, sizeof (data)); - strncpy (data.pr_fname, fname, sizeof (data.pr_fname)); - strncpy (data.pr_psargs, psargs, sizeof (data.pr_psargs)); + strncpy (data.pr_fname, input->pr_fname, sizeof (data.pr_fname)); + strncpy (data.pr_psargs, input->pr_psargs, sizeof (data.pr_psargs)); return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, &data, sizeof (data)); } @@ -9101,13 +9099,13 @@ elfcore_write_prpsinfo (bfd *abfd, psinfo_t data; int note_type = NT_PSINFO; #else - prpsinfo_t data; + prpsinfo64_t data; int note_type = NT_PRPSINFO; #endif memset (&data, 0, sizeof (data)); - strncpy (data.pr_fname, fname, sizeof (data.pr_fname)); - strncpy (data.pr_psargs, psargs, sizeof (data.pr_psargs)); + strncpy (data.pr_fname, input->pr_fname, sizeof (data.pr_fname)); + strncpy (data.pr_psargs, input->pr_psargs, sizeof (data.pr_psargs)); return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, &data, sizeof (data)); } diff --git a/bfd/elf32-arm.c b/bfd/elf32-arm.c index fd7d26a..cacc895 100644 --- a/bfd/elf32-arm.c +++ b/bfd/elf32-arm.c @@ -30,6 +30,7 @@ #include "elf-nacl.h" #include "elf-vxworks.h" #include "elf/arm.h" +#include "elf-psinfo.h" /* Return the relocation section associated with NAME. HTAB is the bfd's elf32_arm_link_hash_entry. */ @@ -2004,17 +2005,19 @@ elf32_arm_nabi_write_core_note (bfd *abfd, char *buf, int *bufsiz, case NT_PRPSINFO: { - char data[124]; + const struct elf_internal_prpsinfo *prpsinfo; + struct elf_external_prpsinfo32 data; va_list ap; va_start (ap, note_type); - memset (data, 0, sizeof (data)); - strncpy (data + 28, va_arg (ap, const char *), 16); - strncpy (data + 44, va_arg (ap, const char *), 80); + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); va_end (ap); + memset (&data, 0, sizeof (data)); + PRPSINFO32_COPY_FIELDS (abfd, prpsinfo, data); + return elfcore_write_note (abfd, buf, bufsiz, - "CORE", note_type, data, sizeof (data)); + "CORE", note_type, &data, sizeof (data)); } case NT_PRSTATUS: diff --git a/bfd/elf32-i386.c b/bfd/elf32-i386.c index a188cec..70b5e9b 100644 --- a/bfd/elf32-i386.c +++ b/bfd/elf32-i386.c @@ -31,12 +31,20 @@ #include "objalloc.h" #include "hashtab.h" #include "dwarf2.h" +#include "elf-bfd.h" +#include "elf-psinfo.h" + +#include <stdarg.h> /* 386 uses REL relocations instead of RELA. */ #define USE_REL 1 #include "elf/i386.h" +#ifdef CORE_HEADER +#include CORE_HEADER +#endif + static reloc_howto_type elf_howto_table[]= { HOWTO(R_386_NONE, 0, 0, 0, FALSE, 0, complain_overflow_bitfield, @@ -500,6 +508,59 @@ elf_i386_grok_psinfo (bfd *abfd, Elf_Internal_Note *note) return TRUE; } + +static char * +elf_i386_write_core_note (bfd *abfd, char *buf, int *bufsiz, + int note_type, ...) +{ + va_list ap; + + switch (note_type) + { + default: + return NULL; + + case NT_PRPSINFO: + { + const struct elf_internal_prpsinfo *prpsinfo; + struct elf_external_prpsinfo32 data; + + va_start (ap, note_type); + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); + va_end (ap); + + memset (&data, 0, sizeof (data)); + PRPSINFO32_COPY_FIELDS (abfd, prpsinfo, data); + + return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, + &data, sizeof (data)); + } + /* NOTREACHED */ + + case NT_PRSTATUS: + { + long pid; + int cursig; + const void *gregs; + prstatus32_t prstat; + + va_start (ap, note_type); + pid = va_arg (ap, long); + cursig = va_arg (ap, int); + gregs = va_arg (ap, const void *); + va_end (ap); + + memset (&prstat, 0, sizeof (prstat)); + prstat.pr_pid = pid; + prstat.pr_cursig = cursig; + memcpy (&prstat.pr_reg, gregs, sizeof (prstat.pr_reg)); + return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, + &prstat, sizeof (prstat)); + } + } + /* NOTREACHED */ +} + \f /* Functions for the i386 ELF linker. @@ -5140,6 +5201,7 @@ elf_i386_add_symbol_hook (bfd * abfd, #define elf_backend_gc_sweep_hook elf_i386_gc_sweep_hook #define elf_backend_grok_prstatus elf_i386_grok_prstatus #define elf_backend_grok_psinfo elf_i386_grok_psinfo +#define elf_backend_write_core_note elf_i386_write_core_note #define elf_backend_reloc_type_class elf_i386_reloc_type_class #define elf_backend_relocate_section elf_i386_relocate_section #define elf_backend_size_dynamic_sections elf_i386_size_dynamic_sections diff --git a/bfd/elf32-ppc.c b/bfd/elf32-ppc.c index 5241926..2869663 100644 --- a/bfd/elf32-ppc.c +++ b/bfd/elf32-ppc.c @@ -37,6 +37,7 @@ #include "elf32-ppc.h" #include "elf-vxworks.h" #include "dwarf2.h" +#include "elf-psinfo.h" typedef enum split16_format_type { @@ -2222,16 +2223,19 @@ ppc_elf_write_core_note (bfd *abfd, char *buf, int *bufsiz, int note_type, ...) case NT_PRPSINFO: { - char data[128]; + const struct elf_internal_prpsinfo *prpsinfo; + struct elf_external_ppc_prpsinfo32 data; va_list ap; va_start (ap, note_type); - memset (data, 0, sizeof (data)); - strncpy (data + 32, va_arg (ap, const char *), 16); - strncpy (data + 48, va_arg (ap, const char *), 80); + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); va_end (ap); + + memset (&data, 0, sizeof (data)); + PRPSINFO32_PPC_COPY_FIELDS (abfd, prpsinfo, data); + return elfcore_write_note (abfd, buf, bufsiz, - "CORE", note_type, data, sizeof (data)); + "CORE", note_type, &data, sizeof (data)); } case NT_PRSTATUS: diff --git a/bfd/elf64-ppc.c b/bfd/elf64-ppc.c index 10b6f9d..4eda989 100644 --- a/bfd/elf64-ppc.c +++ b/bfd/elf64-ppc.c @@ -34,6 +34,7 @@ #include "elf-bfd.h" #include "elf/ppc64.h" #include "elf64-ppc.h" +#include "elf-psinfo.h" #include "dwarf2.h" static bfd_reloc_status_type ppc64_elf_ha_reloc @@ -2718,16 +2719,19 @@ ppc64_elf_write_core_note (bfd *abfd, char *buf, int *bufsiz, int note_type, case NT_PRPSINFO: { - char data[136]; + const struct elf_internal_prpsinfo *prpsinfo; + struct elf_external_prpsinfo64 data; va_list ap; va_start (ap, note_type); - memset (data, 0, sizeof (data)); - strncpy (data + 40, va_arg (ap, const char *), 16); - strncpy (data + 56, va_arg (ap, const char *), 80); + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); va_end (ap); + + memset (&data, 0, sizeof (data)); + PRPSINFO64_COPY_FIELDS (abfd, prpsinfo, data); + return elfcore_write_note (abfd, buf, bufsiz, - "CORE", note_type, data, sizeof (data)); + "CORE", note_type, &data, sizeof (data)); } case NT_PRSTATUS: diff --git a/bfd/elf64-x86-64.c b/bfd/elf64-x86-64.c index 283681c..2c9939d 100644 --- a/bfd/elf64-x86-64.c +++ b/bfd/elf64-x86-64.c @@ -32,11 +32,13 @@ #include "hashtab.h" #include "dwarf2.h" #include "libiberty.h" +#include "elf-psinfo.h" + +#include <stdarg.h> #include "elf/x86-64.h" #ifdef CORE_HEADER -#include <stdarg.h> #include CORE_HEADER #endif @@ -415,14 +417,13 @@ elf_x86_64_grok_psinfo (bfd *abfd, Elf_Internal_Note *note) return TRUE; } -#ifdef CORE_HEADER static char * elf_x86_64_write_core_note (bfd *abfd, char *buf, int *bufsiz, int note_type, ...) { const struct elf_backend_data *bed = get_elf_backend_data (abfd); va_list ap; - const char *fname, *psargs; + const struct elf_internal_prpsinfo *prpsinfo; long pid; int cursig; const void *gregs; @@ -434,27 +435,28 @@ elf_x86_64_write_core_note (bfd *abfd, char *buf, int *bufsiz, case NT_PRPSINFO: va_start (ap, note_type); - fname = va_arg (ap, const char *); - psargs = va_arg (ap, const char *); + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); va_end (ap); if (bed->s->elfclass == ELFCLASS32) { - prpsinfo32_t data; - memset (&data, 0, sizeof (data)); - strncpy (data.pr_fname, fname, sizeof (data.pr_fname)); - strncpy (data.pr_psargs, psargs, sizeof (data.pr_psargs)); + struct elf_external_prpsinfo32 data32; + + memset (&data32, 0, sizeof (data32)); + PRPSINFO32_COPY_FIELDS (abfd, prpsinfo, data32); + return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, - &data, sizeof (data)); + &data32, sizeof (data32)); } else { - prpsinfo64_t data; - memset (&data, 0, sizeof (data)); - strncpy (data.pr_fname, fname, sizeof (data.pr_fname)); - strncpy (data.pr_psargs, psargs, sizeof (data.pr_psargs)); + struct elf_external_prpsinfo64 data64; + + memset (&data64, 0, sizeof (data64)); + PRPSINFO64_COPY_FIELDS (abfd, prpsinfo, data64); + return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, - &data, sizeof (data)); + &data64, sizeof (data64)); } /* NOTREACHED */ @@ -501,7 +503,7 @@ elf_x86_64_write_core_note (bfd *abfd, char *buf, int *bufsiz, } /* NOTREACHED */ } -#endif + \f /* Functions for the x86-64 ELF linker. */ @@ -5225,9 +5227,7 @@ static const struct bfd_elf_special_section #define elf_backend_gc_sweep_hook elf_x86_64_gc_sweep_hook #define elf_backend_grok_prstatus elf_x86_64_grok_prstatus #define elf_backend_grok_psinfo elf_x86_64_grok_psinfo -#ifdef CORE_HEADER #define elf_backend_write_core_note elf_x86_64_write_core_note -#endif #define elf_backend_reloc_type_class elf_x86_64_reloc_type_class #define elf_backend_relocate_section elf_x86_64_relocate_section #define elf_backend_size_dynamic_sections elf_x86_64_size_dynamic_sections diff --git a/bfd/hosts/x86-64linux.h b/bfd/hosts/x86-64linux.h index 78be09a..6070978 100644 --- a/bfd/hosts/x86-64linux.h +++ b/bfd/hosts/x86-64linux.h @@ -43,11 +43,6 @@ typedef unsigned long long int uint64_t; /* Unsigned 64-bit integer aligned to 8 bytes. */ typedef uint64_t __attribute__ ((__aligned__ (8))) a8_uint64_t; -#undef HAVE_PRPSINFO32_T -#define HAVE_PRPSINFO32_T -#undef HAVE_PRPSINFO32_T_PR_PID -#define HAVE_PRPSINFO32_T_PR_PID - #undef HAVE_PRSTATUS32_T #define HAVE_PRSTATUS32_T @@ -191,36 +186,6 @@ struct elf_prstatus64 int pr_fpvalid; /* True if math copro being used. */ }; -struct elf_prpsinfo32 - { - char pr_state; /* Numeric process state. */ - char pr_sname; /* Char for pr_state. */ - char pr_zomb; /* Zombie. */ - char pr_nice; /* Nice val. */ - unsigned int pr_flag; /* Flags. */ - unsigned short int pr_uid; - unsigned short int pr_gid; - int pr_pid, pr_ppid, pr_pgrp, pr_sid; - /* Lots missing */ - char pr_fname[16]; /* Filename of executable. */ - char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ - }; - -struct elf_prpsinfo64 - { - char pr_state; /* Numeric process state. */ - char pr_sname; /* Char for pr_state. */ - char pr_zomb; /* Zombie. */ - char pr_nice; /* Nice val. */ - a8_uint64_t pr_flag; /* Flags. */ - unsigned int pr_uid; - unsigned int pr_gid; - int pr_pid, pr_ppid, pr_pgrp, pr_sid; - /* Lots missing */ - char pr_fname[16]; /* Filename of executable. */ - char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ - }; - /* The rest of this file provides the types for emulation of the Solaris <proc_service.h> interfaces that should be implemented by users of libthread_db. */ @@ -229,5 +194,3 @@ struct elf_prpsinfo64 typedef struct elf_prstatus32 prstatus32_t; typedef struct elf_prstatusx32 prstatusx32_t; typedef struct elf_prstatus64 prstatus64_t; -typedef struct elf_prpsinfo32 prpsinfo32_t; -typedef struct elf_prpsinfo64 prpsinfo64_t; -- 1.7.7.6 ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: [PATCH/RFC 01/02 v2] Refactor PRPSINFO handling on Binutils 2012-12-17 17:41 ` Sergio Durigan Junior @ 2012-12-17 17:44 ` H.J. Lu 2012-12-17 17:51 ` Sergio Durigan Junior 0 siblings, 1 reply; 21+ messages in thread From: H.J. Lu @ 2012-12-17 17:44 UTC (permalink / raw) To: Sergio Durigan Junior; +Cc: Binutils Development, GDB Patches, Pedro Alves On Mon, Dec 17, 2012 at 9:41 AM, Sergio Durigan Junior <sergiodj@redhat.com> wrote: > On Monday, December 17 2012, H. J. Lu wrote: > >> On Sun, Dec 16, 2012 at 7:09 PM, Sergio Durigan Junior >> <sergiodj@redhat.com> wrote: > >>> + if (bed->elf_machine_code == EM_X86_64) >>> + { >>> + prstatusx32_t prstat; >>> + memset (&prstat, 0, sizeof (prstat)); >>> + prstat.pr_pid = pid; >>> + prstat.pr_cursig = cursig; >>> + memcpy (&prstat.pr_reg, gregs, sizeof (prstat.pr_reg)); >>> + return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, >>> + &prstat, sizeof (prstat)); >>> + } >>> + else >> >> When will elf_i386_write_core_note be called for >> x32 process? > > Ops, sorry, that code sneaked in apparently. Here's the new version of > the patch. > Can you create a git GDB branch for me to try? -- H.J. ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: [PATCH/RFC 01/02 v2] Refactor PRPSINFO handling on Binutils 2012-12-17 17:44 ` H.J. Lu @ 2012-12-17 17:51 ` Sergio Durigan Junior 2012-12-17 22:01 ` H.J. Lu 0 siblings, 1 reply; 21+ messages in thread From: Sergio Durigan Junior @ 2012-12-17 17:51 UTC (permalink / raw) To: H.J. Lu; +Cc: Binutils Development, GDB Patches, Pedro Alves On Monday, December 17 2012, H. J. Lu wrote: >> Ops, sorry, that code sneaked in apparently. Here's the new version of >> the patch. >> > > Can you create a git GDB branch for me to try? Yep. The branch is named archer-sergiodj-gcore-prpsinfo on git://sourceware.org/git/archer.git . Thanks, -- Sergio ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: [PATCH/RFC 01/02 v2] Refactor PRPSINFO handling on Binutils 2012-12-17 17:51 ` Sergio Durigan Junior @ 2012-12-17 22:01 ` H.J. Lu 2012-12-18 5:47 ` Sergio Durigan Junior 0 siblings, 1 reply; 21+ messages in thread From: H.J. Lu @ 2012-12-17 22:01 UTC (permalink / raw) To: Sergio Durigan Junior; +Cc: Binutils Development, GDB Patches, Pedro Alves On Mon, Dec 17, 2012 at 9:50 AM, Sergio Durigan Junior <sergiodj@redhat.com> wrote: > On Monday, December 17 2012, H. J. Lu wrote: > >>> Ops, sorry, that code sneaked in apparently. Here's the new version of >>> the patch. >>> >> >> Can you create a git GDB branch for me to try? > > Yep. > > The branch is named archer-sergiodj-gcore-prpsinfo on > git://sourceware.org/git/archer.git . > I tried it and it works for x32. Thanks. -- H.J. ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: [PATCH/RFC 01/02 v2] Refactor PRPSINFO handling on Binutils 2012-12-17 22:01 ` H.J. Lu @ 2012-12-18 5:47 ` Sergio Durigan Junior 2012-12-18 15:43 ` H.J. Lu 0 siblings, 1 reply; 21+ messages in thread From: Sergio Durigan Junior @ 2012-12-18 5:47 UTC (permalink / raw) To: H.J. Lu; +Cc: Binutils Development, GDB Patches, Pedro Alves On Monday, December 17 2012, H. J. Lu wrote: > I tried it and it works for x32. Thanks for trying it out, H.J. I will wait until other maintainers review this code, since it touches more architectures as well, before I commit the patch. But I assume your message means approval for x32, right? Thanks, -- Sergio ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: [PATCH/RFC 01/02 v2] Refactor PRPSINFO handling on Binutils 2012-12-18 5:47 ` Sergio Durigan Junior @ 2012-12-18 15:43 ` H.J. Lu 0 siblings, 0 replies; 21+ messages in thread From: H.J. Lu @ 2012-12-18 15:43 UTC (permalink / raw) To: Sergio Durigan Junior; +Cc: Binutils Development, GDB Patches, Pedro Alves On Mon, Dec 17, 2012 at 9:46 PM, Sergio Durigan Junior <sergiodj@redhat.com> wrote: > On Monday, December 17 2012, H. J. Lu wrote: > >> I tried it and it works for x32. > > Thanks for trying it out, H.J. I will wait until other maintainers > review this code, since it touches more architectures as well, before I > commit the patch. But I assume your message means approval for x32, > right? > OK for i386 and x86-64 changes in BFD. Thanks. -- H.J. ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: [PATCH/RFC 01/02 v2] Refactor PRPSINFO handling on Binutils 2012-12-17 3:10 [PATCH/RFC 01/02 v2] Refactor PRPSINFO handling on Binutils Sergio Durigan Junior 2012-12-17 15:43 ` H.J. Lu @ 2012-12-18 17:38 ` Jan Kratochvil 2012-12-18 19:19 ` Sergio Durigan Junior 1 sibling, 1 reply; 21+ messages in thread From: Jan Kratochvil @ 2012-12-18 17:38 UTC (permalink / raw) To: Sergio Durigan Junior Cc: Binutils Development, GDB Patches, Pedro Alves, H.J. Lu Hi Sergio, I do not feel too confident in bfd/ but at least there may be more response to my wrong comments. > diff --git a/bfd/Makefile.in b/bfd/Makefile.in > index 92d9d08..e12deb5 100644 > --- a/bfd/Makefile.in > +++ b/bfd/Makefile.in > @@ -1050,7 +1050,7 @@ BUILD_CFILES = \ > CFILES = $(SOURCE_CFILES) $(BUILD_CFILES) > SOURCE_HFILES = \ > aout-target.h aoutf1.h aoutx.h coffcode.h coffswap.h ecoffswap.h \ > - elf-bfd.h elf-hppa.h elf32-hppa.h \ > + elf-bfd.h elf-psinfo.h elf-hppa.h elf32-hppa.h \ > elf64-hppa.h elfcode.h elfcore.h \ > freebsd.h genlink.h go32stub.h \ > libaout.h libbfd.h libcoff.h libecoff.h libhppa.h libieee.h \ > diff --git a/bfd/elf-bfd.h b/bfd/elf-bfd.h > index b8d82b1..d314291 100644 > --- a/bfd/elf-bfd.h > +++ b/bfd/elf-bfd.h > @@ -2234,11 +2234,15 @@ extern bfd_boolean bfd_elf_lookup_section_flags > extern Elf_Internal_Phdr * _bfd_elf_find_segment_containing_section > (bfd * abfd, asection * section); > > +/* Forward declaration of prpsinfo. See `elf-psinfo.h' for more details. */ > + > +struct elf_internal_prpsinfo; > + > /* Exported interface for writing elf corefile notes. */ > extern char *elfcore_write_note > (bfd *, char *, int *, const char *, int, const void *, int); > extern char *elfcore_write_prpsinfo > - (bfd *, char *, int *, const char *, const char *); > + (bfd *, char *, int *, const struct elf_internal_prpsinfo *); > extern char *elfcore_write_prstatus > (bfd *, char *, int *, long, int, const void *); > extern char * elfcore_write_pstatus > diff --git a/bfd/elf-psinfo.h b/bfd/elf-psinfo.h > new file mode 100644 > index 0000000..61b38e1 > --- /dev/null > +++ b/bfd/elf-psinfo.h > @@ -0,0 +1,215 @@ > +/* Declarations for PRPSINFO structures under ELF on GNU/Linux. > + Copyright 2012 Free Software Foundation, Inc. > + > + This file is part of BFD, the Binary File Descriptor library. > + > + 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 3 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., 51 Franklin Street - Fifth Floor, Boston, > + MA 02110-1301, USA. */ > + > +#undef HAVE_PRPSINFO32_T > +#define HAVE_PRPSINFO32_T > +#undef HAVE_PRPSINFO32_T_PR_PID > +#define HAVE_PRPSINFO32_T_PR_PID This does not seem to be useful, these are auto-detected by configure and elf-psinfo.h is included unconditionally. Therefore they could be completely removed. But in reality they should not be removed as your elf-core definitions do not cover very every target supported by bfd, only some of them. > + > +/* Maximum size of the arguments that can be stored in a PRPSINFO > + structure. */ > + > +#define ELF_PRARGSZ (80) > + > +/* Internal structure which holds information to be included in the > + PRPSINFO section of the corefile. > + > + This is an "internal" structure in the sense that it should be used to > + pass information to BFD (via the `elfcore_write_prpsinfo', for example), > + so things like endianess shouldn't be an issue. This structure will > + eventually be converted in one of the `elf_external_*' structures > + below. */ > + > +struct elf_internal_prpsinfo > + { > + char pr_state; /* Numeric process state. */ > + char pr_sname; /* Char for pr_state. */ > + char pr_zomb; /* Zombie. */ > + char pr_nice; /* Nice val. */ > + unsigned long pr_flag; /* Flags. */ > + unsigned int pr_uid; > + unsigned int pr_gid; > + int pr_pid, pr_ppid, pr_pgrp, pr_sid; > + /* Lots missing */ > + char pr_fname[16]; /* Filename of executable. */ > + char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ > + }; > + > +/* External 32-bit structure for PRPSINFO. This structure is ABI-defined, > + thus we choose to use char arrays here in order to avoid dealing with > + different types in different architectures. > + > + This structure will ultimately be written in the corefile's note section, > + as the PRPSINFO. */ > + > +struct elf_external_prpsinfo32 > + { > + char pr_state; /* Numeric process state. */ > + char pr_sname; /* Char for pr_state. */ > + char pr_zomb; /* Zombie. */ > + char pr_nice; /* Nice val. */ > + char pr_flag[4]; /* Flags. */ > + char pr_uid[2]; > + char pr_gid[2]; > + char pr_pid[4]; > + char pr_ppid[4]; > + char pr_pgrp[4]; > + char pr_sid[4]; > + /* Lots missing */ > + char pr_fname[16]; /* Filename of executable. */ > + char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ > + }; As it does not match very every arch I believe you should just copy it into elf*-*.c files containing the *_elf_write_core_note function for archs where you have verified (by comparing some headers, not just by experiment) it does match. > + > +/* External 32-bit PPC structure for PRPSINFO. If it is arch-specific then it should not be in a generic file. I believe elf32-ppc.c and elf64-ppc.c files are fine for it. In the end I do not see a use for this header file. > diff --git a/bfd/elf.c b/bfd/elf.c > index a92dd5d..a39b88c 100644 > --- a/bfd/elf.c > +++ b/bfd/elf.c > @@ -44,6 +44,7 @@ SECTION > #include "elf-bfd.h" > #include "libiberty.h" > #include "safe-ctype.h" > +#include "elf-psinfo.h" > > #ifdef CORE_HEADER > #include CORE_HEADER > @@ -8161,13 +8162,6 @@ elfcore_grok_arm_vfp (bfd *abfd, Elf_Internal_Note *note) > return elfcore_make_note_pseudosection (abfd, ".reg-arm-vfp", note); > } > > -#if defined (HAVE_PRPSINFO_T) > -typedef prpsinfo_t elfcore_psinfo_t; > -#if defined (HAVE_PRPSINFO32_T) /* Sparc64 cross Sparc32 */ > -typedef prpsinfo32_t elfcore_psinfo32_t; > -#endif > -#endif > - This is arch-independent file (elf.c). Some targets are unverified they match your new ABI elfcore definition. As they may provide correct system prpsinfo_t defintion you should use it there, if available. > #if defined (HAVE_PSINFO_T) > typedef psinfo_t elfcore_psinfo_t; > #if defined (HAVE_PSINFO32_T) /* Sparc64 cross Sparc32 */ > @@ -8201,17 +8195,17 @@ _bfd_elfcore_strndup (bfd *abfd, char *start, size_t max) > return dups; > } > > -#if defined (HAVE_PRPSINFO_T) || defined (HAVE_PSINFO_T) All these changes are like the comment above. > static bfd_boolean > elfcore_grok_psinfo (bfd *abfd, Elf_Internal_Note *note) > { > +#if defined (HAVE_PSINFO_T) > if (note->descsz == sizeof (elfcore_psinfo_t)) > { > elfcore_psinfo_t psinfo; > > memcpy (&psinfo, note->descdata, sizeof (psinfo)); > > -#if defined (HAVE_PSINFO_T_PR_PID) || defined (HAVE_PRPSINFO_T_PR_PID) > +#if defined (HAVE_PSINFO_T_PR_PID) > elf_tdata (abfd)->core_pid = psinfo.pr_pid; > #endif > elf_tdata (abfd)->core_program > @@ -8222,7 +8216,7 @@ elfcore_grok_psinfo (bfd *abfd, Elf_Internal_Note *note) > = _bfd_elfcore_strndup (abfd, psinfo.pr_psargs, > sizeof (psinfo.pr_psargs)); > } > -#if defined (HAVE_PRPSINFO32_T) || defined (HAVE_PSINFO32_T) > +#if defined (HAVE_PSINFO32_T) > else if (note->descsz == sizeof (elfcore_psinfo32_t)) > { > /* 64-bit host, 32-bit corefile */ > @@ -8230,7 +8224,7 @@ elfcore_grok_psinfo (bfd *abfd, Elf_Internal_Note *note) > > memcpy (&psinfo, note->descdata, sizeof (psinfo)); > > -#if defined (HAVE_PSINFO32_T_PR_PID) || defined (HAVE_PRPSINFO32_T_PR_PID) > +#if defined (HAVE_PSINFO32_T_PR_PID) > elf_tdata (abfd)->core_pid = psinfo.pr_pid; > #endif > elf_tdata (abfd)->core_program > @@ -8261,10 +8255,14 @@ elfcore_grok_psinfo (bfd *abfd, Elf_Internal_Note *note) > if (0 < n && command[n - 1] == ' ') > command[n - 1] = '\0'; > } > +#else /* defined (HAVE_PSINFO_T) */ > + /* Avoid compiler warning about "unused variables". */ > + (void) abfd; > + (void) note; > > return TRUE; > +#endif > } > -#endif /* defined (HAVE_PRPSINFO_T) || defined (HAVE_PSINFO_T) */ > > #if defined (HAVE_PSTATUS_T) > static bfd_boolean > @@ -9062,16 +9060,16 @@ char * > elfcore_write_prpsinfo (bfd *abfd, > char *buf, > int *bufsiz, > - const char *fname, > - const char *psargs) > + const struct elf_internal_prpsinfo *input) > { > const struct elf_backend_data *bed = get_elf_backend_data (abfd); > > if (bed->elf_backend_write_core_note != NULL) > { > char *ret; > + > ret = (*bed->elf_backend_write_core_note) (abfd, buf, bufsiz, > - NT_PRPSINFO, fname, psargs); > + NT_PRPSINFO, input); > if (ret != NULL) > return ret; > } > @@ -9089,8 +9087,8 @@ elfcore_write_prpsinfo (bfd *abfd, > #endif > > memset (&data, 0, sizeof (data)); > - strncpy (data.pr_fname, fname, sizeof (data.pr_fname)); > - strncpy (data.pr_psargs, psargs, sizeof (data.pr_psargs)); > + strncpy (data.pr_fname, input->pr_fname, sizeof (data.pr_fname)); > + strncpy (data.pr_psargs, input->pr_psargs, sizeof (data.pr_psargs)); > return elfcore_write_note (abfd, buf, bufsiz, > "CORE", note_type, &data, sizeof (data)); > } > @@ -9101,13 +9099,13 @@ elfcore_write_prpsinfo (bfd *abfd, > psinfo_t data; > int note_type = NT_PSINFO; > #else > - prpsinfo_t data; > + prpsinfo64_t data; > int note_type = NT_PRPSINFO; > #endif > > memset (&data, 0, sizeof (data)); > - strncpy (data.pr_fname, fname, sizeof (data.pr_fname)); > - strncpy (data.pr_psargs, psargs, sizeof (data.pr_psargs)); > + strncpy (data.pr_fname, input->pr_fname, sizeof (data.pr_fname)); > + strncpy (data.pr_psargs, input->pr_psargs, sizeof (data.pr_psargs)); > return elfcore_write_note (abfd, buf, bufsiz, > "CORE", note_type, &data, sizeof (data)); > } > diff --git a/bfd/elf32-arm.c b/bfd/elf32-arm.c > index fd7d26a..cacc895 100644 > --- a/bfd/elf32-arm.c > +++ b/bfd/elf32-arm.c > @@ -30,6 +30,7 @@ > #include "elf-nacl.h" > #include "elf-vxworks.h" > #include "elf/arm.h" > +#include "elf-psinfo.h" > > /* Return the relocation section associated with NAME. HTAB is the > bfd's elf32_arm_link_hash_entry. */ > @@ -2004,17 +2005,19 @@ elf32_arm_nabi_write_core_note (bfd *abfd, char *buf, int *bufsiz, > > case NT_PRPSINFO: > { > - char data[124]; > + const struct elf_internal_prpsinfo *prpsinfo; > + struct elf_external_prpsinfo32 data; > va_list ap; > > va_start (ap, note_type); > - memset (data, 0, sizeof (data)); > - strncpy (data + 28, va_arg (ap, const char *), 16); > - strncpy (data + 44, va_arg (ap, const char *), 80); > + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); > va_end (ap); > > + memset (&data, 0, sizeof (data)); > + PRPSINFO32_COPY_FIELDS (abfd, prpsinfo, data); > + > return elfcore_write_note (abfd, buf, bufsiz, > - "CORE", note_type, data, sizeof (data)); > + "CORE", note_type, &data, sizeof (data)); > } > > case NT_PRSTATUS: > diff --git a/bfd/elf32-i386.c b/bfd/elf32-i386.c > index a188cec..5b81baa 100644 > --- a/bfd/elf32-i386.c > +++ b/bfd/elf32-i386.c > @@ -31,12 +31,20 @@ > #include "objalloc.h" > #include "hashtab.h" > #include "dwarf2.h" > +#include "elf-bfd.h" > +#include "elf-psinfo.h" > + > +#include <stdarg.h> > > /* 386 uses REL relocations instead of RELA. */ > #define USE_REL 1 > > #include "elf/i386.h" > > +#ifdef CORE_HEADER > +#include CORE_HEADER > +#endif I believe new CORE_HEADER should not be introduced, they are rather deprecated as they depend on system <procfs.h> which is not compatible for cross-build core handling. (But I may be completely wrong here.) > + > static reloc_howto_type elf_howto_table[]= > { > HOWTO(R_386_NONE, 0, 0, 0, FALSE, 0, complain_overflow_bitfield, > @@ -500,6 +508,67 @@ elf_i386_grok_psinfo (bfd *abfd, Elf_Internal_Note *note) > > return TRUE; > } > + > +static char * > +elf_i386_write_core_note (bfd *abfd, char *buf, int *bufsiz, > + int note_type, ...) > +{ > + const struct elf_backend_data *bed = get_elf_backend_data (abfd); > + va_list ap; > + const struct elf_internal_prpsinfo *prpsinfo; > + long pid; > + int cursig; > + const void *gregs; > + struct elf_external_prpsinfo32 data; > + > + switch (note_type) > + { > + default: > + return NULL; > + > + case NT_PRPSINFO: > + va_start (ap, note_type); > + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); > + va_end (ap); Maybe to use a union pointer instead? But nothing serious, fine with va_arg. > + > + memset (&data, 0, sizeof (data)); > + PRPSINFO32_COPY_FIELDS (abfd, prpsinfo, data); > + > + return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, > + &data, sizeof (data)); > + /* NOTREACHED */ Thanks, Jan ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: [PATCH/RFC 01/02 v2] Refactor PRPSINFO handling on Binutils 2012-12-18 17:38 ` Jan Kratochvil @ 2012-12-18 19:19 ` Sergio Durigan Junior 2012-12-18 19:43 ` Jan Kratochvil 0 siblings, 1 reply; 21+ messages in thread From: Sergio Durigan Junior @ 2012-12-18 19:19 UTC (permalink / raw) To: Jan Kratochvil; +Cc: Binutils Development, GDB Patches, Pedro Alves, H.J. Lu Thanks for the review. On Tuesday, December 18 2012, Jan Kratochvil wrote: >> diff --git a/bfd/Makefile.in b/bfd/Makefile.in >> index 92d9d08..e12deb5 100644 >> --- a/bfd/Makefile.in >> +++ b/bfd/Makefile.in >> @@ -1050,7 +1050,7 @@ BUILD_CFILES = \ >> CFILES = $(SOURCE_CFILES) $(BUILD_CFILES) >> SOURCE_HFILES = \ >> aout-target.h aoutf1.h aoutx.h coffcode.h coffswap.h ecoffswap.h \ >> - elf-bfd.h elf-hppa.h elf32-hppa.h \ >> + elf-bfd.h elf-psinfo.h elf-hppa.h elf32-hppa.h \ >> elf64-hppa.h elfcode.h elfcore.h \ >> freebsd.h genlink.h go32stub.h \ >> libaout.h libbfd.h libcoff.h libecoff.h libhppa.h libieee.h \ >> diff --git a/bfd/elf-bfd.h b/bfd/elf-bfd.h >> index b8d82b1..d314291 100644 >> --- a/bfd/elf-bfd.h >> +++ b/bfd/elf-bfd.h >> @@ -2234,11 +2234,15 @@ extern bfd_boolean bfd_elf_lookup_section_flags >> extern Elf_Internal_Phdr * _bfd_elf_find_segment_containing_section >> (bfd * abfd, asection * section); >> >> +/* Forward declaration of prpsinfo. See `elf-psinfo.h' for more details. */ >> + >> +struct elf_internal_prpsinfo; >> + >> /* Exported interface for writing elf corefile notes. */ >> extern char *elfcore_write_note >> (bfd *, char *, int *, const char *, int, const void *, int); >> extern char *elfcore_write_prpsinfo >> - (bfd *, char *, int *, const char *, const char *); >> + (bfd *, char *, int *, const struct elf_internal_prpsinfo *); >> extern char *elfcore_write_prstatus >> (bfd *, char *, int *, long, int, const void *); >> extern char * elfcore_write_pstatus >> diff --git a/bfd/elf-psinfo.h b/bfd/elf-psinfo.h >> new file mode 100644 >> index 0000000..61b38e1 >> --- /dev/null >> +++ b/bfd/elf-psinfo.h >> @@ -0,0 +1,215 @@ >> +/* Declarations for PRPSINFO structures under ELF on GNU/Linux. >> + Copyright 2012 Free Software Foundation, Inc. >> + >> + This file is part of BFD, the Binary File Descriptor library. >> + >> + 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 3 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., 51 Franklin Street - Fifth Floor, Boston, >> + MA 02110-1301, USA. */ >> + >> +#undef HAVE_PRPSINFO32_T >> +#define HAVE_PRPSINFO32_T >> +#undef HAVE_PRPSINFO32_T_PR_PID >> +#define HAVE_PRPSINFO32_T_PR_PID > > This does not seem to be useful, these are auto-detected by configure and > elf-psinfo.h is included unconditionally. Therefore they could be completely > removed. Indeed, I removed the last referecen to those defines a few minutes before sending the patch. I agree. > But in reality they should not be removed as your elf-core definitions do not > cover very every target supported by bfd, only some of them. The patch covers the existing targets that already implemented the *_write_core_note function, with the exception of i386 which is a new implementation. So I still agree with your comment above, that the defines can be removed. >> +/* Maximum size of the arguments that can be stored in a PRPSINFO >> + structure. */ >> + >> +#define ELF_PRARGSZ (80) >> + >> +/* Internal structure which holds information to be included in the >> + PRPSINFO section of the corefile. >> + >> + This is an "internal" structure in the sense that it should be used to >> + pass information to BFD (via the `elfcore_write_prpsinfo', for example), >> + so things like endianess shouldn't be an issue. This structure will >> + eventually be converted in one of the `elf_external_*' structures >> + below. */ >> + >> +struct elf_internal_prpsinfo >> + { >> + char pr_state; /* Numeric process state. */ >> + char pr_sname; /* Char for pr_state. */ >> + char pr_zomb; /* Zombie. */ >> + char pr_nice; /* Nice val. */ >> + unsigned long pr_flag; /* Flags. */ >> + unsigned int pr_uid; >> + unsigned int pr_gid; >> + int pr_pid, pr_ppid, pr_pgrp, pr_sid; >> + /* Lots missing */ >> + char pr_fname[16]; /* Filename of executable. */ >> + char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ >> + }; >> + >> +/* External 32-bit structure for PRPSINFO. This structure is ABI-defined, >> + thus we choose to use char arrays here in order to avoid dealing with >> + different types in different architectures. >> + >> + This structure will ultimately be written in the corefile's note section, >> + as the PRPSINFO. */ >> + >> +struct elf_external_prpsinfo32 >> + { >> + char pr_state; /* Numeric process state. */ >> + char pr_sname; /* Char for pr_state. */ >> + char pr_zomb; /* Zombie. */ >> + char pr_nice; /* Nice val. */ >> + char pr_flag[4]; /* Flags. */ >> + char pr_uid[2]; >> + char pr_gid[2]; >> + char pr_pid[4]; >> + char pr_ppid[4]; >> + char pr_pgrp[4]; >> + char pr_sid[4]; >> + /* Lots missing */ >> + char pr_fname[16]; /* Filename of executable. */ >> + char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ >> + }; > > As it does not match very every arch I believe you should just copy it into > elf*-*.c files containing the *_elf_write_core_note function for archs where > you have verified (by comparing some headers, not just by experiment) it does > match. I disagree. As I said above, the patch covers all targets that were already implementing *_write_core_note. If some new target decides to implement it, it is just a matter of including "elf-psinfo.h" and using the right structures. >> + >> +/* External 32-bit PPC structure for PRPSINFO. > > If it is arch-specific then it should not be in a generic file. > > I believe elf32-ppc.c and elf64-ppc.c files are fine for it. Ok, I am fine with that. I made this decision based on a quick chat that I had with Pedro, asking him if it would be OK to create an arch-specific structure for the case of 32-bit PPC. I will move this definition to elf32-ppc.c, which is the only place that uses this. > In the end I do not see a use for this header file. As I said above, I disagree. The header file is useful for having a single place which defines those structures (i.e., i386, x32 and ARM use the same elf_external_prpsinfo32 strucutre). Also, the header is useful for including in the BFD clients (I'm thiking "GDB" here) which can use the elf_internal_prpsinfo strucuture to pass information to BFD. However, I agree with you that the arch-specific external structures (like the PPC above) can be declared in their .c files. >> diff --git a/bfd/elf.c b/bfd/elf.c >> index a92dd5d..a39b88c 100644 >> --- a/bfd/elf.c >> +++ b/bfd/elf.c >> @@ -44,6 +44,7 @@ SECTION >> #include "elf-bfd.h" >> #include "libiberty.h" >> #include "safe-ctype.h" >> +#include "elf-psinfo.h" >> >> #ifdef CORE_HEADER >> #include CORE_HEADER >> @@ -8161,13 +8162,6 @@ elfcore_grok_arm_vfp (bfd *abfd, Elf_Internal_Note *note) >> return elfcore_make_note_pseudosection (abfd, ".reg-arm-vfp", note); >> } >> >> -#if defined (HAVE_PRPSINFO_T) >> -typedef prpsinfo_t elfcore_psinfo_t; >> -#if defined (HAVE_PRPSINFO32_T) /* Sparc64 cross Sparc32 */ >> -typedef prpsinfo32_t elfcore_psinfo32_t; >> -#endif >> -#endif >> - > > This is arch-independent file (elf.c). Some targets are unverified they match > your new ABI elfcore definition. As they may provide correct system > prpsinfo_t defintion you should use it there, if available. Ok, I will revert this change. >> #if defined (HAVE_PSINFO_T) >> typedef psinfo_t elfcore_psinfo_t; >> #if defined (HAVE_PSINFO32_T) /* Sparc64 cross Sparc32 */ >> @@ -8201,17 +8195,17 @@ _bfd_elfcore_strndup (bfd *abfd, char *start, size_t max) >> return dups; >> } >> >> -#if defined (HAVE_PRPSINFO_T) || defined (HAVE_PSINFO_T) > > All these changes are like the comment above. I will revert this. >> diff --git a/bfd/elf32-arm.c b/bfd/elf32-arm.c >> index fd7d26a..cacc895 100644 >> --- a/bfd/elf32-arm.c >> +++ b/bfd/elf32-arm.c >> @@ -30,6 +30,7 @@ >> #include "elf-nacl.h" >> #include "elf-vxworks.h" >> #include "elf/arm.h" >> +#include "elf-psinfo.h" >> >> /* Return the relocation section associated with NAME. HTAB is the >> bfd's elf32_arm_link_hash_entry. */ >> @@ -2004,17 +2005,19 @@ elf32_arm_nabi_write_core_note (bfd *abfd, char *buf, int *bufsiz, >> >> case NT_PRPSINFO: >> { >> - char data[124]; >> + const struct elf_internal_prpsinfo *prpsinfo; >> + struct elf_external_prpsinfo32 data; >> va_list ap; >> >> va_start (ap, note_type); >> - memset (data, 0, sizeof (data)); >> - strncpy (data + 28, va_arg (ap, const char *), 16); >> - strncpy (data + 44, va_arg (ap, const char *), 80); >> + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); >> va_end (ap); >> >> + memset (&data, 0, sizeof (data)); >> + PRPSINFO32_COPY_FIELDS (abfd, prpsinfo, data); >> + >> return elfcore_write_note (abfd, buf, bufsiz, >> - "CORE", note_type, data, sizeof (data)); >> + "CORE", note_type, &data, sizeof (data)); >> } >> >> case NT_PRSTATUS: >> diff --git a/bfd/elf32-i386.c b/bfd/elf32-i386.c >> index a188cec..5b81baa 100644 >> --- a/bfd/elf32-i386.c >> +++ b/bfd/elf32-i386.c >> @@ -31,12 +31,20 @@ >> #include "objalloc.h" >> #include "hashtab.h" >> #include "dwarf2.h" >> +#include "elf-bfd.h" >> +#include "elf-psinfo.h" >> + >> +#include <stdarg.h> >> >> /* 386 uses REL relocations instead of RELA. */ >> #define USE_REL 1 >> >> #include "elf/i386.h" >> >> +#ifdef CORE_HEADER >> +#include CORE_HEADER >> +#endif > > I believe new CORE_HEADER should not be introduced, they are rather deprecated > as they depend on system <procfs.h> which is not compatible for cross-build > core handling. (But I may be completely wrong here.) Yeah, this is a point of confusion for me as well. I will remove this part, and resubmit the patch. Let's wait until someone more experienced comments. BTW, in order to be able to remove this, I had to "return NULL" when handling the "NT_PRSTATUS" case inside the elf_i386_write_core_note. Ok, here is the new version of the patch, with some of your comments addressed. I didn't make some changes suggested above because of my disagreement, but we can keep discussing. Thanks, -- Sergio --- bfd/Makefile.in | 2 +- bfd/elf-bfd.h | 6 ++- bfd/elf-psinfo.h | 155 +++++++++++++++++++++++++++++++++++++++++++++++ bfd/elf.c | 17 +++--- bfd/elf32-arm.c | 13 +++-- bfd/elf32-i386.c | 42 +++++++++++++ bfd/elf32-ppc.c | 69 +++++++++++++++++++-- bfd/elf64-ppc.c | 14 +++-- bfd/elf64-x86-64.c | 36 ++++++------ bfd/hosts/x86-64linux.h | 37 ----------- 10 files changed, 311 insertions(+), 80 deletions(-) create mode 100644 bfd/elf-psinfo.h diff --git a/bfd/Makefile.in b/bfd/Makefile.in index 92d9d08..e12deb5 100644 --- a/bfd/Makefile.in +++ b/bfd/Makefile.in @@ -1050,7 +1050,7 @@ BUILD_CFILES = \ CFILES = $(SOURCE_CFILES) $(BUILD_CFILES) SOURCE_HFILES = \ aout-target.h aoutf1.h aoutx.h coffcode.h coffswap.h ecoffswap.h \ - elf-bfd.h elf-hppa.h elf32-hppa.h \ + elf-bfd.h elf-psinfo.h elf-hppa.h elf32-hppa.h \ elf64-hppa.h elfcode.h elfcore.h \ freebsd.h genlink.h go32stub.h \ libaout.h libbfd.h libcoff.h libecoff.h libhppa.h libieee.h \ diff --git a/bfd/elf-bfd.h b/bfd/elf-bfd.h index b8d82b1..d314291 100644 --- a/bfd/elf-bfd.h +++ b/bfd/elf-bfd.h @@ -2234,11 +2234,15 @@ extern bfd_boolean bfd_elf_lookup_section_flags extern Elf_Internal_Phdr * _bfd_elf_find_segment_containing_section (bfd * abfd, asection * section); +/* Forward declaration of prpsinfo. See `elf-psinfo.h' for more details. */ + +struct elf_internal_prpsinfo; + /* Exported interface for writing elf corefile notes. */ extern char *elfcore_write_note (bfd *, char *, int *, const char *, int, const void *, int); extern char *elfcore_write_prpsinfo - (bfd *, char *, int *, const char *, const char *); + (bfd *, char *, int *, const struct elf_internal_prpsinfo *); extern char *elfcore_write_prstatus (bfd *, char *, int *, long, int, const void *); extern char * elfcore_write_pstatus diff --git a/bfd/elf-psinfo.h b/bfd/elf-psinfo.h new file mode 100644 index 0000000..b2d6092 --- /dev/null +++ b/bfd/elf-psinfo.h @@ -0,0 +1,155 @@ +/* Declarations for PRPSINFO structures under ELF on GNU/Linux. + Copyright 2012 Free Software Foundation, Inc. + + This file is part of BFD, the Binary File Descriptor library. + + 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 3 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., 51 Franklin Street - Fifth Floor, Boston, + MA 02110-1301, USA. */ + +/* Maximum size of the arguments that can be stored in a PRPSINFO + structure. */ + +#define ELF_PRARGSZ (80) + +/* Internal structure which holds information to be included in the + PRPSINFO section of the corefile. + + This is an "internal" structure in the sense that it should be used to + pass information to BFD (via the `elfcore_write_prpsinfo', for example), + so things like endianess shouldn't be an issue. This structure will + eventually be converted in one of the `elf_external_*' structures + below. */ + +struct elf_internal_prpsinfo + { + char pr_state; /* Numeric process state. */ + char pr_sname; /* Char for pr_state. */ + char pr_zomb; /* Zombie. */ + char pr_nice; /* Nice val. */ + unsigned long pr_flag; /* Flags. */ + unsigned int pr_uid; + unsigned int pr_gid; + int pr_pid, pr_ppid, pr_pgrp, pr_sid; + /* Lots missing */ + char pr_fname[16]; /* Filename of executable. */ + char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ + }; + +/* External 32-bit structure for PRPSINFO. This structure is ABI-defined, + thus we choose to use char arrays here in order to avoid dealing with + different types in different architectures. + + This structure will ultimately be written in the corefile's note section, + as the PRPSINFO. */ + +struct elf_external_prpsinfo32 + { + char pr_state; /* Numeric process state. */ + char pr_sname; /* Char for pr_state. */ + char pr_zomb; /* Zombie. */ + char pr_nice; /* Nice val. */ + char pr_flag[4]; /* Flags. */ + char pr_uid[2]; + char pr_gid[2]; + char pr_pid[4]; + char pr_ppid[4]; + char pr_pgrp[4]; + char pr_sid[4]; + /* Lots missing */ + char pr_fname[16]; /* Filename of executable. */ + char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ + }; + +/* Helper macro to copy (properly handling endianess) things from the + `elf_internal_prpsinfo' structure to the `elf_external_prpsinfo32' + structure. + + Note that FROM should be a pointer, and TO should be the explicit type. */ + +#define PRPSINFO32_COPY_FIELDS(abfd, from, to) \ + do \ + { \ + H_PUT_8 (abfd, from->pr_state, &to.pr_state); \ + H_PUT_8 (abfd, from->pr_sname, &to.pr_sname); \ + H_PUT_8 (abfd, from->pr_zomb, &to.pr_zomb); \ + H_PUT_8 (abfd, from->pr_nice, &to.pr_nice); \ + H_PUT_32 (abfd, from->pr_flag, to.pr_flag); \ + H_PUT_16 (abfd, from->pr_uid, to.pr_uid); \ + H_PUT_16 (abfd, from->pr_gid, to.pr_gid); \ + H_PUT_32 (abfd, from->pr_pid, to.pr_pid); \ + H_PUT_32 (abfd, from->pr_ppid, to.pr_ppid); \ + H_PUT_32 (abfd, from->pr_pgrp, to.pr_pgrp); \ + H_PUT_32 (abfd, from->pr_sid, to.pr_sid); \ + strncpy (to.pr_fname, from->pr_fname, sizeof (to.pr_fname)); \ + strncpy (to.pr_psargs, from->pr_psargs, sizeof (to.pr_psargs)); \ + } while (0) + +/* External 64-bit structure for PRPSINFO. This structure is ABI-defined, + thus we choose to use char arrays here in order to avoid dealing with + different types in different architectures. + + Differently from the 32-bit version, the PowerPC guys made our lives better + and used the same size as the other architectures. + + This structure will ultimately be written in the corefile's note section, + as the PRPSINFO. */ + +struct elf_external_prpsinfo64 + { + char pr_state; /* Numeric process state. */ + char pr_sname; /* Char for pr_state. */ + char pr_zomb; /* Zombie. */ + char pr_nice; /* Nice val. */ + char pr_flag[8]; /* Flags. */ + char gap[4]; + char pr_uid[4]; + char pr_gid[4]; + char pr_pid[4]; + char pr_ppid[4]; + char pr_pgrp[4]; + char pr_sid[4]; + /* Lots missing */ + char pr_fname[16]; /* Filename of executable. */ + char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ + }; + +/* Helper macro to copy (properly handling endianess) things from the + `elf_internal_prpsinfo' structure to the `elf_external_prpsinfo64' + structure. + + Note that FROM should be a pointer, and TO should be the explicit type. */ + +#define PRPSINFO64_COPY_FIELDS(abfd, from, to) \ + do \ + { \ + H_PUT_8 (abfd, from->pr_state, &to.pr_state); \ + H_PUT_8 (abfd, from->pr_sname, &to.pr_sname); \ + H_PUT_8 (abfd, from->pr_zomb, &to.pr_zomb); \ + H_PUT_8 (abfd, from->pr_nice, &to.pr_nice); \ + H_PUT_64 (abfd, from->pr_flag, to.pr_flag); \ + H_PUT_32 (abfd, from->pr_uid, to.pr_uid); \ + H_PUT_32 (abfd, from->pr_gid, to.pr_gid); \ + H_PUT_32 (abfd, from->pr_pid, to.pr_pid); \ + H_PUT_32 (abfd, from->pr_ppid, to.pr_ppid); \ + H_PUT_32 (abfd, from->pr_pgrp, to.pr_pgrp); \ + H_PUT_32 (abfd, from->pr_sid, to.pr_sid); \ + strncpy (to.pr_fname, from->pr_fname, sizeof (to.pr_fname)); \ + strncpy (to.pr_psargs, from->pr_psargs, sizeof (to.pr_psargs)); \ + } while (0) + +/* Process info. In the end we do provide typedefs for them. */ + +typedef struct elf_external_prpsinfo32 prpsinfo32_t; +typedef struct elf_external_prpsinfo64 prpsinfo64_t; diff --git a/bfd/elf.c b/bfd/elf.c index a92dd5d..4556386 100644 --- a/bfd/elf.c +++ b/bfd/elf.c @@ -44,6 +44,7 @@ SECTION #include "elf-bfd.h" #include "libiberty.h" #include "safe-ctype.h" +#include "elf-psinfo.h" #ifdef CORE_HEADER #include CORE_HEADER @@ -9062,16 +9063,16 @@ char * elfcore_write_prpsinfo (bfd *abfd, char *buf, int *bufsiz, - const char *fname, - const char *psargs) + const struct elf_internal_prpsinfo *input) { const struct elf_backend_data *bed = get_elf_backend_data (abfd); if (bed->elf_backend_write_core_note != NULL) { char *ret; + ret = (*bed->elf_backend_write_core_note) (abfd, buf, bufsiz, - NT_PRPSINFO, fname, psargs); + NT_PRPSINFO, input); if (ret != NULL) return ret; } @@ -9089,8 +9090,8 @@ elfcore_write_prpsinfo (bfd *abfd, #endif memset (&data, 0, sizeof (data)); - strncpy (data.pr_fname, fname, sizeof (data.pr_fname)); - strncpy (data.pr_psargs, psargs, sizeof (data.pr_psargs)); + strncpy (data.pr_fname, input->pr_fname, sizeof (data.pr_fname)); + strncpy (data.pr_psargs, input->pr_psargs, sizeof (data.pr_psargs)); return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, &data, sizeof (data)); } @@ -9101,13 +9102,13 @@ elfcore_write_prpsinfo (bfd *abfd, psinfo_t data; int note_type = NT_PSINFO; #else - prpsinfo_t data; + prpsinfo64_t data; int note_type = NT_PRPSINFO; #endif memset (&data, 0, sizeof (data)); - strncpy (data.pr_fname, fname, sizeof (data.pr_fname)); - strncpy (data.pr_psargs, psargs, sizeof (data.pr_psargs)); + strncpy (data.pr_fname, input->pr_fname, sizeof (data.pr_fname)); + strncpy (data.pr_psargs, input->pr_psargs, sizeof (data.pr_psargs)); return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, &data, sizeof (data)); } diff --git a/bfd/elf32-arm.c b/bfd/elf32-arm.c index fd7d26a..cacc895 100644 --- a/bfd/elf32-arm.c +++ b/bfd/elf32-arm.c @@ -30,6 +30,7 @@ #include "elf-nacl.h" #include "elf-vxworks.h" #include "elf/arm.h" +#include "elf-psinfo.h" /* Return the relocation section associated with NAME. HTAB is the bfd's elf32_arm_link_hash_entry. */ @@ -2004,17 +2005,19 @@ elf32_arm_nabi_write_core_note (bfd *abfd, char *buf, int *bufsiz, case NT_PRPSINFO: { - char data[124]; + const struct elf_internal_prpsinfo *prpsinfo; + struct elf_external_prpsinfo32 data; va_list ap; va_start (ap, note_type); - memset (data, 0, sizeof (data)); - strncpy (data + 28, va_arg (ap, const char *), 16); - strncpy (data + 44, va_arg (ap, const char *), 80); + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); va_end (ap); + memset (&data, 0, sizeof (data)); + PRPSINFO32_COPY_FIELDS (abfd, prpsinfo, data); + return elfcore_write_note (abfd, buf, bufsiz, - "CORE", note_type, data, sizeof (data)); + "CORE", note_type, &data, sizeof (data)); } case NT_PRSTATUS: diff --git a/bfd/elf32-i386.c b/bfd/elf32-i386.c index a188cec..4a14fc9 100644 --- a/bfd/elf32-i386.c +++ b/bfd/elf32-i386.c @@ -31,6 +31,10 @@ #include "objalloc.h" #include "hashtab.h" #include "dwarf2.h" +#include "elf-bfd.h" +#include "elf-psinfo.h" + +#include <stdarg.h> /* 386 uses REL relocations instead of RELA. */ #define USE_REL 1 @@ -500,6 +504,43 @@ elf_i386_grok_psinfo (bfd *abfd, Elf_Internal_Note *note) return TRUE; } + +static char * +elf_i386_write_core_note (bfd *abfd, char *buf, int *bufsiz, + int note_type, ...) +{ + va_list ap; + + switch (note_type) + { + default: + return NULL; + + case NT_PRPSINFO: + { + const struct elf_internal_prpsinfo *prpsinfo; + struct elf_external_prpsinfo32 data; + + va_start (ap, note_type); + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); + va_end (ap); + + memset (&data, 0, sizeof (data)); + PRPSINFO32_COPY_FIELDS (abfd, prpsinfo, data); + + return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, + &data, sizeof (data)); + } + /* NOTREACHED */ + + case NT_PRSTATUS: + /* FIXME: For now, to avoid the inclusion of the "CORE_HEADER", we + return NULL and delegate this to elfcore_write_prstatus. */ + return NULL; + } + /* NOTREACHED */ +} + \f /* Functions for the i386 ELF linker. @@ -5140,6 +5181,7 @@ elf_i386_add_symbol_hook (bfd * abfd, #define elf_backend_gc_sweep_hook elf_i386_gc_sweep_hook #define elf_backend_grok_prstatus elf_i386_grok_prstatus #define elf_backend_grok_psinfo elf_i386_grok_psinfo +#define elf_backend_write_core_note elf_i386_write_core_note #define elf_backend_reloc_type_class elf_i386_reloc_type_class #define elf_backend_relocate_section elf_i386_relocate_section #define elf_backend_size_dynamic_sections elf_i386_size_dynamic_sections diff --git a/bfd/elf32-ppc.c b/bfd/elf32-ppc.c index 5241926..199affa 100644 --- a/bfd/elf32-ppc.c +++ b/bfd/elf32-ppc.c @@ -37,6 +37,7 @@ #include "elf32-ppc.h" #include "elf-vxworks.h" #include "dwarf2.h" +#include "elf-psinfo.h" typedef enum split16_format_type { @@ -2212,6 +2213,61 @@ ppc_elf_grok_psinfo (bfd *abfd, Elf_Internal_Note *note) return TRUE; } +/* External 32-bit PPC structure for PRPSINFO. This structure is ABI-defined, + thus we choose to use char arrays here in order to avoid dealing with + different types in different architectures. + + The reason why we have a different structure only for PPC is because + on this architecture (and *only* here!) the size of 32-bit structure + changes. This is due to the different sizes of `pr_uid' and `pr_gid', + which on non-PPC architectures are declared as `short int' and on PPC + architectures are declared as `int'. + + This structure will ultimately be written in the corefile's note section, + as the PRPSINFO. */ + +struct elf_external_ppc_prpsinfo32 + { + char pr_state; /* Numeric process state. */ + char pr_sname; /* Char for pr_state. */ + char pr_zomb; /* Zombie. */ + char pr_nice; /* Nice val. */ + char pr_flag[4]; /* Flags. */ + char pr_uid[4]; + char pr_gid[4]; + char pr_pid[4]; + char pr_ppid[4]; + char pr_pgrp[4]; + char pr_sid[4]; + /* Lots missing */ + char pr_fname[16]; /* Filename of executable. */ + char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ + }; + +/* Helper macro to copy (properly handling endianess) things from the + `elf_internal_prpsinfo' structure to the `elf_external_ppc_prpsinfo32' + structure. + + Note that FROM should be a pointer, and TO should be the explicit type. */ + +#define PRPSINFO32_PPC_COPY_FIELDS(abfd, from, to) \ + do \ + { \ + H_PUT_8 (abfd, from->pr_state, &to.pr_state); \ + H_PUT_8 (abfd, from->pr_sname, &to.pr_sname); \ + H_PUT_8 (abfd, from->pr_zomb, &to.pr_zomb); \ + H_PUT_8 (abfd, from->pr_nice, &to.pr_nice); \ + H_PUT_32 (abfd, from->pr_flag, to.pr_flag); \ + H_PUT_32 (abfd, from->pr_uid, to.pr_uid); \ + H_PUT_32 (abfd, from->pr_gid, to.pr_gid); \ + H_PUT_32 (abfd, from->pr_pid, to.pr_pid); \ + H_PUT_32 (abfd, from->pr_ppid, to.pr_ppid); \ + H_PUT_32 (abfd, from->pr_pgrp, to.pr_pgrp); \ + H_PUT_32 (abfd, from->pr_sid, to.pr_sid); \ + strncpy (to.pr_fname, from->pr_fname, sizeof (to.pr_fname)); \ + strncpy (to.pr_psargs, from->pr_psargs, sizeof (to.pr_psargs)); \ + } while (0) + static char * ppc_elf_write_core_note (bfd *abfd, char *buf, int *bufsiz, int note_type, ...) { @@ -2222,16 +2278,19 @@ ppc_elf_write_core_note (bfd *abfd, char *buf, int *bufsiz, int note_type, ...) case NT_PRPSINFO: { - char data[128]; + const struct elf_internal_prpsinfo *prpsinfo; + struct elf_external_ppc_prpsinfo32 data; va_list ap; va_start (ap, note_type); - memset (data, 0, sizeof (data)); - strncpy (data + 32, va_arg (ap, const char *), 16); - strncpy (data + 48, va_arg (ap, const char *), 80); + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); va_end (ap); + + memset (&data, 0, sizeof (data)); + PRPSINFO32_PPC_COPY_FIELDS (abfd, prpsinfo, data); + return elfcore_write_note (abfd, buf, bufsiz, - "CORE", note_type, data, sizeof (data)); + "CORE", note_type, &data, sizeof (data)); } case NT_PRSTATUS: diff --git a/bfd/elf64-ppc.c b/bfd/elf64-ppc.c index 10b6f9d..4eda989 100644 --- a/bfd/elf64-ppc.c +++ b/bfd/elf64-ppc.c @@ -34,6 +34,7 @@ #include "elf-bfd.h" #include "elf/ppc64.h" #include "elf64-ppc.h" +#include "elf-psinfo.h" #include "dwarf2.h" static bfd_reloc_status_type ppc64_elf_ha_reloc @@ -2718,16 +2719,19 @@ ppc64_elf_write_core_note (bfd *abfd, char *buf, int *bufsiz, int note_type, case NT_PRPSINFO: { - char data[136]; + const struct elf_internal_prpsinfo *prpsinfo; + struct elf_external_prpsinfo64 data; va_list ap; va_start (ap, note_type); - memset (data, 0, sizeof (data)); - strncpy (data + 40, va_arg (ap, const char *), 16); - strncpy (data + 56, va_arg (ap, const char *), 80); + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); va_end (ap); + + memset (&data, 0, sizeof (data)); + PRPSINFO64_COPY_FIELDS (abfd, prpsinfo, data); + return elfcore_write_note (abfd, buf, bufsiz, - "CORE", note_type, data, sizeof (data)); + "CORE", note_type, &data, sizeof (data)); } case NT_PRSTATUS: diff --git a/bfd/elf64-x86-64.c b/bfd/elf64-x86-64.c index 283681c..2c9939d 100644 --- a/bfd/elf64-x86-64.c +++ b/bfd/elf64-x86-64.c @@ -32,11 +32,13 @@ #include "hashtab.h" #include "dwarf2.h" #include "libiberty.h" +#include "elf-psinfo.h" + +#include <stdarg.h> #include "elf/x86-64.h" #ifdef CORE_HEADER -#include <stdarg.h> #include CORE_HEADER #endif @@ -415,14 +417,13 @@ elf_x86_64_grok_psinfo (bfd *abfd, Elf_Internal_Note *note) return TRUE; } -#ifdef CORE_HEADER static char * elf_x86_64_write_core_note (bfd *abfd, char *buf, int *bufsiz, int note_type, ...) { const struct elf_backend_data *bed = get_elf_backend_data (abfd); va_list ap; - const char *fname, *psargs; + const struct elf_internal_prpsinfo *prpsinfo; long pid; int cursig; const void *gregs; @@ -434,27 +435,28 @@ elf_x86_64_write_core_note (bfd *abfd, char *buf, int *bufsiz, case NT_PRPSINFO: va_start (ap, note_type); - fname = va_arg (ap, const char *); - psargs = va_arg (ap, const char *); + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); va_end (ap); if (bed->s->elfclass == ELFCLASS32) { - prpsinfo32_t data; - memset (&data, 0, sizeof (data)); - strncpy (data.pr_fname, fname, sizeof (data.pr_fname)); - strncpy (data.pr_psargs, psargs, sizeof (data.pr_psargs)); + struct elf_external_prpsinfo32 data32; + + memset (&data32, 0, sizeof (data32)); + PRPSINFO32_COPY_FIELDS (abfd, prpsinfo, data32); + return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, - &data, sizeof (data)); + &data32, sizeof (data32)); } else { - prpsinfo64_t data; - memset (&data, 0, sizeof (data)); - strncpy (data.pr_fname, fname, sizeof (data.pr_fname)); - strncpy (data.pr_psargs, psargs, sizeof (data.pr_psargs)); + struct elf_external_prpsinfo64 data64; + + memset (&data64, 0, sizeof (data64)); + PRPSINFO64_COPY_FIELDS (abfd, prpsinfo, data64); + return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, - &data, sizeof (data)); + &data64, sizeof (data64)); } /* NOTREACHED */ @@ -501,7 +503,7 @@ elf_x86_64_write_core_note (bfd *abfd, char *buf, int *bufsiz, } /* NOTREACHED */ } -#endif + \f /* Functions for the x86-64 ELF linker. */ @@ -5225,9 +5227,7 @@ static const struct bfd_elf_special_section #define elf_backend_gc_sweep_hook elf_x86_64_gc_sweep_hook #define elf_backend_grok_prstatus elf_x86_64_grok_prstatus #define elf_backend_grok_psinfo elf_x86_64_grok_psinfo -#ifdef CORE_HEADER #define elf_backend_write_core_note elf_x86_64_write_core_note -#endif #define elf_backend_reloc_type_class elf_x86_64_reloc_type_class #define elf_backend_relocate_section elf_x86_64_relocate_section #define elf_backend_size_dynamic_sections elf_x86_64_size_dynamic_sections diff --git a/bfd/hosts/x86-64linux.h b/bfd/hosts/x86-64linux.h index 78be09a..6070978 100644 --- a/bfd/hosts/x86-64linux.h +++ b/bfd/hosts/x86-64linux.h @@ -43,11 +43,6 @@ typedef unsigned long long int uint64_t; /* Unsigned 64-bit integer aligned to 8 bytes. */ typedef uint64_t __attribute__ ((__aligned__ (8))) a8_uint64_t; -#undef HAVE_PRPSINFO32_T -#define HAVE_PRPSINFO32_T -#undef HAVE_PRPSINFO32_T_PR_PID -#define HAVE_PRPSINFO32_T_PR_PID - #undef HAVE_PRSTATUS32_T #define HAVE_PRSTATUS32_T @@ -191,36 +186,6 @@ struct elf_prstatus64 int pr_fpvalid; /* True if math copro being used. */ }; -struct elf_prpsinfo32 - { - char pr_state; /* Numeric process state. */ - char pr_sname; /* Char for pr_state. */ - char pr_zomb; /* Zombie. */ - char pr_nice; /* Nice val. */ - unsigned int pr_flag; /* Flags. */ - unsigned short int pr_uid; - unsigned short int pr_gid; - int pr_pid, pr_ppid, pr_pgrp, pr_sid; - /* Lots missing */ - char pr_fname[16]; /* Filename of executable. */ - char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ - }; - -struct elf_prpsinfo64 - { - char pr_state; /* Numeric process state. */ - char pr_sname; /* Char for pr_state. */ - char pr_zomb; /* Zombie. */ - char pr_nice; /* Nice val. */ - a8_uint64_t pr_flag; /* Flags. */ - unsigned int pr_uid; - unsigned int pr_gid; - int pr_pid, pr_ppid, pr_pgrp, pr_sid; - /* Lots missing */ - char pr_fname[16]; /* Filename of executable. */ - char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ - }; - /* The rest of this file provides the types for emulation of the Solaris <proc_service.h> interfaces that should be implemented by users of libthread_db. */ @@ -229,5 +194,3 @@ struct elf_prpsinfo64 typedef struct elf_prstatus32 prstatus32_t; typedef struct elf_prstatusx32 prstatusx32_t; typedef struct elf_prstatus64 prstatus64_t; -typedef struct elf_prpsinfo32 prpsinfo32_t; -typedef struct elf_prpsinfo64 prpsinfo64_t; -- 1.7.7.6 ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: [PATCH/RFC 01/02 v2] Refactor PRPSINFO handling on Binutils 2012-12-18 19:19 ` Sergio Durigan Junior @ 2012-12-18 19:43 ` Jan Kratochvil 2012-12-30 1:50 ` Sergio Durigan Junior 0 siblings, 1 reply; 21+ messages in thread From: Jan Kratochvil @ 2012-12-18 19:43 UTC (permalink / raw) To: Sergio Durigan Junior Cc: Binutils Development, GDB Patches, Pedro Alves, H.J. Lu On Tue, 18 Dec 2012 20:19:06 +0100, Sergio Durigan Junior wrote: > On Tuesday, December 18 2012, Jan Kratochvil wrote: > The patch covers the existing targets that already implemented the > *_write_core_note function, with the exception of i386 which is a new > implementation. OK. > I disagree. As I said above, the patch covers all targets that were > already implementing *_write_core_note. If some new target decides to > implement it, it is just a matter of including "elf-psinfo.h" and using > the right structures. OK. > As I said above, I disagree. The header file is useful for having a > single place which defines those structures (i.e., i386, x32 and ARM use > the same elf_external_prpsinfo32 strucutre). That is a matter of opinion -> bfd maintainers, whether to copy the definition into each arch file or have some common header file for it despite it is compatible only with some of the archs. > Also, the header is useful > for including in the BFD clients (I'm thiking "GDB" here) which can use > the elf_internal_prpsinfo strucuture to pass information to BFD. I forgot about elf_internal_prpsinfo, that one needs to be included in BFD applications (like GDB). But elf_internal_prpsinfo should be then in a different file, maybe bfd.h? (I do not know much.) GDB does not need to know the elf_external_* layouts so those should not be defined in header file(s) available to GDB. Thanks, Jan ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: [PATCH/RFC 01/02 v2] Refactor PRPSINFO handling on Binutils 2012-12-18 19:43 ` Jan Kratochvil @ 2012-12-30 1:50 ` Sergio Durigan Junior 2013-01-01 14:30 ` Jan Kratochvil 0 siblings, 1 reply; 21+ messages in thread From: Sergio Durigan Junior @ 2012-12-30 1:50 UTC (permalink / raw) To: Jan Kratochvil; +Cc: Binutils Development, GDB Patches, Pedro Alves, H.J. Lu On Tuesday, December 18 2012, Jan Kratochvil wrote: > On Tue, 18 Dec 2012 20:19:06 +0100, Sergio Durigan Junior wrote: >> As I said above, I disagree. The header file is useful for having a >> single place which defines those structures (i.e., i386, x32 and ARM use >> the same elf_external_prpsinfo32 strucutre). > > That is a matter of opinion -> bfd maintainers, whether to copy the definition > into each arch file or have some common header file for it despite it is > compatible only with some of the archs. I agree it's a matter of opinion, I will wait until one of the maintainers say something about it. >> Also, the header is useful >> for including in the BFD clients (I'm thiking "GDB" here) which can use >> the elf_internal_prpsinfo strucuture to pass information to BFD. > > I forgot about elf_internal_prpsinfo, that one needs to be included in BFD > applications (like GDB). But elf_internal_prpsinfo should be then in > a different file, maybe bfd.h? (I do not know much.) GDB does not need to > know the elf_external_* layouts so those should not be defined in header > file(s) available to GDB. Agreed, this new version of the patch reflects the change. I decided to move the definition of elf_internal_prpsinfo to elf-bfd.h, it's a better place IMO. I will also send an updated version of the GDB patch which doesn't include elf-psinfo.h. Thanks, -- Sergio 2012-12-29 Sergio Durigan Junior <sergiodj@redhat.com> * Makefile.in (BUILD_CFILES): Add `elf-psinfo.h'. * elf-bfd.h (ELF_PRARGSZ): New conditional definition. (elf_internal_prpsinfo): New structure declaration. (elfcore_write_prpsinfo): Change prototype, accepting `elf_internal_prpsinfo' as argument. * elf-psinfo.h: New file. * elf.c (elfcore_write_prpsinfo): Change prototype, accepting `elf_internal_prpsinfo' as argument. Rewrite parts of the code to make use of the new argument. * elf32-arm.c: Include `elf-psinfo.h'. (elf32_arm_nabi_write_core_note): Refactor `NT_PRPSINFO' case. * elf32-i386.c: Include `elf-bfd.h', `elf-psinfo.h' and `stdarg.h'. (elf_i386_write_core_note): New function. * elf32-ppc.c: Include `elf-psinfo.h'. (elf_external_ppc_prpsinfo32): New structure declaration. (ppc_elf_write_core_note): Refactor `NT_PRPSINFO' case. * elf64-ppc.c: Include `elf-psinfo.h'. (ppc64_elf_write_core_note): Refactor `NT_PRPSINFO' case. * elf64-x86-64.c: Include `elf-psinfo.h'. Include `stdarg.h' unconditionally. (elf_x86_64_write_core_note): Remove `#ifdef CORE_HEADER', making the function unconditionally available. Refactor `NT_PRPSINFO' case. * hosts/x86-64linux.h (HAVE_PRPSINFO32_T, HAVE_PRPSINFO32_T_PR_PID, elf_prpsinfo32, elf_prpsinfo64, prpsinfo32_t, prpsinfo64_t): Remove definitions, moving some of them to `elf-psinfo.h'. --- bfd/Makefile.in | 2 +- bfd/elf-bfd.h | 38 +++++++++++++- bfd/elf-psinfo.h | 133 +++++++++++++++++++++++++++++++++++++++++++++++ bfd/elf.c | 17 +++--- bfd/elf32-arm.c | 13 +++-- bfd/elf32-i386.c | 42 +++++++++++++++ bfd/elf32-ppc.c | 70 +++++++++++++++++++++++-- bfd/elf64-ppc.c | 14 +++-- bfd/elf64-x86-64.c | 36 ++++++------ bfd/hosts/x86-64linux.h | 37 ------------- 10 files changed, 322 insertions(+), 80 deletions(-) create mode 100644 bfd/elf-psinfo.h diff --git a/bfd/Makefile.in b/bfd/Makefile.in index c51c342..adea836 100644 --- a/bfd/Makefile.in +++ b/bfd/Makefile.in @@ -1068,7 +1068,7 @@ BUILD_CFILES = \ CFILES = $(SOURCE_CFILES) $(BUILD_CFILES) SOURCE_HFILES = \ aout-target.h aoutf1.h aoutx.h coffcode.h coffswap.h ecoffswap.h \ - elf-bfd.h elf-hppa.h elf32-hppa.h \ + elf-bfd.h elf-psinfo.h elf-hppa.h elf32-hppa.h \ elf64-hppa.h elfcode.h elfcore.h \ freebsd.h genlink.h go32stub.h \ libaout.h libbfd.h libcoff.h libecoff.h libhppa.h libieee.h \ diff --git a/bfd/elf-bfd.h b/bfd/elf-bfd.h index b8d82b1..90ced7a 100644 --- a/bfd/elf-bfd.h +++ b/bfd/elf-bfd.h @@ -1722,6 +1722,38 @@ struct elf_obj_tdata (elf_known_obj_attributes (bfd) [OBJ_ATTR_PROC]) #define elf_other_obj_attributes_proc(bfd) \ (elf_other_obj_attributes (bfd) [OBJ_ATTR_PROC]) + +#ifndef ELF_PRARGSZ +/* Maximum size of the arguments that can be stored in a PRPSINFO + structure. */ + +#define ELF_PRARGSZ (80) +#endif + +/* Internal structure which holds information to be included in the + PRPSINFO section of the corefile. + + This is an "internal" structure in the sense that it should be used to + pass information to BFD (via the `elfcore_write_prpsinfo', for example), + so things like endianess shouldn't be an issue. This structure will + eventually be converted in one of the `elf_external_*' structures + below. */ + +struct elf_internal_prpsinfo + { + char pr_state; /* Numeric process state. */ + char pr_sname; /* Char for pr_state. */ + char pr_zomb; /* Zombie. */ + char pr_nice; /* Nice val. */ + unsigned long pr_flag; /* Flags. */ + unsigned int pr_uid; + unsigned int pr_gid; + int pr_pid, pr_ppid, pr_pgrp, pr_sid; + /* Lots missing */ + char pr_fname[16]; /* Filename of executable. */ + char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ + }; + \f extern void _bfd_elf_swap_verdef_in (bfd *, const Elf_External_Verdef *, Elf_Internal_Verdef *); @@ -2234,11 +2266,15 @@ extern bfd_boolean bfd_elf_lookup_section_flags extern Elf_Internal_Phdr * _bfd_elf_find_segment_containing_section (bfd * abfd, asection * section); +/* Forward declaration of prpsinfo. See `elf-psinfo.h' for more details. */ + +struct elf_internal_prpsinfo; + /* Exported interface for writing elf corefile notes. */ extern char *elfcore_write_note (bfd *, char *, int *, const char *, int, const void *, int); extern char *elfcore_write_prpsinfo - (bfd *, char *, int *, const char *, const char *); + (bfd *, char *, int *, const struct elf_internal_prpsinfo *); extern char *elfcore_write_prstatus (bfd *, char *, int *, long, int, const void *); extern char * elfcore_write_pstatus diff --git a/bfd/elf-psinfo.h b/bfd/elf-psinfo.h new file mode 100644 index 0000000..ddf3aa1 --- /dev/null +++ b/bfd/elf-psinfo.h @@ -0,0 +1,133 @@ +/* Declarations for PRPSINFO structures under ELF on GNU/Linux. + Copyright 2012 Free Software Foundation, Inc. + + This file is part of BFD, the Binary File Descriptor library. + + 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 3 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., 51 Franklin Street - Fifth Floor, Boston, + MA 02110-1301, USA. */ + +#ifndef ELF_PRARGSZ +/* Maximum size of the arguments that can be stored in a PRPSINFO + structure. */ + +#define ELF_PRARGSZ (80) +#endif + +/* External 32-bit structure for PRPSINFO. This structure is ABI-defined, + thus we choose to use char arrays here in order to avoid dealing with + different types in different architectures. + + This structure will ultimately be written in the corefile's note section, + as the PRPSINFO. */ + +struct elf_external_prpsinfo32 + { + char pr_state; /* Numeric process state. */ + char pr_sname; /* Char for pr_state. */ + char pr_zomb; /* Zombie. */ + char pr_nice; /* Nice val. */ + char pr_flag[4]; /* Flags. */ + char pr_uid[2]; + char pr_gid[2]; + char pr_pid[4]; + char pr_ppid[4]; + char pr_pgrp[4]; + char pr_sid[4]; + /* Lots missing */ + char pr_fname[16]; /* Filename of executable. */ + char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ + }; + +/* Helper macro to copy (properly handling endianess) things from the + `elf_internal_prpsinfo' structure to the `elf_external_prpsinfo32' + structure. + + Note that FROM should be a pointer, and TO should be the explicit type. */ + +#define PRPSINFO32_COPY_FIELDS(abfd, from, to) \ + do \ + { \ + H_PUT_8 (abfd, from->pr_state, &to.pr_state); \ + H_PUT_8 (abfd, from->pr_sname, &to.pr_sname); \ + H_PUT_8 (abfd, from->pr_zomb, &to.pr_zomb); \ + H_PUT_8 (abfd, from->pr_nice, &to.pr_nice); \ + H_PUT_32 (abfd, from->pr_flag, to.pr_flag); \ + H_PUT_16 (abfd, from->pr_uid, to.pr_uid); \ + H_PUT_16 (abfd, from->pr_gid, to.pr_gid); \ + H_PUT_32 (abfd, from->pr_pid, to.pr_pid); \ + H_PUT_32 (abfd, from->pr_ppid, to.pr_ppid); \ + H_PUT_32 (abfd, from->pr_pgrp, to.pr_pgrp); \ + H_PUT_32 (abfd, from->pr_sid, to.pr_sid); \ + strncpy (to.pr_fname, from->pr_fname, sizeof (to.pr_fname)); \ + strncpy (to.pr_psargs, from->pr_psargs, sizeof (to.pr_psargs)); \ + } while (0) + +/* External 64-bit structure for PRPSINFO. This structure is ABI-defined, + thus we choose to use char arrays here in order to avoid dealing with + different types in different architectures. + + Differently from the 32-bit version, the PowerPC guys made our lives better + and used the same size as the other architectures. + + This structure will ultimately be written in the corefile's note section, + as the PRPSINFO. */ + +struct elf_external_prpsinfo64 + { + char pr_state; /* Numeric process state. */ + char pr_sname; /* Char for pr_state. */ + char pr_zomb; /* Zombie. */ + char pr_nice; /* Nice val. */ + char pr_flag[8]; /* Flags. */ + char gap[4]; + char pr_uid[4]; + char pr_gid[4]; + char pr_pid[4]; + char pr_ppid[4]; + char pr_pgrp[4]; + char pr_sid[4]; + /* Lots missing */ + char pr_fname[16]; /* Filename of executable. */ + char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ + }; + +/* Helper macro to copy (properly handling endianess) things from the + `elf_internal_prpsinfo' structure to the `elf_external_prpsinfo64' + structure. + + Note that FROM should be a pointer, and TO should be the explicit type. */ + +#define PRPSINFO64_COPY_FIELDS(abfd, from, to) \ + do \ + { \ + H_PUT_8 (abfd, from->pr_state, &to.pr_state); \ + H_PUT_8 (abfd, from->pr_sname, &to.pr_sname); \ + H_PUT_8 (abfd, from->pr_zomb, &to.pr_zomb); \ + H_PUT_8 (abfd, from->pr_nice, &to.pr_nice); \ + H_PUT_64 (abfd, from->pr_flag, to.pr_flag); \ + H_PUT_32 (abfd, from->pr_uid, to.pr_uid); \ + H_PUT_32 (abfd, from->pr_gid, to.pr_gid); \ + H_PUT_32 (abfd, from->pr_pid, to.pr_pid); \ + H_PUT_32 (abfd, from->pr_ppid, to.pr_ppid); \ + H_PUT_32 (abfd, from->pr_pgrp, to.pr_pgrp); \ + H_PUT_32 (abfd, from->pr_sid, to.pr_sid); \ + strncpy (to.pr_fname, from->pr_fname, sizeof (to.pr_fname)); \ + strncpy (to.pr_psargs, from->pr_psargs, sizeof (to.pr_psargs)); \ + } while (0) + +/* Process info. In the end we do provide typedefs for them. */ + +typedef struct elf_external_prpsinfo32 prpsinfo32_t; +typedef struct elf_external_prpsinfo64 prpsinfo64_t; diff --git a/bfd/elf.c b/bfd/elf.c index 17e9ad4..aad8b27 100644 --- a/bfd/elf.c +++ b/bfd/elf.c @@ -44,6 +44,7 @@ SECTION #include "elf-bfd.h" #include "libiberty.h" #include "safe-ctype.h" +#include "elf-psinfo.h" #ifdef CORE_HEADER #include CORE_HEADER @@ -9063,16 +9064,16 @@ char * elfcore_write_prpsinfo (bfd *abfd, char *buf, int *bufsiz, - const char *fname, - const char *psargs) + const struct elf_internal_prpsinfo *input) { const struct elf_backend_data *bed = get_elf_backend_data (abfd); if (bed->elf_backend_write_core_note != NULL) { char *ret; + ret = (*bed->elf_backend_write_core_note) (abfd, buf, bufsiz, - NT_PRPSINFO, fname, psargs); + NT_PRPSINFO, input); if (ret != NULL) return ret; } @@ -9090,8 +9091,8 @@ elfcore_write_prpsinfo (bfd *abfd, #endif memset (&data, 0, sizeof (data)); - strncpy (data.pr_fname, fname, sizeof (data.pr_fname)); - strncpy (data.pr_psargs, psargs, sizeof (data.pr_psargs)); + strncpy (data.pr_fname, input->pr_fname, sizeof (data.pr_fname)); + strncpy (data.pr_psargs, input->pr_psargs, sizeof (data.pr_psargs)); return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, &data, sizeof (data)); } @@ -9102,13 +9103,13 @@ elfcore_write_prpsinfo (bfd *abfd, psinfo_t data; int note_type = NT_PSINFO; #else - prpsinfo_t data; + prpsinfo64_t data; int note_type = NT_PRPSINFO; #endif memset (&data, 0, sizeof (data)); - strncpy (data.pr_fname, fname, sizeof (data.pr_fname)); - strncpy (data.pr_psargs, psargs, sizeof (data.pr_psargs)); + strncpy (data.pr_fname, input->pr_fname, sizeof (data.pr_fname)); + strncpy (data.pr_psargs, input->pr_psargs, sizeof (data.pr_psargs)); return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, &data, sizeof (data)); } diff --git a/bfd/elf32-arm.c b/bfd/elf32-arm.c index e2f8a96..a354602 100644 --- a/bfd/elf32-arm.c +++ b/bfd/elf32-arm.c @@ -30,6 +30,7 @@ #include "elf-nacl.h" #include "elf-vxworks.h" #include "elf/arm.h" +#include "elf-psinfo.h" /* Return the relocation section associated with NAME. HTAB is the bfd's elf32_arm_link_hash_entry. */ @@ -2004,17 +2005,19 @@ elf32_arm_nabi_write_core_note (bfd *abfd, char *buf, int *bufsiz, case NT_PRPSINFO: { - char data[124]; + const struct elf_internal_prpsinfo *prpsinfo; + struct elf_external_prpsinfo32 data; va_list ap; va_start (ap, note_type); - memset (data, 0, sizeof (data)); - strncpy (data + 28, va_arg (ap, const char *), 16); - strncpy (data + 44, va_arg (ap, const char *), 80); + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); va_end (ap); + memset (&data, 0, sizeof (data)); + PRPSINFO32_COPY_FIELDS (abfd, prpsinfo, data); + return elfcore_write_note (abfd, buf, bufsiz, - "CORE", note_type, data, sizeof (data)); + "CORE", note_type, &data, sizeof (data)); } case NT_PRSTATUS: diff --git a/bfd/elf32-i386.c b/bfd/elf32-i386.c index f76c7a7..0198eef 100644 --- a/bfd/elf32-i386.c +++ b/bfd/elf32-i386.c @@ -31,6 +31,10 @@ #include "objalloc.h" #include "hashtab.h" #include "dwarf2.h" +#include "elf-bfd.h" +#include "elf-psinfo.h" + +#include <stdarg.h> /* 386 uses REL relocations instead of RELA. */ #define USE_REL 1 @@ -500,6 +504,43 @@ elf_i386_grok_psinfo (bfd *abfd, Elf_Internal_Note *note) return TRUE; } + +static char * +elf_i386_write_core_note (bfd *abfd, char *buf, int *bufsiz, + int note_type, ...) +{ + va_list ap; + + switch (note_type) + { + default: + return NULL; + + case NT_PRPSINFO: + { + const struct elf_internal_prpsinfo *prpsinfo; + struct elf_external_prpsinfo32 data; + + va_start (ap, note_type); + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); + va_end (ap); + + memset (&data, 0, sizeof (data)); + PRPSINFO32_COPY_FIELDS (abfd, prpsinfo, data); + + return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, + &data, sizeof (data)); + } + /* NOTREACHED */ + + case NT_PRSTATUS: + /* FIXME: For now, to avoid the inclusion of the "CORE_HEADER", we + return NULL and delegate this to elfcore_write_prstatus. */ + return NULL; + } + /* NOTREACHED */ +} + \f /* Functions for the i386 ELF linker. @@ -5042,6 +5083,7 @@ elf_i386_add_symbol_hook (bfd * abfd, #define elf_backend_gc_sweep_hook elf_i386_gc_sweep_hook #define elf_backend_grok_prstatus elf_i386_grok_prstatus #define elf_backend_grok_psinfo elf_i386_grok_psinfo +#define elf_backend_write_core_note elf_i386_write_core_note #define elf_backend_reloc_type_class elf_i386_reloc_type_class #define elf_backend_relocate_section elf_i386_relocate_section #define elf_backend_size_dynamic_sections elf_i386_size_dynamic_sections diff --git a/bfd/elf32-ppc.c b/bfd/elf32-ppc.c index 5241926..b239e5c 100644 --- a/bfd/elf32-ppc.c +++ b/bfd/elf32-ppc.c @@ -37,6 +37,7 @@ #include "elf32-ppc.h" #include "elf-vxworks.h" #include "dwarf2.h" +#include "elf-psinfo.h" typedef enum split16_format_type { @@ -1777,6 +1778,62 @@ static reloc_howto_type ppc_elf_howto_raw[] = { 0xffff, /* dst_mask */ FALSE), /* pcrel_offset */ }; + +/* External 32-bit PPC structure for PRPSINFO. This structure is ABI-defined, + thus we choose to use char arrays here in order to avoid dealing with + different types in different architectures. + + The reason why we have a different structure only for PPC is because + on this architecture (and *only* here!) the size of 32-bit structure + changes. This is due to the different sizes of `pr_uid' and `pr_gid', + which on non-PPC architectures are declared as `short int' and on PPC + architectures are declared as `int'. + + This structure will ultimately be written in the corefile's note section, + as the PRPSINFO. */ + +struct elf_external_ppc_prpsinfo32 + { + char pr_state; /* Numeric process state. */ + char pr_sname; /* Char for pr_state. */ + char pr_zomb; /* Zombie. */ + char pr_nice; /* Nice val. */ + char pr_flag[4]; /* Flags. */ + char pr_uid[4]; + char pr_gid[4]; + char pr_pid[4]; + char pr_ppid[4]; + char pr_pgrp[4]; + char pr_sid[4]; + /* Lots missing */ + char pr_fname[16]; /* Filename of executable. */ + char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ + }; + +/* Helper macro to copy (properly handling endianess) things from the + `elf_internal_prpsinfo' structure to the `elf_external_ppc_prpsinfo32' + structure. + + Note that FROM should be a pointer, and TO should be the explicit type. */ + +#define PRPSINFO32_PPC_COPY_FIELDS(abfd, from, to) \ + do \ + { \ + H_PUT_8 (abfd, from->pr_state, &to.pr_state); \ + H_PUT_8 (abfd, from->pr_sname, &to.pr_sname); \ + H_PUT_8 (abfd, from->pr_zomb, &to.pr_zomb); \ + H_PUT_8 (abfd, from->pr_nice, &to.pr_nice); \ + H_PUT_32 (abfd, from->pr_flag, to.pr_flag); \ + H_PUT_32 (abfd, from->pr_uid, to.pr_uid); \ + H_PUT_32 (abfd, from->pr_gid, to.pr_gid); \ + H_PUT_32 (abfd, from->pr_pid, to.pr_pid); \ + H_PUT_32 (abfd, from->pr_ppid, to.pr_ppid); \ + H_PUT_32 (abfd, from->pr_pgrp, to.pr_pgrp); \ + H_PUT_32 (abfd, from->pr_sid, to.pr_sid); \ + strncpy (to.pr_fname, from->pr_fname, sizeof (to.pr_fname)); \ + strncpy (to.pr_psargs, from->pr_psargs, sizeof (to.pr_psargs)); \ + } while (0) + \f /* Initialize the ppc_elf_howto_table, so that linear accesses can be done. */ @@ -2222,16 +2279,19 @@ ppc_elf_write_core_note (bfd *abfd, char *buf, int *bufsiz, int note_type, ...) case NT_PRPSINFO: { - char data[128]; + const struct elf_internal_prpsinfo *prpsinfo; + struct elf_external_ppc_prpsinfo32 data; va_list ap; va_start (ap, note_type); - memset (data, 0, sizeof (data)); - strncpy (data + 32, va_arg (ap, const char *), 16); - strncpy (data + 48, va_arg (ap, const char *), 80); + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); va_end (ap); + + memset (&data, 0, sizeof (data)); + PRPSINFO32_PPC_COPY_FIELDS (abfd, prpsinfo, data); + return elfcore_write_note (abfd, buf, bufsiz, - "CORE", note_type, data, sizeof (data)); + "CORE", note_type, &data, sizeof (data)); } case NT_PRSTATUS: diff --git a/bfd/elf64-ppc.c b/bfd/elf64-ppc.c index 10b6f9d..4eda989 100644 --- a/bfd/elf64-ppc.c +++ b/bfd/elf64-ppc.c @@ -34,6 +34,7 @@ #include "elf-bfd.h" #include "elf/ppc64.h" #include "elf64-ppc.h" +#include "elf-psinfo.h" #include "dwarf2.h" static bfd_reloc_status_type ppc64_elf_ha_reloc @@ -2718,16 +2719,19 @@ ppc64_elf_write_core_note (bfd *abfd, char *buf, int *bufsiz, int note_type, case NT_PRPSINFO: { - char data[136]; + const struct elf_internal_prpsinfo *prpsinfo; + struct elf_external_prpsinfo64 data; va_list ap; va_start (ap, note_type); - memset (data, 0, sizeof (data)); - strncpy (data + 40, va_arg (ap, const char *), 16); - strncpy (data + 56, va_arg (ap, const char *), 80); + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); va_end (ap); + + memset (&data, 0, sizeof (data)); + PRPSINFO64_COPY_FIELDS (abfd, prpsinfo, data); + return elfcore_write_note (abfd, buf, bufsiz, - "CORE", note_type, data, sizeof (data)); + "CORE", note_type, &data, sizeof (data)); } case NT_PRSTATUS: diff --git a/bfd/elf64-x86-64.c b/bfd/elf64-x86-64.c index 92bf991..c9bcf48 100644 --- a/bfd/elf64-x86-64.c +++ b/bfd/elf64-x86-64.c @@ -32,11 +32,13 @@ #include "hashtab.h" #include "dwarf2.h" #include "libiberty.h" +#include "elf-psinfo.h" + +#include <stdarg.h> #include "elf/x86-64.h" #ifdef CORE_HEADER -#include <stdarg.h> #include CORE_HEADER #endif @@ -415,14 +417,13 @@ elf_x86_64_grok_psinfo (bfd *abfd, Elf_Internal_Note *note) return TRUE; } -#ifdef CORE_HEADER static char * elf_x86_64_write_core_note (bfd *abfd, char *buf, int *bufsiz, int note_type, ...) { const struct elf_backend_data *bed = get_elf_backend_data (abfd); va_list ap; - const char *fname, *psargs; + const struct elf_internal_prpsinfo *prpsinfo; long pid; int cursig; const void *gregs; @@ -434,27 +435,28 @@ elf_x86_64_write_core_note (bfd *abfd, char *buf, int *bufsiz, case NT_PRPSINFO: va_start (ap, note_type); - fname = va_arg (ap, const char *); - psargs = va_arg (ap, const char *); + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); va_end (ap); if (bed->s->elfclass == ELFCLASS32) { - prpsinfo32_t data; - memset (&data, 0, sizeof (data)); - strncpy (data.pr_fname, fname, sizeof (data.pr_fname)); - strncpy (data.pr_psargs, psargs, sizeof (data.pr_psargs)); + struct elf_external_prpsinfo32 data32; + + memset (&data32, 0, sizeof (data32)); + PRPSINFO32_COPY_FIELDS (abfd, prpsinfo, data32); + return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, - &data, sizeof (data)); + &data32, sizeof (data32)); } else { - prpsinfo64_t data; - memset (&data, 0, sizeof (data)); - strncpy (data.pr_fname, fname, sizeof (data.pr_fname)); - strncpy (data.pr_psargs, psargs, sizeof (data.pr_psargs)); + struct elf_external_prpsinfo64 data64; + + memset (&data64, 0, sizeof (data64)); + PRPSINFO64_COPY_FIELDS (abfd, prpsinfo, data64); + return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, - &data, sizeof (data)); + &data64, sizeof (data64)); } /* NOTREACHED */ @@ -501,7 +503,7 @@ elf_x86_64_write_core_note (bfd *abfd, char *buf, int *bufsiz, } /* NOTREACHED */ } -#endif + \f /* Functions for the x86-64 ELF linker. */ @@ -5157,9 +5159,7 @@ static const struct bfd_elf_special_section #define elf_backend_gc_sweep_hook elf_x86_64_gc_sweep_hook #define elf_backend_grok_prstatus elf_x86_64_grok_prstatus #define elf_backend_grok_psinfo elf_x86_64_grok_psinfo -#ifdef CORE_HEADER #define elf_backend_write_core_note elf_x86_64_write_core_note -#endif #define elf_backend_reloc_type_class elf_x86_64_reloc_type_class #define elf_backend_relocate_section elf_x86_64_relocate_section #define elf_backend_size_dynamic_sections elf_x86_64_size_dynamic_sections diff --git a/bfd/hosts/x86-64linux.h b/bfd/hosts/x86-64linux.h index 78be09a..6070978 100644 --- a/bfd/hosts/x86-64linux.h +++ b/bfd/hosts/x86-64linux.h @@ -43,11 +43,6 @@ typedef unsigned long long int uint64_t; /* Unsigned 64-bit integer aligned to 8 bytes. */ typedef uint64_t __attribute__ ((__aligned__ (8))) a8_uint64_t; -#undef HAVE_PRPSINFO32_T -#define HAVE_PRPSINFO32_T -#undef HAVE_PRPSINFO32_T_PR_PID -#define HAVE_PRPSINFO32_T_PR_PID - #undef HAVE_PRSTATUS32_T #define HAVE_PRSTATUS32_T @@ -191,36 +186,6 @@ struct elf_prstatus64 int pr_fpvalid; /* True if math copro being used. */ }; -struct elf_prpsinfo32 - { - char pr_state; /* Numeric process state. */ - char pr_sname; /* Char for pr_state. */ - char pr_zomb; /* Zombie. */ - char pr_nice; /* Nice val. */ - unsigned int pr_flag; /* Flags. */ - unsigned short int pr_uid; - unsigned short int pr_gid; - int pr_pid, pr_ppid, pr_pgrp, pr_sid; - /* Lots missing */ - char pr_fname[16]; /* Filename of executable. */ - char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ - }; - -struct elf_prpsinfo64 - { - char pr_state; /* Numeric process state. */ - char pr_sname; /* Char for pr_state. */ - char pr_zomb; /* Zombie. */ - char pr_nice; /* Nice val. */ - a8_uint64_t pr_flag; /* Flags. */ - unsigned int pr_uid; - unsigned int pr_gid; - int pr_pid, pr_ppid, pr_pgrp, pr_sid; - /* Lots missing */ - char pr_fname[16]; /* Filename of executable. */ - char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ - }; - /* The rest of this file provides the types for emulation of the Solaris <proc_service.h> interfaces that should be implemented by users of libthread_db. */ @@ -229,5 +194,3 @@ struct elf_prpsinfo64 typedef struct elf_prstatus32 prstatus32_t; typedef struct elf_prstatusx32 prstatusx32_t; typedef struct elf_prstatus64 prstatus64_t; -typedef struct elf_prpsinfo32 prpsinfo32_t; -typedef struct elf_prpsinfo64 prpsinfo64_t; -- 1.7.7.6 ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: [PATCH/RFC 01/02 v2] Refactor PRPSINFO handling on Binutils 2012-12-30 1:50 ` Sergio Durigan Junior @ 2013-01-01 14:30 ` Jan Kratochvil 2013-01-02 23:32 ` Sergio Durigan Junior 0 siblings, 1 reply; 21+ messages in thread From: Jan Kratochvil @ 2013-01-01 14:30 UTC (permalink / raw) To: Sergio Durigan Junior Cc: Binutils Development, GDB Patches, Pedro Alves, H.J. Lu Hi Sergio, thanks for the updated, I have just seen some more minor issues: On Sun, 30 Dec 2012 02:49:36 +0100, Sergio Durigan Junior wrote: > --- a/bfd/Makefile.in > +++ b/bfd/Makefile.in > @@ -1068,7 +1068,7 @@ BUILD_CFILES = \ > CFILES = $(SOURCE_CFILES) $(BUILD_CFILES) > SOURCE_HFILES = \ > aout-target.h aoutf1.h aoutx.h coffcode.h coffswap.h ecoffswap.h \ > - elf-bfd.h elf-hppa.h elf32-hppa.h \ > + elf-bfd.h elf-psinfo.h elf-hppa.h elf32-hppa.h \ > elf64-hppa.h elfcode.h elfcore.h \ > freebsd.h genlink.h go32stub.h \ > libaout.h libbfd.h libcoff.h libecoff.h libhppa.h libieee.h \ > diff --git a/bfd/elf-bfd.h b/bfd/elf-bfd.h > index b8d82b1..90ced7a 100644 > --- a/bfd/elf-bfd.h > +++ b/bfd/elf-bfd.h > @@ -1722,6 +1722,38 @@ struct elf_obj_tdata > (elf_known_obj_attributes (bfd) [OBJ_ATTR_PROC]) > #define elf_other_obj_attributes_proc(bfd) \ > (elf_other_obj_attributes (bfd) [OBJ_ATTR_PROC]) > + > +#ifndef ELF_PRARGSZ > +/* Maximum size of the arguments that can be stored in a PRPSINFO > + structure. */ > + > +#define ELF_PRARGSZ (80) > +#endif This should be unrelated to the system definition, BFD now defines everything about PRPSINFO on its own and different system definiton of it can just break it. Host system may be some exotic kind with no core files support by BFD. > + > +/* Internal structure which holds information to be included in the > + PRPSINFO section of the corefile. > + > + This is an "internal" structure in the sense that it should be used to > + pass information to BFD (via the `elfcore_write_prpsinfo', for example), > + so things like endianess shouldn't be an issue. This structure will > + eventually be converted in one of the `elf_external_*' structures > + below. */ > + > +struct elf_internal_prpsinfo > + { > + char pr_state; /* Numeric process state. */ > + char pr_sname; /* Char for pr_state. */ > + char pr_zomb; /* Zombie. */ > + char pr_nice; /* Nice val. */ > + unsigned long pr_flag; /* Flags. */ > + unsigned int pr_uid; > + unsigned int pr_gid; > + int pr_pid, pr_ppid, pr_pgrp, pr_sid; > + /* Lots missing */ This comment seems off-topic here. It fully represents the core file structure. > + char pr_fname[16]; /* Filename of executable. */ > + char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ As this is only internal representation the sizes can be +1 including the terminating '\0' for a more convenient use by the callers. > + }; > + > \f > extern void _bfd_elf_swap_verdef_in > (bfd *, const Elf_External_Verdef *, Elf_Internal_Verdef *); > @@ -2234,11 +2266,15 @@ extern bfd_boolean bfd_elf_lookup_section_flags > extern Elf_Internal_Phdr * _bfd_elf_find_segment_containing_section > (bfd * abfd, asection * section); > > +/* Forward declaration of prpsinfo. See `elf-psinfo.h' for more details. */ > + > +struct elf_internal_prpsinfo; > + > /* Exported interface for writing elf corefile notes. */ > extern char *elfcore_write_note > (bfd *, char *, int *, const char *, int, const void *, int); > extern char *elfcore_write_prpsinfo > - (bfd *, char *, int *, const char *, const char *); > + (bfd *, char *, int *, const struct elf_internal_prpsinfo *); > extern char *elfcore_write_prstatus > (bfd *, char *, int *, long, int, const void *); > extern char * elfcore_write_pstatus > diff --git a/bfd/elf-psinfo.h b/bfd/elf-psinfo.h > new file mode 100644 > index 0000000..ddf3aa1 > --- /dev/null > +++ b/bfd/elf-psinfo.h > @@ -0,0 +1,133 @@ > +/* Declarations for PRPSINFO structures under ELF on GNU/Linux. s/Declarations/Definitions/ > + Copyright 2012 Free Software Foundation, Inc. 2013 now. :-) > + > + This file is part of BFD, the Binary File Descriptor library. > + > + 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 3 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., 51 Franklin Street - Fifth Floor, Boston, > + MA 02110-1301, USA. */ > + > +#ifndef ELF_PRARGSZ > +/* Maximum size of the arguments that can be stored in a PRPSINFO > + structure. */ > + > +#define ELF_PRARGSZ (80) > +#endif The same comment as above. > + > +/* External 32-bit structure for PRPSINFO. This structure is ABI-defined, > + thus we choose to use char arrays here in order to avoid dealing with > + different types in different architectures. > + > + This structure will ultimately be written in the corefile's note section, > + as the PRPSINFO. */ > + > +struct elf_external_prpsinfo32 > + { > + char pr_state; /* Numeric process state. */ > + char pr_sname; /* Char for pr_state. */ > + char pr_zomb; /* Zombie. */ > + char pr_nice; /* Nice val. */ > + char pr_flag[4]; /* Flags. */ > + char pr_uid[2]; > + char pr_gid[2]; > + char pr_pid[4]; > + char pr_ppid[4]; > + char pr_pgrp[4]; > + char pr_sid[4]; > + /* Lots missing */ Also unrelated comment I think. It is in Linux kernel where this IMO means that the core file could contain more info. But it can no longer be changed so I find the comment irrelevant now. > + char pr_fname[16]; /* Filename of executable. */ > + char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ > + }; > + > +/* Helper macro to copy (properly handling endianess) things from the > + `elf_internal_prpsinfo' structure to the `elf_external_prpsinfo32' > + structure. > + > + Note that FROM should be a pointer, and TO should be the explicit type. */ > + > +#define PRPSINFO32_COPY_FIELDS(abfd, from, to) \ > + do \ > + { \ > + H_PUT_8 (abfd, from->pr_state, &to.pr_state); \ > + H_PUT_8 (abfd, from->pr_sname, &to.pr_sname); \ > + H_PUT_8 (abfd, from->pr_zomb, &to.pr_zomb); \ > + H_PUT_8 (abfd, from->pr_nice, &to.pr_nice); \ > + H_PUT_32 (abfd, from->pr_flag, to.pr_flag); \ > + H_PUT_16 (abfd, from->pr_uid, to.pr_uid); \ > + H_PUT_16 (abfd, from->pr_gid, to.pr_gid); \ > + H_PUT_32 (abfd, from->pr_pid, to.pr_pid); \ > + H_PUT_32 (abfd, from->pr_ppid, to.pr_ppid); \ > + H_PUT_32 (abfd, from->pr_pgrp, to.pr_pgrp); \ > + H_PUT_32 (abfd, from->pr_sid, to.pr_sid); \ > + strncpy (to.pr_fname, from->pr_fname, sizeof (to.pr_fname)); \ > + strncpy (to.pr_psargs, from->pr_psargs, sizeof (to.pr_psargs)); \ > + } while (0) > + > +/* External 64-bit structure for PRPSINFO. This structure is ABI-defined, > + thus we choose to use char arrays here in order to avoid dealing with > + different types in different architectures. > + > + Differently from the 32-bit version, the PowerPC guys made our lives better > + and used the same size as the other architectures. > + > + This structure will ultimately be written in the corefile's note section, > + as the PRPSINFO. */ > + > +struct elf_external_prpsinfo64 > + { > + char pr_state; /* Numeric process state. */ > + char pr_sname; /* Char for pr_state. */ > + char pr_zomb; /* Zombie. */ > + char pr_nice; /* Nice val. */ > + char pr_flag[8]; /* Flags. */ > + char gap[4]; > + char pr_uid[4]; > + char pr_gid[4]; > + char pr_pid[4]; > + char pr_ppid[4]; > + char pr_pgrp[4]; > + char pr_sid[4]; > + /* Lots missing */ > + char pr_fname[16]; /* Filename of executable. */ > + char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ > + }; > + > +/* Helper macro to copy (properly handling endianess) things from the > + `elf_internal_prpsinfo' structure to the `elf_external_prpsinfo64' > + structure. > + > + Note that FROM should be a pointer, and TO should be the explicit type. */ > + > +#define PRPSINFO64_COPY_FIELDS(abfd, from, to) \ > + do \ > + { \ > + H_PUT_8 (abfd, from->pr_state, &to.pr_state); \ > + H_PUT_8 (abfd, from->pr_sname, &to.pr_sname); \ > + H_PUT_8 (abfd, from->pr_zomb, &to.pr_zomb); \ > + H_PUT_8 (abfd, from->pr_nice, &to.pr_nice); \ > + H_PUT_64 (abfd, from->pr_flag, to.pr_flag); \ > + H_PUT_32 (abfd, from->pr_uid, to.pr_uid); \ > + H_PUT_32 (abfd, from->pr_gid, to.pr_gid); \ > + H_PUT_32 (abfd, from->pr_pid, to.pr_pid); \ > + H_PUT_32 (abfd, from->pr_ppid, to.pr_ppid); \ > + H_PUT_32 (abfd, from->pr_pgrp, to.pr_pgrp); \ > + H_PUT_32 (abfd, from->pr_sid, to.pr_sid); \ > + strncpy (to.pr_fname, from->pr_fname, sizeof (to.pr_fname)); \ > + strncpy (to.pr_psargs, from->pr_psargs, sizeof (to.pr_psargs)); \ > + } while (0) > + > +/* Process info. In the end we do provide typedefs for them. */ > + > +typedef struct elf_external_prpsinfo32 prpsinfo32_t; > +typedef struct elf_external_prpsinfo64 prpsinfo64_t; There was some comment that *_t types are reserved for system (POSIX?) use. So when BFD now now longer uses the system ones and fully defines them on its own they should have some different namespace, not *_t. > diff --git a/bfd/elf.c b/bfd/elf.c > index 17e9ad4..aad8b27 100644 > --- a/bfd/elf.c > +++ b/bfd/elf.c > @@ -44,6 +44,7 @@ SECTION > #include "elf-bfd.h" > #include "libiberty.h" > #include "safe-ctype.h" > +#include "elf-psinfo.h" > > #ifdef CORE_HEADER > #include CORE_HEADER > @@ -9063,16 +9064,16 @@ char * > elfcore_write_prpsinfo (bfd *abfd, > char *buf, > int *bufsiz, > - const char *fname, > - const char *psargs) > + const struct elf_internal_prpsinfo *input) > { > const struct elf_backend_data *bed = get_elf_backend_data (abfd); > > if (bed->elf_backend_write_core_note != NULL) > { > char *ret; > + > ret = (*bed->elf_backend_write_core_note) (abfd, buf, bufsiz, > - NT_PRPSINFO, fname, psargs); > + NT_PRPSINFO, input); > if (ret != NULL) > return ret; > } > @@ -9090,8 +9091,8 @@ elfcore_write_prpsinfo (bfd *abfd, > #endif > > memset (&data, 0, sizeof (data)); > - strncpy (data.pr_fname, fname, sizeof (data.pr_fname)); > - strncpy (data.pr_psargs, psargs, sizeof (data.pr_psargs)); > + strncpy (data.pr_fname, input->pr_fname, sizeof (data.pr_fname)); > + strncpy (data.pr_psargs, input->pr_psargs, sizeof (data.pr_psargs)); > return elfcore_write_note (abfd, buf, bufsiz, > "CORE", note_type, &data, sizeof (data)); > } > @@ -9102,13 +9103,13 @@ elfcore_write_prpsinfo (bfd *abfd, > psinfo_t data; > int note_type = NT_PSINFO; > #else > - prpsinfo_t data; > + prpsinfo64_t data; > int note_type = NT_PRPSINFO; > #endif > > memset (&data, 0, sizeof (data)); > - strncpy (data.pr_fname, fname, sizeof (data.pr_fname)); > - strncpy (data.pr_psargs, psargs, sizeof (data.pr_psargs)); > + strncpy (data.pr_fname, input->pr_fname, sizeof (data.pr_fname)); > + strncpy (data.pr_psargs, input->pr_psargs, sizeof (data.pr_psargs)); > return elfcore_write_note (abfd, buf, bufsiz, > "CORE", note_type, &data, sizeof (data)); > } > diff --git a/bfd/elf32-arm.c b/bfd/elf32-arm.c > index e2f8a96..a354602 100644 > --- a/bfd/elf32-arm.c > +++ b/bfd/elf32-arm.c > @@ -30,6 +30,7 @@ > #include "elf-nacl.h" > #include "elf-vxworks.h" > #include "elf/arm.h" > +#include "elf-psinfo.h" > > /* Return the relocation section associated with NAME. HTAB is the > bfd's elf32_arm_link_hash_entry. */ > @@ -2004,17 +2005,19 @@ elf32_arm_nabi_write_core_note (bfd *abfd, char *buf, int *bufsiz, > > case NT_PRPSINFO: > { > - char data[124]; > + const struct elf_internal_prpsinfo *prpsinfo; > + struct elf_external_prpsinfo32 data; > va_list ap; > > va_start (ap, note_type); > - memset (data, 0, sizeof (data)); > - strncpy (data + 28, va_arg (ap, const char *), 16); > - strncpy (data + 44, va_arg (ap, const char *), 80); > + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); > va_end (ap); > > + memset (&data, 0, sizeof (data)); > + PRPSINFO32_COPY_FIELDS (abfd, prpsinfo, data); > + > return elfcore_write_note (abfd, buf, bufsiz, > - "CORE", note_type, data, sizeof (data)); > + "CORE", note_type, &data, sizeof (data)); > } > > case NT_PRSTATUS: > diff --git a/bfd/elf32-i386.c b/bfd/elf32-i386.c > index f76c7a7..0198eef 100644 > --- a/bfd/elf32-i386.c > +++ b/bfd/elf32-i386.c > @@ -31,6 +31,10 @@ > #include "objalloc.h" > #include "hashtab.h" > #include "dwarf2.h" > +#include "elf-bfd.h" > +#include "elf-psinfo.h" > + > +#include <stdarg.h> > > /* 386 uses REL relocations instead of RELA. */ > #define USE_REL 1 > @@ -500,6 +504,43 @@ elf_i386_grok_psinfo (bfd *abfd, Elf_Internal_Note *note) > > return TRUE; > } > + > +static char * > +elf_i386_write_core_note (bfd *abfd, char *buf, int *bufsiz, > + int note_type, ...) > +{ > + va_list ap; > + > + switch (note_type) > + { > + default: > + return NULL; > + > + case NT_PRPSINFO: > + { > + const struct elf_internal_prpsinfo *prpsinfo; > + struct elf_external_prpsinfo32 data; > + > + va_start (ap, note_type); > + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); > + va_end (ap); > + > + memset (&data, 0, sizeof (data)); > + PRPSINFO32_COPY_FIELDS (abfd, prpsinfo, data); > + > + return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, > + &data, sizeof (data)); > + } > + /* NOTREACHED */ > + > + case NT_PRSTATUS: > + /* FIXME: For now, to avoid the inclusion of the "CORE_HEADER", we > + return NULL and delegate this to elfcore_write_prstatus. */ > + return NULL; I do not think this 'case NT_PRSTATUS:' needs to be here at all, it is also in fact unrelated to this patchset, but that is again just a matter of style, -> bfd maintainers. > + } > + /* NOTREACHED */ > +} > + > \f > /* Functions for the i386 ELF linker. > > @@ -5042,6 +5083,7 @@ elf_i386_add_symbol_hook (bfd * abfd, > #define elf_backend_gc_sweep_hook elf_i386_gc_sweep_hook > #define elf_backend_grok_prstatus elf_i386_grok_prstatus > #define elf_backend_grok_psinfo elf_i386_grok_psinfo > +#define elf_backend_write_core_note elf_i386_write_core_note > #define elf_backend_reloc_type_class elf_i386_reloc_type_class > #define elf_backend_relocate_section elf_i386_relocate_section > #define elf_backend_size_dynamic_sections elf_i386_size_dynamic_sections > diff --git a/bfd/elf32-ppc.c b/bfd/elf32-ppc.c > index 5241926..b239e5c 100644 > --- a/bfd/elf32-ppc.c > +++ b/bfd/elf32-ppc.c > @@ -37,6 +37,7 @@ > #include "elf32-ppc.h" > #include "elf-vxworks.h" > #include "dwarf2.h" > +#include "elf-psinfo.h" > > typedef enum split16_format_type > { > @@ -1777,6 +1778,62 @@ static reloc_howto_type ppc_elf_howto_raw[] = { > 0xffff, /* dst_mask */ > FALSE), /* pcrel_offset */ > }; > + > +/* External 32-bit PPC structure for PRPSINFO. This structure is ABI-defined, > + thus we choose to use char arrays here in order to avoid dealing with > + different types in different architectures. > + > + The reason why we have a different structure only for PPC is because > + on this architecture (and *only* here!) the size of 32-bit structure > + changes. This is due to the different sizes of `pr_uid' and `pr_gid', > + which on non-PPC architectures are declared as `short int' and on PPC > + architectures are declared as `int'. > + > + This structure will ultimately be written in the corefile's note section, > + as the PRPSINFO. */ > + > +struct elf_external_ppc_prpsinfo32 > + { > + char pr_state; /* Numeric process state. */ > + char pr_sname; /* Char for pr_state. */ > + char pr_zomb; /* Zombie. */ > + char pr_nice; /* Nice val. */ > + char pr_flag[4]; /* Flags. */ > + char pr_uid[4]; > + char pr_gid[4]; > + char pr_pid[4]; > + char pr_ppid[4]; > + char pr_pgrp[4]; > + char pr_sid[4]; > + /* Lots missing */ Likewise. > + char pr_fname[16]; /* Filename of executable. */ > + char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ > + }; > + > +/* Helper macro to copy (properly handling endianess) things from the > + `elf_internal_prpsinfo' structure to the `elf_external_ppc_prpsinfo32' > + structure. > + > + Note that FROM should be a pointer, and TO should be the explicit type. */ > + > +#define PRPSINFO32_PPC_COPY_FIELDS(abfd, from, to) \ > + do \ > + { \ > + H_PUT_8 (abfd, from->pr_state, &to.pr_state); \ > + H_PUT_8 (abfd, from->pr_sname, &to.pr_sname); \ > + H_PUT_8 (abfd, from->pr_zomb, &to.pr_zomb); \ > + H_PUT_8 (abfd, from->pr_nice, &to.pr_nice); \ > + H_PUT_32 (abfd, from->pr_flag, to.pr_flag); \ > + H_PUT_32 (abfd, from->pr_uid, to.pr_uid); \ > + H_PUT_32 (abfd, from->pr_gid, to.pr_gid); \ > + H_PUT_32 (abfd, from->pr_pid, to.pr_pid); \ > + H_PUT_32 (abfd, from->pr_ppid, to.pr_ppid); \ > + H_PUT_32 (abfd, from->pr_pgrp, to.pr_pgrp); \ > + H_PUT_32 (abfd, from->pr_sid, to.pr_sid); \ > + strncpy (to.pr_fname, from->pr_fname, sizeof (to.pr_fname)); \ > + strncpy (to.pr_psargs, from->pr_psargs, sizeof (to.pr_psargs)); \ > + } while (0) > + > \f > /* Initialize the ppc_elf_howto_table, so that linear accesses can be done. */ > > @@ -2222,16 +2279,19 @@ ppc_elf_write_core_note (bfd *abfd, char *buf, int *bufsiz, int note_type, ...) > > case NT_PRPSINFO: > { > - char data[128]; > + const struct elf_internal_prpsinfo *prpsinfo; > + struct elf_external_ppc_prpsinfo32 data; > va_list ap; > > va_start (ap, note_type); > - memset (data, 0, sizeof (data)); > - strncpy (data + 32, va_arg (ap, const char *), 16); > - strncpy (data + 48, va_arg (ap, const char *), 80); > + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); > va_end (ap); > + > + memset (&data, 0, sizeof (data)); > + PRPSINFO32_PPC_COPY_FIELDS (abfd, prpsinfo, data); > + > return elfcore_write_note (abfd, buf, bufsiz, > - "CORE", note_type, data, sizeof (data)); > + "CORE", note_type, &data, sizeof (data)); > } > > case NT_PRSTATUS: > diff --git a/bfd/elf64-ppc.c b/bfd/elf64-ppc.c > index 10b6f9d..4eda989 100644 > --- a/bfd/elf64-ppc.c > +++ b/bfd/elf64-ppc.c > @@ -34,6 +34,7 @@ > #include "elf-bfd.h" > #include "elf/ppc64.h" > #include "elf64-ppc.h" > +#include "elf-psinfo.h" > #include "dwarf2.h" > > static bfd_reloc_status_type ppc64_elf_ha_reloc > @@ -2718,16 +2719,19 @@ ppc64_elf_write_core_note (bfd *abfd, char *buf, int *bufsiz, int note_type, > > case NT_PRPSINFO: > { > - char data[136]; > + const struct elf_internal_prpsinfo *prpsinfo; > + struct elf_external_prpsinfo64 data; > va_list ap; > > va_start (ap, note_type); > - memset (data, 0, sizeof (data)); > - strncpy (data + 40, va_arg (ap, const char *), 16); > - strncpy (data + 56, va_arg (ap, const char *), 80); > + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); > va_end (ap); > + > + memset (&data, 0, sizeof (data)); > + PRPSINFO64_COPY_FIELDS (abfd, prpsinfo, data); > + > return elfcore_write_note (abfd, buf, bufsiz, > - "CORE", note_type, data, sizeof (data)); > + "CORE", note_type, &data, sizeof (data)); > } > > case NT_PRSTATUS: > diff --git a/bfd/elf64-x86-64.c b/bfd/elf64-x86-64.c > index 92bf991..c9bcf48 100644 > --- a/bfd/elf64-x86-64.c > +++ b/bfd/elf64-x86-64.c > @@ -32,11 +32,13 @@ > #include "hashtab.h" > #include "dwarf2.h" > #include "libiberty.h" > +#include "elf-psinfo.h" > + > +#include <stdarg.h> > > #include "elf/x86-64.h" > > #ifdef CORE_HEADER > -#include <stdarg.h> > #include CORE_HEADER > #endif > > @@ -415,14 +417,13 @@ elf_x86_64_grok_psinfo (bfd *abfd, Elf_Internal_Note *note) > return TRUE; > } > > -#ifdef CORE_HEADER I think the NT_PRSTATUS part still needs to have #ifdef CORE_HEADER (and using the NULL return fallback if CORE_HEADER is not available). > static char * > elf_x86_64_write_core_note (bfd *abfd, char *buf, int *bufsiz, > int note_type, ...) > { > const struct elf_backend_data *bed = get_elf_backend_data (abfd); > va_list ap; > - const char *fname, *psargs; > + const struct elf_internal_prpsinfo *prpsinfo; > long pid; > int cursig; > const void *gregs; > @@ -434,27 +435,28 @@ elf_x86_64_write_core_note (bfd *abfd, char *buf, int *bufsiz, > > case NT_PRPSINFO: > va_start (ap, note_type); > - fname = va_arg (ap, const char *); > - psargs = va_arg (ap, const char *); > + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); > va_end (ap); > > if (bed->s->elfclass == ELFCLASS32) > { > - prpsinfo32_t data; > - memset (&data, 0, sizeof (data)); > - strncpy (data.pr_fname, fname, sizeof (data.pr_fname)); > - strncpy (data.pr_psargs, psargs, sizeof (data.pr_psargs)); > + struct elf_external_prpsinfo32 data32; > + > + memset (&data32, 0, sizeof (data32)); > + PRPSINFO32_COPY_FIELDS (abfd, prpsinfo, data32); > + > return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, > - &data, sizeof (data)); > + &data32, sizeof (data32)); > } > else > { > - prpsinfo64_t data; > - memset (&data, 0, sizeof (data)); > - strncpy (data.pr_fname, fname, sizeof (data.pr_fname)); > - strncpy (data.pr_psargs, psargs, sizeof (data.pr_psargs)); > + struct elf_external_prpsinfo64 data64; > + > + memset (&data64, 0, sizeof (data64)); > + PRPSINFO64_COPY_FIELDS (abfd, prpsinfo, data64); > + > return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, > - &data, sizeof (data)); > + &data64, sizeof (data64)); > } > /* NOTREACHED */ > > @@ -501,7 +503,7 @@ elf_x86_64_write_core_note (bfd *abfd, char *buf, int *bufsiz, > } > /* NOTREACHED */ > } > -#endif > + > \f > /* Functions for the x86-64 ELF linker. */ > > @@ -5157,9 +5159,7 @@ static const struct bfd_elf_special_section > #define elf_backend_gc_sweep_hook elf_x86_64_gc_sweep_hook > #define elf_backend_grok_prstatus elf_x86_64_grok_prstatus > #define elf_backend_grok_psinfo elf_x86_64_grok_psinfo > -#ifdef CORE_HEADER > #define elf_backend_write_core_note elf_x86_64_write_core_note > -#endif > #define elf_backend_reloc_type_class elf_x86_64_reloc_type_class > #define elf_backend_relocate_section elf_x86_64_relocate_section > #define elf_backend_size_dynamic_sections elf_x86_64_size_dynamic_sections > diff --git a/bfd/hosts/x86-64linux.h b/bfd/hosts/x86-64linux.h > index 78be09a..6070978 100644 > --- a/bfd/hosts/x86-64linux.h > +++ b/bfd/hosts/x86-64linux.h > @@ -43,11 +43,6 @@ typedef unsigned long long int uint64_t; > /* Unsigned 64-bit integer aligned to 8 bytes. */ > typedef uint64_t __attribute__ ((__aligned__ (8))) a8_uint64_t; > > -#undef HAVE_PRPSINFO32_T > -#define HAVE_PRPSINFO32_T > -#undef HAVE_PRPSINFO32_T_PR_PID > -#define HAVE_PRPSINFO32_T_PR_PID > - > #undef HAVE_PRSTATUS32_T > #define HAVE_PRSTATUS32_T > > @@ -191,36 +186,6 @@ struct elf_prstatus64 > int pr_fpvalid; /* True if math copro being used. */ > }; > > -struct elf_prpsinfo32 > - { > - char pr_state; /* Numeric process state. */ > - char pr_sname; /* Char for pr_state. */ > - char pr_zomb; /* Zombie. */ > - char pr_nice; /* Nice val. */ > - unsigned int pr_flag; /* Flags. */ > - unsigned short int pr_uid; > - unsigned short int pr_gid; > - int pr_pid, pr_ppid, pr_pgrp, pr_sid; > - /* Lots missing */ > - char pr_fname[16]; /* Filename of executable. */ > - char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ > - }; > - > -struct elf_prpsinfo64 > - { > - char pr_state; /* Numeric process state. */ > - char pr_sname; /* Char for pr_state. */ > - char pr_zomb; /* Zombie. */ > - char pr_nice; /* Nice val. */ > - a8_uint64_t pr_flag; /* Flags. */ > - unsigned int pr_uid; > - unsigned int pr_gid; > - int pr_pid, pr_ppid, pr_pgrp, pr_sid; > - /* Lots missing */ > - char pr_fname[16]; /* Filename of executable. */ > - char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ > - }; > - > /* The rest of this file provides the types for emulation of the > Solaris <proc_service.h> interfaces that should be implemented by > users of libthread_db. */ > @@ -229,5 +194,3 @@ struct elf_prpsinfo64 > typedef struct elf_prstatus32 prstatus32_t; > typedef struct elf_prstatusx32 prstatusx32_t; > typedef struct elf_prstatus64 prstatus64_t; > -typedef struct elf_prpsinfo32 prpsinfo32_t; > -typedef struct elf_prpsinfo64 prpsinfo64_t; > -- > 1.7.7.6 Thanks, Jan ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: [PATCH/RFC 01/02 v2] Refactor PRPSINFO handling on Binutils 2013-01-01 14:30 ` Jan Kratochvil @ 2013-01-02 23:32 ` Sergio Durigan Junior 2013-01-03 13:44 ` Jan Kratochvil 0 siblings, 1 reply; 21+ messages in thread From: Sergio Durigan Junior @ 2013-01-02 23:32 UTC (permalink / raw) To: Jan Kratochvil; +Cc: Binutils Development, GDB Patches, Pedro Alves, H.J. Lu On Tuesday, January 01 2013, Jan Kratochvil wrote: > thanks for the updated, I have just seen some more minor issues: Thanks for the comments. I have some questions. > On Sun, 30 Dec 2012 02:49:36 +0100, Sergio Durigan Junior wrote: >> --- a/bfd/Makefile.in >> +++ b/bfd/Makefile.in >> @@ -1068,7 +1068,7 @@ BUILD_CFILES = \ >> CFILES = $(SOURCE_CFILES) $(BUILD_CFILES) >> SOURCE_HFILES = \ >> aout-target.h aoutf1.h aoutx.h coffcode.h coffswap.h ecoffswap.h \ >> - elf-bfd.h elf-hppa.h elf32-hppa.h \ >> + elf-bfd.h elf-psinfo.h elf-hppa.h elf32-hppa.h \ >> elf64-hppa.h elfcode.h elfcore.h \ >> freebsd.h genlink.h go32stub.h \ >> libaout.h libbfd.h libcoff.h libecoff.h libhppa.h libieee.h \ >> diff --git a/bfd/elf-bfd.h b/bfd/elf-bfd.h >> index b8d82b1..90ced7a 100644 >> --- a/bfd/elf-bfd.h >> +++ b/bfd/elf-bfd.h >> @@ -1722,6 +1722,38 @@ struct elf_obj_tdata >> (elf_known_obj_attributes (bfd) [OBJ_ATTR_PROC]) >> #define elf_other_obj_attributes_proc(bfd) \ >> (elf_other_obj_attributes (bfd) [OBJ_ATTR_PROC]) >> + >> +#ifndef ELF_PRARGSZ >> +/* Maximum size of the arguments that can be stored in a PRPSINFO >> + structure. */ >> + >> +#define ELF_PRARGSZ (80) >> +#endif > > This should be unrelated to the system definition, BFD now defines everything > about PRPSINFO on its own and different system definiton of it can just break > it. Host system may be some exotic kind with no core files support by > BFD. Ok, I understand your argument, but it is not clear what you are suggesting. This definition should be present here and in the elf-psinfo.h file. >> +/* Internal structure which holds information to be included in the >> + PRPSINFO section of the corefile. >> + >> + This is an "internal" structure in the sense that it should be used to >> + pass information to BFD (via the `elfcore_write_prpsinfo', for example), >> + so things like endianess shouldn't be an issue. This structure will >> + eventually be converted in one of the `elf_external_*' structures >> + below. */ >> + >> +struct elf_internal_prpsinfo >> + { >> + char pr_state; /* Numeric process state. */ >> + char pr_sname; /* Char for pr_state. */ >> + char pr_zomb; /* Zombie. */ >> + char pr_nice; /* Nice val. */ >> + unsigned long pr_flag; /* Flags. */ >> + unsigned int pr_uid; >> + unsigned int pr_gid; >> + int pr_pid, pr_ppid, pr_pgrp, pr_sid; >> + /* Lots missing */ > > This comment seems off-topic here. It fully represents the core file > structure. I can remove the comment, but it doesn't say that the structure does not represent a corefile struct. It just explains the reason why it is called "internal". >> + >> + This file is part of BFD, the Binary File Descriptor library. >> + >> + 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 3 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., 51 Franklin Street - Fifth Floor, Boston, >> + MA 02110-1301, USA. */ >> + >> +#ifndef ELF_PRARGSZ >> +/* Maximum size of the arguments that can be stored in a PRPSINFO >> + structure. */ >> + >> +#define ELF_PRARGSZ (80) >> +#endif > > The same comment as above. The same question as above. >> +/* Process info. In the end we do provide typedefs for them. */ >> + >> +typedef struct elf_external_prpsinfo32 prpsinfo32_t; >> +typedef struct elf_external_prpsinfo64 prpsinfo64_t; > > There was some comment that *_t types are reserved for system (POSIX?) use. > So when BFD now now longer uses the system ones and fully defines them on its > own they should have some different namespace, not *_t. Ok, but renaming these types will require renaming the files that use them as well. Thanks, -- Sergio ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: [PATCH/RFC 01/02 v2] Refactor PRPSINFO handling on Binutils 2013-01-02 23:32 ` Sergio Durigan Junior @ 2013-01-03 13:44 ` Jan Kratochvil 2013-01-03 15:46 ` Sergio Durigan Junior 0 siblings, 1 reply; 21+ messages in thread From: Jan Kratochvil @ 2013-01-03 13:44 UTC (permalink / raw) To: Sergio Durigan Junior Cc: Binutils Development, GDB Patches, Pedro Alves, H.J. Lu On Thu, 03 Jan 2013 00:32:12 +0100, Sergio Durigan Junior wrote: > On Tuesday, January 01 2013, Jan Kratochvil wrote: > > On Sun, 30 Dec 2012 02:49:36 +0100, Sergio Durigan Junior wrote: > >> --- a/bfd/elf-bfd.h > >> +++ b/bfd/elf-bfd.h > >> @@ -1722,6 +1722,38 @@ struct elf_obj_tdata > >> (elf_known_obj_attributes (bfd) [OBJ_ATTR_PROC]) > >> #define elf_other_obj_attributes_proc(bfd) \ > >> (elf_other_obj_attributes (bfd) [OBJ_ATTR_PROC]) > >> + > >> +#ifndef ELF_PRARGSZ > >> +/* Maximum size of the arguments that can be stored in a PRPSINFO > >> + structure. */ > >> + > >> +#define ELF_PRARGSZ (80) > >> +#endif > > > > This should be unrelated to the system definition, BFD now defines everything > > about PRPSINFO on its own and different system definiton of it can just break > > it. Host system may be some exotic kind with no core files support by > > BFD. > > Ok, I understand your argument, but it is not clear what you are > suggesting. This definition should be present here and in the > elf-psinfo.h file. Suggesting for example instead of + char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ to just use + char pr_psargs[80]; /* Initial part of arg list. */ although as I also suggested: On Tue, 01 Jan 2013 15:30:27 +0100, Jan Kratochvil wrote: > As this is only internal representation the sizes can be +1 including the > terminating '\0' for a more convenient use by the callers. it could be (no longer requiring those strncpy around): + char pr_psargs[81]; /* Initial part of arg list. */ If you prefer it could be (note the different bfd-only #define name): +#define BFD_ELF_PRARGSZ (80) + char pr_psargs[BFD_ELF_PRARGSZ + 1]; /* Initial part of arg list. */ but I do not see a reason for such #define. The goal is not to clash with the existing system symbol ELF_PRARGSZ as that's symbol meaning is different (irrelevant for the internal BFD representation). > >> +/* Internal structure which holds information to be included in the > >> + PRPSINFO section of the corefile. > >> + > >> + This is an "internal" structure in the sense that it should be used to > >> + pass information to BFD (via the `elfcore_write_prpsinfo', for example), > >> + so things like endianess shouldn't be an issue. This structure will > >> + eventually be converted in one of the `elf_external_*' structures > >> + below. */ > >> + > >> +struct elf_internal_prpsinfo > >> + { > >> + char pr_state; /* Numeric process state. */ > >> + char pr_sname; /* Char for pr_state. */ > >> + char pr_zomb; /* Zombie. */ > >> + char pr_nice; /* Nice val. */ > >> + unsigned long pr_flag; /* Flags. */ > >> + unsigned int pr_uid; > >> + unsigned int pr_gid; > >> + int pr_pid, pr_ppid, pr_pgrp, pr_sid; > >> + /* Lots missing */ > > > > This comment seems off-topic here. It fully represents the core file > > structure. > > I can remove the comment, but it doesn't say that the structure does not > represent a corefile struct. It just explains the reason why it is > called "internal". As /usr/include/linux/elfcore.h (=from Linux kernel) contains: struct elf_prpsinfo { [...] pid_t pr_pid, pr_ppid, pr_pgrp, pr_sid; /* Lots missing */ char pr_fname[16]; /* filename of executable */ [...] }; we should look at it from the point of Linux kernel. It probably made sense as Linux kernel could store some more info there. But currently neither Linux kernel nor BFD can change the binary format anymore so (1) I do not want to discuss whether it should be removed from Linux kernel or not, that is offtopic, (2) in BFD it seems irrelevant to me, BFD only needs to mimic the Linux kernel binary structure, there is nothing missing in BFD as BFD decodes very every field Linux kernel stores there. > >> +/* Process info. In the end we do provide typedefs for them. */ > >> + > >> +typedef struct elf_external_prpsinfo32 prpsinfo32_t; > >> +typedef struct elf_external_prpsinfo64 prpsinfo64_t; > > > > There was some comment that *_t types are reserved for system (POSIX?) use. > > So when BFD now now longer uses the system ones and fully defines them on its > > own they should have some different namespace, not *_t. > > Ok, but renaming these types will require renaming the files that use > them as well. Yes. Thanks, Jan ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: [PATCH/RFC 01/02 v2] Refactor PRPSINFO handling on Binutils 2013-01-03 13:44 ` Jan Kratochvil @ 2013-01-03 15:46 ` Sergio Durigan Junior 2013-01-04 4:40 ` Sergio Durigan Junior 0 siblings, 1 reply; 21+ messages in thread From: Sergio Durigan Junior @ 2013-01-03 15:46 UTC (permalink / raw) To: Jan Kratochvil; +Cc: Binutils Development, GDB Patches, Pedro Alves, H.J. Lu On Thursday, January 03 2013, Jan Kratochvil wrote: > On Thu, 03 Jan 2013 00:32:12 +0100, Sergio Durigan Junior wrote: >> On Tuesday, January 01 2013, Jan Kratochvil wrote: >> > On Sun, 30 Dec 2012 02:49:36 +0100, Sergio Durigan Junior wrote: >> >> +/* Internal structure which holds information to be included in the >> >> + PRPSINFO section of the corefile. >> >> + >> >> + This is an "internal" structure in the sense that it should be used to >> >> + pass information to BFD (via the `elfcore_write_prpsinfo', for example), >> >> + so things like endianess shouldn't be an issue. This structure will >> >> + eventually be converted in one of the `elf_external_*' structures >> >> + below. */ >> >> + >> >> +struct elf_internal_prpsinfo >> >> + { >> >> + char pr_state; /* Numeric process state. */ >> >> + char pr_sname; /* Char for pr_state. */ >> >> + char pr_zomb; /* Zombie. */ >> >> + char pr_nice; /* Nice val. */ >> >> + unsigned long pr_flag; /* Flags. */ >> >> + unsigned int pr_uid; >> >> + unsigned int pr_gid; >> >> + int pr_pid, pr_ppid, pr_pgrp, pr_sid; >> >> + /* Lots missing */ >> > >> > This comment seems off-topic here. It fully represents the core file >> > structure. >> >> I can remove the comment, but it doesn't say that the structure does not >> represent a corefile struct. It just explains the reason why it is >> called "internal". > > As /usr/include/linux/elfcore.h (=from Linux kernel) contains: > > struct elf_prpsinfo > { > [...] > pid_t pr_pid, pr_ppid, pr_pgrp, pr_sid; > /* Lots missing */ > char pr_fname[16]; /* filename of executable */ > [...] > }; > > we should look at it from the point of Linux kernel. It probably made sense > as Linux kernel could store some more info there. Ops, sorry, I thought you were talking about the comment above the structure, and not about the "Lots missing". Then I agree, it can be removed. Sorry about the confusion. I will send an updated patch in a few moments. -- Sergio ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: [PATCH/RFC 01/02 v2] Refactor PRPSINFO handling on Binutils 2013-01-03 15:46 ` Sergio Durigan Junior @ 2013-01-04 4:40 ` Sergio Durigan Junior 2013-01-09 20:49 ` Sergio Durigan Junior 2013-01-10 18:26 ` Pedro Alves 0 siblings, 2 replies; 21+ messages in thread From: Sergio Durigan Junior @ 2013-01-04 4:40 UTC (permalink / raw) To: Jan Kratochvil; +Cc: Binutils Development, GDB Patches, Pedro Alves, H.J. Lu On Thursday, January 03 2013, I wrote: > Ops, sorry, I thought you were talking about the comment above the > structure, and not about the "Lots missing". Then I agree, it can be > removed. Sorry about the confusion. I will send an updated patch in a > few moments. Here it is. Thanks for the comments. -- Sergio 2013-01-04 Sergio Durigan Junior <sergiodj@redhat.com> * Makefile.in (BUILD_CFILES): Add `elf-psinfo.h'. * elf-bfd.h (ELF_PRARGSZ): New conditional definition. (elf_internal_prpsinfo): New structure declaration. (elfcore_write_prpsinfo): Change prototype, accepting `elf_internal_prpsinfo' as argument. * elf-psinfo.h: New file. * elf.c (elfcore_write_prpsinfo): Change prototype, accepting `elf_internal_prpsinfo' as argument. Rewrite parts of the code to make use of the new argument. * elf32-arm.c: Include `elf-psinfo.h'. (elf32_arm_nabi_write_core_note): Refactor `NT_PRPSINFO' case. * elf32-i386.c: Include `elf-bfd.h', `elf-psinfo.h' and `stdarg.h'. (elf_i386_write_core_note): New function. * elf32-ppc.c: Include `elf-psinfo.h'. (elf_external_ppc_prpsinfo32): New structure declaration. (ppc_elf_write_core_note): Refactor `NT_PRPSINFO' case. * elf64-ppc.c: Include `elf-psinfo.h'. (ppc64_elf_write_core_note): Refactor `NT_PRPSINFO' case. * elf64-x86-64.c: Include `elf-psinfo.h'. Include `stdarg.h' unconditionally. (elf_x86_64_write_core_note): Remove `#ifdef CORE_HEADER', making the function unconditionally available. Refactor `NT_PRPSINFO' case. Refactor `NT_PRSTATUS' case, making it conditional to `CORE_HEADER'. * hosts/x86-64linux.h (HAVE_PRPSINFO32_T, HAVE_PRPSINFO32_T_PR_PID, elf_prpsinfo32, elf_prpsinfo64, prpsinfo32_t, prpsinfo64_t): Remove definitions, moving some of them to `elf-psinfo.h'. --- bfd/Makefile.in | 2 +- bfd/elf-bfd.h | 26 +++++++++- bfd/elf-psinfo.h | 124 +++++++++++++++++++++++++++++++++++++++++++++++ bfd/elf.c | 21 ++++---- bfd/elf32-arm.c | 13 +++-- bfd/elf32-i386.c | 37 ++++++++++++++ bfd/elf32-ppc.c | 70 ++++++++++++++++++++++++-- bfd/elf64-ppc.c | 14 +++-- bfd/elf64-x86-64.c | 40 ++++++++------- bfd/hosts/x86-64linux.h | 37 -------------- 10 files changed, 302 insertions(+), 82 deletions(-) create mode 100644 bfd/elf-psinfo.h diff --git a/bfd/Makefile.in b/bfd/Makefile.in index c51c342..adea836 100644 --- a/bfd/Makefile.in +++ b/bfd/Makefile.in @@ -1068,7 +1068,7 @@ BUILD_CFILES = \ CFILES = $(SOURCE_CFILES) $(BUILD_CFILES) SOURCE_HFILES = \ aout-target.h aoutf1.h aoutx.h coffcode.h coffswap.h ecoffswap.h \ - elf-bfd.h elf-hppa.h elf32-hppa.h \ + elf-bfd.h elf-psinfo.h elf-hppa.h elf32-hppa.h \ elf64-hppa.h elfcode.h elfcore.h \ freebsd.h genlink.h go32stub.h \ libaout.h libbfd.h libcoff.h libecoff.h libhppa.h libieee.h \ diff --git a/bfd/elf-bfd.h b/bfd/elf-bfd.h index b8d82b1..1572cba 100644 --- a/bfd/elf-bfd.h +++ b/bfd/elf-bfd.h @@ -1722,6 +1722,30 @@ struct elf_obj_tdata (elf_known_obj_attributes (bfd) [OBJ_ATTR_PROC]) #define elf_other_obj_attributes_proc(bfd) \ (elf_other_obj_attributes (bfd) [OBJ_ATTR_PROC]) + +/* Internal structure which holds information to be included in the + PRPSINFO section of the corefile. + + This is an "internal" structure in the sense that it should be used to + pass information to BFD (via the `elfcore_write_prpsinfo', for example), + so things like endianess shouldn't be an issue. This structure will + eventually be converted in one of the `elf_external_*' structures + below. */ + +struct elf_internal_prpsinfo + { + char pr_state; /* Numeric process state. */ + char pr_sname; /* Char for pr_state. */ + char pr_zomb; /* Zombie. */ + char pr_nice; /* Nice val. */ + unsigned long pr_flag; /* Flags. */ + unsigned int pr_uid; + unsigned int pr_gid; + int pr_pid, pr_ppid, pr_pgrp, pr_sid; + char pr_fname[16 + 1]; /* Filename of executable. */ + char pr_psargs[80 + 1]; /* Initial part of arg list. */ + }; + \f extern void _bfd_elf_swap_verdef_in (bfd *, const Elf_External_Verdef *, Elf_Internal_Verdef *); @@ -2238,7 +2262,7 @@ extern Elf_Internal_Phdr * _bfd_elf_find_segment_containing_section extern char *elfcore_write_note (bfd *, char *, int *, const char *, int, const void *, int); extern char *elfcore_write_prpsinfo - (bfd *, char *, int *, const char *, const char *); + (bfd *, char *, int *, const struct elf_internal_prpsinfo *); extern char *elfcore_write_prstatus (bfd *, char *, int *, long, int, const void *); extern char * elfcore_write_pstatus diff --git a/bfd/elf-psinfo.h b/bfd/elf-psinfo.h new file mode 100644 index 0000000..6689a58 --- /dev/null +++ b/bfd/elf-psinfo.h @@ -0,0 +1,124 @@ +/* Definitions for PRPSINFO structures under ELF on GNU/Linux. + Copyright 2013 Free Software Foundation, Inc. + + This file is part of BFD, the Binary File Descriptor library. + + 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 3 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., 51 Franklin Street - Fifth Floor, Boston, + MA 02110-1301, USA. */ + +/* External 32-bit structure for PRPSINFO. This structure is ABI-defined, + thus we choose to use char arrays here in order to avoid dealing with + different types in different architectures. + + This structure will ultimately be written in the corefile's note section, + as the PRPSINFO. */ + +struct elf_external_prpsinfo32 + { + char pr_state; /* Numeric process state. */ + char pr_sname; /* Char for pr_state. */ + char pr_zomb; /* Zombie. */ + char pr_nice; /* Nice val. */ + char pr_flag[4]; /* Flags. */ + char pr_uid[2]; + char pr_gid[2]; + char pr_pid[4]; + char pr_ppid[4]; + char pr_pgrp[4]; + char pr_sid[4]; + char pr_fname[16]; /* Filename of executable. */ + char pr_psargs[80]; /* Initial part of arg list. */ + }; + +/* Helper macro to copy (properly handling endianess) things from the + `elf_internal_prpsinfo' structure to the `elf_external_prpsinfo32' + structure. + + Note that FROM should be a pointer, and TO should be the explicit type. */ + +#define PRPSINFO32_COPY_FIELDS(abfd, from, to) \ + do \ + { \ + H_PUT_8 (abfd, from->pr_state, &to.pr_state); \ + H_PUT_8 (abfd, from->pr_sname, &to.pr_sname); \ + H_PUT_8 (abfd, from->pr_zomb, &to.pr_zomb); \ + H_PUT_8 (abfd, from->pr_nice, &to.pr_nice); \ + H_PUT_32 (abfd, from->pr_flag, to.pr_flag); \ + H_PUT_16 (abfd, from->pr_uid, to.pr_uid); \ + H_PUT_16 (abfd, from->pr_gid, to.pr_gid); \ + H_PUT_32 (abfd, from->pr_pid, to.pr_pid); \ + H_PUT_32 (abfd, from->pr_ppid, to.pr_ppid); \ + H_PUT_32 (abfd, from->pr_pgrp, to.pr_pgrp); \ + H_PUT_32 (abfd, from->pr_sid, to.pr_sid); \ + strncpy (to.pr_fname, from->pr_fname, sizeof (to.pr_fname)); \ + strncpy (to.pr_psargs, from->pr_psargs, sizeof (to.pr_psargs)); \ + } while (0) + +/* External 64-bit structure for PRPSINFO. This structure is ABI-defined, + thus we choose to use char arrays here in order to avoid dealing with + different types in different architectures. + + Differently from the 32-bit version, the PowerPC guys made our lives better + and used the same size as the other architectures. + + This structure will ultimately be written in the corefile's note section, + as the PRPSINFO. */ + +struct elf_external_prpsinfo64 + { + char pr_state; /* Numeric process state. */ + char pr_sname; /* Char for pr_state. */ + char pr_zomb; /* Zombie. */ + char pr_nice; /* Nice val. */ + char pr_flag[8]; /* Flags. */ + char gap[4]; + char pr_uid[4]; + char pr_gid[4]; + char pr_pid[4]; + char pr_ppid[4]; + char pr_pgrp[4]; + char pr_sid[4]; + char pr_fname[16]; /* Filename of executable. */ + char pr_psargs[80]; /* Initial part of arg list. */ + }; + +/* Helper macro to copy (properly handling endianess) things from the + `elf_internal_prpsinfo' structure to the `elf_external_prpsinfo64' + structure. + + Note that FROM should be a pointer, and TO should be the explicit type. */ + +#define PRPSINFO64_COPY_FIELDS(abfd, from, to) \ + do \ + { \ + H_PUT_8 (abfd, from->pr_state, &to.pr_state); \ + H_PUT_8 (abfd, from->pr_sname, &to.pr_sname); \ + H_PUT_8 (abfd, from->pr_zomb, &to.pr_zomb); \ + H_PUT_8 (abfd, from->pr_nice, &to.pr_nice); \ + H_PUT_64 (abfd, from->pr_flag, to.pr_flag); \ + H_PUT_32 (abfd, from->pr_uid, to.pr_uid); \ + H_PUT_32 (abfd, from->pr_gid, to.pr_gid); \ + H_PUT_32 (abfd, from->pr_pid, to.pr_pid); \ + H_PUT_32 (abfd, from->pr_ppid, to.pr_ppid); \ + H_PUT_32 (abfd, from->pr_pgrp, to.pr_pgrp); \ + H_PUT_32 (abfd, from->pr_sid, to.pr_sid); \ + strncpy (to.pr_fname, from->pr_fname, sizeof (to.pr_fname)); \ + strncpy (to.pr_psargs, from->pr_psargs, sizeof (to.pr_psargs)); \ + } while (0) + +/* Process info. In the end we do provide typedefs for them. */ + +typedef struct elf_external_prpsinfo32 prpsinfo32; +typedef struct elf_external_prpsinfo64 prpsinfo64; diff --git a/bfd/elf.c b/bfd/elf.c index 17e9ad4..c4f04ea 100644 --- a/bfd/elf.c +++ b/bfd/elf.c @@ -44,6 +44,7 @@ SECTION #include "elf-bfd.h" #include "libiberty.h" #include "safe-ctype.h" +#include "elf-psinfo.h" #ifdef CORE_HEADER #include CORE_HEADER @@ -8165,7 +8166,7 @@ elfcore_grok_arm_vfp (bfd *abfd, Elf_Internal_Note *note) #if defined (HAVE_PRPSINFO_T) typedef prpsinfo_t elfcore_psinfo_t; #if defined (HAVE_PRPSINFO32_T) /* Sparc64 cross Sparc32 */ -typedef prpsinfo32_t elfcore_psinfo32_t; +typedef prpsinfo32 elfcore_psinfo32_t; #endif #endif @@ -9063,16 +9064,16 @@ char * elfcore_write_prpsinfo (bfd *abfd, char *buf, int *bufsiz, - const char *fname, - const char *psargs) + const struct elf_internal_prpsinfo *input) { const struct elf_backend_data *bed = get_elf_backend_data (abfd); if (bed->elf_backend_write_core_note != NULL) { char *ret; + ret = (*bed->elf_backend_write_core_note) (abfd, buf, bufsiz, - NT_PRPSINFO, fname, psargs); + NT_PRPSINFO, input); if (ret != NULL) return ret; } @@ -9085,13 +9086,13 @@ elfcore_write_prpsinfo (bfd *abfd, psinfo32_t data; int note_type = NT_PSINFO; #else - prpsinfo32_t data; + prpsinfo32 data; int note_type = NT_PRPSINFO; #endif memset (&data, 0, sizeof (data)); - strncpy (data.pr_fname, fname, sizeof (data.pr_fname)); - strncpy (data.pr_psargs, psargs, sizeof (data.pr_psargs)); + strncpy (data.pr_fname, input->pr_fname, sizeof (data.pr_fname)); + strncpy (data.pr_psargs, input->pr_psargs, sizeof (data.pr_psargs)); return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, &data, sizeof (data)); } @@ -9102,13 +9103,13 @@ elfcore_write_prpsinfo (bfd *abfd, psinfo_t data; int note_type = NT_PSINFO; #else - prpsinfo_t data; + prpsinfo64 data; int note_type = NT_PRPSINFO; #endif memset (&data, 0, sizeof (data)); - strncpy (data.pr_fname, fname, sizeof (data.pr_fname)); - strncpy (data.pr_psargs, psargs, sizeof (data.pr_psargs)); + strncpy (data.pr_fname, input->pr_fname, sizeof (data.pr_fname)); + strncpy (data.pr_psargs, input->pr_psargs, sizeof (data.pr_psargs)); return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, &data, sizeof (data)); } diff --git a/bfd/elf32-arm.c b/bfd/elf32-arm.c index e2f8a96..a354602 100644 --- a/bfd/elf32-arm.c +++ b/bfd/elf32-arm.c @@ -30,6 +30,7 @@ #include "elf-nacl.h" #include "elf-vxworks.h" #include "elf/arm.h" +#include "elf-psinfo.h" /* Return the relocation section associated with NAME. HTAB is the bfd's elf32_arm_link_hash_entry. */ @@ -2004,17 +2005,19 @@ elf32_arm_nabi_write_core_note (bfd *abfd, char *buf, int *bufsiz, case NT_PRPSINFO: { - char data[124]; + const struct elf_internal_prpsinfo *prpsinfo; + struct elf_external_prpsinfo32 data; va_list ap; va_start (ap, note_type); - memset (data, 0, sizeof (data)); - strncpy (data + 28, va_arg (ap, const char *), 16); - strncpy (data + 44, va_arg (ap, const char *), 80); + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); va_end (ap); + memset (&data, 0, sizeof (data)); + PRPSINFO32_COPY_FIELDS (abfd, prpsinfo, data); + return elfcore_write_note (abfd, buf, bufsiz, - "CORE", note_type, data, sizeof (data)); + "CORE", note_type, &data, sizeof (data)); } case NT_PRSTATUS: diff --git a/bfd/elf32-i386.c b/bfd/elf32-i386.c index f76c7a7..45a1e26 100644 --- a/bfd/elf32-i386.c +++ b/bfd/elf32-i386.c @@ -31,6 +31,10 @@ #include "objalloc.h" #include "hashtab.h" #include "dwarf2.h" +#include "elf-bfd.h" +#include "elf-psinfo.h" + +#include <stdarg.h> /* 386 uses REL relocations instead of RELA. */ #define USE_REL 1 @@ -500,6 +504,38 @@ elf_i386_grok_psinfo (bfd *abfd, Elf_Internal_Note *note) return TRUE; } + +static char * +elf_i386_write_core_note (bfd *abfd, char *buf, int *bufsiz, + int note_type, ...) +{ + va_list ap; + + switch (note_type) + { + default: + return NULL; + + case NT_PRPSINFO: + { + const struct elf_internal_prpsinfo *prpsinfo; + struct elf_external_prpsinfo32 data; + + va_start (ap, note_type); + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); + va_end (ap); + + memset (&data, 0, sizeof (data)); + PRPSINFO32_COPY_FIELDS (abfd, prpsinfo, data); + + return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, + &data, sizeof (data)); + } + /* NOTREACHED */ + } + /* NOTREACHED */ +} + \f /* Functions for the i386 ELF linker. @@ -5042,6 +5078,7 @@ elf_i386_add_symbol_hook (bfd * abfd, #define elf_backend_gc_sweep_hook elf_i386_gc_sweep_hook #define elf_backend_grok_prstatus elf_i386_grok_prstatus #define elf_backend_grok_psinfo elf_i386_grok_psinfo +#define elf_backend_write_core_note elf_i386_write_core_note #define elf_backend_reloc_type_class elf_i386_reloc_type_class #define elf_backend_relocate_section elf_i386_relocate_section #define elf_backend_size_dynamic_sections elf_i386_size_dynamic_sections diff --git a/bfd/elf32-ppc.c b/bfd/elf32-ppc.c index 5241926..02d494f 100644 --- a/bfd/elf32-ppc.c +++ b/bfd/elf32-ppc.c @@ -37,6 +37,7 @@ #include "elf32-ppc.h" #include "elf-vxworks.h" #include "dwarf2.h" +#include "elf-psinfo.h" typedef enum split16_format_type { @@ -1777,6 +1778,62 @@ static reloc_howto_type ppc_elf_howto_raw[] = { 0xffff, /* dst_mask */ FALSE), /* pcrel_offset */ }; + +/* External 32-bit PPC structure for PRPSINFO. This structure is ABI-defined, + thus we choose to use char arrays here in order to avoid dealing with + different types in different architectures. + + The reason why we have a different structure only for PPC is because + on this architecture (and *only* here!) the size of 32-bit structure + changes. This is due to the different sizes of `pr_uid' and `pr_gid', + which on non-PPC architectures are declared as `short int' and on PPC + architectures are declared as `int'. + + This structure will ultimately be written in the corefile's note section, + as the PRPSINFO. */ + +struct elf_external_ppc_prpsinfo32 + { + char pr_state; /* Numeric process state. */ + char pr_sname; /* Char for pr_state. */ + char pr_zomb; /* Zombie. */ + char pr_nice; /* Nice val. */ + char pr_flag[4]; /* Flags. */ + char pr_uid[4]; + char pr_gid[4]; + char pr_pid[4]; + char pr_ppid[4]; + char pr_pgrp[4]; + char pr_sid[4]; + /* Lots missing */ + char pr_fname[16]; /* Filename of executable. */ + char pr_psargs[80]; /* Initial part of arg list. */ + }; + +/* Helper macro to copy (properly handling endianess) things from the + `elf_internal_prpsinfo' structure to the `elf_external_ppc_prpsinfo32' + structure. + + Note that FROM should be a pointer, and TO should be the explicit type. */ + +#define PRPSINFO32_PPC_COPY_FIELDS(abfd, from, to) \ + do \ + { \ + H_PUT_8 (abfd, from->pr_state, &to.pr_state); \ + H_PUT_8 (abfd, from->pr_sname, &to.pr_sname); \ + H_PUT_8 (abfd, from->pr_zomb, &to.pr_zomb); \ + H_PUT_8 (abfd, from->pr_nice, &to.pr_nice); \ + H_PUT_32 (abfd, from->pr_flag, to.pr_flag); \ + H_PUT_32 (abfd, from->pr_uid, to.pr_uid); \ + H_PUT_32 (abfd, from->pr_gid, to.pr_gid); \ + H_PUT_32 (abfd, from->pr_pid, to.pr_pid); \ + H_PUT_32 (abfd, from->pr_ppid, to.pr_ppid); \ + H_PUT_32 (abfd, from->pr_pgrp, to.pr_pgrp); \ + H_PUT_32 (abfd, from->pr_sid, to.pr_sid); \ + strncpy (to.pr_fname, from->pr_fname, sizeof (to.pr_fname)); \ + strncpy (to.pr_psargs, from->pr_psargs, sizeof (to.pr_psargs)); \ + } while (0) + \f /* Initialize the ppc_elf_howto_table, so that linear accesses can be done. */ @@ -2222,16 +2279,19 @@ ppc_elf_write_core_note (bfd *abfd, char *buf, int *bufsiz, int note_type, ...) case NT_PRPSINFO: { - char data[128]; + const struct elf_internal_prpsinfo *prpsinfo; + struct elf_external_ppc_prpsinfo32 data; va_list ap; va_start (ap, note_type); - memset (data, 0, sizeof (data)); - strncpy (data + 32, va_arg (ap, const char *), 16); - strncpy (data + 48, va_arg (ap, const char *), 80); + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); va_end (ap); + + memset (&data, 0, sizeof (data)); + PRPSINFO32_PPC_COPY_FIELDS (abfd, prpsinfo, data); + return elfcore_write_note (abfd, buf, bufsiz, - "CORE", note_type, data, sizeof (data)); + "CORE", note_type, &data, sizeof (data)); } case NT_PRSTATUS: diff --git a/bfd/elf64-ppc.c b/bfd/elf64-ppc.c index 10b6f9d..4eda989 100644 --- a/bfd/elf64-ppc.c +++ b/bfd/elf64-ppc.c @@ -34,6 +34,7 @@ #include "elf-bfd.h" #include "elf/ppc64.h" #include "elf64-ppc.h" +#include "elf-psinfo.h" #include "dwarf2.h" static bfd_reloc_status_type ppc64_elf_ha_reloc @@ -2718,16 +2719,19 @@ ppc64_elf_write_core_note (bfd *abfd, char *buf, int *bufsiz, int note_type, case NT_PRPSINFO: { - char data[136]; + const struct elf_internal_prpsinfo *prpsinfo; + struct elf_external_prpsinfo64 data; va_list ap; va_start (ap, note_type); - memset (data, 0, sizeof (data)); - strncpy (data + 40, va_arg (ap, const char *), 16); - strncpy (data + 56, va_arg (ap, const char *), 80); + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); va_end (ap); + + memset (&data, 0, sizeof (data)); + PRPSINFO64_COPY_FIELDS (abfd, prpsinfo, data); + return elfcore_write_note (abfd, buf, bufsiz, - "CORE", note_type, data, sizeof (data)); + "CORE", note_type, &data, sizeof (data)); } case NT_PRSTATUS: diff --git a/bfd/elf64-x86-64.c b/bfd/elf64-x86-64.c index 92bf991..40ce80f 100644 --- a/bfd/elf64-x86-64.c +++ b/bfd/elf64-x86-64.c @@ -32,11 +32,13 @@ #include "hashtab.h" #include "dwarf2.h" #include "libiberty.h" +#include "elf-psinfo.h" + +#include <stdarg.h> #include "elf/x86-64.h" #ifdef CORE_HEADER -#include <stdarg.h> #include CORE_HEADER #endif @@ -415,14 +417,13 @@ elf_x86_64_grok_psinfo (bfd *abfd, Elf_Internal_Note *note) return TRUE; } -#ifdef CORE_HEADER static char * elf_x86_64_write_core_note (bfd *abfd, char *buf, int *bufsiz, int note_type, ...) { const struct elf_backend_data *bed = get_elf_backend_data (abfd); va_list ap; - const char *fname, *psargs; + const struct elf_internal_prpsinfo *prpsinfo; long pid; int cursig; const void *gregs; @@ -434,31 +435,33 @@ elf_x86_64_write_core_note (bfd *abfd, char *buf, int *bufsiz, case NT_PRPSINFO: va_start (ap, note_type); - fname = va_arg (ap, const char *); - psargs = va_arg (ap, const char *); + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); va_end (ap); if (bed->s->elfclass == ELFCLASS32) { - prpsinfo32_t data; - memset (&data, 0, sizeof (data)); - strncpy (data.pr_fname, fname, sizeof (data.pr_fname)); - strncpy (data.pr_psargs, psargs, sizeof (data.pr_psargs)); + struct elf_external_prpsinfo32 data32; + + memset (&data32, 0, sizeof (data32)); + PRPSINFO32_COPY_FIELDS (abfd, prpsinfo, data32); + return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, - &data, sizeof (data)); + &data32, sizeof (data32)); } else { - prpsinfo64_t data; - memset (&data, 0, sizeof (data)); - strncpy (data.pr_fname, fname, sizeof (data.pr_fname)); - strncpy (data.pr_psargs, psargs, sizeof (data.pr_psargs)); + struct elf_external_prpsinfo64 data64; + + memset (&data64, 0, sizeof (data64)); + PRPSINFO64_COPY_FIELDS (abfd, prpsinfo, data64); + return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, - &data, sizeof (data)); + &data64, sizeof (data64)); } /* NOTREACHED */ case NT_PRSTATUS: +#ifdef CORE_HEADER va_start (ap, note_type); pid = va_arg (ap, long); cursig = va_arg (ap, int); @@ -498,10 +501,13 @@ elf_x86_64_write_core_note (bfd *abfd, char *buf, int *bufsiz, return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, &prstat, sizeof (prstat)); } +#else + return NULL; +#endif /* CORE_HEADER */ } /* NOTREACHED */ } -#endif + \f /* Functions for the x86-64 ELF linker. */ @@ -5157,9 +5163,7 @@ static const struct bfd_elf_special_section #define elf_backend_gc_sweep_hook elf_x86_64_gc_sweep_hook #define elf_backend_grok_prstatus elf_x86_64_grok_prstatus #define elf_backend_grok_psinfo elf_x86_64_grok_psinfo -#ifdef CORE_HEADER #define elf_backend_write_core_note elf_x86_64_write_core_note -#endif #define elf_backend_reloc_type_class elf_x86_64_reloc_type_class #define elf_backend_relocate_section elf_x86_64_relocate_section #define elf_backend_size_dynamic_sections elf_x86_64_size_dynamic_sections diff --git a/bfd/hosts/x86-64linux.h b/bfd/hosts/x86-64linux.h index 78be09a..6070978 100644 --- a/bfd/hosts/x86-64linux.h +++ b/bfd/hosts/x86-64linux.h @@ -43,11 +43,6 @@ typedef unsigned long long int uint64_t; /* Unsigned 64-bit integer aligned to 8 bytes. */ typedef uint64_t __attribute__ ((__aligned__ (8))) a8_uint64_t; -#undef HAVE_PRPSINFO32_T -#define HAVE_PRPSINFO32_T -#undef HAVE_PRPSINFO32_T_PR_PID -#define HAVE_PRPSINFO32_T_PR_PID - #undef HAVE_PRSTATUS32_T #define HAVE_PRSTATUS32_T @@ -191,36 +186,6 @@ struct elf_prstatus64 int pr_fpvalid; /* True if math copro being used. */ }; -struct elf_prpsinfo32 - { - char pr_state; /* Numeric process state. */ - char pr_sname; /* Char for pr_state. */ - char pr_zomb; /* Zombie. */ - char pr_nice; /* Nice val. */ - unsigned int pr_flag; /* Flags. */ - unsigned short int pr_uid; - unsigned short int pr_gid; - int pr_pid, pr_ppid, pr_pgrp, pr_sid; - /* Lots missing */ - char pr_fname[16]; /* Filename of executable. */ - char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ - }; - -struct elf_prpsinfo64 - { - char pr_state; /* Numeric process state. */ - char pr_sname; /* Char for pr_state. */ - char pr_zomb; /* Zombie. */ - char pr_nice; /* Nice val. */ - a8_uint64_t pr_flag; /* Flags. */ - unsigned int pr_uid; - unsigned int pr_gid; - int pr_pid, pr_ppid, pr_pgrp, pr_sid; - /* Lots missing */ - char pr_fname[16]; /* Filename of executable. */ - char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ - }; - /* The rest of this file provides the types for emulation of the Solaris <proc_service.h> interfaces that should be implemented by users of libthread_db. */ @@ -229,5 +194,3 @@ struct elf_prpsinfo64 typedef struct elf_prstatus32 prstatus32_t; typedef struct elf_prstatusx32 prstatusx32_t; typedef struct elf_prstatus64 prstatus64_t; -typedef struct elf_prpsinfo32 prpsinfo32_t; -typedef struct elf_prpsinfo64 prpsinfo64_t; -- 1.7.7.6 ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: [PATCH/RFC 01/02 v2] Refactor PRPSINFO handling on Binutils 2013-01-04 4:40 ` Sergio Durigan Junior @ 2013-01-09 20:49 ` Sergio Durigan Junior 2013-01-10 18:26 ` Pedro Alves 1 sibling, 0 replies; 21+ messages in thread From: Sergio Durigan Junior @ 2013-01-09 20:49 UTC (permalink / raw) To: Jan Kratochvil; +Cc: Binutils Development, GDB Patches, Pedro Alves, H.J. Lu On Friday, January 04 2013, I wrote: > On Thursday, January 03 2013, I wrote: > >> Ops, sorry, I thought you were talking about the comment above the >> structure, and not about the "Lots missing". Then I agree, it can be >> removed. Sorry about the confusion. I will send an updated patch in a >> few moments. > > Here it is. Thanks for the comments. Ping. I can send an updated version if needed. Thanks, > 2013-01-04 Sergio Durigan Junior <sergiodj@redhat.com> > > * Makefile.in (BUILD_CFILES): Add `elf-psinfo.h'. > * elf-bfd.h (ELF_PRARGSZ): New conditional definition. > (elf_internal_prpsinfo): New structure declaration. > (elfcore_write_prpsinfo): Change prototype, accepting > `elf_internal_prpsinfo' as argument. > * elf-psinfo.h: New file. > * elf.c (elfcore_write_prpsinfo): Change prototype, accepting > `elf_internal_prpsinfo' as argument. Rewrite parts of the code to > make use of the new argument. > * elf32-arm.c: Include `elf-psinfo.h'. > (elf32_arm_nabi_write_core_note): Refactor `NT_PRPSINFO' case. > * elf32-i386.c: Include `elf-bfd.h', `elf-psinfo.h' and `stdarg.h'. > (elf_i386_write_core_note): New function. > * elf32-ppc.c: Include `elf-psinfo.h'. > (elf_external_ppc_prpsinfo32): New structure declaration. > (ppc_elf_write_core_note): Refactor `NT_PRPSINFO' case. > * elf64-ppc.c: Include `elf-psinfo.h'. > (ppc64_elf_write_core_note): Refactor `NT_PRPSINFO' case. > * elf64-x86-64.c: Include `elf-psinfo.h'. Include `stdarg.h' > unconditionally. > (elf_x86_64_write_core_note): Remove `#ifdef CORE_HEADER', making the > function unconditionally available. Refactor `NT_PRPSINFO' case. > Refactor `NT_PRSTATUS' case, making it conditional to `CORE_HEADER'. > * hosts/x86-64linux.h (HAVE_PRPSINFO32_T, HAVE_PRPSINFO32_T_PR_PID, > elf_prpsinfo32, elf_prpsinfo64, prpsinfo32_t, prpsinfo64_t): Remove > definitions, moving some of them to `elf-psinfo.h'. > > --- > bfd/Makefile.in | 2 +- > bfd/elf-bfd.h | 26 +++++++++- > bfd/elf-psinfo.h | 124 +++++++++++++++++++++++++++++++++++++++++++++++ > bfd/elf.c | 21 ++++---- > bfd/elf32-arm.c | 13 +++-- > bfd/elf32-i386.c | 37 ++++++++++++++ > bfd/elf32-ppc.c | 70 ++++++++++++++++++++++++-- > bfd/elf64-ppc.c | 14 +++-- > bfd/elf64-x86-64.c | 40 ++++++++------- > bfd/hosts/x86-64linux.h | 37 -------------- > 10 files changed, 302 insertions(+), 82 deletions(-) > create mode 100644 bfd/elf-psinfo.h > > diff --git a/bfd/Makefile.in b/bfd/Makefile.in > index c51c342..adea836 100644 > --- a/bfd/Makefile.in > +++ b/bfd/Makefile.in > @@ -1068,7 +1068,7 @@ BUILD_CFILES = \ > CFILES = $(SOURCE_CFILES) $(BUILD_CFILES) > SOURCE_HFILES = \ > aout-target.h aoutf1.h aoutx.h coffcode.h coffswap.h ecoffswap.h \ > - elf-bfd.h elf-hppa.h elf32-hppa.h \ > + elf-bfd.h elf-psinfo.h elf-hppa.h elf32-hppa.h \ > elf64-hppa.h elfcode.h elfcore.h \ > freebsd.h genlink.h go32stub.h \ > libaout.h libbfd.h libcoff.h libecoff.h libhppa.h libieee.h \ > diff --git a/bfd/elf-bfd.h b/bfd/elf-bfd.h > index b8d82b1..1572cba 100644 > --- a/bfd/elf-bfd.h > +++ b/bfd/elf-bfd.h > @@ -1722,6 +1722,30 @@ struct elf_obj_tdata > (elf_known_obj_attributes (bfd) [OBJ_ATTR_PROC]) > #define elf_other_obj_attributes_proc(bfd) \ > (elf_other_obj_attributes (bfd) [OBJ_ATTR_PROC]) > + > +/* Internal structure which holds information to be included in the > + PRPSINFO section of the corefile. > + > + This is an "internal" structure in the sense that it should be used to > + pass information to BFD (via the `elfcore_write_prpsinfo', for example), > + so things like endianess shouldn't be an issue. This structure will > + eventually be converted in one of the `elf_external_*' structures > + below. */ > + > +struct elf_internal_prpsinfo > + { > + char pr_state; /* Numeric process state. */ > + char pr_sname; /* Char for pr_state. */ > + char pr_zomb; /* Zombie. */ > + char pr_nice; /* Nice val. */ > + unsigned long pr_flag; /* Flags. */ > + unsigned int pr_uid; > + unsigned int pr_gid; > + int pr_pid, pr_ppid, pr_pgrp, pr_sid; > + char pr_fname[16 + 1]; /* Filename of executable. */ > + char pr_psargs[80 + 1]; /* Initial part of arg list. */ > + }; > + > \f > extern void _bfd_elf_swap_verdef_in > (bfd *, const Elf_External_Verdef *, Elf_Internal_Verdef *); > @@ -2238,7 +2262,7 @@ extern Elf_Internal_Phdr * _bfd_elf_find_segment_containing_section > extern char *elfcore_write_note > (bfd *, char *, int *, const char *, int, const void *, int); > extern char *elfcore_write_prpsinfo > - (bfd *, char *, int *, const char *, const char *); > + (bfd *, char *, int *, const struct elf_internal_prpsinfo *); > extern char *elfcore_write_prstatus > (bfd *, char *, int *, long, int, const void *); > extern char * elfcore_write_pstatus > diff --git a/bfd/elf-psinfo.h b/bfd/elf-psinfo.h > new file mode 100644 > index 0000000..6689a58 > --- /dev/null > +++ b/bfd/elf-psinfo.h > @@ -0,0 +1,124 @@ > +/* Definitions for PRPSINFO structures under ELF on GNU/Linux. > + Copyright 2013 Free Software Foundation, Inc. > + > + This file is part of BFD, the Binary File Descriptor library. > + > + 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 3 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., 51 Franklin Street - Fifth Floor, Boston, > + MA 02110-1301, USA. */ > + > +/* External 32-bit structure for PRPSINFO. This structure is ABI-defined, > + thus we choose to use char arrays here in order to avoid dealing with > + different types in different architectures. > + > + This structure will ultimately be written in the corefile's note section, > + as the PRPSINFO. */ > + > +struct elf_external_prpsinfo32 > + { > + char pr_state; /* Numeric process state. */ > + char pr_sname; /* Char for pr_state. */ > + char pr_zomb; /* Zombie. */ > + char pr_nice; /* Nice val. */ > + char pr_flag[4]; /* Flags. */ > + char pr_uid[2]; > + char pr_gid[2]; > + char pr_pid[4]; > + char pr_ppid[4]; > + char pr_pgrp[4]; > + char pr_sid[4]; > + char pr_fname[16]; /* Filename of executable. */ > + char pr_psargs[80]; /* Initial part of arg list. */ > + }; > + > +/* Helper macro to copy (properly handling endianess) things from the > + `elf_internal_prpsinfo' structure to the `elf_external_prpsinfo32' > + structure. > + > + Note that FROM should be a pointer, and TO should be the explicit type. */ > + > +#define PRPSINFO32_COPY_FIELDS(abfd, from, to) \ > + do \ > + { \ > + H_PUT_8 (abfd, from->pr_state, &to.pr_state); \ > + H_PUT_8 (abfd, from->pr_sname, &to.pr_sname); \ > + H_PUT_8 (abfd, from->pr_zomb, &to.pr_zomb); \ > + H_PUT_8 (abfd, from->pr_nice, &to.pr_nice); \ > + H_PUT_32 (abfd, from->pr_flag, to.pr_flag); \ > + H_PUT_16 (abfd, from->pr_uid, to.pr_uid); \ > + H_PUT_16 (abfd, from->pr_gid, to.pr_gid); \ > + H_PUT_32 (abfd, from->pr_pid, to.pr_pid); \ > + H_PUT_32 (abfd, from->pr_ppid, to.pr_ppid); \ > + H_PUT_32 (abfd, from->pr_pgrp, to.pr_pgrp); \ > + H_PUT_32 (abfd, from->pr_sid, to.pr_sid); \ > + strncpy (to.pr_fname, from->pr_fname, sizeof (to.pr_fname)); \ > + strncpy (to.pr_psargs, from->pr_psargs, sizeof (to.pr_psargs)); \ > + } while (0) > + > +/* External 64-bit structure for PRPSINFO. This structure is ABI-defined, > + thus we choose to use char arrays here in order to avoid dealing with > + different types in different architectures. > + > + Differently from the 32-bit version, the PowerPC guys made our lives better > + and used the same size as the other architectures. > + > + This structure will ultimately be written in the corefile's note section, > + as the PRPSINFO. */ > + > +struct elf_external_prpsinfo64 > + { > + char pr_state; /* Numeric process state. */ > + char pr_sname; /* Char for pr_state. */ > + char pr_zomb; /* Zombie. */ > + char pr_nice; /* Nice val. */ > + char pr_flag[8]; /* Flags. */ > + char gap[4]; > + char pr_uid[4]; > + char pr_gid[4]; > + char pr_pid[4]; > + char pr_ppid[4]; > + char pr_pgrp[4]; > + char pr_sid[4]; > + char pr_fname[16]; /* Filename of executable. */ > + char pr_psargs[80]; /* Initial part of arg list. */ > + }; > + > +/* Helper macro to copy (properly handling endianess) things from the > + `elf_internal_prpsinfo' structure to the `elf_external_prpsinfo64' > + structure. > + > + Note that FROM should be a pointer, and TO should be the explicit type. */ > + > +#define PRPSINFO64_COPY_FIELDS(abfd, from, to) \ > + do \ > + { \ > + H_PUT_8 (abfd, from->pr_state, &to.pr_state); \ > + H_PUT_8 (abfd, from->pr_sname, &to.pr_sname); \ > + H_PUT_8 (abfd, from->pr_zomb, &to.pr_zomb); \ > + H_PUT_8 (abfd, from->pr_nice, &to.pr_nice); \ > + H_PUT_64 (abfd, from->pr_flag, to.pr_flag); \ > + H_PUT_32 (abfd, from->pr_uid, to.pr_uid); \ > + H_PUT_32 (abfd, from->pr_gid, to.pr_gid); \ > + H_PUT_32 (abfd, from->pr_pid, to.pr_pid); \ > + H_PUT_32 (abfd, from->pr_ppid, to.pr_ppid); \ > + H_PUT_32 (abfd, from->pr_pgrp, to.pr_pgrp); \ > + H_PUT_32 (abfd, from->pr_sid, to.pr_sid); \ > + strncpy (to.pr_fname, from->pr_fname, sizeof (to.pr_fname)); \ > + strncpy (to.pr_psargs, from->pr_psargs, sizeof (to.pr_psargs)); \ > + } while (0) > + > +/* Process info. In the end we do provide typedefs for them. */ > + > +typedef struct elf_external_prpsinfo32 prpsinfo32; > +typedef struct elf_external_prpsinfo64 prpsinfo64; > diff --git a/bfd/elf.c b/bfd/elf.c > index 17e9ad4..c4f04ea 100644 > --- a/bfd/elf.c > +++ b/bfd/elf.c > @@ -44,6 +44,7 @@ SECTION > #include "elf-bfd.h" > #include "libiberty.h" > #include "safe-ctype.h" > +#include "elf-psinfo.h" > > #ifdef CORE_HEADER > #include CORE_HEADER > @@ -8165,7 +8166,7 @@ elfcore_grok_arm_vfp (bfd *abfd, Elf_Internal_Note *note) > #if defined (HAVE_PRPSINFO_T) > typedef prpsinfo_t elfcore_psinfo_t; > #if defined (HAVE_PRPSINFO32_T) /* Sparc64 cross Sparc32 */ > -typedef prpsinfo32_t elfcore_psinfo32_t; > +typedef prpsinfo32 elfcore_psinfo32_t; > #endif > #endif > > @@ -9063,16 +9064,16 @@ char * > elfcore_write_prpsinfo (bfd *abfd, > char *buf, > int *bufsiz, > - const char *fname, > - const char *psargs) > + const struct elf_internal_prpsinfo *input) > { > const struct elf_backend_data *bed = get_elf_backend_data (abfd); > > if (bed->elf_backend_write_core_note != NULL) > { > char *ret; > + > ret = (*bed->elf_backend_write_core_note) (abfd, buf, bufsiz, > - NT_PRPSINFO, fname, psargs); > + NT_PRPSINFO, input); > if (ret != NULL) > return ret; > } > @@ -9085,13 +9086,13 @@ elfcore_write_prpsinfo (bfd *abfd, > psinfo32_t data; > int note_type = NT_PSINFO; > #else > - prpsinfo32_t data; > + prpsinfo32 data; > int note_type = NT_PRPSINFO; > #endif > > memset (&data, 0, sizeof (data)); > - strncpy (data.pr_fname, fname, sizeof (data.pr_fname)); > - strncpy (data.pr_psargs, psargs, sizeof (data.pr_psargs)); > + strncpy (data.pr_fname, input->pr_fname, sizeof (data.pr_fname)); > + strncpy (data.pr_psargs, input->pr_psargs, sizeof (data.pr_psargs)); > return elfcore_write_note (abfd, buf, bufsiz, > "CORE", note_type, &data, sizeof (data)); > } > @@ -9102,13 +9103,13 @@ elfcore_write_prpsinfo (bfd *abfd, > psinfo_t data; > int note_type = NT_PSINFO; > #else > - prpsinfo_t data; > + prpsinfo64 data; > int note_type = NT_PRPSINFO; > #endif > > memset (&data, 0, sizeof (data)); > - strncpy (data.pr_fname, fname, sizeof (data.pr_fname)); > - strncpy (data.pr_psargs, psargs, sizeof (data.pr_psargs)); > + strncpy (data.pr_fname, input->pr_fname, sizeof (data.pr_fname)); > + strncpy (data.pr_psargs, input->pr_psargs, sizeof (data.pr_psargs)); > return elfcore_write_note (abfd, buf, bufsiz, > "CORE", note_type, &data, sizeof (data)); > } > diff --git a/bfd/elf32-arm.c b/bfd/elf32-arm.c > index e2f8a96..a354602 100644 > --- a/bfd/elf32-arm.c > +++ b/bfd/elf32-arm.c > @@ -30,6 +30,7 @@ > #include "elf-nacl.h" > #include "elf-vxworks.h" > #include "elf/arm.h" > +#include "elf-psinfo.h" > > /* Return the relocation section associated with NAME. HTAB is the > bfd's elf32_arm_link_hash_entry. */ > @@ -2004,17 +2005,19 @@ elf32_arm_nabi_write_core_note (bfd *abfd, char *buf, int *bufsiz, > > case NT_PRPSINFO: > { > - char data[124]; > + const struct elf_internal_prpsinfo *prpsinfo; > + struct elf_external_prpsinfo32 data; > va_list ap; > > va_start (ap, note_type); > - memset (data, 0, sizeof (data)); > - strncpy (data + 28, va_arg (ap, const char *), 16); > - strncpy (data + 44, va_arg (ap, const char *), 80); > + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); > va_end (ap); > > + memset (&data, 0, sizeof (data)); > + PRPSINFO32_COPY_FIELDS (abfd, prpsinfo, data); > + > return elfcore_write_note (abfd, buf, bufsiz, > - "CORE", note_type, data, sizeof (data)); > + "CORE", note_type, &data, sizeof (data)); > } > > case NT_PRSTATUS: > diff --git a/bfd/elf32-i386.c b/bfd/elf32-i386.c > index f76c7a7..45a1e26 100644 > --- a/bfd/elf32-i386.c > +++ b/bfd/elf32-i386.c > @@ -31,6 +31,10 @@ > #include "objalloc.h" > #include "hashtab.h" > #include "dwarf2.h" > +#include "elf-bfd.h" > +#include "elf-psinfo.h" > + > +#include <stdarg.h> > > /* 386 uses REL relocations instead of RELA. */ > #define USE_REL 1 > @@ -500,6 +504,38 @@ elf_i386_grok_psinfo (bfd *abfd, Elf_Internal_Note *note) > > return TRUE; > } > + > +static char * > +elf_i386_write_core_note (bfd *abfd, char *buf, int *bufsiz, > + int note_type, ...) > +{ > + va_list ap; > + > + switch (note_type) > + { > + default: > + return NULL; > + > + case NT_PRPSINFO: > + { > + const struct elf_internal_prpsinfo *prpsinfo; > + struct elf_external_prpsinfo32 data; > + > + va_start (ap, note_type); > + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); > + va_end (ap); > + > + memset (&data, 0, sizeof (data)); > + PRPSINFO32_COPY_FIELDS (abfd, prpsinfo, data); > + > + return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, > + &data, sizeof (data)); > + } > + /* NOTREACHED */ > + } > + /* NOTREACHED */ > +} > + > \f > /* Functions for the i386 ELF linker. > > @@ -5042,6 +5078,7 @@ elf_i386_add_symbol_hook (bfd * abfd, > #define elf_backend_gc_sweep_hook elf_i386_gc_sweep_hook > #define elf_backend_grok_prstatus elf_i386_grok_prstatus > #define elf_backend_grok_psinfo elf_i386_grok_psinfo > +#define elf_backend_write_core_note elf_i386_write_core_note > #define elf_backend_reloc_type_class elf_i386_reloc_type_class > #define elf_backend_relocate_section elf_i386_relocate_section > #define elf_backend_size_dynamic_sections elf_i386_size_dynamic_sections > diff --git a/bfd/elf32-ppc.c b/bfd/elf32-ppc.c > index 5241926..02d494f 100644 > --- a/bfd/elf32-ppc.c > +++ b/bfd/elf32-ppc.c > @@ -37,6 +37,7 @@ > #include "elf32-ppc.h" > #include "elf-vxworks.h" > #include "dwarf2.h" > +#include "elf-psinfo.h" > > typedef enum split16_format_type > { > @@ -1777,6 +1778,62 @@ static reloc_howto_type ppc_elf_howto_raw[] = { > 0xffff, /* dst_mask */ > FALSE), /* pcrel_offset */ > }; > + > +/* External 32-bit PPC structure for PRPSINFO. This structure is ABI-defined, > + thus we choose to use char arrays here in order to avoid dealing with > + different types in different architectures. > + > + The reason why we have a different structure only for PPC is because > + on this architecture (and *only* here!) the size of 32-bit structure > + changes. This is due to the different sizes of `pr_uid' and `pr_gid', > + which on non-PPC architectures are declared as `short int' and on PPC > + architectures are declared as `int'. > + > + This structure will ultimately be written in the corefile's note section, > + as the PRPSINFO. */ > + > +struct elf_external_ppc_prpsinfo32 > + { > + char pr_state; /* Numeric process state. */ > + char pr_sname; /* Char for pr_state. */ > + char pr_zomb; /* Zombie. */ > + char pr_nice; /* Nice val. */ > + char pr_flag[4]; /* Flags. */ > + char pr_uid[4]; > + char pr_gid[4]; > + char pr_pid[4]; > + char pr_ppid[4]; > + char pr_pgrp[4]; > + char pr_sid[4]; > + /* Lots missing */ > + char pr_fname[16]; /* Filename of executable. */ > + char pr_psargs[80]; /* Initial part of arg list. */ > + }; > + > +/* Helper macro to copy (properly handling endianess) things from the > + `elf_internal_prpsinfo' structure to the `elf_external_ppc_prpsinfo32' > + structure. > + > + Note that FROM should be a pointer, and TO should be the explicit type. */ > + > +#define PRPSINFO32_PPC_COPY_FIELDS(abfd, from, to) \ > + do \ > + { \ > + H_PUT_8 (abfd, from->pr_state, &to.pr_state); \ > + H_PUT_8 (abfd, from->pr_sname, &to.pr_sname); \ > + H_PUT_8 (abfd, from->pr_zomb, &to.pr_zomb); \ > + H_PUT_8 (abfd, from->pr_nice, &to.pr_nice); \ > + H_PUT_32 (abfd, from->pr_flag, to.pr_flag); \ > + H_PUT_32 (abfd, from->pr_uid, to.pr_uid); \ > + H_PUT_32 (abfd, from->pr_gid, to.pr_gid); \ > + H_PUT_32 (abfd, from->pr_pid, to.pr_pid); \ > + H_PUT_32 (abfd, from->pr_ppid, to.pr_ppid); \ > + H_PUT_32 (abfd, from->pr_pgrp, to.pr_pgrp); \ > + H_PUT_32 (abfd, from->pr_sid, to.pr_sid); \ > + strncpy (to.pr_fname, from->pr_fname, sizeof (to.pr_fname)); \ > + strncpy (to.pr_psargs, from->pr_psargs, sizeof (to.pr_psargs)); \ > + } while (0) > + > \f > /* Initialize the ppc_elf_howto_table, so that linear accesses can be done. */ > > @@ -2222,16 +2279,19 @@ ppc_elf_write_core_note (bfd *abfd, char *buf, int *bufsiz, int note_type, ...) > > case NT_PRPSINFO: > { > - char data[128]; > + const struct elf_internal_prpsinfo *prpsinfo; > + struct elf_external_ppc_prpsinfo32 data; > va_list ap; > > va_start (ap, note_type); > - memset (data, 0, sizeof (data)); > - strncpy (data + 32, va_arg (ap, const char *), 16); > - strncpy (data + 48, va_arg (ap, const char *), 80); > + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); > va_end (ap); > + > + memset (&data, 0, sizeof (data)); > + PRPSINFO32_PPC_COPY_FIELDS (abfd, prpsinfo, data); > + > return elfcore_write_note (abfd, buf, bufsiz, > - "CORE", note_type, data, sizeof (data)); > + "CORE", note_type, &data, sizeof (data)); > } > > case NT_PRSTATUS: > diff --git a/bfd/elf64-ppc.c b/bfd/elf64-ppc.c > index 10b6f9d..4eda989 100644 > --- a/bfd/elf64-ppc.c > +++ b/bfd/elf64-ppc.c > @@ -34,6 +34,7 @@ > #include "elf-bfd.h" > #include "elf/ppc64.h" > #include "elf64-ppc.h" > +#include "elf-psinfo.h" > #include "dwarf2.h" > > static bfd_reloc_status_type ppc64_elf_ha_reloc > @@ -2718,16 +2719,19 @@ ppc64_elf_write_core_note (bfd *abfd, char *buf, int *bufsiz, int note_type, > > case NT_PRPSINFO: > { > - char data[136]; > + const struct elf_internal_prpsinfo *prpsinfo; > + struct elf_external_prpsinfo64 data; > va_list ap; > > va_start (ap, note_type); > - memset (data, 0, sizeof (data)); > - strncpy (data + 40, va_arg (ap, const char *), 16); > - strncpy (data + 56, va_arg (ap, const char *), 80); > + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); > va_end (ap); > + > + memset (&data, 0, sizeof (data)); > + PRPSINFO64_COPY_FIELDS (abfd, prpsinfo, data); > + > return elfcore_write_note (abfd, buf, bufsiz, > - "CORE", note_type, data, sizeof (data)); > + "CORE", note_type, &data, sizeof (data)); > } > > case NT_PRSTATUS: > diff --git a/bfd/elf64-x86-64.c b/bfd/elf64-x86-64.c > index 92bf991..40ce80f 100644 > --- a/bfd/elf64-x86-64.c > +++ b/bfd/elf64-x86-64.c > @@ -32,11 +32,13 @@ > #include "hashtab.h" > #include "dwarf2.h" > #include "libiberty.h" > +#include "elf-psinfo.h" > + > +#include <stdarg.h> > > #include "elf/x86-64.h" > > #ifdef CORE_HEADER > -#include <stdarg.h> > #include CORE_HEADER > #endif > > @@ -415,14 +417,13 @@ elf_x86_64_grok_psinfo (bfd *abfd, Elf_Internal_Note *note) > return TRUE; > } > > -#ifdef CORE_HEADER > static char * > elf_x86_64_write_core_note (bfd *abfd, char *buf, int *bufsiz, > int note_type, ...) > { > const struct elf_backend_data *bed = get_elf_backend_data (abfd); > va_list ap; > - const char *fname, *psargs; > + const struct elf_internal_prpsinfo *prpsinfo; > long pid; > int cursig; > const void *gregs; > @@ -434,31 +435,33 @@ elf_x86_64_write_core_note (bfd *abfd, char *buf, int *bufsiz, > > case NT_PRPSINFO: > va_start (ap, note_type); > - fname = va_arg (ap, const char *); > - psargs = va_arg (ap, const char *); > + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); > va_end (ap); > > if (bed->s->elfclass == ELFCLASS32) > { > - prpsinfo32_t data; > - memset (&data, 0, sizeof (data)); > - strncpy (data.pr_fname, fname, sizeof (data.pr_fname)); > - strncpy (data.pr_psargs, psargs, sizeof (data.pr_psargs)); > + struct elf_external_prpsinfo32 data32; > + > + memset (&data32, 0, sizeof (data32)); > + PRPSINFO32_COPY_FIELDS (abfd, prpsinfo, data32); > + > return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, > - &data, sizeof (data)); > + &data32, sizeof (data32)); > } > else > { > - prpsinfo64_t data; > - memset (&data, 0, sizeof (data)); > - strncpy (data.pr_fname, fname, sizeof (data.pr_fname)); > - strncpy (data.pr_psargs, psargs, sizeof (data.pr_psargs)); > + struct elf_external_prpsinfo64 data64; > + > + memset (&data64, 0, sizeof (data64)); > + PRPSINFO64_COPY_FIELDS (abfd, prpsinfo, data64); > + > return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, > - &data, sizeof (data)); > + &data64, sizeof (data64)); > } > /* NOTREACHED */ > > case NT_PRSTATUS: > +#ifdef CORE_HEADER > va_start (ap, note_type); > pid = va_arg (ap, long); > cursig = va_arg (ap, int); > @@ -498,10 +501,13 @@ elf_x86_64_write_core_note (bfd *abfd, char *buf, int *bufsiz, > return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, > &prstat, sizeof (prstat)); > } > +#else > + return NULL; > +#endif /* CORE_HEADER */ > } > /* NOTREACHED */ > } > -#endif > + > \f > /* Functions for the x86-64 ELF linker. */ > > @@ -5157,9 +5163,7 @@ static const struct bfd_elf_special_section > #define elf_backend_gc_sweep_hook elf_x86_64_gc_sweep_hook > #define elf_backend_grok_prstatus elf_x86_64_grok_prstatus > #define elf_backend_grok_psinfo elf_x86_64_grok_psinfo > -#ifdef CORE_HEADER > #define elf_backend_write_core_note elf_x86_64_write_core_note > -#endif > #define elf_backend_reloc_type_class elf_x86_64_reloc_type_class > #define elf_backend_relocate_section elf_x86_64_relocate_section > #define elf_backend_size_dynamic_sections elf_x86_64_size_dynamic_sections > diff --git a/bfd/hosts/x86-64linux.h b/bfd/hosts/x86-64linux.h > index 78be09a..6070978 100644 > --- a/bfd/hosts/x86-64linux.h > +++ b/bfd/hosts/x86-64linux.h > @@ -43,11 +43,6 @@ typedef unsigned long long int uint64_t; > /* Unsigned 64-bit integer aligned to 8 bytes. */ > typedef uint64_t __attribute__ ((__aligned__ (8))) a8_uint64_t; > > -#undef HAVE_PRPSINFO32_T > -#define HAVE_PRPSINFO32_T > -#undef HAVE_PRPSINFO32_T_PR_PID > -#define HAVE_PRPSINFO32_T_PR_PID > - > #undef HAVE_PRSTATUS32_T > #define HAVE_PRSTATUS32_T > > @@ -191,36 +186,6 @@ struct elf_prstatus64 > int pr_fpvalid; /* True if math copro being used. */ > }; > > -struct elf_prpsinfo32 > - { > - char pr_state; /* Numeric process state. */ > - char pr_sname; /* Char for pr_state. */ > - char pr_zomb; /* Zombie. */ > - char pr_nice; /* Nice val. */ > - unsigned int pr_flag; /* Flags. */ > - unsigned short int pr_uid; > - unsigned short int pr_gid; > - int pr_pid, pr_ppid, pr_pgrp, pr_sid; > - /* Lots missing */ > - char pr_fname[16]; /* Filename of executable. */ > - char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ > - }; > - > -struct elf_prpsinfo64 > - { > - char pr_state; /* Numeric process state. */ > - char pr_sname; /* Char for pr_state. */ > - char pr_zomb; /* Zombie. */ > - char pr_nice; /* Nice val. */ > - a8_uint64_t pr_flag; /* Flags. */ > - unsigned int pr_uid; > - unsigned int pr_gid; > - int pr_pid, pr_ppid, pr_pgrp, pr_sid; > - /* Lots missing */ > - char pr_fname[16]; /* Filename of executable. */ > - char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ > - }; > - > /* The rest of this file provides the types for emulation of the > Solaris <proc_service.h> interfaces that should be implemented by > users of libthread_db. */ > @@ -229,5 +194,3 @@ struct elf_prpsinfo64 > typedef struct elf_prstatus32 prstatus32_t; > typedef struct elf_prstatusx32 prstatusx32_t; > typedef struct elf_prstatus64 prstatus64_t; > -typedef struct elf_prpsinfo32 prpsinfo32_t; > -typedef struct elf_prpsinfo64 prpsinfo64_t; > -- > 1.7.7.6 -- Sergio ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: [PATCH/RFC 01/02 v2] Refactor PRPSINFO handling on Binutils 2013-01-04 4:40 ` Sergio Durigan Junior 2013-01-09 20:49 ` Sergio Durigan Junior @ 2013-01-10 18:26 ` Pedro Alves 2013-01-10 19:47 ` Sergio Durigan Junior 1 sibling, 1 reply; 21+ messages in thread From: Pedro Alves @ 2013-01-10 18:26 UTC (permalink / raw) To: Sergio Durigan Junior Cc: Jan Kratochvil, Binutils Development, GDB Patches, H.J. Lu On 01/04/2013 04:39 AM, Sergio Durigan Junior wrote:> +++ b/bfd/elf-psinfo.h > @@ -0,0 +1,124 @@ > +/* Definitions for PRPSINFO structures under ELF on GNU/Linux. What about other OSs, like e.g., Solaris? > +/* External 64-bit structure for PRPSINFO. This structure is ABI-defined, > + thus we choose to use char arrays here in order to avoid dealing with > + different types in different architectures. > + > + Differently from the 32-bit version, the PowerPC guys made our lives better > + and used the same size as the other architectures. In the current revision, this comment appears out of the blue. Better would be to instead add a comment further up, above the 32-bit version stating that these are used by most architectures, although some define their own versions (like e.g., PPC). > + > + This structure will ultimately be written in the corefile's note section, > + as the PRPSINFO. */ > + > +struct elf_external_prpsinfo64 > +#define PRPSINFO32_COPY_FIELDS(abfd, from, to) \ > + do \ Personally, I'd prefer calling these SWAP instead of COPY, as you're not really doing straight copying, and "swap" is what bfd calls this idiom about everywhere. ... > +/* Process info. In the end we do provide typedefs for them. */ > + > +typedef struct elf_external_prpsinfo32 prpsinfo32; > +typedef struct elf_external_prpsinfo64 prpsinfo64; What's the point of these typedefs? To me, they just obscure things, and are easily confused with the host types... > @@ -8165,7 +8166,7 @@ elfcore_grok_arm_vfp (bfd *abfd, Elf_Internal_Note *note) > #if defined (HAVE_PRPSINFO_T) > typedef prpsinfo_t elfcore_psinfo_t; > #if defined (HAVE_PRPSINFO32_T) /* Sparc64 cross Sparc32 */ > -typedef prpsinfo32_t elfcore_psinfo32_t; > +typedef prpsinfo32 elfcore_psinfo32_t; ... like here. HAVE_PRPSINFO32_T/prpsinfo32_t were about a host type. prpsinfo32 is always defined (it's a bfd type). This in fact looks suspiciously wrong, and a potential breakage if in fact Sparc32 has a different psinfo32_t (what OS was that?), or in the other spots, some other arcane port/OS/arch having a different psinfo32_t than the Linux one. Either the #ifdef can be removed and this made unconditional, and host independent (the best), or the type should remain the host type (until all ports convert to implement elf_backend_write_core_note&co host-independent hooks). > #endif > #endif > > + The reason why we have a different structure only for PPC is because > + on this architecture (and *only* here!) the size of 32-bit structure This "only here" bit of the comment should go away, because it'll generate confusion whenever some other arch needs its own structure, making this outdated, because nobody will remember to update it. > @@ -415,14 +417,13 @@ elf_x86_64_grok_psinfo (bfd *abfd, Elf_Internal_Note *note) > return TRUE; > } > > -#ifdef CORE_HEADER > static char * > elf_x86_64_write_core_note (bfd *abfd, char *buf, int *bufsiz, > int note_type, ...) > { ... > case NT_PRSTATUS: > +#ifdef CORE_HEADER > va_start (ap, note_type); > pid = va_arg (ap, long); > cursig = va_arg (ap, int); > @@ -498,10 +501,13 @@ elf_x86_64_write_core_note (bfd *abfd, char *buf, int *bufsiz, > return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, > &prstat, sizeof (prstat)); > } > +#else > + return NULL; > +#endif /* CORE_HEADER */ > } > /* NOTREACHED */ > } > -#endif > + Do you plan on following up with similar treatment for prstatus? Thanks for doing this, -- Pedro Alves ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: [PATCH/RFC 01/02 v2] Refactor PRPSINFO handling on Binutils 2013-01-10 18:26 ` Pedro Alves @ 2013-01-10 19:47 ` Sergio Durigan Junior 2013-01-11 15:45 ` Pedro Alves 0 siblings, 1 reply; 21+ messages in thread From: Sergio Durigan Junior @ 2013-01-10 19:47 UTC (permalink / raw) To: Pedro Alves; +Cc: Jan Kratochvil, Binutils Development, GDB Patches, H.J. Lu Thanks for the review. On Thursday, January 10 2013, Pedro Alves wrote: > On 01/04/2013 04:39 AM, Sergio Durigan Junior wrote:> +++ b/bfd/elf-psinfo.h >> @@ -0,0 +1,124 @@ >> +/* Definitions for PRPSINFO structures under ELF on GNU/Linux. > > What about other OSs, like e.g., Solaris? Since I took the definitions from the Linux kernel, I thought it'd be better to explicitly mention that. I'm afraid I don't know how Solaris handle corefiles, do you think this comment should be expanded? >> +/* External 64-bit structure for PRPSINFO. This structure is ABI-defined, >> + thus we choose to use char arrays here in order to avoid dealing with >> + different types in different architectures. >> + >> + Differently from the 32-bit version, the PowerPC guys made our lives better >> + and used the same size as the other architectures. > > In the current revision, this comment appears out of the blue. > Better would be to instead add a comment further up, above the > 32-bit version stating that these are used by most architectures, > although some define their own versions (like e.g., PPC). You're right, the PowerPC note doesn't belong here, I will remove it, thanks. >> +/* Process info. In the end we do provide typedefs for them. */ >> + >> +typedef struct elf_external_prpsinfo32 prpsinfo32; >> +typedef struct elf_external_prpsinfo64 prpsinfo64; > > What's the point of these typedefs? To me, they just > obscure things, and are easily confused with the host > types... > >> @@ -8165,7 +8166,7 @@ elfcore_grok_arm_vfp (bfd *abfd, Elf_Internal_Note *note) >> #if defined (HAVE_PRPSINFO_T) >> typedef prpsinfo_t elfcore_psinfo_t; >> #if defined (HAVE_PRPSINFO32_T) /* Sparc64 cross Sparc32 */ >> -typedef prpsinfo32_t elfcore_psinfo32_t; >> +typedef prpsinfo32 elfcore_psinfo32_t; > > ... like here. HAVE_PRPSINFO32_T/prpsinfo32_t were > about a host type. prpsinfo32 is always defined (it's a > bfd type). This in fact looks suspiciously wrong, and a > potential breakage if in fact Sparc32 has a different > psinfo32_t (what OS was that?), or in the other spots, > some other arcane port/OS/arch having a different psinfo32_t > than the Linux one. Either the #ifdef can be removed and > this made unconditional, and host independent (the best), > or the type should remain the host type (until all ports > convert to implement elf_backend_write_core_note&co > host-independent hooks). Thanks for the explanation. I confess this is an area which I don't feel very confident, so I decided not to mess with anything and just leave things as they were. I will remove the typedef's from elf-psinfo.h. >> #endif >> #endif >> > >> + The reason why we have a different structure only for PPC is because >> + on this architecture (and *only* here!) the size of 32-bit structure > > This "only here" bit of the comment should go away, because > it'll generate confusion whenever some other arch needs > its own structure, making this outdated, because nobody > will remember to update it. Ops, sorry about it, I will remove. >> case NT_PRSTATUS: >> +#ifdef CORE_HEADER >> va_start (ap, note_type); >> pid = va_arg (ap, long); >> cursig = va_arg (ap, int); >> @@ -498,10 +501,13 @@ elf_x86_64_write_core_note (bfd *abfd, char *buf, int *bufsiz, >> return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, >> &prstat, sizeof (prstat)); >> } >> +#else >> + return NULL; >> +#endif /* CORE_HEADER */ >> } >> /* NOTREACHED */ >> } >> -#endif >> + > > Do you plan on following up with similar treatment for prstatus? Yeah, I was actually talking about it yesterday on #gdb. Since PRPSTATUS is quite similar, I believe it could be easily done as well. But first I am focusing on getting the PRPSINFO part upstream. Here is the updated version of the patch. Thanks. -- Sergio 2013-01-10 Sergio Durigan Junior <sergiodj@redhat.com> * Makefile.in (BUILD_CFILES): Add `elf-psinfo.h'. * elf-bfd.h (ELF_PRARGSZ): New conditional definition. (elf_internal_prpsinfo): New structure declaration. (elfcore_write_prpsinfo): Change prototype, accepting `elf_internal_prpsinfo' as argument. * elf-psinfo.h: New file. * elf.c (elfcore_write_prpsinfo): Change prototype, accepting `elf_internal_prpsinfo' as argument. Rewrite parts of the code to make use of the new argument. * elf32-arm.c: Include `elf-psinfo.h'. (elf32_arm_nabi_write_core_note): Refactor `NT_PRPSINFO' case. * elf32-i386.c: Include `elf-bfd.h', `elf-psinfo.h' and `stdarg.h'. (elf_i386_write_core_note): New function. * elf32-ppc.c: Include `elf-psinfo.h'. (elf_external_ppc_prpsinfo32): New structure declaration. (ppc_elf_write_core_note): Refactor `NT_PRPSINFO' case. * elf64-ppc.c: Include `elf-psinfo.h'. (ppc64_elf_write_core_note): Refactor `NT_PRPSINFO' case. * elf64-x86-64.c: Include `elf-psinfo.h'. Include `stdarg.h' unconditionally. (elf_x86_64_write_core_note): Remove `#ifdef CORE_HEADER', making the function unconditionally available. Refactor `NT_PRPSINFO' case. Refactor `NT_PRSTATUS' case, making it conditional to `CORE_HEADER'. * hosts/x86-64linux.h (HAVE_PRPSINFO32_T, HAVE_PRPSINFO32_T_PR_PID, elf_prpsinfo32, elf_prpsinfo64, prpsinfo32_t, prpsinfo64_t): Remove definitions. --- bfd/Makefile.in | 2 +- bfd/elf-bfd.h | 26 ++++++++++- bfd/elf-psinfo.h | 119 +++++++++++++++++++++++++++++++++++++++++++++++ bfd/elf.c | 15 +++--- bfd/elf32-arm.c | 13 +++-- bfd/elf32-i386.c | 37 +++++++++++++++ bfd/elf32-ppc.c | 70 +++++++++++++++++++++++++-- bfd/elf64-ppc.c | 14 ++++-- bfd/elf64-x86-64.c | 40 +++++++++------- bfd/hosts/x86-64linux.h | 37 --------------- 10 files changed, 294 insertions(+), 79 deletions(-) create mode 100644 bfd/elf-psinfo.h diff --git a/bfd/Makefile.in b/bfd/Makefile.in index af4e5ed..f6c8857 100644 --- a/bfd/Makefile.in +++ b/bfd/Makefile.in @@ -1072,7 +1072,7 @@ BUILD_CFILES = \ CFILES = $(SOURCE_CFILES) $(BUILD_CFILES) SOURCE_HFILES = \ aout-target.h aoutf1.h aoutx.h coffcode.h coffswap.h ecoffswap.h \ - elf-bfd.h elf-hppa.h elf32-hppa.h \ + elf-bfd.h elf-psinfo.h elf-hppa.h elf32-hppa.h \ elf64-hppa.h elfcode.h elfcore.h \ freebsd.h genlink.h go32stub.h \ libaout.h libbfd.h libcoff.h libecoff.h libhppa.h libieee.h \ diff --git a/bfd/elf-bfd.h b/bfd/elf-bfd.h index 43a077c..c035c0f 100644 --- a/bfd/elf-bfd.h +++ b/bfd/elf-bfd.h @@ -1723,6 +1723,30 @@ struct elf_obj_tdata (elf_known_obj_attributes (bfd) [OBJ_ATTR_PROC]) #define elf_other_obj_attributes_proc(bfd) \ (elf_other_obj_attributes (bfd) [OBJ_ATTR_PROC]) + +/* Internal structure which holds information to be included in the + PRPSINFO section of the corefile. + + This is an "internal" structure in the sense that it should be used to + pass information to BFD (via the `elfcore_write_prpsinfo', for example), + so things like endianess shouldn't be an issue. This structure will + eventually be converted in one of the `elf_external_*' structures + below. */ + +struct elf_internal_prpsinfo + { + char pr_state; /* Numeric process state. */ + char pr_sname; /* Char for pr_state. */ + char pr_zomb; /* Zombie. */ + char pr_nice; /* Nice val. */ + unsigned long pr_flag; /* Flags. */ + unsigned int pr_uid; + unsigned int pr_gid; + int pr_pid, pr_ppid, pr_pgrp, pr_sid; + char pr_fname[16 + 1]; /* Filename of executable. */ + char pr_psargs[80 + 1]; /* Initial part of arg list. */ + }; + \f extern void _bfd_elf_swap_verdef_in (bfd *, const Elf_External_Verdef *, Elf_Internal_Verdef *); @@ -2239,7 +2263,7 @@ extern Elf_Internal_Phdr * _bfd_elf_find_segment_containing_section extern char *elfcore_write_note (bfd *, char *, int *, const char *, int, const void *, int); extern char *elfcore_write_prpsinfo - (bfd *, char *, int *, const char *, const char *); + (bfd *, char *, int *, const struct elf_internal_prpsinfo *); extern char *elfcore_write_prstatus (bfd *, char *, int *, long, int, const void *); extern char * elfcore_write_pstatus diff --git a/bfd/elf-psinfo.h b/bfd/elf-psinfo.h new file mode 100644 index 0000000..e241842 --- /dev/null +++ b/bfd/elf-psinfo.h @@ -0,0 +1,119 @@ +/* Definitions for PRPSINFO structures under ELF on GNU/Linux. + Copyright 2013 Free Software Foundation, Inc. + + This file is part of BFD, the Binary File Descriptor library. + + 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 3 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., 51 Franklin Street - Fifth Floor, Boston, + MA 02110-1301, USA. */ + +/* The PRPSINFO structures defined below are used by most architectures, + although some of them define their own versions (like e.g., PPC). */ + +/* External 32-bit structure for PRPSINFO. This structure is ABI-defined, + thus we choose to use char arrays here in order to avoid dealing with + different types in different architectures. + + This structure will ultimately be written in the corefile's note section, + as the PRPSINFO. */ + +struct elf_external_prpsinfo32 + { + char pr_state; /* Numeric process state. */ + char pr_sname; /* Char for pr_state. */ + char pr_zomb; /* Zombie. */ + char pr_nice; /* Nice val. */ + char pr_flag[4]; /* Flags. */ + char pr_uid[2]; + char pr_gid[2]; + char pr_pid[4]; + char pr_ppid[4]; + char pr_pgrp[4]; + char pr_sid[4]; + char pr_fname[16]; /* Filename of executable. */ + char pr_psargs[80]; /* Initial part of arg list. */ + }; + +/* Helper macro to swap (properly handling endianess) things from the + `elf_internal_prpsinfo' structure to the `elf_external_prpsinfo32' + structure. + + Note that FROM should be a pointer, and TO should be the explicit type. */ + +#define PRPSINFO32_SWAP_FIELDS(abfd, from, to) \ + do \ + { \ + H_PUT_8 (abfd, from->pr_state, &to.pr_state); \ + H_PUT_8 (abfd, from->pr_sname, &to.pr_sname); \ + H_PUT_8 (abfd, from->pr_zomb, &to.pr_zomb); \ + H_PUT_8 (abfd, from->pr_nice, &to.pr_nice); \ + H_PUT_32 (abfd, from->pr_flag, to.pr_flag); \ + H_PUT_16 (abfd, from->pr_uid, to.pr_uid); \ + H_PUT_16 (abfd, from->pr_gid, to.pr_gid); \ + H_PUT_32 (abfd, from->pr_pid, to.pr_pid); \ + H_PUT_32 (abfd, from->pr_ppid, to.pr_ppid); \ + H_PUT_32 (abfd, from->pr_pgrp, to.pr_pgrp); \ + H_PUT_32 (abfd, from->pr_sid, to.pr_sid); \ + strncpy (to.pr_fname, from->pr_fname, sizeof (to.pr_fname)); \ + strncpy (to.pr_psargs, from->pr_psargs, sizeof (to.pr_psargs)); \ + } while (0) + +/* External 64-bit structure for PRPSINFO. This structure is ABI-defined, + thus we choose to use char arrays here in order to avoid dealing with + different types in different architectures. + + This structure will ultimately be written in the corefile's note section, + as the PRPSINFO. */ + +struct elf_external_prpsinfo64 + { + char pr_state; /* Numeric process state. */ + char pr_sname; /* Char for pr_state. */ + char pr_zomb; /* Zombie. */ + char pr_nice; /* Nice val. */ + char pr_flag[8]; /* Flags. */ + char gap[4]; + char pr_uid[4]; + char pr_gid[4]; + char pr_pid[4]; + char pr_ppid[4]; + char pr_pgrp[4]; + char pr_sid[4]; + char pr_fname[16]; /* Filename of executable. */ + char pr_psargs[80]; /* Initial part of arg list. */ + }; + +/* Helper macro to swap (properly handling endianess) things from the + `elf_internal_prpsinfo' structure to the `elf_external_prpsinfo64' + structure. + + Note that FROM should be a pointer, and TO should be the explicit type. */ + +#define PRPSINFO64_SWAP_FIELDS(abfd, from, to) \ + do \ + { \ + H_PUT_8 (abfd, from->pr_state, &to.pr_state); \ + H_PUT_8 (abfd, from->pr_sname, &to.pr_sname); \ + H_PUT_8 (abfd, from->pr_zomb, &to.pr_zomb); \ + H_PUT_8 (abfd, from->pr_nice, &to.pr_nice); \ + H_PUT_64 (abfd, from->pr_flag, to.pr_flag); \ + H_PUT_32 (abfd, from->pr_uid, to.pr_uid); \ + H_PUT_32 (abfd, from->pr_gid, to.pr_gid); \ + H_PUT_32 (abfd, from->pr_pid, to.pr_pid); \ + H_PUT_32 (abfd, from->pr_ppid, to.pr_ppid); \ + H_PUT_32 (abfd, from->pr_pgrp, to.pr_pgrp); \ + H_PUT_32 (abfd, from->pr_sid, to.pr_sid); \ + strncpy (to.pr_fname, from->pr_fname, sizeof (to.pr_fname)); \ + strncpy (to.pr_psargs, from->pr_psargs, sizeof (to.pr_psargs)); \ + } while (0) diff --git a/bfd/elf.c b/bfd/elf.c index 9cd3542..444bb44 100644 --- a/bfd/elf.c +++ b/bfd/elf.c @@ -45,6 +45,7 @@ SECTION #include "elf-bfd.h" #include "libiberty.h" #include "safe-ctype.h" +#include "elf-psinfo.h" #ifdef CORE_HEADER #include CORE_HEADER @@ -9103,16 +9104,16 @@ char * elfcore_write_prpsinfo (bfd *abfd, char *buf, int *bufsiz, - const char *fname, - const char *psargs) + const struct elf_internal_prpsinfo *input) { const struct elf_backend_data *bed = get_elf_backend_data (abfd); if (bed->elf_backend_write_core_note != NULL) { char *ret; + ret = (*bed->elf_backend_write_core_note) (abfd, buf, bufsiz, - NT_PRPSINFO, fname, psargs); + NT_PRPSINFO, input); if (ret != NULL) return ret; } @@ -9130,8 +9131,8 @@ elfcore_write_prpsinfo (bfd *abfd, #endif memset (&data, 0, sizeof (data)); - strncpy (data.pr_fname, fname, sizeof (data.pr_fname)); - strncpy (data.pr_psargs, psargs, sizeof (data.pr_psargs)); + strncpy (data.pr_fname, input->pr_fname, sizeof (data.pr_fname)); + strncpy (data.pr_psargs, input->pr_psargs, sizeof (data.pr_psargs)); return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, &data, sizeof (data)); } @@ -9147,8 +9148,8 @@ elfcore_write_prpsinfo (bfd *abfd, #endif memset (&data, 0, sizeof (data)); - strncpy (data.pr_fname, fname, sizeof (data.pr_fname)); - strncpy (data.pr_psargs, psargs, sizeof (data.pr_psargs)); + strncpy (data.pr_fname, input->pr_fname, sizeof (data.pr_fname)); + strncpy (data.pr_psargs, input->pr_psargs, sizeof (data.pr_psargs)); return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, &data, sizeof (data)); } diff --git a/bfd/elf32-arm.c b/bfd/elf32-arm.c index e2f8a96..c9c3d15 100644 --- a/bfd/elf32-arm.c +++ b/bfd/elf32-arm.c @@ -30,6 +30,7 @@ #include "elf-nacl.h" #include "elf-vxworks.h" #include "elf/arm.h" +#include "elf-psinfo.h" /* Return the relocation section associated with NAME. HTAB is the bfd's elf32_arm_link_hash_entry. */ @@ -2004,17 +2005,19 @@ elf32_arm_nabi_write_core_note (bfd *abfd, char *buf, int *bufsiz, case NT_PRPSINFO: { - char data[124]; + const struct elf_internal_prpsinfo *prpsinfo; + struct elf_external_prpsinfo32 data; va_list ap; va_start (ap, note_type); - memset (data, 0, sizeof (data)); - strncpy (data + 28, va_arg (ap, const char *), 16); - strncpy (data + 44, va_arg (ap, const char *), 80); + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); va_end (ap); + memset (&data, 0, sizeof (data)); + PRPSINFO32_SWAP_FIELDS (abfd, prpsinfo, data); + return elfcore_write_note (abfd, buf, bufsiz, - "CORE", note_type, data, sizeof (data)); + "CORE", note_type, &data, sizeof (data)); } case NT_PRSTATUS: diff --git a/bfd/elf32-i386.c b/bfd/elf32-i386.c index f76c7a7..b81b35b 100644 --- a/bfd/elf32-i386.c +++ b/bfd/elf32-i386.c @@ -31,6 +31,10 @@ #include "objalloc.h" #include "hashtab.h" #include "dwarf2.h" +#include "elf-bfd.h" +#include "elf-psinfo.h" + +#include <stdarg.h> /* 386 uses REL relocations instead of RELA. */ #define USE_REL 1 @@ -500,6 +504,38 @@ elf_i386_grok_psinfo (bfd *abfd, Elf_Internal_Note *note) return TRUE; } + +static char * +elf_i386_write_core_note (bfd *abfd, char *buf, int *bufsiz, + int note_type, ...) +{ + va_list ap; + + switch (note_type) + { + default: + return NULL; + + case NT_PRPSINFO: + { + const struct elf_internal_prpsinfo *prpsinfo; + struct elf_external_prpsinfo32 data; + + va_start (ap, note_type); + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); + va_end (ap); + + memset (&data, 0, sizeof (data)); + PRPSINFO32_SWAP_FIELDS (abfd, prpsinfo, data); + + return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, + &data, sizeof (data)); + } + /* NOTREACHED */ + } + /* NOTREACHED */ +} + \f /* Functions for the i386 ELF linker. @@ -5042,6 +5078,7 @@ elf_i386_add_symbol_hook (bfd * abfd, #define elf_backend_gc_sweep_hook elf_i386_gc_sweep_hook #define elf_backend_grok_prstatus elf_i386_grok_prstatus #define elf_backend_grok_psinfo elf_i386_grok_psinfo +#define elf_backend_write_core_note elf_i386_write_core_note #define elf_backend_reloc_type_class elf_i386_reloc_type_class #define elf_backend_relocate_section elf_i386_relocate_section #define elf_backend_size_dynamic_sections elf_i386_size_dynamic_sections diff --git a/bfd/elf32-ppc.c b/bfd/elf32-ppc.c index 5241926..429ccb2 100644 --- a/bfd/elf32-ppc.c +++ b/bfd/elf32-ppc.c @@ -37,6 +37,7 @@ #include "elf32-ppc.h" #include "elf-vxworks.h" #include "dwarf2.h" +#include "elf-psinfo.h" typedef enum split16_format_type { @@ -1777,6 +1778,62 @@ static reloc_howto_type ppc_elf_howto_raw[] = { 0xffff, /* dst_mask */ FALSE), /* pcrel_offset */ }; + +/* External 32-bit PPC structure for PRPSINFO. This structure is ABI-defined, + thus we choose to use char arrays here in order to avoid dealing with + different types in different architectures. + + The reason why we have a different structure only for PPC is because + on this architecture the size of 32-bit structure changes. This is + due to the different sizes of `pr_uid' and `pr_gid', which on non-PPC + architectures are declared as `short int' and on PPC architectures are + declared as `int'. + + This structure will ultimately be written in the corefile's note section, + as the PRPSINFO. */ + +struct elf_external_ppc_prpsinfo32 + { + char pr_state; /* Numeric process state. */ + char pr_sname; /* Char for pr_state. */ + char pr_zomb; /* Zombie. */ + char pr_nice; /* Nice val. */ + char pr_flag[4]; /* Flags. */ + char pr_uid[4]; + char pr_gid[4]; + char pr_pid[4]; + char pr_ppid[4]; + char pr_pgrp[4]; + char pr_sid[4]; + /* Lots missing */ + char pr_fname[16]; /* Filename of executable. */ + char pr_psargs[80]; /* Initial part of arg list. */ + }; + +/* Helper macro to swap (properly handling endianess) things from the + `elf_internal_prpsinfo' structure to the `elf_external_ppc_prpsinfo32' + structure. + + Note that FROM should be a pointer, and TO should be the explicit type. */ + +#define PRPSINFO32_PPC_SWAP_FIELDS(abfd, from, to) \ + do \ + { \ + H_PUT_8 (abfd, from->pr_state, &to.pr_state); \ + H_PUT_8 (abfd, from->pr_sname, &to.pr_sname); \ + H_PUT_8 (abfd, from->pr_zomb, &to.pr_zomb); \ + H_PUT_8 (abfd, from->pr_nice, &to.pr_nice); \ + H_PUT_32 (abfd, from->pr_flag, to.pr_flag); \ + H_PUT_32 (abfd, from->pr_uid, to.pr_uid); \ + H_PUT_32 (abfd, from->pr_gid, to.pr_gid); \ + H_PUT_32 (abfd, from->pr_pid, to.pr_pid); \ + H_PUT_32 (abfd, from->pr_ppid, to.pr_ppid); \ + H_PUT_32 (abfd, from->pr_pgrp, to.pr_pgrp); \ + H_PUT_32 (abfd, from->pr_sid, to.pr_sid); \ + strncpy (to.pr_fname, from->pr_fname, sizeof (to.pr_fname)); \ + strncpy (to.pr_psargs, from->pr_psargs, sizeof (to.pr_psargs)); \ + } while (0) + \f /* Initialize the ppc_elf_howto_table, so that linear accesses can be done. */ @@ -2222,16 +2279,19 @@ ppc_elf_write_core_note (bfd *abfd, char *buf, int *bufsiz, int note_type, ...) case NT_PRPSINFO: { - char data[128]; + const struct elf_internal_prpsinfo *prpsinfo; + struct elf_external_ppc_prpsinfo32 data; va_list ap; va_start (ap, note_type); - memset (data, 0, sizeof (data)); - strncpy (data + 32, va_arg (ap, const char *), 16); - strncpy (data + 48, va_arg (ap, const char *), 80); + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); va_end (ap); + + memset (&data, 0, sizeof (data)); + PRPSINFO32_PPC_SWAP_FIELDS (abfd, prpsinfo, data); + return elfcore_write_note (abfd, buf, bufsiz, - "CORE", note_type, data, sizeof (data)); + "CORE", note_type, &data, sizeof (data)); } case NT_PRSTATUS: diff --git a/bfd/elf64-ppc.c b/bfd/elf64-ppc.c index 10b6f9d..937ef7f 100644 --- a/bfd/elf64-ppc.c +++ b/bfd/elf64-ppc.c @@ -34,6 +34,7 @@ #include "elf-bfd.h" #include "elf/ppc64.h" #include "elf64-ppc.h" +#include "elf-psinfo.h" #include "dwarf2.h" static bfd_reloc_status_type ppc64_elf_ha_reloc @@ -2718,16 +2719,19 @@ ppc64_elf_write_core_note (bfd *abfd, char *buf, int *bufsiz, int note_type, case NT_PRPSINFO: { - char data[136]; + const struct elf_internal_prpsinfo *prpsinfo; + struct elf_external_prpsinfo64 data; va_list ap; va_start (ap, note_type); - memset (data, 0, sizeof (data)); - strncpy (data + 40, va_arg (ap, const char *), 16); - strncpy (data + 56, va_arg (ap, const char *), 80); + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); va_end (ap); + + memset (&data, 0, sizeof (data)); + PRPSINFO64_SWAP_FIELDS (abfd, prpsinfo, data); + return elfcore_write_note (abfd, buf, bufsiz, - "CORE", note_type, data, sizeof (data)); + "CORE", note_type, &data, sizeof (data)); } case NT_PRSTATUS: diff --git a/bfd/elf64-x86-64.c b/bfd/elf64-x86-64.c index 92bf991..b0f6194 100644 --- a/bfd/elf64-x86-64.c +++ b/bfd/elf64-x86-64.c @@ -32,11 +32,13 @@ #include "hashtab.h" #include "dwarf2.h" #include "libiberty.h" +#include "elf-psinfo.h" + +#include <stdarg.h> #include "elf/x86-64.h" #ifdef CORE_HEADER -#include <stdarg.h> #include CORE_HEADER #endif @@ -415,14 +417,13 @@ elf_x86_64_grok_psinfo (bfd *abfd, Elf_Internal_Note *note) return TRUE; } -#ifdef CORE_HEADER static char * elf_x86_64_write_core_note (bfd *abfd, char *buf, int *bufsiz, int note_type, ...) { const struct elf_backend_data *bed = get_elf_backend_data (abfd); va_list ap; - const char *fname, *psargs; + const struct elf_internal_prpsinfo *prpsinfo; long pid; int cursig; const void *gregs; @@ -434,31 +435,33 @@ elf_x86_64_write_core_note (bfd *abfd, char *buf, int *bufsiz, case NT_PRPSINFO: va_start (ap, note_type); - fname = va_arg (ap, const char *); - psargs = va_arg (ap, const char *); + prpsinfo = va_arg (ap, const struct elf_internal_prpsinfo *); va_end (ap); if (bed->s->elfclass == ELFCLASS32) { - prpsinfo32_t data; - memset (&data, 0, sizeof (data)); - strncpy (data.pr_fname, fname, sizeof (data.pr_fname)); - strncpy (data.pr_psargs, psargs, sizeof (data.pr_psargs)); + struct elf_external_prpsinfo32 data32; + + memset (&data32, 0, sizeof (data32)); + PRPSINFO32_SWAP_FIELDS (abfd, prpsinfo, data32); + return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, - &data, sizeof (data)); + &data32, sizeof (data32)); } else { - prpsinfo64_t data; - memset (&data, 0, sizeof (data)); - strncpy (data.pr_fname, fname, sizeof (data.pr_fname)); - strncpy (data.pr_psargs, psargs, sizeof (data.pr_psargs)); + struct elf_external_prpsinfo64 data64; + + memset (&data64, 0, sizeof (data64)); + PRPSINFO64_SWAP_FIELDS (abfd, prpsinfo, data64); + return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, - &data, sizeof (data)); + &data64, sizeof (data64)); } /* NOTREACHED */ case NT_PRSTATUS: +#ifdef CORE_HEADER va_start (ap, note_type); pid = va_arg (ap, long); cursig = va_arg (ap, int); @@ -498,10 +501,13 @@ elf_x86_64_write_core_note (bfd *abfd, char *buf, int *bufsiz, return elfcore_write_note (abfd, buf, bufsiz, "CORE", note_type, &prstat, sizeof (prstat)); } +#else + return NULL; +#endif /* CORE_HEADER */ } /* NOTREACHED */ } -#endif + \f /* Functions for the x86-64 ELF linker. */ @@ -5157,9 +5163,7 @@ static const struct bfd_elf_special_section #define elf_backend_gc_sweep_hook elf_x86_64_gc_sweep_hook #define elf_backend_grok_prstatus elf_x86_64_grok_prstatus #define elf_backend_grok_psinfo elf_x86_64_grok_psinfo -#ifdef CORE_HEADER #define elf_backend_write_core_note elf_x86_64_write_core_note -#endif #define elf_backend_reloc_type_class elf_x86_64_reloc_type_class #define elf_backend_relocate_section elf_x86_64_relocate_section #define elf_backend_size_dynamic_sections elf_x86_64_size_dynamic_sections diff --git a/bfd/hosts/x86-64linux.h b/bfd/hosts/x86-64linux.h index 78be09a..6070978 100644 --- a/bfd/hosts/x86-64linux.h +++ b/bfd/hosts/x86-64linux.h @@ -43,11 +43,6 @@ typedef unsigned long long int uint64_t; /* Unsigned 64-bit integer aligned to 8 bytes. */ typedef uint64_t __attribute__ ((__aligned__ (8))) a8_uint64_t; -#undef HAVE_PRPSINFO32_T -#define HAVE_PRPSINFO32_T -#undef HAVE_PRPSINFO32_T_PR_PID -#define HAVE_PRPSINFO32_T_PR_PID - #undef HAVE_PRSTATUS32_T #define HAVE_PRSTATUS32_T @@ -191,36 +186,6 @@ struct elf_prstatus64 int pr_fpvalid; /* True if math copro being used. */ }; -struct elf_prpsinfo32 - { - char pr_state; /* Numeric process state. */ - char pr_sname; /* Char for pr_state. */ - char pr_zomb; /* Zombie. */ - char pr_nice; /* Nice val. */ - unsigned int pr_flag; /* Flags. */ - unsigned short int pr_uid; - unsigned short int pr_gid; - int pr_pid, pr_ppid, pr_pgrp, pr_sid; - /* Lots missing */ - char pr_fname[16]; /* Filename of executable. */ - char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ - }; - -struct elf_prpsinfo64 - { - char pr_state; /* Numeric process state. */ - char pr_sname; /* Char for pr_state. */ - char pr_zomb; /* Zombie. */ - char pr_nice; /* Nice val. */ - a8_uint64_t pr_flag; /* Flags. */ - unsigned int pr_uid; - unsigned int pr_gid; - int pr_pid, pr_ppid, pr_pgrp, pr_sid; - /* Lots missing */ - char pr_fname[16]; /* Filename of executable. */ - char pr_psargs[ELF_PRARGSZ]; /* Initial part of arg list. */ - }; - /* The rest of this file provides the types for emulation of the Solaris <proc_service.h> interfaces that should be implemented by users of libthread_db. */ @@ -229,5 +194,3 @@ struct elf_prpsinfo64 typedef struct elf_prstatus32 prstatus32_t; typedef struct elf_prstatusx32 prstatusx32_t; typedef struct elf_prstatus64 prstatus64_t; -typedef struct elf_prpsinfo32 prpsinfo32_t; -typedef struct elf_prpsinfo64 prpsinfo64_t; -- 1.7.7.6 ^ permalink raw reply [flat|nested] 21+ messages in thread
* Re: [PATCH/RFC 01/02 v2] Refactor PRPSINFO handling on Binutils 2013-01-10 19:47 ` Sergio Durigan Junior @ 2013-01-11 15:45 ` Pedro Alves 0 siblings, 0 replies; 21+ messages in thread From: Pedro Alves @ 2013-01-11 15:45 UTC (permalink / raw) To: Sergio Durigan Junior Cc: Jan Kratochvil, Binutils Development, GDB Patches, H.J. Lu On 01/10/2013 07:47 PM, Sergio Durigan Junior wrote: >> On 01/04/2013 04:39 AM, Sergio Durigan Junior wrote:> +++ b/bfd/elf-psinfo.h >>> @@ -0,0 +1,124 @@ >>> +/* Definitions for PRPSINFO structures under ELF on GNU/Linux. >> >> What about other OSs, like e.g., Solaris? > > Since I took the definitions from the Linux kernel, I thought it'd be > better to explicitly mention that. I'm afraid I don't know how Solaris > handle corefiles, do you think this comment should be expanded? It's not that different on other Unixen, but the structures may be different. But I'm actually pondering about is whether we're tying the whole new interface to Linux, causing problems for converting other non-Linux ports. E.g., a quick websearch for prpsinfo finds: http://bintree.net/freebsd/d0/ddc/sys_2procfs_8h_source.html 00075 typedef struct prpsinfo { 00076 int pr_version; /* Version number of struct (1) */ 00077 size_t pr_psinfosz; /* sizeof(prpsinfo_t) (1) */ 00078 char pr_fname[PRFNAMESZ+1]; /* Command name, null terminated (1) */ 00079 char pr_psargs[PRARGSZ+1]; /* Arguments, null terminated (1) */ 00080 } prpsinfo_t; Other BSDs are probably similar, Solaris, IRIX, etc., will probably have a different structure in their own ways. So indeed it looks like there's a problem here, and I think these differences need to be contemplated. How is the question. One way would be for the hook to still take a "struct elf_internal_prpsinfo" pointer, but make it so that "struct elf_internal_prpsinfo" itself is opaque to the common code. Both GDB's core generator code, and then bfd's elf_backend_write_core_note hook would then have to agree on what the type of "struct elf_internal_prpsinfo" really is, and either cast appropriately (e.g., to/from struct elf_linux_internal_prpsinfo), or including a file that has the proper definition of "struct elf_internal_prpsinfo" for the target (I think that violates C++'s ODR, so I tend to dislike it, although gdb/binutils do this for other similar cases). This is largely what the patch does already, except it takes no consideration, either in naming or in comments that "struct elf_internal_prpsinfo" is Linux specific, giving the impression that it'd work for all ports. But it doesn't look like it would. E.g., elf64-x86-64.c:elf_x86_64_write_core_note with the patch is always using the Linux specific structure. We need to instead have a Linux-specific version of that hook; comments at the top of the file show it's used with FreeBSD and Solaris too as well, and those will need their own versions (could be the current pre-patch version). Etc. -- Pedro Alves ^ permalink raw reply [flat|nested] 21+ messages in thread
end of thread, other threads:[~2013-01-11 15:45 UTC | newest] Thread overview: 21+ messages (download: mbox.gz / follow: Atom feed) -- links below jump to the message on this page -- 2012-12-17 3:10 [PATCH/RFC 01/02 v2] Refactor PRPSINFO handling on Binutils Sergio Durigan Junior 2012-12-17 15:43 ` H.J. Lu 2012-12-17 17:41 ` Sergio Durigan Junior 2012-12-17 17:44 ` H.J. Lu 2012-12-17 17:51 ` Sergio Durigan Junior 2012-12-17 22:01 ` H.J. Lu 2012-12-18 5:47 ` Sergio Durigan Junior 2012-12-18 15:43 ` H.J. Lu 2012-12-18 17:38 ` Jan Kratochvil 2012-12-18 19:19 ` Sergio Durigan Junior 2012-12-18 19:43 ` Jan Kratochvil 2012-12-30 1:50 ` Sergio Durigan Junior 2013-01-01 14:30 ` Jan Kratochvil 2013-01-02 23:32 ` Sergio Durigan Junior 2013-01-03 13:44 ` Jan Kratochvil 2013-01-03 15:46 ` Sergio Durigan Junior 2013-01-04 4:40 ` Sergio Durigan Junior 2013-01-09 20:49 ` Sergio Durigan Junior 2013-01-10 18:26 ` Pedro Alves 2013-01-10 19:47 ` Sergio Durigan Junior 2013-01-11 15:45 ` Pedro Alves
This is a public inbox, see mirroring instructions for how to clone and mirror all data and code used for this inbox; as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).