crash/gdb-7.6-ppc64le-support.patch
Dave Anderson f64b1a5954 Implement support for the ppc64le PPC64 little-endian architecture.
Since this required a large number of patches to be applied to
architecture-neutral files in the gdb-7.6 tree, the changes are
only applied if the host build system is a ppc64le.
(ptesarik@suse.cz, normand@linux.vnet.ibm.com)
2014-09-05 10:34:10 -04:00

4951 lines
171 KiB
Diff
Raw Blame History

This file contains invisible Unicode characters

This file contains invisible Unicode characters that are indistinguishable to humans but may be processed differently by a computer. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

#
# gdb-7.6-ppc64_sysv_abi_push_float.patch
#
From: Tiago Daitx <tdaitx@sourceware.org>
Date: Mon Apr 1 04:05:35 2013 +0000
Git-commit: d81e75c0756f21d2c3d45ce86d8b45c65f01ef67
References: ppc64le enablement
gdb/ChangeLog
2013-03-01 Tiago Stürmer Daitx <tdaitx@linux.vnet.ibm.com>
* ppc-sysv-tdep.c (ppc64_sysv_abi_push_float): New function.
(ppc64_sysv_abi_push_dummy_call): Handle complex arguments.
Acked-by: Petr Tesarik <ptesarik@suse.cz>
---
gdb/ChangeLog | 5 +
gdb/ppc-sysv-tdep.c | 196 +++++++++++++++++++++++++++++++++-------------------
2 files changed, 131 insertions(+), 70 deletions(-)
--- a/gdb/ChangeLog
+++ b/gdb/ChangeLog
@@ -1,3 +1,8 @@
+2013-03-31 Tiago Stürmer Daitx <tdaitx@linux.vnet.ibm.com>
+
+ * ppc-sysv-tdep.c (ppc64_sysv_abi_push_float): New function.
+ (ppc64_sysv_abi_push_dummy_call): Handle complex arguments.
+
2013-04-26 Joel Brobecker <brobecker@adacore.com>
* NEWS: Change "since GDB 7.5" into "in GDB 7.6".
--- a/gdb/ppc-sysv-tdep.c
+++ b/gdb/ppc-sysv-tdep.c
@@ -1101,6 +1101,83 @@ convert_code_addr_to_desc_addr (CORE_ADD
return 1;
}
+/* Push a float in either registers, or in the stack. Using the ppc 64 bit
+ SysV ABI.
+
+ This implements a dumbed down version of the ABI. It always writes
+ values to memory, GPR and FPR, even when not necessary. Doing this
+ greatly simplifies the logic. */
+
+static void
+ppc64_sysv_abi_push_float (struct gdbarch *gdbarch, struct regcache *regcache,
+ struct gdbarch_tdep *tdep, struct type *type,
+ const bfd_byte *val, int freg, int greg,
+ CORE_ADDR gparam)
+{
+ gdb_byte regval[MAX_REGISTER_SIZE];
+ const gdb_byte *p;
+
+ if (TYPE_LENGTH (type) <= 8)
+ {
+ /* Version 1.7 of the 64-bit PowerPC ELF ABI says:
+
+ "Single precision floating point values are mapped to
+ the first word in a single doubleword."
+
+ And version 1.9 says:
+
+ "Single precision floating point values are mapped to
+ the second word in a single doubleword."
+
+ GDB then writes single precision floating point values
+ at both words in a doubleword, to support both ABIs. */
+ if (TYPE_LENGTH (type) == 4)
+ {
+ memcpy (regval, val, 4);
+ memcpy (regval + 4, val, 4);
+ p = regval;
+ }
+ else
+ p = val;
+
+ /* Write value in the stack's parameter save area. */
+ write_memory (gparam, p, 8);
+
+ /* Floats and Doubles go in f1 .. f13. They also consume a left aligned
+ GREG, and can end up in memory. */
+ if (freg <= 13)
+ {
+ struct type *regtype;
+
+ regtype = register_type (gdbarch, tdep->ppc_fp0_regnum + freg);
+ convert_typed_floating (val, type, regval, regtype);
+ regcache_cooked_write (regcache, tdep->ppc_fp0_regnum + freg, regval);
+ }
+ if (greg <= 10)
+ regcache_cooked_write (regcache, tdep->ppc_gp0_regnum + greg, regval);
+ }
+ else
+ {
+ /* IBM long double stored in two doublewords of the
+ parameter save area and corresponding registers. */
+ if (!tdep->soft_float && freg <= 13)
+ {
+ regcache_cooked_write (regcache, tdep->ppc_fp0_regnum + freg, val);
+ if (freg <= 12)
+ regcache_cooked_write (regcache, tdep->ppc_fp0_regnum + freg + 1,
+ val + 8);
+ }
+ if (greg <= 10)
+ {
+ regcache_cooked_write (regcache, tdep->ppc_gp0_regnum + greg, val);
+ if (greg <= 9)
+ regcache_cooked_write (regcache, tdep->ppc_gp0_regnum + greg + 1,
+ val + 8);
+ }
+ write_memory (gparam, val, TYPE_LENGTH (type));
+ }
+}
+
/* Pass the arguments in either registers, or in the stack. Using the
ppc 64 bit SysV ABI.
@@ -1218,53 +1295,9 @@ ppc64_sysv_abi_push_dummy_call (struct g
if (TYPE_CODE (type) == TYPE_CODE_FLT && TYPE_LENGTH (type) <= 8)
{
- /* Floats and Doubles go in f1 .. f13. They also
- consume a left aligned GREG,, and can end up in
- memory. */
if (write_pass)
- {
- gdb_byte regval[MAX_REGISTER_SIZE];
- const gdb_byte *p;
-
- /* Version 1.7 of the 64-bit PowerPC ELF ABI says:
-
- "Single precision floating point values are mapped to
- the first word in a single doubleword."
-
- And version 1.9 says:
-
- "Single precision floating point values are mapped to
- the second word in a single doubleword."
-
- GDB then writes single precision floating point values
- at both words in a doubleword, to support both ABIs. */
- if (TYPE_LENGTH (type) == 4)
- {
- memcpy (regval, val, 4);
- memcpy (regval + 4, val, 4);
- p = regval;
- }
- else
- p = val;
-
- /* Write value in the stack's parameter save area. */
- write_memory (gparam, p, 8);
-
- if (freg <= 13)
- {
- struct type *regtype
- = register_type (gdbarch, tdep->ppc_fp0_regnum);
-
- convert_typed_floating (val, type, regval, regtype);
- regcache_cooked_write (regcache,
- tdep->ppc_fp0_regnum + freg,
- regval);
- }
- if (greg <= 10)
- regcache_cooked_write (regcache,
- tdep->ppc_gp0_regnum + greg,
- regval);
- }
+ ppc64_sysv_abi_push_float (gdbarch, regcache, tdep, type,
+ val, freg, greg, gparam);
freg++;
greg++;
@@ -1276,35 +1309,58 @@ ppc64_sysv_abi_push_dummy_call (struct g
&& (gdbarch_long_double_format (gdbarch)
== floatformats_ibm_long_double))
{
- /* IBM long double stored in two doublewords of the
- parameter save area and corresponding registers. */
if (write_pass)
+ ppc64_sysv_abi_push_float (gdbarch, regcache, tdep, type,
+ val, freg, greg, gparam);
+ freg += 2;
+ greg += 2;
+ gparam = align_up (gparam + TYPE_LENGTH (type), tdep->wordsize);
+ }
+ else if (TYPE_CODE (type) == TYPE_CODE_COMPLEX
+ && (TYPE_LENGTH (type) == 8 || TYPE_LENGTH (type) == 16))
+ {
+ int i;
+
+ for (i = 0; i < 2; i++)
{
- if (!tdep->soft_float && freg <= 13)
- {
- regcache_cooked_write (regcache,
- tdep->ppc_fp0_regnum + freg,
- val);
- if (freg <= 12)
- regcache_cooked_write (regcache,
- tdep->ppc_fp0_regnum + freg + 1,
- val + 8);
- }
- if (greg <= 10)
+ if (write_pass)
{
- regcache_cooked_write (regcache,
- tdep->ppc_gp0_regnum + greg,
- val);
- if (greg <= 9)
- regcache_cooked_write (regcache,
- tdep->ppc_gp0_regnum + greg + 1,
- val + 8);
+ struct type *target_type;
+
+ target_type = check_typedef (TYPE_TARGET_TYPE (type));
+ ppc64_sysv_abi_push_float (gdbarch, regcache, tdep,
+ target_type, val + i *
+ TYPE_LENGTH (target_type),
+ freg, greg, gparam);
}
- write_memory (gparam, val, TYPE_LENGTH (type));
+ freg++;
+ greg++;
+ /* Always consume parameter stack space. */
+ gparam = align_up (gparam + 8, tdep->wordsize);
+ }
+ }
+ else if (TYPE_CODE (type) == TYPE_CODE_COMPLEX
+ && TYPE_LENGTH (type) == 32
+ && (gdbarch_long_double_format (gdbarch)
+ == floatformats_ibm_long_double))
+ {
+ int i;
+
+ for (i = 0; i < 2; i++)
+ {
+ struct type *target_type;
+
+ target_type = check_typedef (TYPE_TARGET_TYPE (type));
+ if (write_pass)
+ ppc64_sysv_abi_push_float (gdbarch, regcache, tdep,
+ target_type, val + i *
+ TYPE_LENGTH (target_type),
+ freg, greg, gparam);
+ freg += 2;
+ greg += 2;
+ gparam = align_up (gparam + TYPE_LENGTH (target_type),
+ tdep->wordsize);
}
- freg += 2;
- greg += 2;
- gparam = align_up (gparam + TYPE_LENGTH (type), tdep->wordsize);
}
else if (TYPE_CODE (type) == TYPE_CODE_DECFLOAT
&& TYPE_LENGTH (type) <= 8)
#
# gdb-7.6-bound_minimal_symbol.patch
#
From: Tom Tromey <tromey@redhat.com>
Date: Mon Apr 8 19:59:09 2013 +0000
Git-commit: 7cbd4a934e9cf3808e1199c62e65b4c25b24b4e5
References: ppc64le enablement
* minsyms.h (struct bound_minimal_symbol): New.
(lookup_minimal_symbol_and_objfile): Return bound_minimal_symbol.
Remove objfile argument.
(lookup_minimal_symbol_by_pc_section, lookup_minimal_symbol_by_pc):
Return bound_minimal_symbol.
* minsyms.c (lookup_minimal_symbol_by_pc_1)
(lookup_minimal_symbol_by_pc_section, lookup_minimal_symbol_by_pc):
Return bound_minimal_symbol.
(in_gnu_ifunc_stub): Update.
(lookup_minimal_symbol_and_objfile): Return bound_minimal_symbol.
Remove 'objfile_p' argument.
(lookup_solib_trampoline_symbol_by_pc): Update.
* ada-tasks.c, amd64-windows-tdep.c, arm-tdep.c,
arm-wince-tdep.c, block.c, blockframe.c, breakpoint.c, btrace.c,
c-valprint.c, dwarf2loc.c, elfread.c, frame.c, frv-tdep.c,
glibc-tdep.c, gnu-v2-abi.c, gnu-v3-abi.c, hppa-hpux-tdep.c,
i386-tdep.c, ia64-tdep.c, infcall.c, infcmd.c, jit.c,
linux-fork.c, m32c-tdep.c, m68hc11-tdep.c, maint.c,
mips-tdep.c, p-valprint.c, parse.c, ppc-linux-tdep.c,
ppc-sysv-tdep.c, printcmd.c, rs6000-tdep.c, sh64-tdep.c,
stack.c, symtab.c, tui/tui-disasm.c: Update.
Acked-by: Petr Tesarik <ptesarik@suse.cz>
---
gdb/ChangeLog | 24 +++++++++++++++++++
gdb/ada-tasks.c | 6 ++--
gdb/amd64-windows-tdep.c | 12 +++++----
gdb/arm-tdep.c | 23 +++++++++---------
gdb/arm-wince-tdep.c | 14 +++++------
gdb/block.c | 5 ++--
gdb/blockframe.c | 8 +++---
gdb/breakpoint.c | 6 ++--
gdb/btrace.c | 8 +++---
gdb/c-valprint.c | 14 +++++------
gdb/coff-pe-read.c | 19 ++++++---------
gdb/dwarf2loc.c | 51 ++++++++++++++++++++++++------------------
gdb/elfread.c | 10 ++++----
gdb/frame.c | 2 -
gdb/frv-tdep.c | 8 +++---
gdb/glibc-tdep.c | 11 ++++-----
gdb/gnu-v2-abi.c | 6 ++--
gdb/gnu-v3-abi.c | 4 +--
gdb/hppa-hpux-tdep.c | 37 +++++++++++++++++-------------
gdb/i386-tdep.c | 10 ++++----
gdb/ia64-tdep.c | 4 +--
gdb/infcall.c | 6 ++--
gdb/infcmd.c | 6 ++--
gdb/jit.c | 18 ++++++++------
gdb/linux-fork.c | 6 ++--
gdb/m32c-tdep.c | 15 ++++++------
gdb/m68hc11-tdep.c | 8 +++---
gdb/maint.c | 10 ++++----
gdb/minsyms.c | 57 ++++++++++++++++++++++++++++++++---------------
gdb/minsyms.h | 32 ++++++++++++++++++--------
gdb/mips-tdep.c | 48 +++++++++++++++++++--------------------
gdb/p-valprint.c | 13 +++++-----
gdb/parse.c | 7 +++--
gdb/ppc-linux-tdep.c | 9 ++++---
gdb/ppc-sysv-tdep.c | 7 +++--
gdb/printcmd.c | 5 ++--
gdb/rs6000-tdep.c | 16 ++++++-------
gdb/sh64-tdep.c | 6 ++--
gdb/stack.c | 28 ++++++++++++-----------
gdb/symtab.c | 23 +++++++++---------
gdb/tui/tui-disasm.c | 2 -
41 files changed, 345 insertions(+), 259 deletions(-)
--- a/gdb/ChangeLog
+++ b/gdb/ChangeLog
@@ -1,3 +1,27 @@
+2013-04-08 Tom Tromey <tromey@redhat.com>
+
+ * minsyms.h (struct bound_minimal_symbol): New.
+ (lookup_minimal_symbol_and_objfile): Return bound_minimal_symbol.
+ Remove objfile argument.
+ (lookup_minimal_symbol_by_pc_section, lookup_minimal_symbol_by_pc):
+ Return bound_minimal_symbol.
+ * minsyms.c (lookup_minimal_symbol_by_pc_1)
+ (lookup_minimal_symbol_by_pc_section, lookup_minimal_symbol_by_pc):
+ Return bound_minimal_symbol.
+ (in_gnu_ifunc_stub): Update.
+ (lookup_minimal_symbol_and_objfile): Return bound_minimal_symbol.
+ Remove 'objfile_p' argument.
+ (lookup_solib_trampoline_symbol_by_pc): Update.
+ * ada-tasks.c, amd64-windows-tdep.c, arm-tdep.c,
+ arm-wince-tdep.c, block.c, blockframe.c, breakpoint.c, btrace.c,
+ c-valprint.c, dwarf2loc.c, elfread.c, frame.c, frv-tdep.c,
+ glibc-tdep.c, gnu-v2-abi.c, gnu-v3-abi.c, hppa-hpux-tdep.c,
+ i386-tdep.c, ia64-tdep.c, infcall.c, infcmd.c, jit.c,
+ linux-fork.c, m32c-tdep.c, m68hc11-tdep.c, maint.c,
+ mips-tdep.c, p-valprint.c, parse.c, ppc-linux-tdep.c,
+ ppc-sysv-tdep.c, printcmd.c, rs6000-tdep.c, sh64-tdep.c,
+ stack.c, symtab.c, tui/tui-disasm.c: Update.
+
2013-03-31 Tiago Stürmer Daitx <tdaitx@linux.vnet.ibm.com>
* ppc-sysv-tdep.c (ppc64_sysv_abi_push_float): New function.
--- a/gdb/ada-tasks.c
+++ b/gdb/ada-tasks.c
@@ -635,12 +635,12 @@ read_atcb (CORE_ADDR task_id, struct ada
sizeof (task_info->name) - 1);
else
{
- struct minimal_symbol *msym;
+ struct bound_minimal_symbol msym;
msym = lookup_minimal_symbol_by_pc (task_id);
- if (msym)
+ if (msym.minsym)
{
- const char *full_name = SYMBOL_LINKAGE_NAME (msym);
+ const char *full_name = SYMBOL_LINKAGE_NAME (msym.minsym);
const char *task_name = full_name;
const char *p;
--- a/gdb/amd64-windows-tdep.c
+++ b/gdb/amd64-windows-tdep.c
@@ -140,14 +140,14 @@ amd64_skip_main_prologue (struct gdbarch
if (target_read_memory (pc + 1, buf, sizeof buf) == 0)
{
- struct minimal_symbol *s;
+ struct bound_minimal_symbol s;
CORE_ADDR call_dest;
call_dest = pc + 5 + extract_signed_integer (buf, 4, byte_order);
s = lookup_minimal_symbol_by_pc (call_dest);
- if (s != NULL
- && SYMBOL_LINKAGE_NAME (s) != NULL
- && strcmp (SYMBOL_LINKAGE_NAME (s), "__main") == 0)
+ if (s.minsym != NULL
+ && SYMBOL_LINKAGE_NAME (s.minsym) != NULL
+ && strcmp (SYMBOL_LINKAGE_NAME (s.minsym), "__main") == 0)
pc += 5;
}
}
@@ -175,7 +175,9 @@ amd64_windows_skip_trampoline_code (stru
CORE_ADDR indirect_addr = pc + offset + 6;
struct minimal_symbol *indsym
- = indirect_addr ? lookup_minimal_symbol_by_pc (indirect_addr) : NULL;
+ = (indirect_addr
+ ? lookup_minimal_symbol_by_pc (indirect_addr).minsym
+ : NULL);
const char *symname = indsym ? SYMBOL_LINKAGE_NAME (indsym) : NULL;
if (symname)
--- a/gdb/arm-tdep.c
+++ b/gdb/arm-tdep.c
@@ -381,7 +381,7 @@ arm_find_mapping_symbol (CORE_ADDR memad
int
arm_pc_is_thumb (struct gdbarch *gdbarch, CORE_ADDR memaddr)
{
- struct minimal_symbol *sym;
+ struct bound_minimal_symbol sym;
char type;
struct displaced_step_closure* dsc
= get_displaced_step_closure_by_addr(memaddr);
@@ -423,8 +423,8 @@ arm_pc_is_thumb (struct gdbarch *gdbarch
/* Thumb functions have a "special" bit set in minimal symbols. */
sym = lookup_minimal_symbol_by_pc (memaddr);
- if (sym)
- return (MSYMBOL_IS_SPECIAL (sym));
+ if (sym.minsym)
+ return (MSYMBOL_IS_SPECIAL (sym.minsym));
/* If the user wants to override the fallback mode, let them. */
if (strcmp (arm_fallback_mode_string, "arm") == 0)
@@ -468,14 +468,14 @@ static int
skip_prologue_function (struct gdbarch *gdbarch, CORE_ADDR pc, int is_thumb)
{
enum bfd_endian byte_order_for_code = gdbarch_byte_order_for_code (gdbarch);
- struct minimal_symbol *msym;
+ struct bound_minimal_symbol msym;
msym = lookup_minimal_symbol_by_pc (pc);
- if (msym != NULL
- && SYMBOL_VALUE_ADDRESS (msym) == pc
- && SYMBOL_LINKAGE_NAME (msym) != NULL)
+ if (msym.minsym != NULL
+ && SYMBOL_VALUE_ADDRESS (msym.minsym) == pc
+ && SYMBOL_LINKAGE_NAME (msym.minsym) != NULL)
{
- const char *name = SYMBOL_LINKAGE_NAME (msym);
+ const char *name = SYMBOL_LINKAGE_NAME (msym.minsym);
/* The GNU linker's Thumb call stub to foo is named
__foo_from_thumb. */
@@ -1284,7 +1284,7 @@ arm_skip_stack_protector(CORE_ADDR pc, s
{
enum bfd_endian byte_order_for_code = gdbarch_byte_order_for_code (gdbarch);
unsigned int basereg;
- struct minimal_symbol *stack_chk_guard;
+ struct bound_minimal_symbol stack_chk_guard;
int offset;
int is_thumb = arm_pc_is_thumb (gdbarch, pc);
CORE_ADDR addr;
@@ -1299,8 +1299,9 @@ arm_skip_stack_protector(CORE_ADDR pc, s
/* If name of symbol doesn't start with '__stack_chk_guard', this
instruction sequence is not for stack protector. If symbol is
removed, we conservatively think this sequence is for stack protector. */
- if (stack_chk_guard
- && strncmp (SYMBOL_LINKAGE_NAME (stack_chk_guard), "__stack_chk_guard",
+ if (stack_chk_guard.minsym
+ && strncmp (SYMBOL_LINKAGE_NAME (stack_chk_guard.minsym),
+ "__stack_chk_guard",
strlen ("__stack_chk_guard")) != 0)
return pc;
--- a/gdb/arm-wince-tdep.c
+++ b/gdb/arm-wince-tdep.c
@@ -43,7 +43,7 @@ arm_pe_skip_trampoline_code (struct fram
struct gdbarch *gdbarch = get_frame_arch (frame);
enum bfd_endian byte_order = gdbarch_byte_order (gdbarch);
ULONGEST indirect;
- struct minimal_symbol *indsym;
+ struct bound_minimal_symbol indsym;
const char *symname;
CORE_ADDR next_pc;
@@ -62,10 +62,10 @@ arm_pe_skip_trampoline_code (struct fram
return 0;
indsym = lookup_minimal_symbol_by_pc (indirect);
- if (indsym == NULL)
+ if (indsym.minsym == NULL)
return 0;
- symname = SYMBOL_LINKAGE_NAME (indsym);
+ symname = SYMBOL_LINKAGE_NAME (indsym.minsym);
if (symname == NULL || strncmp (symname, "__imp_", 6) != 0)
return 0;
@@ -100,11 +100,11 @@ arm_wince_skip_main_prologue (struct gdb
long offset = sign_extend (this_instr & 0x000fffff, 23) << 2;
CORE_ADDR call_dest = (pc + 8 + offset) & 0xffffffffU;
- struct minimal_symbol *s = lookup_minimal_symbol_by_pc (call_dest);
+ struct bound_minimal_symbol s = lookup_minimal_symbol_by_pc (call_dest);
- if (s != NULL
- && SYMBOL_LINKAGE_NAME (s) != NULL
- && strcmp (SYMBOL_LINKAGE_NAME (s), "__gccmain") == 0)
+ if (s.minsym != NULL
+ && SYMBOL_LINKAGE_NAME (s.minsym) != NULL
+ && strcmp (SYMBOL_LINKAGE_NAME (s.minsym), "__gccmain") == 0)
pc += 4;
}
--- a/gdb/block.c
+++ b/gdb/block.c
@@ -208,7 +208,7 @@ call_site_for_pc (struct gdbarch *gdbarc
if (slot == NULL)
{
- struct minimal_symbol *msym = lookup_minimal_symbol_by_pc (pc);
+ struct bound_minimal_symbol msym = lookup_minimal_symbol_by_pc (pc);
/* DW_TAG_gnu_call_site will be missing just if GCC could not determine
the call target. */
@@ -216,7 +216,8 @@ call_site_for_pc (struct gdbarch *gdbarc
_("DW_OP_GNU_entry_value resolving cannot find "
"DW_TAG_GNU_call_site %s in %s"),
paddress (gdbarch, pc),
- msym == NULL ? "???" : SYMBOL_PRINT_NAME (msym));
+ (msym.minsym == NULL ? "???"
+ : SYMBOL_PRINT_NAME (msym.minsym)));
}
return *slot;
--- a/gdb/blockframe.c
+++ b/gdb/blockframe.c
@@ -88,7 +88,7 @@ CORE_ADDR
get_pc_function_start (CORE_ADDR pc)
{
struct block *bl;
- struct minimal_symbol *msymbol;
+ struct bound_minimal_symbol msymbol;
bl = block_for_pc (pc);
if (bl)
@@ -103,9 +103,9 @@ get_pc_function_start (CORE_ADDR pc)
}
msymbol = lookup_minimal_symbol_by_pc (pc);
- if (msymbol)
+ if (msymbol.minsym)
{
- CORE_ADDR fstart = SYMBOL_VALUE_ADDRESS (msymbol);
+ CORE_ADDR fstart = SYMBOL_VALUE_ADDRESS (msymbol.minsym);
if (find_pc_section (fstart))
return fstart;
@@ -218,7 +218,7 @@ find_pc_partial_function_gnu_ifunc (CORE
&& section == cache_pc_function_section)
goto return_cached_value;
- msymbol = lookup_minimal_symbol_by_pc_section (mapped_pc, section);
+ msymbol = lookup_minimal_symbol_by_pc_section (mapped_pc, section).minsym;
ALL_OBJFILES (objfile)
{
if (objfile->sf)
--- a/gdb/breakpoint.c
+++ b/gdb/breakpoint.c
@@ -9824,14 +9824,14 @@ resolve_sal_pc (struct symtab_and_line *
if we have line numbers but no functions (as can
happen in assembly source). */
- struct minimal_symbol *msym;
+ struct bound_minimal_symbol msym;
struct cleanup *old_chain = save_current_space_and_thread ();
switch_to_program_space_and_thread (sal->pspace);
msym = lookup_minimal_symbol_by_pc (sal->pc);
- if (msym)
- sal->section = SYMBOL_OBJ_SECTION (msym);
+ if (msym.minsym)
+ sal->section = SYMBOL_OBJ_SECTION (msym.minsym);
do_cleanups (old_chain);
}
--- a/gdb/btrace.c
+++ b/gdb/btrace.c
@@ -272,7 +272,7 @@ compute_ftrace (VEC (btrace_inst_s) *itr
for (idx = 0; VEC_iterate (btrace_inst_s, itrace, idx, binst); ++idx)
{
struct symtab_and_line sal;
- struct minimal_symbol *mfun;
+ struct bound_minimal_symbol mfun;
struct symbol *fun;
const char *filename;
CORE_ADDR pc;
@@ -285,7 +285,7 @@ compute_ftrace (VEC (btrace_inst_s) *itr
fun = find_pc_function (pc);
mfun = lookup_minimal_symbol_by_pc (pc);
- if (fun == NULL && mfun == NULL)
+ if (fun == NULL && mfun.minsym == NULL)
{
DEBUG_FTRACE ("no symbol at %u, pc=%s", idx,
core_addr_to_string_nz (pc));
@@ -293,11 +293,11 @@ compute_ftrace (VEC (btrace_inst_s) *itr
}
/* If we're switching functions, we start over. */
- if (ftrace_function_switched (bfun, mfun, fun))
+ if (ftrace_function_switched (bfun, mfun.minsym, fun))
{
bfun = VEC_safe_push (btrace_func_s, ftrace, NULL);
- ftrace_init_func (bfun, mfun, fun, idx);
+ ftrace_init_func (bfun, mfun.minsym, fun, idx);
ftrace_debug (bfun, "init");
}
--- a/gdb/c-valprint.c
+++ b/gdb/c-valprint.c
@@ -310,18 +310,18 @@ c_val_print (struct type *type, const gd
CORE_ADDR vt_address = unpack_pointer (type,
valaddr
+ embedded_offset);
- struct minimal_symbol *msymbol =
- lookup_minimal_symbol_by_pc (vt_address);
+ struct bound_minimal_symbol msymbol =
+ lookup_minimal_symbol_by_pc (vt_address);
/* If 'symbol_print' is set, we did the work above. */
if (!options->symbol_print
- && (msymbol != NULL)
- && (vt_address == SYMBOL_VALUE_ADDRESS (msymbol)))
+ && (msymbol.minsym != NULL)
+ && (vt_address == SYMBOL_VALUE_ADDRESS (msymbol.minsym)))
{
if (want_space)
fputs_filtered (" ", stream);
fputs_filtered (" <", stream);
- fputs_filtered (SYMBOL_PRINT_NAME (msymbol), stream);
+ fputs_filtered (SYMBOL_PRINT_NAME (msymbol.minsym), stream);
fputs_filtered (">", stream);
want_space = 1;
}
@@ -337,8 +337,8 @@ c_val_print (struct type *type, const gd
if (want_space)
fputs_filtered (" ", stream);
- if (msymbol != NULL)
- wsym = lookup_symbol (SYMBOL_LINKAGE_NAME (msymbol),
+ if (msymbol.minsym != NULL)
+ wsym = lookup_symbol (SYMBOL_LINKAGE_NAME (msymbol.minsym),
block, VAR_DOMAIN,
&is_this_fld);
--- a/gdb/coff-pe-read.c
+++ b/gdb/coff-pe-read.c
@@ -203,8 +203,7 @@ add_pe_forwarded_sym (const char *sym_na
const char *dll_name, struct objfile *objfile)
{
CORE_ADDR vma;
- struct objfile *forward_objfile;
- struct minimal_symbol *msymbol;
+ struct bound_minimal_symbol msymbol;
short section;
enum minimal_symbol_type msymtype;
int dll_name_len = strlen (dll_name);
@@ -218,20 +217,18 @@ add_pe_forwarded_sym (const char *sym_na
forward_func_name);
- msymbol = lookup_minimal_symbol_and_objfile (forward_qualified_name,
- &forward_objfile);
+ msymbol = lookup_minimal_symbol_and_objfile (forward_qualified_name);
- if (!msymbol)
+ if (!msymbol.minsym)
{
int i;
for (i = 0; i < forward_dll_name_len; i++)
forward_qualified_name[i] = tolower (forward_qualified_name[i]);
- msymbol = lookup_minimal_symbol_and_objfile (forward_qualified_name,
- &forward_objfile);
+ msymbol = lookup_minimal_symbol_and_objfile (forward_qualified_name);
}
- if (!msymbol)
+ if (!msymbol.minsym)
{
if (debug_coff_pe_read)
fprintf_unfiltered (gdb_stdlog, _("Unable to find function \"%s\" in"
@@ -246,9 +243,9 @@ add_pe_forwarded_sym (const char *sym_na
" \"%s\" in dll \"%s\", pointing to \"%s\"\n"),
sym_name, dll_name, forward_qualified_name);
- vma = SYMBOL_VALUE_ADDRESS (msymbol);
- section = SYMBOL_SECTION (msymbol);
- msymtype = MSYMBOL_TYPE (msymbol);
+ vma = SYMBOL_VALUE_ADDRESS (msymbol.minsym);
+ section = SYMBOL_SECTION (msymbol.minsym);
+ msymtype = MSYMBOL_TYPE (msymbol.minsym);
/* Generate a (hopefully unique) qualified name using the first part
of the dll name, e.g. KERNEL32!AddAtomA. This matches the style
--- a/gdb/dwarf2loc.c
+++ b/gdb/dwarf2loc.c
@@ -500,19 +500,20 @@ call_site_to_target_addr (struct gdbarch
dwarf_block = FIELD_DWARF_BLOCK (call_site->target);
if (dwarf_block == NULL)
{
- struct minimal_symbol *msym;
+ struct bound_minimal_symbol msym;
msym = lookup_minimal_symbol_by_pc (call_site->pc - 1);
throw_error (NO_ENTRY_VALUE_ERROR,
_("DW_AT_GNU_call_site_target is not specified "
"at %s in %s"),
paddress (call_site_gdbarch, call_site->pc),
- msym == NULL ? "???" : SYMBOL_PRINT_NAME (msym));
+ (msym.minsym == NULL ? "???"
+ : SYMBOL_PRINT_NAME (msym.minsym)));
}
if (caller_frame == NULL)
{
- struct minimal_symbol *msym;
+ struct bound_minimal_symbol msym;
msym = lookup_minimal_symbol_by_pc (call_site->pc - 1);
throw_error (NO_ENTRY_VALUE_ERROR,
@@ -520,7 +521,8 @@ call_site_to_target_addr (struct gdbarch
"requires known frame which is currently not "
"available at %s in %s"),
paddress (call_site_gdbarch, call_site->pc),
- msym == NULL ? "???" : SYMBOL_PRINT_NAME (msym));
+ (msym.minsym == NULL ? "???"
+ : SYMBOL_PRINT_NAME (msym.minsym)));
}
caller_arch = get_frame_arch (caller_frame);
@@ -547,7 +549,7 @@ call_site_to_target_addr (struct gdbarch
msym = lookup_minimal_symbol (physname, NULL, NULL);
if (msym == NULL)
{
- msym = lookup_minimal_symbol_by_pc (call_site->pc - 1);
+ msym = lookup_minimal_symbol_by_pc (call_site->pc - 1).minsym;
throw_error (NO_ENTRY_VALUE_ERROR,
_("Cannot find function \"%s\" for a call site target "
"at %s in %s"),
@@ -643,14 +645,15 @@ func_verify_no_selftailcall (struct gdba
if (target_addr == verify_addr)
{
- struct minimal_symbol *msym;
+ struct bound_minimal_symbol msym;
msym = lookup_minimal_symbol_by_pc (verify_addr);
throw_error (NO_ENTRY_VALUE_ERROR,
_("DW_OP_GNU_entry_value resolving has found "
"function \"%s\" at %s can call itself via tail "
"calls"),
- msym == NULL ? "???" : SYMBOL_PRINT_NAME (msym),
+ (msym.minsym == NULL ? "???"
+ : SYMBOL_PRINT_NAME (msym.minsym)),
paddress (gdbarch, verify_addr));
}
@@ -674,10 +677,11 @@ static void
tailcall_dump (struct gdbarch *gdbarch, const struct call_site *call_site)
{
CORE_ADDR addr = call_site->pc;
- struct minimal_symbol *msym = lookup_minimal_symbol_by_pc (addr - 1);
+ struct bound_minimal_symbol msym = lookup_minimal_symbol_by_pc (addr - 1);
fprintf_unfiltered (gdb_stdlog, " %s(%s)", paddress (gdbarch, addr),
- msym == NULL ? "???" : SYMBOL_PRINT_NAME (msym));
+ (msym.minsym == NULL ? "???"
+ : SYMBOL_PRINT_NAME (msym.minsym)));
}
@@ -907,7 +911,7 @@ call_site_find_chain_1 (struct gdbarch *
if (retval == NULL)
{
- struct minimal_symbol *msym_caller, *msym_callee;
+ struct bound_minimal_symbol msym_caller, msym_callee;
msym_caller = lookup_minimal_symbol_by_pc (caller_pc);
msym_callee = lookup_minimal_symbol_by_pc (callee_pc);
@@ -915,11 +919,11 @@ call_site_find_chain_1 (struct gdbarch *
_("There are no unambiguously determinable intermediate "
"callers or callees between caller function \"%s\" at %s "
"and callee function \"%s\" at %s"),
- (msym_caller == NULL
- ? "???" : SYMBOL_PRINT_NAME (msym_caller)),
+ (msym_caller.minsym == NULL
+ ? "???" : SYMBOL_PRINT_NAME (msym_caller.minsym)),
paddress (gdbarch, caller_pc),
- (msym_callee == NULL
- ? "???" : SYMBOL_PRINT_NAME (msym_callee)),
+ (msym_callee.minsym == NULL
+ ? "???" : SYMBOL_PRINT_NAME (msym_callee.minsym)),
paddress (gdbarch, callee_pc));
}
@@ -1011,7 +1015,8 @@ dwarf_expr_reg_to_entry_parameter (struc
caller_frame = get_prev_frame (frame);
if (gdbarch != frame_unwind_arch (frame))
{
- struct minimal_symbol *msym = lookup_minimal_symbol_by_pc (func_addr);
+ struct bound_minimal_symbol msym
+ = lookup_minimal_symbol_by_pc (func_addr);
struct gdbarch *caller_gdbarch = frame_unwind_arch (frame);
throw_error (NO_ENTRY_VALUE_ERROR,
@@ -1019,18 +1024,21 @@ dwarf_expr_reg_to_entry_parameter (struc
"(of %s (%s)) does not match caller gdbarch %s"),
gdbarch_bfd_arch_info (gdbarch)->printable_name,
paddress (gdbarch, func_addr),
- msym == NULL ? "???" : SYMBOL_PRINT_NAME (msym),
+ (msym.minsym == NULL ? "???"
+ : SYMBOL_PRINT_NAME (msym.minsym)),
gdbarch_bfd_arch_info (caller_gdbarch)->printable_name);
}
if (caller_frame == NULL)
{
- struct minimal_symbol *msym = lookup_minimal_symbol_by_pc (func_addr);
+ struct bound_minimal_symbol msym
+ = lookup_minimal_symbol_by_pc (func_addr);
throw_error (NO_ENTRY_VALUE_ERROR, _("DW_OP_GNU_entry_value resolving "
"requires caller of %s (%s)"),
paddress (gdbarch, func_addr),
- msym == NULL ? "???" : SYMBOL_PRINT_NAME (msym));
+ (msym.minsym == NULL ? "???"
+ : SYMBOL_PRINT_NAME (msym.minsym)));
}
caller_pc = get_frame_pc (caller_frame);
call_site = call_site_for_pc (gdbarch, caller_pc);
@@ -1040,8 +1048,8 @@ dwarf_expr_reg_to_entry_parameter (struc
{
struct minimal_symbol *target_msym, *func_msym;
- target_msym = lookup_minimal_symbol_by_pc (target_addr);
- func_msym = lookup_minimal_symbol_by_pc (func_addr);
+ target_msym = lookup_minimal_symbol_by_pc (target_addr).minsym;
+ func_msym = lookup_minimal_symbol_by_pc (func_addr).minsym;
throw_error (NO_ENTRY_VALUE_ERROR,
_("DW_OP_GNU_entry_value resolving expects callee %s at %s "
"but the called frame is for %s at %s"),
@@ -1064,7 +1072,8 @@ dwarf_expr_reg_to_entry_parameter (struc
}
if (iparams == call_site->parameter_count)
{
- struct minimal_symbol *msym = lookup_minimal_symbol_by_pc (caller_pc);
+ struct minimal_symbol *msym
+ = lookup_minimal_symbol_by_pc (caller_pc).minsym;
/* DW_TAG_GNU_call_site_parameter will be missing just if GCC could not
determine its value. */
--- a/gdb/elfread.c
+++ b/gdb/elfread.c
@@ -735,7 +735,7 @@ elf_gnu_ifunc_cache_eq (const void *a_vo
static int
elf_gnu_ifunc_record_cache (const char *name, CORE_ADDR addr)
{
- struct minimal_symbol *msym;
+ struct bound_minimal_symbol msym;
asection *sect;
struct objfile *objfile;
htab_t htab;
@@ -743,13 +743,13 @@ elf_gnu_ifunc_record_cache (const char *
void **slot;
msym = lookup_minimal_symbol_by_pc (addr);
- if (msym == NULL)
+ if (msym.minsym == NULL)
return 0;
- if (SYMBOL_VALUE_ADDRESS (msym) != addr)
+ if (SYMBOL_VALUE_ADDRESS (msym.minsym) != addr)
return 0;
/* minimal symbols have always SYMBOL_OBJ_SECTION non-NULL. */
- sect = SYMBOL_OBJ_SECTION (msym)->the_bfd_section;
- objfile = SYMBOL_OBJ_SECTION (msym)->objfile;
+ sect = SYMBOL_OBJ_SECTION (msym.minsym)->the_bfd_section;
+ objfile = SYMBOL_OBJ_SECTION (msym.minsym)->objfile;
/* If .plt jumps back to .plt the symbol is still deferred for later
resolution and it has no use for GDB. Besides ".text" this symbol can
--- a/gdb/frame.c
+++ b/gdb/frame.c
@@ -1678,7 +1678,7 @@ get_prev_frame_1 (struct frame_info *thi
/* gcc -fsplit-stack __morestack can continue the stack anywhere. */
this_pc_in_block = get_frame_address_in_block (this_frame);
- morestack_msym = lookup_minimal_symbol_by_pc (this_pc_in_block);
+ morestack_msym = lookup_minimal_symbol_by_pc (this_pc_in_block).minsym;
if (morestack_msym)
morestack_name = SYMBOL_LINKAGE_NAME (morestack_msym);
if (!morestack_name || strcmp (morestack_name, "__morestack") != 0)
--- a/gdb/frv-tdep.c
+++ b/gdb/frv-tdep.c
@@ -1072,7 +1072,7 @@ frv_skip_main_prologue (struct gdbarch *
{
LONGEST displ;
CORE_ADDR call_dest;
- struct minimal_symbol *s;
+ struct bound_minimal_symbol s;
displ = ((op & 0xfe000000) >> 7) | (op & 0x0003ffff);
if ((displ & 0x00800000) != 0)
@@ -1081,9 +1081,9 @@ frv_skip_main_prologue (struct gdbarch *
call_dest = pc + 4 * displ;
s = lookup_minimal_symbol_by_pc (call_dest);
- if (s != NULL
- && SYMBOL_LINKAGE_NAME (s) != NULL
- && strcmp (SYMBOL_LINKAGE_NAME (s), "__main") == 0)
+ if (s.minsym != NULL
+ && SYMBOL_LINKAGE_NAME (s.minsym) != NULL
+ && strcmp (SYMBOL_LINKAGE_NAME (s.minsym), "__main") == 0)
{
pc += 4;
return pc;
--- a/gdb/glibc-tdep.c
+++ b/gdb/glibc-tdep.c
@@ -53,19 +53,18 @@ glibc_skip_solib_resolver (struct gdbarc
of GNU/Linux will provide a portable, efficient interface for
debugging programs that use shared libraries. */
- struct objfile *objfile;
- struct minimal_symbol *resolver
- = lookup_minimal_symbol_and_objfile ("_dl_runtime_resolve", &objfile);
+ struct bound_minimal_symbol resolver
+ = lookup_minimal_symbol_and_objfile ("_dl_runtime_resolve");
- if (resolver)
+ if (resolver.minsym)
{
/* The dynamic linker began using this name in early 2005. */
struct minimal_symbol *fixup
- = lookup_minimal_symbol ("_dl_fixup", NULL, objfile);
+ = lookup_minimal_symbol ("_dl_fixup", NULL, resolver.objfile);
/* This is the name used in older versions. */
if (! fixup)
- fixup = lookup_minimal_symbol ("fixup", NULL, objfile);
+ fixup = lookup_minimal_symbol ("fixup", NULL, resolver.objfile);
if (fixup && SYMBOL_VALUE_ADDRESS (fixup) == pc)
return frame_unwind_caller_pc (get_current_frame ());
--- a/gdb/gnu-v2-abi.c
+++ b/gdb/gnu-v2-abi.c
@@ -191,7 +191,7 @@ gnuv2_value_rtti_type (struct value *v,
struct type *known_type;
struct type *rtti_type;
CORE_ADDR vtbl;
- struct minimal_symbol *minsym;
+ struct bound_minimal_symbol minsym;
char *demangled_name, *p;
const char *linkage_name;
struct type *btype;
@@ -245,8 +245,8 @@ gnuv2_value_rtti_type (struct value *v,
/* Try to find a symbol that is the vtable. */
minsym=lookup_minimal_symbol_by_pc(vtbl);
- if (minsym==NULL
- || (linkage_name=SYMBOL_LINKAGE_NAME (minsym))==NULL
+ if (minsym.minsym==NULL
+ || (linkage_name=SYMBOL_LINKAGE_NAME (minsym.minsym))==NULL
|| !is_vtable_name (linkage_name))
return NULL;
--- a/gdb/gnu-v3-abi.c
+++ b/gdb/gnu-v3-abi.c
@@ -306,7 +306,7 @@ gnuv3_rtti_type (struct value *value,
/* Find the linker symbol for this vtable. */
vtable_symbol
= lookup_minimal_symbol_by_pc (value_address (vtable)
- + value_embedded_offset (vtable));
+ + value_embedded_offset (vtable)).minsym;
if (! vtable_symbol)
return NULL;
@@ -988,7 +988,7 @@ gnuv3_skip_trampoline (struct frame_info
real_stop_pc = stop_pc;
/* Find the linker symbol for this potential thunk. */
- thunk_sym = lookup_minimal_symbol_by_pc (real_stop_pc);
+ thunk_sym = lookup_minimal_symbol_by_pc (real_stop_pc).minsym;
section = find_pc_section (real_stop_pc);
if (thunk_sym == NULL || section == NULL)
return 0;
--- a/gdb/hppa-hpux-tdep.c
+++ b/gdb/hppa-hpux-tdep.c
@@ -89,7 +89,7 @@ hppa32_hpux_in_solib_call_trampoline (st
CORE_ADDR pc, char *name)
{
enum bfd_endian byte_order = gdbarch_byte_order (gdbarch);
- struct minimal_symbol *minsym;
+ struct bound_minimal_symbol minsym;
struct unwind_table_entry *u;
/* First see if PC is in one of the two C-library trampolines. */
@@ -98,7 +98,8 @@ hppa32_hpux_in_solib_call_trampoline (st
return 1;
minsym = lookup_minimal_symbol_by_pc (pc);
- if (minsym && strcmp (SYMBOL_LINKAGE_NAME (minsym), ".stub") == 0)
+ if (minsym.minsym
+ && strcmp (SYMBOL_LINKAGE_NAME (minsym.minsym), ".stub") == 0)
return 1;
/* Get the unwind descriptor corresponding to PC, return zero
@@ -174,16 +175,16 @@ hppa64_hpux_in_solib_call_trampoline (st
step. If it does, then assume we are not in a stub and return.
Finally peek at the instructions to see if they look like a stub. */
- struct minimal_symbol *minsym;
+ struct bound_minimal_symbol minsym;
asection *sec;
CORE_ADDR addr;
int insn;
minsym = lookup_minimal_symbol_by_pc (pc);
- if (! minsym)
+ if (! minsym.minsym)
return 0;
- sec = SYMBOL_OBJ_SECTION (minsym)->the_bfd_section;
+ sec = SYMBOL_OBJ_SECTION (minsym.minsym)->the_bfd_section;
if (bfd_get_section_vma (sec->owner, sec) <= pc
&& pc < (bfd_get_section_vma (sec->owner, sec)
@@ -311,7 +312,7 @@ hppa_hpux_skip_trampoline_code (struct f
int word_size = gdbarch_ptr_bit (gdbarch) / 8;
long orig_pc = pc;
long prev_inst, curr_inst, loc;
- struct minimal_symbol *msym;
+ struct bound_minimal_symbol msym;
struct unwind_table_entry *u;
/* Addresses passed to dyncall may *NOT* be the actual address
@@ -366,10 +367,12 @@ hppa_hpux_skip_trampoline_code (struct f
/*--------------------------------------------------------------------------*/
msym = lookup_minimal_symbol_by_pc (pc);
- if (msym == NULL || MSYMBOL_TYPE (msym) != mst_solib_trampoline)
+ if (msym.minsym == NULL
+ || MSYMBOL_TYPE (msym.minsym) != mst_solib_trampoline)
return orig_pc == pc ? 0 : pc & ~0x3;
- else if (msym != NULL && MSYMBOL_TYPE (msym) == mst_solib_trampoline)
+ else if (msym.minsym != NULL
+ && MSYMBOL_TYPE (msym.minsym) == mst_solib_trampoline)
{
struct objfile *objfile;
struct minimal_symbol *msymbol;
@@ -384,7 +387,7 @@ hppa_hpux_skip_trampoline_code (struct f
{
if (MSYMBOL_TYPE (msymbol) == mst_text
&& strcmp (SYMBOL_LINKAGE_NAME (msymbol),
- SYMBOL_LINKAGE_NAME (msym)) == 0)
+ SYMBOL_LINKAGE_NAME (msym.minsym)) == 0)
{
function_found = 1;
break;
@@ -401,7 +404,7 @@ hppa_hpux_skip_trampoline_code (struct f
should be mst_text. So we need to fix the msym, and also
get out of this function. */
{
- MSYMBOL_TYPE (msym) = mst_text;
+ MSYMBOL_TYPE (msym.minsym) = mst_text;
return orig_pc == pc ? 0 : pc & ~0x3;
}
}
@@ -472,21 +475,22 @@ hppa_hpux_skip_trampoline_code (struct f
(curr_inst == 0xeaa0d000) ||
(curr_inst == 0xeaa0d002))
{
- struct minimal_symbol *stubsym, *libsym;
+ struct bound_minimal_symbol stubsym;
+ struct minimal_symbol *libsym;
stubsym = lookup_minimal_symbol_by_pc (loc);
- if (stubsym == NULL)
+ if (stubsym.minsym == NULL)
{
warning (_("Unable to find symbol for 0x%lx"), loc);
return orig_pc == pc ? 0 : pc & ~0x3;
}
- libsym = lookup_minimal_symbol (SYMBOL_LINKAGE_NAME (stubsym),
+ libsym = lookup_minimal_symbol (SYMBOL_LINKAGE_NAME (stubsym.minsym),
NULL, NULL);
if (libsym == NULL)
{
warning (_("Unable to find library symbol for %s."),
- SYMBOL_PRINT_NAME (stubsym));
+ SYMBOL_PRINT_NAME (stubsym.minsym));
return orig_pc == pc ? 0 : pc & ~0x3;
}
@@ -1025,7 +1029,8 @@ static CORE_ADDR
hppa_hpux_find_import_stub_for_addr (CORE_ADDR funcaddr)
{
struct objfile *objfile;
- struct minimal_symbol *funsym, *stubsym;
+ struct bound_minimal_symbol funsym;
+ struct minimal_symbol *stubsym;
CORE_ADDR stubaddr;
funsym = lookup_minimal_symbol_by_pc (funcaddr);
@@ -1034,7 +1039,7 @@ hppa_hpux_find_import_stub_for_addr (COR
ALL_OBJFILES (objfile)
{
stubsym = lookup_minimal_symbol_solib_trampoline
- (SYMBOL_LINKAGE_NAME (funsym), objfile);
+ (SYMBOL_LINKAGE_NAME (funsym.minsym), objfile);
if (stubsym)
{
--- a/gdb/i386-tdep.c
+++ b/gdb/i386-tdep.c
@@ -1687,15 +1687,15 @@ i386_skip_main_prologue (struct gdbarch
{
/* Make sure address is computed correctly as a 32bit
integer even if CORE_ADDR is 64 bit wide. */
- struct minimal_symbol *s;
+ struct bound_minimal_symbol s;
CORE_ADDR call_dest;
call_dest = pc + 5 + extract_signed_integer (buf, 4, byte_order);
call_dest = call_dest & 0xffffffffU;
s = lookup_minimal_symbol_by_pc (call_dest);
- if (s != NULL
- && SYMBOL_LINKAGE_NAME (s) != NULL
- && strcmp (SYMBOL_LINKAGE_NAME (s), "__main") == 0)
+ if (s.minsym != NULL
+ && SYMBOL_LINKAGE_NAME (s.minsym) != NULL
+ && strcmp (SYMBOL_LINKAGE_NAME (s.minsym), "__main") == 0)
pc += 5;
}
}
@@ -3352,7 +3352,7 @@ i386_pe_skip_trampoline_code (struct fra
unsigned long indirect =
read_memory_unsigned_integer (pc + 2, 4, byte_order);
struct minimal_symbol *indsym =
- indirect ? lookup_minimal_symbol_by_pc (indirect) : 0;
+ indirect ? lookup_minimal_symbol_by_pc (indirect).minsym : 0;
const char *symname = indsym ? SYMBOL_LINKAGE_NAME (indsym) : 0;
if (symname)
--- a/gdb/ia64-tdep.c
+++ b/gdb/ia64-tdep.c
@@ -3651,11 +3651,11 @@ ia64_convert_from_func_ptr_addr (struct
/* There are also descriptors embedded in vtables. */
if (s)
{
- struct minimal_symbol *minsym;
+ struct bound_minimal_symbol minsym;
minsym = lookup_minimal_symbol_by_pc (addr);
- if (minsym && is_vtable_name (SYMBOL_LINKAGE_NAME (minsym)))
+ if (minsym.minsym && is_vtable_name (SYMBOL_LINKAGE_NAME (minsym.minsym)))
return read_memory_unsigned_integer (addr, 8, byte_order);
}
--- a/gdb/infcall.c
+++ b/gdb/infcall.c
@@ -355,10 +355,10 @@ get_function_name (CORE_ADDR funaddr, ch
{
/* Try the minimal symbols. */
- struct minimal_symbol *msymbol = lookup_minimal_symbol_by_pc (funaddr);
+ struct bound_minimal_symbol msymbol = lookup_minimal_symbol_by_pc (funaddr);
- if (msymbol)
- return SYMBOL_PRINT_NAME (msymbol);
+ if (msymbol.minsym)
+ return SYMBOL_PRINT_NAME (msymbol.minsym);
}
{
--- a/gdb/infcmd.c
+++ b/gdb/infcmd.c
@@ -1332,12 +1332,12 @@ until_next_command (int from_tty)
if (!func)
{
- struct minimal_symbol *msymbol = lookup_minimal_symbol_by_pc (pc);
+ struct bound_minimal_symbol msymbol = lookup_minimal_symbol_by_pc (pc);
- if (msymbol == NULL)
+ if (msymbol.minsym == NULL)
error (_("Execution is not within a known function."));
- tp->control.step_range_start = SYMBOL_VALUE_ADDRESS (msymbol);
+ tp->control.step_range_start = SYMBOL_VALUE_ADDRESS (msymbol.minsym);
tp->control.step_range_end = pc;
}
else
--- a/gdb/jit.c
+++ b/gdb/jit.c
@@ -1016,8 +1016,8 @@ static int
jit_breakpoint_re_set_internal (struct gdbarch *gdbarch,
struct jit_program_space_data *ps_data)
{
- struct minimal_symbol *reg_symbol, *desc_symbol;
- struct objfile *objf;
+ struct bound_minimal_symbol reg_symbol;
+ struct minimal_symbol *desc_symbol;
struct jit_objfile_data *objf_data;
CORE_ADDR addr;
@@ -1025,19 +1025,21 @@ jit_breakpoint_re_set_internal (struct g
{
/* Lookup the registration symbol. If it is missing, then we
assume we are not attached to a JIT. */
- reg_symbol = lookup_minimal_symbol_and_objfile (jit_break_name, &objf);
- if (reg_symbol == NULL || SYMBOL_VALUE_ADDRESS (reg_symbol) == 0)
+ reg_symbol = lookup_minimal_symbol_and_objfile (jit_break_name);
+ if (reg_symbol.minsym == NULL
+ || SYMBOL_VALUE_ADDRESS (reg_symbol.minsym) == 0)
return 1;
- desc_symbol = lookup_minimal_symbol (jit_descriptor_name, NULL, objf);
+ desc_symbol = lookup_minimal_symbol (jit_descriptor_name, NULL,
+ reg_symbol.objfile);
if (desc_symbol == NULL || SYMBOL_VALUE_ADDRESS (desc_symbol) == 0)
return 1;
- objf_data = get_jit_objfile_data (objf);
- objf_data->register_code = reg_symbol;
+ objf_data = get_jit_objfile_data (reg_symbol.objfile);
+ objf_data->register_code = reg_symbol.minsym;
objf_data->descriptor = desc_symbol;
- ps_data->objfile = objf;
+ ps_data->objfile = reg_symbol.objfile;
}
else
objf_data = get_jit_objfile_data (ps_data->objfile);
--- a/gdb/linux-fork.c
+++ b/gdb/linux-fork.c
@@ -592,11 +592,11 @@ info_checkpoints_command (char *arg, int
printf_filtered (_(", line %d"), sal.line);
if (!sal.symtab && !sal.line)
{
- struct minimal_symbol *msym;
+ struct bound_minimal_symbol msym;
msym = lookup_minimal_symbol_by_pc (pc);
- if (msym)
- printf_filtered (", <%s>", SYMBOL_LINKAGE_NAME (msym));
+ if (msym.minsym)
+ printf_filtered (", <%s>", SYMBOL_LINKAGE_NAME (msym.minsym));
}
putchar_filtered ('\n');
--- a/gdb/m32c-tdep.c
+++ b/gdb/m32c-tdep.c
@@ -2457,14 +2457,15 @@ m32c_m16c_address_to_pointer (struct gdb
struct minimal_symbol *tramp_msym;
/* Try to find a linker symbol at this address. */
- struct minimal_symbol *func_msym = lookup_minimal_symbol_by_pc (addr);
+ struct bound_minimal_symbol func_msym
+ = lookup_minimal_symbol_by_pc (addr);
- if (! func_msym)
+ if (! func_msym.minsym)
error (_("Cannot convert code address %s to function pointer:\n"
"couldn't find a symbol at that address, to find trampoline."),
paddress (gdbarch, addr));
- func_name = SYMBOL_LINKAGE_NAME (func_msym);
+ func_name = SYMBOL_LINKAGE_NAME (func_msym.minsym);
tramp_name = xmalloc (strlen (func_name) + 5);
strcpy (tramp_name, func_name);
strcat (tramp_name, ".plt");
@@ -2535,11 +2536,11 @@ m32c_m16c_pointer_to_address (struct gdb
{
/* See if there is a minimal symbol at that address whose name is
"NAME.plt". */
- struct minimal_symbol *ptr_msym = lookup_minimal_symbol_by_pc (ptr);
+ struct bound_minimal_symbol ptr_msym = lookup_minimal_symbol_by_pc (ptr);
- if (ptr_msym)
+ if (ptr_msym.minsym)
{
- const char *ptr_msym_name = SYMBOL_LINKAGE_NAME (ptr_msym);
+ const char *ptr_msym_name = SYMBOL_LINKAGE_NAME (ptr_msym.minsym);
int len = strlen (ptr_msym_name);
if (len > 4
@@ -2572,7 +2573,7 @@ m32c_m16c_pointer_to_address (struct gdb
{
ptr_msym = lookup_minimal_symbol_by_pc ((aspace << 16) | ptr);
- if (ptr_msym)
+ if (ptr_msym.minsym)
ptr |= aspace << 16;
}
}
--- a/gdb/m68hc11-tdep.c
+++ b/gdb/m68hc11-tdep.c
@@ -587,18 +587,18 @@ m68hc11_analyze_instruction (struct gdba
static enum insn_return_kind
m68hc11_get_return_insn (CORE_ADDR pc)
{
- struct minimal_symbol *sym;
+ struct bound_minimal_symbol sym;
/* A flag indicating that this is a STO_M68HC12_FAR or STO_M68HC12_INTERRUPT
function is stored by elfread.c in the high bit of the info field.
Use this to decide which instruction the function uses to return. */
sym = lookup_minimal_symbol_by_pc (pc);
- if (sym == 0)
+ if (sym.minsym == 0)
return RETURN_RTS;
- if (MSYMBOL_IS_RTC (sym))
+ if (MSYMBOL_IS_RTC (sym.minsym))
return RETURN_RTC;
- else if (MSYMBOL_IS_RTI (sym))
+ else if (MSYMBOL_IS_RTI (sym.minsym))
return RETURN_RTI;
else
return RETURN_RTS;
--- a/gdb/maint.c
+++ b/gdb/maint.c
@@ -445,7 +445,7 @@ maintenance_translate_address (char *arg
CORE_ADDR address;
struct obj_section *sect;
char *p;
- struct minimal_symbol *sym;
+ struct bound_minimal_symbol sym;
struct objfile *objfile;
if (arg == NULL || *arg == 0)
@@ -480,13 +480,13 @@ maintenance_translate_address (char *arg
else
sym = lookup_minimal_symbol_by_pc (address);
- if (sym)
+ if (sym.minsym)
{
- const char *symbol_name = SYMBOL_PRINT_NAME (sym);
+ const char *symbol_name = SYMBOL_PRINT_NAME (sym.minsym);
const char *symbol_offset
- = pulongest (address - SYMBOL_VALUE_ADDRESS (sym));
+ = pulongest (address - SYMBOL_VALUE_ADDRESS (sym.minsym));
- sect = SYMBOL_OBJ_SECTION(sym);
+ sect = SYMBOL_OBJ_SECTION(sym.minsym);
if (sect != NULL)
{
const char *section_name;
--- a/gdb/minsyms.c
+++ b/gdb/minsyms.c
@@ -474,7 +474,7 @@ lookup_minimal_symbol_solib_trampoline (
there are text and trampoline symbols at the same address.
Otherwise prefer mst_text symbols. */
-static struct minimal_symbol *
+static struct bound_minimal_symbol
lookup_minimal_symbol_by_pc_section_1 (CORE_ADDR pc,
struct obj_section *section,
int want_trampoline)
@@ -485,6 +485,8 @@ lookup_minimal_symbol_by_pc_section_1 (C
struct objfile *objfile;
struct minimal_symbol *msymbol;
struct minimal_symbol *best_symbol = NULL;
+ struct objfile *best_objfile = NULL;
+ struct bound_minimal_symbol result;
enum minimal_symbol_type want_type, other_type;
want_type = want_trampoline ? mst_solib_trampoline : mst_text;
@@ -690,14 +692,18 @@ lookup_minimal_symbol_by_pc_section_1 (C
SYMBOL_VALUE_ADDRESS (&msymbol[hi]))))
{
best_symbol = &msymbol[hi];
+ best_objfile = objfile;
}
}
}
}
- return (best_symbol);
+
+ result.minsym = best_symbol;
+ result.objfile = best_objfile;
+ return result;
}
-struct minimal_symbol *
+struct bound_minimal_symbol
lookup_minimal_symbol_by_pc_section (CORE_ADDR pc, struct obj_section *section)
{
if (section == NULL)
@@ -707,17 +713,31 @@ lookup_minimal_symbol_by_pc_section (COR
debugging) always returns NULL making the call somewhat useless. */
section = find_pc_section (pc);
if (section == NULL)
- return NULL;
+ {
+ struct bound_minimal_symbol result;
+
+ memset (&result, 0, sizeof (result));
+ return result;
+ }
}
return lookup_minimal_symbol_by_pc_section_1 (pc, section, 0);
}
/* See minsyms.h. */
-struct minimal_symbol *
+struct bound_minimal_symbol
lookup_minimal_symbol_by_pc (CORE_ADDR pc)
{
- return lookup_minimal_symbol_by_pc_section (pc, NULL);
+ struct obj_section *section = find_pc_section (pc);
+
+ if (section == NULL)
+ {
+ struct bound_minimal_symbol result;
+
+ memset (&result, 0, sizeof (result));
+ return result;
+ }
+ return lookup_minimal_symbol_by_pc_section_1 (pc, section, 0);
}
/* Return non-zero iff PC is in an STT_GNU_IFUNC function resolver. */
@@ -725,9 +745,9 @@ lookup_minimal_symbol_by_pc (CORE_ADDR p
int
in_gnu_ifunc_stub (CORE_ADDR pc)
{
- struct minimal_symbol *msymbol = lookup_minimal_symbol_by_pc (pc);
+ struct bound_minimal_symbol msymbol = lookup_minimal_symbol_by_pc (pc);
- return msymbol && MSYMBOL_TYPE (msymbol) == mst_text_gnu_ifunc;
+ return msymbol.minsym && MSYMBOL_TYPE (msymbol.minsym) == mst_text_gnu_ifunc;
}
/* See elf_gnu_ifunc_resolve_addr for its real implementation. */
@@ -785,10 +805,10 @@ const struct gnu_ifunc_fns *gnu_ifunc_fn
/* See minsyms.h. */
-struct minimal_symbol *
-lookup_minimal_symbol_and_objfile (const char *name,
- struct objfile **objfile_p)
+struct bound_minimal_symbol
+lookup_minimal_symbol_and_objfile (const char *name)
{
+ struct bound_minimal_symbol result;
struct objfile *objfile;
unsigned int hash = msymbol_hash (name) % MINIMAL_SYMBOL_HASH_SIZE;
@@ -802,13 +822,15 @@ lookup_minimal_symbol_and_objfile (const
{
if (strcmp (SYMBOL_LINKAGE_NAME (msym), name) == 0)
{
- *objfile_p = objfile;
- return msym;
+ result.minsym = msym;
+ result.objfile = objfile;
+ return result;
}
}
}
- return 0;
+ memset (&result, 0, sizeof (result));
+ return result;
}
@@ -1287,14 +1309,15 @@ static struct minimal_symbol *
lookup_solib_trampoline_symbol_by_pc (CORE_ADDR pc)
{
struct obj_section *section = find_pc_section (pc);
- struct minimal_symbol *msymbol;
+ struct bound_minimal_symbol msymbol;
if (section == NULL)
return NULL;
msymbol = lookup_minimal_symbol_by_pc_section_1 (pc, section, 1);
- if (msymbol != NULL && MSYMBOL_TYPE (msymbol) == mst_solib_trampoline)
- return msymbol;
+ if (msymbol.minsym != NULL
+ && MSYMBOL_TYPE (msymbol.minsym) == mst_solib_trampoline)
+ return msymbol.minsym;
return NULL;
}
--- a/gdb/minsyms.h
+++ b/gdb/minsyms.h
@@ -20,6 +20,23 @@
#ifndef MINSYMS_H
#define MINSYMS_H
+/* Several lookup functions return both a minimal symbol and the
+ objfile in which it is found. This structure is used in these
+ cases. */
+
+struct bound_minimal_symbol
+{
+ /* The minimal symbol that was found, or NULL if no minimal symbol
+ was found. */
+
+ struct minimal_symbol *minsym;
+
+ /* If MINSYM is not NULL, then this is the objfile in which the
+ symbol is defined. */
+
+ struct objfile *objfile;
+};
+
/* This header declares most of the API for dealing with minimal
symbols and minimal symbol tables. A few things are declared
elsewhere; see below.
@@ -169,12 +186,9 @@ struct minimal_symbol *lookup_minimal_sy
struct objfile *);
/* Find the minimal symbol named NAME, and return both the minsym
- struct and its objfile. This only checks the linkage name. Sets
- *OBJFILE_P and returns the minimal symbol, if it is found. If it
- is not found, returns NULL. */
+ struct and its objfile. This only checks the linkage name. */
-struct minimal_symbol *lookup_minimal_symbol_and_objfile (const char *,
- struct objfile **);
+struct bound_minimal_symbol lookup_minimal_symbol_and_objfile (const char *);
/* Look through all the current minimal symbol tables and find the
first minimal symbol that matches NAME and has text type. If OBJF
@@ -213,10 +227,10 @@ struct minimal_symbol *lookup_minimal_sy
If SECTION is NULL, this uses the result of find_pc_section
instead.
- Returns a pointer to the minimal symbol if such a symbol is found,
- or NULL if PC is not in a suitable range. */
+ The result has a non-NULL 'minsym' member if such a symbol is
+ found, or NULL if PC is not in a suitable range. */
-struct minimal_symbol *lookup_minimal_symbol_by_pc_section
+struct bound_minimal_symbol lookup_minimal_symbol_by_pc_section
(CORE_ADDR,
struct obj_section *);
@@ -226,7 +240,7 @@ struct minimal_symbol *lookup_minimal_sy
This is a wrapper that calls lookup_minimal_symbol_by_pc_section
with a NULL section argument. */
-struct minimal_symbol *lookup_minimal_symbol_by_pc (CORE_ADDR);
+struct bound_minimal_symbol lookup_minimal_symbol_by_pc (CORE_ADDR);
/* Iterate over all the minimal symbols in the objfile OBJF which
match NAME. Both the ordinary and demangled names of each symbol
--- a/gdb/mips-tdep.c
+++ b/gdb/mips-tdep.c
@@ -1115,15 +1115,15 @@ show_mask_address (struct ui_file *file,
int
mips_pc_is_mips (CORE_ADDR memaddr)
{
- struct minimal_symbol *sym;
+ struct bound_minimal_symbol sym;
/* Flags indicating that this is a MIPS16 or microMIPS function is
stored by elfread.c in the high bit of the info field. Use this
to decide if the function is standard MIPS. Otherwise if bit 0
of the address is clear, then this is a standard MIPS function. */
sym = lookup_minimal_symbol_by_pc (memaddr);
- if (sym)
- return msymbol_is_mips (sym);
+ if (sym.minsym)
+ return msymbol_is_mips (sym.minsym);
else
return is_mips_addr (memaddr);
}
@@ -1133,15 +1133,15 @@ mips_pc_is_mips (CORE_ADDR memaddr)
int
mips_pc_is_mips16 (struct gdbarch *gdbarch, CORE_ADDR memaddr)
{
- struct minimal_symbol *sym;
+ struct bound_minimal_symbol sym;
/* A flag indicating that this is a MIPS16 function is stored by
elfread.c in the high bit of the info field. Use this to decide
if the function is MIPS16. Otherwise if bit 0 of the address is
set, then ELF file flags will tell if this is a MIPS16 function. */
sym = lookup_minimal_symbol_by_pc (memaddr);
- if (sym)
- return msymbol_is_mips16 (sym);
+ if (sym.minsym)
+ return msymbol_is_mips16 (sym.minsym);
else
return is_mips16_addr (gdbarch, memaddr);
}
@@ -1151,7 +1151,7 @@ mips_pc_is_mips16 (struct gdbarch *gdbar
int
mips_pc_is_micromips (struct gdbarch *gdbarch, CORE_ADDR memaddr)
{
- struct minimal_symbol *sym;
+ struct bound_minimal_symbol sym;
/* A flag indicating that this is a microMIPS function is stored by
elfread.c in the high bit of the info field. Use this to decide
@@ -1159,8 +1159,8 @@ mips_pc_is_micromips (struct gdbarch *gd
is set, then ELF file flags will tell if this is a microMIPS
function. */
sym = lookup_minimal_symbol_by_pc (memaddr);
- if (sym)
- return msymbol_is_micromips (sym);
+ if (sym.minsym)
+ return msymbol_is_micromips (sym.minsym);
else
return is_micromips_addr (gdbarch, memaddr);
}
@@ -1171,7 +1171,7 @@ mips_pc_is_micromips (struct gdbarch *gd
static enum mips_isa
mips_pc_isa (struct gdbarch *gdbarch, CORE_ADDR memaddr)
{
- struct minimal_symbol *sym;
+ struct bound_minimal_symbol sym;
/* A flag indicating that this is a MIPS16 or a microMIPS function
is stored by elfread.c in the high bit of the info field. Use
@@ -1179,11 +1179,11 @@ mips_pc_isa (struct gdbarch *gdbarch, CO
MIPS. Otherwise if bit 0 of the address is set, then ELF file
flags will tell if this is a MIPS16 or a microMIPS function. */
sym = lookup_minimal_symbol_by_pc (memaddr);
- if (sym)
+ if (sym.minsym)
{
- if (msymbol_is_micromips (sym))
+ if (msymbol_is_micromips (sym.minsym))
return ISA_MICROMIPS;
- else if (msymbol_is_mips16 (sym))
+ else if (msymbol_is_mips16 (sym.minsym))
return ISA_MIPS16;
else
return ISA_MIPS;
@@ -3582,7 +3582,7 @@ mips_stub_frame_sniffer (const struct fr
gdb_byte dummy[4];
struct obj_section *s;
CORE_ADDR pc = get_frame_address_in_block (this_frame);
- struct minimal_symbol *msym;
+ struct bound_minimal_symbol msym;
/* Use the stub unwinder for unreadable code. */
if (target_read_memory (get_frame_pc (this_frame), dummy, 4) != 0)
@@ -3602,9 +3602,9 @@ mips_stub_frame_sniffer (const struct fr
/* Calling a PIC function from a non-PIC function passes through a
stub. The stub for foo is named ".pic.foo". */
msym = lookup_minimal_symbol_by_pc (pc);
- if (msym != NULL
- && SYMBOL_LINKAGE_NAME (msym) != NULL
- && strncmp (SYMBOL_LINKAGE_NAME (msym), ".pic.", 5) == 0)
+ if (msym.minsym != NULL
+ && SYMBOL_LINKAGE_NAME (msym.minsym) != NULL
+ && strncmp (SYMBOL_LINKAGE_NAME (msym.minsym), ".pic.", 5) == 0)
return 1;
return 0;
@@ -7626,7 +7626,7 @@ mips_skip_pic_trampoline_code (struct fr
{
struct gdbarch *gdbarch = get_frame_arch (frame);
enum bfd_endian byte_order = gdbarch_byte_order (gdbarch);
- struct minimal_symbol *msym;
+ struct bound_minimal_symbol msym;
int i;
gdb_byte stub_code[16];
int32_t stub_words[4];
@@ -7635,18 +7635,18 @@ mips_skip_pic_trampoline_code (struct fr
instructions inserted before foo or a three instruction sequence
which jumps to foo. */
msym = lookup_minimal_symbol_by_pc (pc);
- if (msym == NULL
- || SYMBOL_VALUE_ADDRESS (msym) != pc
- || SYMBOL_LINKAGE_NAME (msym) == NULL
- || strncmp (SYMBOL_LINKAGE_NAME (msym), ".pic.", 5) != 0)
+ if (msym.minsym == NULL
+ || SYMBOL_VALUE_ADDRESS (msym.minsym) != pc
+ || SYMBOL_LINKAGE_NAME (msym.minsym) == NULL
+ || strncmp (SYMBOL_LINKAGE_NAME (msym.minsym), ".pic.", 5) != 0)
return 0;
/* A two-instruction header. */
- if (MSYMBOL_SIZE (msym) == 8)
+ if (MSYMBOL_SIZE (msym.minsym) == 8)
return pc + 8;
/* A three-instruction (plus delay slot) trampoline. */
- if (MSYMBOL_SIZE (msym) == 16)
+ if (MSYMBOL_SIZE (msym.minsym) == 16)
{
if (target_read_memory (pc, stub_code, 16) != 0)
return 0;
--- a/gdb/p-valprint.c
+++ b/gdb/p-valprint.c
@@ -221,18 +221,18 @@ pascal_val_print (struct type *type, con
/* Print vtbl's nicely. */
CORE_ADDR vt_address = unpack_pointer (type,
valaddr + embedded_offset);
- struct minimal_symbol *msymbol =
+ struct bound_minimal_symbol msymbol =
lookup_minimal_symbol_by_pc (vt_address);
/* If 'symbol_print' is set, we did the work above. */
if (!options->symbol_print
- && (msymbol != NULL)
- && (vt_address == SYMBOL_VALUE_ADDRESS (msymbol)))
+ && (msymbol.minsym != NULL)
+ && (vt_address == SYMBOL_VALUE_ADDRESS (msymbol.minsym)))
{
if (want_space)
fputs_filtered (" ", stream);
fputs_filtered ("<", stream);
- fputs_filtered (SYMBOL_PRINT_NAME (msymbol), stream);
+ fputs_filtered (SYMBOL_PRINT_NAME (msymbol.minsym), stream);
fputs_filtered (">", stream);
want_space = 1;
}
@@ -247,8 +247,9 @@ pascal_val_print (struct type *type, con
if (want_space)
fputs_filtered (" ", stream);
- if (msymbol != NULL)
- wsym = lookup_symbol (SYMBOL_LINKAGE_NAME (msymbol), block,
+ if (msymbol.minsym != NULL)
+ wsym = lookup_symbol (SYMBOL_LINKAGE_NAME (msymbol.minsym),
+ block,
VAR_DOMAIN, &is_this_fld);
if (wsym)
--- a/gdb/parse.c
+++ b/gdb/parse.c
@@ -508,13 +508,14 @@ write_exp_msymbol (struct minimal_symbol
pc = gdbarch_convert_from_func_ptr_addr (gdbarch, addr, &current_target);
if (pc != addr)
{
- struct minimal_symbol *ifunc_msym = lookup_minimal_symbol_by_pc (pc);
+ struct bound_minimal_symbol ifunc_msym = lookup_minimal_symbol_by_pc (pc);
/* In this case, assume we have a code symbol instead of
a data symbol. */
- if (ifunc_msym != NULL && MSYMBOL_TYPE (ifunc_msym) == mst_text_gnu_ifunc
- && SYMBOL_VALUE_ADDRESS (ifunc_msym) == pc)
+ if (ifunc_msym.minsym != NULL
+ && MSYMBOL_TYPE (ifunc_msym.minsym) == mst_text_gnu_ifunc
+ && SYMBOL_VALUE_ADDRESS (ifunc_msym.minsym) == pc)
{
/* A function descriptor has been resolved but PC is still in the
STT_GNU_IFUNC resolver body (such as because inferior does not
--- a/gdb/ppc-linux-tdep.c
+++ b/gdb/ppc-linux-tdep.c
@@ -332,7 +332,7 @@ static struct ppc_insn_pattern powerpc32
static int
powerpc_linux_in_dynsym_resolve_code (CORE_ADDR pc)
{
- struct minimal_symbol *sym;
+ struct bound_minimal_symbol sym;
/* Check whether PC is in the dynamic linker. This also checks
whether it is in the .plt section, used by non-PIC executables. */
@@ -341,9 +341,10 @@ powerpc_linux_in_dynsym_resolve_code (CO
/* Check if we are in the resolver. */
sym = lookup_minimal_symbol_by_pc (pc);
- if (sym != NULL
- && (strcmp (SYMBOL_LINKAGE_NAME (sym), "__glink") == 0
- || strcmp (SYMBOL_LINKAGE_NAME (sym), "__glink_PLTresolve") == 0))
+ if (sym.minsym != NULL
+ && (strcmp (SYMBOL_LINKAGE_NAME (sym.minsym), "__glink") == 0
+ || strcmp (SYMBOL_LINKAGE_NAME (sym.minsym),
+ "__glink_PLTresolve") == 0))
return 1;
return 0;
--- a/gdb/ppc-sysv-tdep.c
+++ b/gdb/ppc-sysv-tdep.c
@@ -1076,12 +1076,13 @@ static int
convert_code_addr_to_desc_addr (CORE_ADDR code_addr, CORE_ADDR *desc_addr)
{
struct obj_section *dot_fn_section;
- struct minimal_symbol *dot_fn;
+ struct bound_minimal_symbol dot_fn;
struct minimal_symbol *fn;
+
/* Find the minimal symbol that corresponds to CODE_ADDR (should
have a name of the form ".FN"). */
dot_fn = lookup_minimal_symbol_by_pc (code_addr);
- if (dot_fn == NULL || SYMBOL_LINKAGE_NAME (dot_fn)[0] != '.')
+ if (dot_fn.minsym == NULL || SYMBOL_LINKAGE_NAME (dot_fn.minsym)[0] != '.')
return 0;
/* Get the section that contains CODE_ADDR. Need this for the
"objfile" that it contains. */
@@ -1092,7 +1093,7 @@ convert_code_addr_to_desc_addr (CORE_ADD
address. Only look for the minimal symbol in ".FN"'s object file
- avoids problems when two object files (i.e., shared libraries)
contain a minimal symbol with the same name. */
- fn = lookup_minimal_symbol (SYMBOL_LINKAGE_NAME (dot_fn) + 1, NULL,
+ fn = lookup_minimal_symbol (SYMBOL_LINKAGE_NAME (dot_fn.minsym) + 1, NULL,
dot_fn_section->objfile);
if (fn == NULL)
return 0;
--- a/gdb/printcmd.c
+++ b/gdb/printcmd.c
@@ -668,7 +668,7 @@ build_address_symbolic (struct gdbarch *
save some memory, but for many debug format--ELF/DWARF or
anything/stabs--it would be inconvenient to eliminate those minimal
symbols anyway). */
- msymbol = lookup_minimal_symbol_by_pc_section (addr, section);
+ msymbol = lookup_minimal_symbol_by_pc_section (addr, section).minsym;
symbol = find_pc_sect_function (addr, section);
if (symbol)
@@ -1166,7 +1166,8 @@ sym_info (char *arg, int from_tty)
if (obj_section_addr (osect) <= sect_addr
&& sect_addr < obj_section_endaddr (osect)
- && (msymbol = lookup_minimal_symbol_by_pc_section (sect_addr, osect)))
+ && (msymbol
+ = lookup_minimal_symbol_by_pc_section (sect_addr, osect).minsym))
{
const char *obj_name, *mapped, *sec_name, *msym_name;
char *loc_string;
--- a/gdb/rs6000-tdep.c
+++ b/gdb/rs6000-tdep.c
@@ -2152,15 +2152,15 @@ rs6000_skip_main_prologue (struct gdbarc
{
CORE_ADDR displ = op & BL_DISPLACEMENT_MASK;
CORE_ADDR call_dest = pc + 4 + displ;
- struct minimal_symbol *s = lookup_minimal_symbol_by_pc (call_dest);
+ struct bound_minimal_symbol s = lookup_minimal_symbol_by_pc (call_dest);
/* We check for ___eabi (three leading underscores) in addition
to __eabi in case the GCC option "-fleading-underscore" was
used to compile the program. */
- if (s != NULL
- && SYMBOL_LINKAGE_NAME (s) != NULL
- && (strcmp (SYMBOL_LINKAGE_NAME (s), "__eabi") == 0
- || strcmp (SYMBOL_LINKAGE_NAME (s), "___eabi") == 0))
+ if (s.minsym != NULL
+ && SYMBOL_LINKAGE_NAME (s.minsym) != NULL
+ && (strcmp (SYMBOL_LINKAGE_NAME (s.minsym), "__eabi") == 0
+ || strcmp (SYMBOL_LINKAGE_NAME (s.minsym), "___eabi") == 0))
pc += 4;
}
return pc;
@@ -2226,7 +2226,7 @@ rs6000_skip_trampoline_code (struct fram
unsigned int ii, op;
int rel;
CORE_ADDR solib_target_pc;
- struct minimal_symbol *msymbol;
+ struct bound_minimal_symbol msymbol;
static unsigned trampoline_code[] =
{
@@ -2242,9 +2242,9 @@ rs6000_skip_trampoline_code (struct fram
/* Check for bigtoc fixup code. */
msymbol = lookup_minimal_symbol_by_pc (pc);
- if (msymbol
+ if (msymbol.minsym
&& rs6000_in_solib_return_trampoline (gdbarch, pc,
- SYMBOL_LINKAGE_NAME (msymbol)))
+ SYMBOL_LINKAGE_NAME (msymbol.minsym)))
{
/* Double-check that the third instruction from PC is relative "b". */
op = read_memory_integer (pc + 8, 4, byte_order);
--- a/gdb/sh64-tdep.c
+++ b/gdb/sh64-tdep.c
@@ -237,7 +237,7 @@ sh64_elf_make_msymbol_special (asymbol *
static int
pc_is_isa32 (bfd_vma memaddr)
{
- struct minimal_symbol *sym;
+ struct bound_minimal_symbol sym;
/* If bit 0 of the address is set, assume this is a
ISA32 (shmedia) address. */
@@ -248,8 +248,8 @@ pc_is_isa32 (bfd_vma memaddr)
the high bit of the info field. Use this to decide if the function is
ISA16 or ISA32. */
sym = lookup_minimal_symbol_by_pc (memaddr);
- if (sym)
- return MSYMBOL_IS_SPECIAL (sym);
+ if (sym.minsym)
+ return MSYMBOL_IS_SPECIAL (sym.minsym);
else
return 0;
}
--- a/gdb/stack.c
+++ b/gdb/stack.c
@@ -1036,23 +1036,25 @@ find_frame_funname (struct frame_info *f
changed (and we'll create a find_pc_minimal_function or some
such). */
- struct minimal_symbol *msymbol = NULL;
+ struct bound_minimal_symbol msymbol;
/* Don't attempt to do this for inlined functions, which do not
have a corresponding minimal symbol. */
if (!block_inlined_p (SYMBOL_BLOCK_VALUE (func)))
msymbol
= lookup_minimal_symbol_by_pc (get_frame_address_in_block (frame));
+ else
+ memset (&msymbol, 0, sizeof (msymbol));
- if (msymbol != NULL
- && (SYMBOL_VALUE_ADDRESS (msymbol)
+ if (msymbol.minsym != NULL
+ && (SYMBOL_VALUE_ADDRESS (msymbol.minsym)
> BLOCK_START (SYMBOL_BLOCK_VALUE (func))))
{
/* We also don't know anything about the function besides
its address and name. */
func = 0;
- *funname = SYMBOL_PRINT_NAME (msymbol);
- *funlang = SYMBOL_LANGUAGE (msymbol);
+ *funname = SYMBOL_PRINT_NAME (msymbol.minsym);
+ *funlang = SYMBOL_LANGUAGE (msymbol.minsym);
}
else
{
@@ -1079,17 +1081,17 @@ find_frame_funname (struct frame_info *f
}
else
{
- struct minimal_symbol *msymbol;
+ struct bound_minimal_symbol msymbol;
CORE_ADDR pc;
if (!get_frame_address_in_block_if_available (frame, &pc))
return;
msymbol = lookup_minimal_symbol_by_pc (pc);
- if (msymbol != NULL)
+ if (msymbol.minsym != NULL)
{
- *funname = SYMBOL_PRINT_NAME (msymbol);
- *funlang = SYMBOL_LANGUAGE (msymbol);
+ *funname = SYMBOL_PRINT_NAME (msymbol.minsym);
+ *funlang = SYMBOL_LANGUAGE (msymbol.minsym);
}
}
}
@@ -1423,13 +1425,13 @@ frame_info (char *addr_exp, int from_tty
}
else if (frame_pc_p)
{
- struct minimal_symbol *msymbol;
+ struct bound_minimal_symbol msymbol;
msymbol = lookup_minimal_symbol_by_pc (frame_pc);
- if (msymbol != NULL)
+ if (msymbol.minsym != NULL)
{
- funname = SYMBOL_PRINT_NAME (msymbol);
- funlang = SYMBOL_LANGUAGE (msymbol);
+ funname = SYMBOL_PRINT_NAME (msymbol.minsym);
+ funlang = SYMBOL_LANGUAGE (msymbol.minsym);
}
}
calling_frame_info = get_prev_frame (fi);
--- a/gdb/symtab.c
+++ b/gdb/symtab.c
@@ -956,7 +956,7 @@ find_pc_sect_symtab_via_partial (CORE_AD
/* If we know that this is not a text address, return failure. This is
necessary because we loop based on texthigh and textlow, which do
not include the data ranges. */
- msymbol = lookup_minimal_symbol_by_pc_section (pc, section);
+ msymbol = lookup_minimal_symbol_by_pc_section (pc, section).minsym;
if (msymbol
&& (MSYMBOL_TYPE (msymbol) == mst_data
|| MSYMBOL_TYPE (msymbol) == mst_bss
@@ -2088,7 +2088,7 @@ find_pc_sect_symtab (CORE_ADDR pc, struc
addresses, which do not include the data ranges, and because
we call find_pc_sect_psymtab which has a similar restriction based
on the partial_symtab's texthigh and textlow. */
- msymbol = lookup_minimal_symbol_by_pc_section (pc, section);
+ msymbol = lookup_minimal_symbol_by_pc_section (pc, section).minsym;
if (msymbol
&& (MSYMBOL_TYPE (msymbol) == mst_data
|| MSYMBOL_TYPE (msymbol) == mst_bss
@@ -2219,7 +2219,7 @@ find_pc_sect_line (CORE_ADDR pc, struct
struct linetable_entry *item;
struct symtab_and_line val;
struct blockvector *bv;
- struct minimal_symbol *msymbol;
+ struct bound_minimal_symbol msymbol;
struct minimal_symbol *mfunsym;
struct objfile *objfile;
@@ -2305,11 +2305,12 @@ find_pc_sect_line (CORE_ADDR pc, struct
* infinite recursion.
*/
msymbol = lookup_minimal_symbol_by_pc (pc);
- if (msymbol != NULL)
- if (MSYMBOL_TYPE (msymbol) == mst_solib_trampoline)
+ if (msymbol.minsym != NULL)
+ if (MSYMBOL_TYPE (msymbol.minsym) == mst_solib_trampoline)
{
- mfunsym = lookup_minimal_symbol_text (SYMBOL_LINKAGE_NAME (msymbol),
- NULL);
+ mfunsym
+ = lookup_minimal_symbol_text (SYMBOL_LINKAGE_NAME (msymbol.minsym),
+ NULL);
if (mfunsym == NULL)
/* I eliminated this warning since it is coming out
* in the following situation:
@@ -2325,7 +2326,7 @@ find_pc_sect_line (CORE_ADDR pc, struct
;
/* fall through */
else if (SYMBOL_VALUE_ADDRESS (mfunsym)
- == SYMBOL_VALUE_ADDRESS (msymbol))
+ == SYMBOL_VALUE_ADDRESS (msymbol.minsym))
/* Avoid infinite recursion */
/* See above comment about why warning is commented out. */
/* warning ("In stub for %s; unable to find real function/line info",
@@ -2838,7 +2839,7 @@ skip_prologue_sal (struct symtab_and_lin
else
{
struct minimal_symbol *msymbol
- = lookup_minimal_symbol_by_pc_section (sal->pc, sal->section);
+ = lookup_minimal_symbol_by_pc_section (sal->pc, sal->section).minsym;
if (msymbol == NULL)
{
@@ -2894,8 +2895,8 @@ skip_prologue_sal (struct symtab_and_lin
if (skip && start_sal.pc != pc
&& (sym ? (BLOCK_START (SYMBOL_BLOCK_VALUE (sym)) <= start_sal.end
&& start_sal.end < BLOCK_END (SYMBOL_BLOCK_VALUE (sym)))
- : (lookup_minimal_symbol_by_pc_section (start_sal.end, section)
- == lookup_minimal_symbol_by_pc_section (pc, section))))
+ : (lookup_minimal_symbol_by_pc_section (start_sal.end, section).minsym
+ == lookup_minimal_symbol_by_pc_section (pc, section).minsym)))
{
/* First pc of next line */
pc = start_sal.end;
--- a/gdb/tui/tui-disasm.c
+++ b/gdb/tui/tui-disasm.c
@@ -121,7 +121,7 @@ tui_find_disassembly_address (struct gdb
pos = max_lines - 1;
do {
new_low -= 1 * max_lines;
- msymbol = lookup_minimal_symbol_by_pc_section (new_low, 0);
+ msymbol = lookup_minimal_symbol_by_pc_section (new_low, 0).minsym;
if (msymbol)
new_low = SYMBOL_VALUE_ADDRESS (msymbol);
#
# gdb-7.6-add-powerpc64le-linux.patch
#
From: Alan Modra <amodra@gmail.com>
Date: Thu Apr 25 13:22:52 2013 +0000
Git-commit: 49926cd0c84887c581110fb2a471b21ff19048d2
References: ppc64le enablement
bfd/
* config.bfd: Add powerpc64le-linux.
Acked-by: Petr Tesarik <ptesarik@suse.cz>
---
bfd/ChangeLog | 4 ++++
bfd/config.bfd | 3 ++-
2 files changed, 6 insertions(+), 1 deletion(-)
--- a/bfd/ChangeLog
+++ b/bfd/ChangeLog
@@ -1,3 +1,7 @@
+2013-04-25 Alan Modra <amodra@gmail.com>
+
+ * config.bfd: Add powerpc64le-linux.
+
2013-03-08 Venkataramanan Kumar <venkataramanan.kumar@linaro.org>
* elf64-aarch64.c (elf_backend_can_gc_sections): Enable gc-section
--- a/bfd/config.bfd
+++ b/bfd/config.bfd
@@ -1242,7 +1242,8 @@ case "${targ}" in
targ_selvecs="bfd_elf64_powerpcle_vec bfd_elf32_powerpc_vec bfd_elf32_powerpcle_vec rs6000coff_vec rs6000coff64_vec aix5coff64_vec"
want64=true
;;
- powerpc64le-*-elf* | powerpcle-*-elf64*)
+ powerpc64le-*-elf* | powerpcle-*-elf64* | powerpc64le-*-linux* | \
+ powerpc64le-*-*bsd*)
targ_defvec=bfd_elf64_powerpcle_vec
targ_selvecs="bfd_elf64_powerpc_vec bfd_elf32_powerpcle_vec bfd_elf32_powerpc_vec rs6000coff_vec rs6000coff64_vec aix5coff64_vec"
want64=true
#
# gdb-7.6-update-autoconf-2013-04-24.patch
#
From: Jan-Benedict Glaw <jbglaw@lug-owl.de>
Date: Mon Apr 29 15:13:53 2013 +0000
Git-commit: 5dad867ccace0a74c90b729372c9c01392756875
References: ppc64le enablement
* config.guess: Update from config repo.
* config.sub: Ditto.
Acked-by: Petr Tesarik <ptesarik@suse.cz>
---
ChangeLog | 5 +++++
config.guess | 25 +++++++++++++++++--------
config.sub | 23 +++++++++++------------
3 files changed, 33 insertions(+), 20 deletions(-)
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,8 @@
+2013-04-29 Jan-Benedict Glaw <jbglaw@lug-owl.de>
+
+ * config.guess: Update from config repo.
+ * config.sub: Ditto.
+
2013-02-15 Yufeng Zhang <yufeng.zhang@arm.com>
* configure.ac: Sync with GCC repo.
--- a/config.guess
+++ b/config.guess
@@ -1,10 +1,8 @@
#! /bin/sh
# Attempt to guess a canonical system name.
-# Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999,
-# 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010,
-# 2011, 2012, 2013 Free Software Foundation, Inc.
+# Copyright 1992-2013 Free Software Foundation, Inc.
-timestamp='2012-12-30'
+timestamp='2013-04-24'
# This file is free software; you can redistribute it and/or modify it
# under the terms of the GNU General Public License as published by
@@ -52,9 +50,7 @@ version="\
GNU config.guess ($timestamp)
Originally written by Per Bothner.
-Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000,
-2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011,
-2012, 2013 Free Software Foundation, Inc.
+Copyright 1992-2013 Free Software Foundation, Inc.
This is free software; see the source for copying conditions. There is NO
warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE."
@@ -887,6 +883,9 @@ EOF
if test "$?" = 0 ; then LIBC="libc1" ; else LIBC="" ; fi
echo ${UNAME_MACHINE}-unknown-linux-gnu${LIBC}
exit ;;
+ arc:Linux:*:* | arceb:Linux:*:*)
+ echo ${UNAME_MACHINE}-unknown-linux-gnu
+ exit ;;
arm*:Linux:*:*)
eval $set_cc_for_build
if echo __ARM_EABI__ | $CC_FOR_BUILD -E - 2>/dev/null \
@@ -925,6 +924,11 @@ EOF
#ifdef __dietlibc__
LIBC=dietlibc
#endif
+ #else
+ #include <features.h>
+ #ifdef __UCLIBC__
+ LIBC=uclibc
+ #endif
EOF
eval `$CC_FOR_BUILD -E $dummy.c 2>/dev/null | grep '^LIBC'`
echo "${UNAME_MACHINE}-pc-linux-${LIBC}"
@@ -957,6 +961,9 @@ EOF
eval `$CC_FOR_BUILD -E $dummy.c 2>/dev/null | grep '^CPU'`
test x"${CPU}" != x && { echo "${CPU}-unknown-linux-gnu"; exit; }
;;
+ or1k:Linux:*:*)
+ echo ${UNAME_MACHINE}-unknown-linux-gnu
+ exit ;;
or32:Linux:*:*)
echo ${UNAME_MACHINE}-unknown-linux-gnu
exit ;;
@@ -999,7 +1006,9 @@ EOF
echo ${UNAME_MACHINE}-dec-linux-gnu
exit ;;
x86_64:Linux:*:*)
- echo ${UNAME_MACHINE}-unknown-linux-gnu
+ LIBC=gnu
+ test -r /lib/libc.so && od -An -S13 /lib/libc.so | grep -q __uClibc_main && LIBC=uclibc
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
exit ;;
xtensa*:Linux:*:*)
echo ${UNAME_MACHINE}-unknown-linux-gnu
--- a/config.sub
+++ b/config.sub
@@ -1,10 +1,8 @@
#! /bin/sh
# Configuration validation subroutine script.
-# Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999,
-# 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010,
-# 2011, 2012, 2013 Free Software Foundation, Inc.
+# Copyright 1992-2013 Free Software Foundation, Inc.
-timestamp='2013-01-11'
+timestamp='2013-04-24'
# This file is free software; you can redistribute it and/or modify it
# under the terms of the GNU General Public License as published by
@@ -70,9 +68,7 @@ Report bugs and patches to <config-patch
version="\
GNU config.sub ($timestamp)
-Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000,
-2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011,
-2012, 2013 Free Software Foundation, Inc.
+Copyright 1992-2013 Free Software Foundation, Inc.
This is free software; see the source for copying conditions. There is NO
warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE."
@@ -256,7 +252,7 @@ case $basic_machine in
| alpha | alphaev[4-8] | alphaev56 | alphaev6[78] | alphapca5[67] \
| alpha64 | alpha64ev[4-8] | alpha64ev56 | alpha64ev6[78] | alpha64pca5[67] \
| am33_2.0 \
- | arc \
+ | arc | arceb \
| arm | arm[bl]e | arme[lb] | armv[2-8] | armv[3-8][lb] | armv7[arm] \
| avr | avr32 \
| be32 | be64 \
@@ -297,10 +293,10 @@ case $basic_machine in
| mt \
| msp430 \
| nds32 | nds32le | nds32be \
- | nios | nios2 \
+ | nios | nios2 | nios2eb | nios2el \
| ns16k | ns32k \
| open8 \
- | or32 \
+ | or1k | or32 \
| pdp10 | pdp11 | pj | pjl \
| powerpc | powerpc64 | powerpc64le | powerpcle \
| pyramid \
@@ -370,7 +366,7 @@ case $basic_machine in
| aarch64-* | aarch64_be-* \
| alpha-* | alphaev[4-8]-* | alphaev56-* | alphaev6[78]-* \
| alpha64-* | alpha64ev[4-8]-* | alpha64ev56-* | alpha64ev6[78]-* \
- | alphapca5[67]-* | alpha64pca5[67]-* | arc-* \
+ | alphapca5[67]-* | alpha64pca5[67]-* | arc-* | arceb-* \
| arm-* | armbe-* | armle-* | armeb-* | armv*-* \
| avr-* | avr32-* \
| be32-* | be64-* \
@@ -414,7 +410,7 @@ case $basic_machine in
| mt-* \
| msp430-* \
| nds32-* | nds32le-* | nds32be-* \
- | nios-* | nios2-* \
+ | nios-* | nios2-* | nios2eb-* | nios2el-* \
| none-* | np1-* | ns16k-* | ns32k-* \
| open8-* \
| orion-* \
@@ -1593,6 +1589,9 @@ case $basic_machine in
mips*-*)
os=-elf
;;
+ or1k-*)
+ os=-elf
+ ;;
or32-*)
os=-coff
;;
#
# gdb-7.6-ppc_insns_match_pattern.patch
#
From: Alan Modra <amodra@gmail.com>
Date: Tue Jun 4 02:44:35 2013 +0000
Git-commit: 845d47080b7d7e068e4ec3d11fe6e27b403ac6e3
References: ppc64le enablement
* ppc-tdep.h (ppc_insns_match_pattern): Update prototype.
* rs6000-tdep.c (read_insn): Add frame param, don't assume big-endian.
(ppc_insns_match_pattern): Add frame param. Avoid multiple
target mem reads on optional insns.
* ppc-linux-tdep.c (ppc_skip_trampoline_code): Update
ppc_insns_match_pattern calls.
* ppc64-tdep.c (ppc64_standard_linkage2, ppc64_standard_linkage3):
Add match for power7 thread safety insns, and new order of
std 2,40(1) insn. Correct code shown for _dl_runtime_resolve
invocation in comment, and update rest of comment.
(PPC64_STANDARD_LINKAGE1_LEN, PPC64_STANDARD_LINKAGE2_LEN,
PPC64_STANDARD_LINKAGE3_LEN): Delete.
(ppc64_standard_linkage2_target): Update insn offsets.
(ppc64_skip_trampoline_code): Use a single insn buffer. Match newer
stubs first. Update calls.
Acked-by: Petr Tesarik <ptesarik@suse.cz>
---
gdb/ChangeLog | 18 ++++++
gdb/ppc-linux-tdep.c | 4 -
gdb/ppc-tdep.h | 4 -
gdb/ppc64-tdep.c | 140 ++++++++++++++++++++++++++++++---------------------
gdb/rs6000-tdep.c | 35 +++++++-----
5 files changed, 128 insertions(+), 73 deletions(-)
--- a/gdb/ChangeLog
+++ b/gdb/ChangeLog
@@ -1,3 +1,21 @@
+2013-06-04 Alan Modra <amodra@gmail.com>
+
+ * ppc-tdep.h (ppc_insns_match_pattern): Update prototype.
+ * rs6000-tdep.c (read_insn): Add frame param, don't assume big-endian.
+ (ppc_insns_match_pattern): Add frame param. Avoid multiple
+ target mem reads on optional insns.
+ * ppc-linux-tdep.c (ppc_skip_trampoline_code): Update
+ ppc_insns_match_pattern calls.
+ * ppc64-tdep.c (ppc64_standard_linkage2, ppc64_standard_linkage3):
+ Add match for power7 thread safety insns, and new order of
+ std 2,40(1) insn. Correct code shown for _dl_runtime_resolve
+ invocation in comment, and update rest of comment.
+ (PPC64_STANDARD_LINKAGE1_LEN, PPC64_STANDARD_LINKAGE2_LEN,
+ PPC64_STANDARD_LINKAGE3_LEN): Delete.
+ (ppc64_standard_linkage2_target): Update insn offsets.
+ (ppc64_skip_trampoline_code): Use a single insn buffer. Match newer
+ stubs first. Update calls.
+
2013-04-08 Tom Tromey <tromey@redhat.com>
* minsyms.h (struct bound_minimal_symbol): New.
--- a/gdb/ppc-linux-tdep.c
+++ b/gdb/ppc-linux-tdep.c
@@ -361,7 +361,7 @@ ppc_skip_trampoline_code (struct frame_i
enum bfd_endian byte_order = gdbarch_byte_order (gdbarch);
CORE_ADDR target = 0;
- if (ppc_insns_match_pattern (pc, powerpc32_plt_stub, insnbuf))
+ if (ppc_insns_match_pattern (frame, pc, powerpc32_plt_stub, insnbuf))
{
/* Insn pattern is
lis r11, xxxx
@@ -373,7 +373,7 @@ ppc_skip_trampoline_code (struct frame_i
target = read_memory_unsigned_integer (target, 4, byte_order);
}
- if (ppc_insns_match_pattern (pc, powerpc32_plt_stub_so, insnbuf))
+ if (ppc_insns_match_pattern (frame, pc, powerpc32_plt_stub_so, insnbuf))
{
/* Insn pattern is
lwz r11, xxxx(r30)
--- a/gdb/ppc-tdep.h
+++ b/gdb/ppc-tdep.h
@@ -300,9 +300,9 @@ struct ppc_insn_pattern
int optional; /* If non-zero, this insn may be absent. */
};
-extern int ppc_insns_match_pattern (CORE_ADDR pc,
+extern int ppc_insns_match_pattern (struct frame_info *frame, CORE_ADDR pc,
struct ppc_insn_pattern *pattern,
- unsigned int *insn);
+ unsigned int *insns);
extern CORE_ADDR ppc_insn_d_field (unsigned int insn);
extern CORE_ADDR ppc_insn_ds_field (unsigned int insn);
--- a/gdb/ppc64-tdep.c
+++ b/gdb/ppc64-tdep.c
@@ -59,9 +59,10 @@ ppc64_desc_entry_point (struct gdbarch *
return (CORE_ADDR) read_memory_unsigned_integer (desc, 8, byte_order);
}
-/* Pattern for the standard linkage function. These are built by
- build_plt_stub in elf64-ppc.c, whose GLINK argument is always
- zero. */
+/* Patterns for the standard linkage functions. These are built by
+ build_plt_stub in bfd/elf64-ppc.c. */
+
+/* Old PLT call stub. */
static struct ppc_insn_pattern ppc64_standard_linkage1[] =
{
@@ -95,15 +96,23 @@ static struct ppc_insn_pattern ppc64_sta
{ 0, 0, 0 }
};
-#define PPC64_STANDARD_LINKAGE1_LEN ARRAY_SIZE (ppc64_standard_linkage1)
+/* Current PLT call stub to access PLT entries more than +/- 32k from r2.
+ Also supports older stub with different placement of std 2,40(1),
+ a stub that omits the std 2,40(1), and both versions of power7
+ thread safety read barriers. Note that there are actually two more
+ instructions following "cmpldi r2, 0", "bnectr+" and "b <glink_i>",
+ but there isn't any need to match them. */
static struct ppc_insn_pattern ppc64_standard_linkage2[] =
{
+ /* std r2, 40(r1) <optional> */
+ { -1, insn_ds (62, 2, 1, 40, 0), 1 },
+
/* addis r12, r2, <any> */
{ insn_d (-1, -1, -1, 0), insn_d (15, 12, 2, 0), 0 },
- /* std r2, 40(r1) */
- { -1, insn_ds (62, 2, 1, 40, 0), 0 },
+ /* std r2, 40(r1) <optional> */
+ { -1, insn_ds (62, 2, 1, 40, 0), 1 },
/* ld r11, <any>(r12) */
{ insn_ds (-1, -1, -1, 0, -1), insn_ds (58, 11, 12, 0, 0), 0 },
@@ -114,24 +123,33 @@ static struct ppc_insn_pattern ppc64_sta
/* mtctr r11 */
{ insn_xfx (-1, -1, -1, -1), insn_xfx (31, 11, 9, 467), 0 },
+ /* xor r11, r11, r11 <optional> */
+ { -1, 0x7d6b5a78, 1 },
+
+ /* add r12, r12, r11 <optional> */
+ { -1, 0x7d8c5a14, 1 },
+
/* ld r2, <any>(r12) */
{ insn_ds (-1, -1, -1, 0, -1), insn_ds (58, 2, 12, 0, 0), 0 },
/* ld r11, <any>(r12) <optional> */
{ insn_ds (-1, -1, -1, 0, -1), insn_ds (58, 11, 12, 0, 0), 1 },
- /* bctr */
- { -1, 0x4e800420, 0 },
+ /* bctr <optional> */
+ { -1, 0x4e800420, 1 },
+
+ /* cmpldi r2, 0 <optional> */
+ { -1, 0x28220000, 1 },
{ 0, 0, 0 }
};
-#define PPC64_STANDARD_LINKAGE2_LEN ARRAY_SIZE (ppc64_standard_linkage2)
+/* Current PLT call stub to access PLT entries within +/- 32k of r2. */
static struct ppc_insn_pattern ppc64_standard_linkage3[] =
{
- /* std r2, 40(r1) */
- { -1, insn_ds (62, 2, 1, 40, 0), 0 },
+ /* std r2, 40(r1) <optional> */
+ { -1, insn_ds (62, 2, 1, 40, 0), 1 },
/* ld r11, <any>(r2) */
{ insn_ds (-1, -1, -1, 0, -1), insn_ds (58, 11, 2, 0, 0), 0 },
@@ -142,56 +160,71 @@ static struct ppc_insn_pattern ppc64_sta
/* mtctr r11 */
{ insn_xfx (-1, -1, -1, -1), insn_xfx (31, 11, 9, 467), 0 },
+ /* xor r11, r11, r11 <optional> */
+ { -1, 0x7d6b5a78, 1 },
+
+ /* add r2, r2, r11 <optional> */
+ { -1, 0x7c425a14, 1 },
+
/* ld r11, <any>(r2) <optional> */
{ insn_ds (-1, -1, -1, 0, -1), insn_ds (58, 11, 2, 0, 0), 1 },
/* ld r2, <any>(r2) */
{ insn_ds (-1, -1, -1, 0, -1), insn_ds (58, 2, 2, 0, 0), 0 },
- /* bctr */
- { -1, 0x4e800420, 0 },
+ /* bctr <optional> */
+ { -1, 0x4e800420, 1 },
+
+ /* cmpldi r2, 0 <optional> */
+ { -1, 0x28220000, 1 },
{ 0, 0, 0 }
};
-#define PPC64_STANDARD_LINKAGE3_LEN ARRAY_SIZE (ppc64_standard_linkage3)
-
/* When the dynamic linker is doing lazy symbol resolution, the first
call to a function in another object will go like this:
- The user's function calls the linkage function:
- 100007c4: 4b ff fc d5 bl 10000498
- 100007c8: e8 41 00 28 ld r2,40(r1)
+ 100003d4: 4b ff ff ad bl 10000380 <nnnn.plt_call.printf>
+ 100003d8: e8 41 00 28 ld r2,40(r1)
- - The linkage function loads the entry point (and other stuff) from
- the function descriptor in the PLT, and jumps to it:
+ - The linkage function loads the entry point and toc pointer from
+ the function descriptor in the PLT, and jumps to it:
- 10000498: 3d 82 00 00 addis r12,r2,0
- 1000049c: f8 41 00 28 std r2,40(r1)
- 100004a0: e9 6c 80 98 ld r11,-32616(r12)
- 100004a4: e8 4c 80 a0 ld r2,-32608(r12)
- 100004a8: 7d 69 03 a6 mtctr r11
- 100004ac: e9 6c 80 a8 ld r11,-32600(r12)
- 100004b0: 4e 80 04 20 bctr
+ <nnnn.plt_call.printf>:
+ 10000380: f8 41 00 28 std r2,40(r1)
+ 10000384: e9 62 80 78 ld r11,-32648(r2)
+ 10000388: 7d 69 03 a6 mtctr r11
+ 1000038c: e8 42 80 80 ld r2,-32640(r2)
+ 10000390: 28 22 00 00 cmpldi r2,0
+ 10000394: 4c e2 04 20 bnectr+
+ 10000398: 48 00 03 a0 b 10000738 <printf@plt>
- But since this is the first time that PLT entry has been used, it
- sends control to its glink entry. That loads the number of the
- PLT entry and jumps to the common glink0 code:
+ sends control to its glink entry. That loads the number of the
+ PLT entry and jumps to the common glink0 code:
- 10000c98: 38 00 00 00 li r0,0
- 10000c9c: 4b ff ff dc b 10000c78
+ <printf@plt>:
+ 10000738: 38 00 00 01 li r0,1
+ 1000073c: 4b ff ff bc b 100006f8 <__glink_PLTresolve>
- The common glink0 code then transfers control to the dynamic
- linker's fixup code:
+ linker's fixup code:
- 10000c78: e8 41 00 28 ld r2,40(r1)
- 10000c7c: 3d 82 00 00 addis r12,r2,0
- 10000c80: e9 6c 80 80 ld r11,-32640(r12)
- 10000c84: e8 4c 80 88 ld r2,-32632(r12)
- 10000c88: 7d 69 03 a6 mtctr r11
- 10000c8c: e9 6c 80 90 ld r11,-32624(r12)
- 10000c90: 4e 80 04 20 bctr
+ 100006f0: 0000000000010440 .quad plt0 - (. + 16)
+ <__glink_PLTresolve>:
+ 100006f8: 7d 88 02 a6 mflr r12
+ 100006fc: 42 9f 00 05 bcl 20,4*cr7+so,10000700
+ 10000700: 7d 68 02 a6 mflr r11
+ 10000704: e8 4b ff f0 ld r2,-16(r11)
+ 10000708: 7d 88 03 a6 mtlr r12
+ 1000070c: 7d 82 5a 14 add r12,r2,r11
+ 10000710: e9 6c 00 00 ld r11,0(r12)
+ 10000714: e8 4c 00 08 ld r2,8(r12)
+ 10000718: 7d 69 03 a6 mtctr r11
+ 1000071c: e9 6c 00 10 ld r11,16(r12)
+ 10000720: 4e 80 04 20 bctr
Eventually, this code will figure out how to skip all of this,
including the dynamic linker. At the moment, we just get through
@@ -234,8 +267,8 @@ ppc64_standard_linkage2_target (struct f
CORE_ADDR desc
= ((CORE_ADDR) get_frame_register_unsigned (frame,
tdep->ppc_gp0_regnum + 2)
- + (ppc_insn_d_field (insn[0]) << 16)
- + ppc_insn_ds_field (insn[2]));
+ + (ppc_insn_d_field (insn[1]) << 16)
+ + ppc_insn_ds_field (insn[3]));
/* The first word of the descriptor is the entry point. Return that. */
return ppc64_desc_entry_point (gdbarch, desc);
@@ -266,23 +299,20 @@ ppc64_standard_linkage3_target (struct f
CORE_ADDR
ppc64_skip_trampoline_code (struct frame_info *frame, CORE_ADDR pc)
{
- unsigned int ppc64_standard_linkage1_insn[PPC64_STANDARD_LINKAGE1_LEN];
- unsigned int ppc64_standard_linkage2_insn[PPC64_STANDARD_LINKAGE2_LEN];
- unsigned int ppc64_standard_linkage3_insn[PPC64_STANDARD_LINKAGE3_LEN];
+#define MAX(a,b) ((a) > (b) ? (a) : (b))
+ unsigned int insns[MAX (MAX (ARRAY_SIZE (ppc64_standard_linkage1),
+ ARRAY_SIZE (ppc64_standard_linkage2)),
+ ARRAY_SIZE (ppc64_standard_linkage3)) - 1];
CORE_ADDR target;
- if (ppc_insns_match_pattern (pc, ppc64_standard_linkage1,
- ppc64_standard_linkage1_insn))
- pc = ppc64_standard_linkage1_target (frame, pc,
- ppc64_standard_linkage1_insn);
- else if (ppc_insns_match_pattern (pc, ppc64_standard_linkage2,
- ppc64_standard_linkage2_insn))
- pc = ppc64_standard_linkage2_target (frame, pc,
- ppc64_standard_linkage2_insn);
- else if (ppc_insns_match_pattern (pc, ppc64_standard_linkage3,
- ppc64_standard_linkage3_insn))
- pc = ppc64_standard_linkage3_target (frame, pc,
- ppc64_standard_linkage3_insn);
+ if (ppc_insns_match_pattern (frame, pc, ppc64_standard_linkage3, insns)
+ && (insns[8] != 0 || insns[9] != 0))
+ pc = ppc64_standard_linkage3_target (frame, pc, insns);
+ else if (ppc_insns_match_pattern (frame, pc, ppc64_standard_linkage2, insns)
+ && (insns[10] != 0 || insns[11] != 0))
+ pc = ppc64_standard_linkage2_target (frame, pc, insns);
+ else if (ppc_insns_match_pattern (frame, pc, ppc64_standard_linkage1, insns))
+ pc = ppc64_standard_linkage1_target (frame, pc, insns);
else
return 0;
--- a/gdb/rs6000-tdep.c
+++ b/gdb/rs6000-tdep.c
@@ -4238,14 +4238,15 @@ show_powerpc_exact_watchpoints (struct u
fprintf_filtered (file, _("Use of exact watchpoints is %s.\n"), value);
}
-/* Read a PPC instruction from memory. PPC instructions are always
- big-endian, no matter what endianness the program is running in, so
- we can hardcode BFD_ENDIAN_BIG for read_memory_unsigned_integer. */
+/* Read a PPC instruction from memory. */
static unsigned int
-read_insn (CORE_ADDR pc)
+read_insn (struct frame_info *frame, CORE_ADDR pc)
{
- return read_memory_unsigned_integer (pc, 4, BFD_ENDIAN_BIG);
+ struct gdbarch *gdbarch = get_frame_arch (frame);
+ enum bfd_endian byte_order = gdbarch_byte_order (gdbarch);
+
+ return read_memory_unsigned_integer (pc, 4, byte_order);
}
/* Return non-zero if the instructions at PC match the series
@@ -4262,19 +4263,25 @@ read_insn (CORE_ADDR pc)
i'th instruction in memory. */
int
-ppc_insns_match_pattern (CORE_ADDR pc, struct ppc_insn_pattern *pattern,
- unsigned int *insn)
+ppc_insns_match_pattern (struct frame_info *frame, CORE_ADDR pc,
+ struct ppc_insn_pattern *pattern,
+ unsigned int *insns)
{
int i;
+ unsigned int insn;
- for (i = 0; pattern[i].mask; i++)
+ for (i = 0, insn = 0; pattern[i].mask; i++)
{
- insn[i] = read_insn (pc);
- if ((insn[i] & pattern[i].mask) == pattern[i].data)
- pc += 4;
- else if (pattern[i].optional)
- insn[i] = 0;
- else
+ if (insn == 0)
+ insn = read_insn (frame, pc);
+ insns[i] = 0;
+ if ((insn & pattern[i].mask) == pattern[i].data)
+ {
+ insns[i] = insn;
+ pc += 4;
+ insn = 0;
+ }
+ else if (!pattern[i].optional)
return 0;
}
#
# gdb-7.6-floatformat.patch
#
From: DJ Delorie <dj@redhat.com>
Date: Tue Aug 20 06:02:53 2013 +0000
Git-commit: 21290977cbdd41c6f4e7b297e63901ad491acadd
References: ppc64le enablement
merge from gcc
Acked-by: Petr Tesarik <ptesarik@suse.cz>
---
include/ChangeLog | 10 ++++++++++
include/dwarf2.def | 3 +++
include/floatformat.h | 3 ++-
libiberty/ChangeLog | 6 ++++++
libiberty/floatformat.c | 13 +++++++++++--
5 files changed, 32 insertions(+), 3 deletions(-)
--- a/include/ChangeLog
+++ b/include/ChangeLog
@@ -1,3 +1,13 @@
+2013-08-20 Alan Modra <amodra@gmail.com>
+
+ * floatformat.h (floatformat_ibm_long_double): Delete.
+ (floatformat_ibm_long_double_big): Declare.
+ (floatformat_ibm_long_double_little): Declare.
+
+2013-08-19 Dehao Chen <dehao@google.com>
+
+ * dwarf2.def (DW_AT_GNU_discriminator): New attribute.
+
2013-03-12 Sebastian Huber <sebastian.huber@embedded-brains.de>
* opcode/nios2.h: Edit comment.
--- a/include/dwarf2.def
+++ b/include/dwarf2.def
@@ -390,6 +390,9 @@ DW_AT (DW_AT_GNU_ranges_base, 0x2132)
DW_AT (DW_AT_GNU_addr_base, 0x2133)
DW_AT (DW_AT_GNU_pubnames, 0x2134)
DW_AT (DW_AT_GNU_pubtypes, 0x2135)
+/* Attribute for discriminator.
+ See http://gcc.gnu.org/wiki/Discriminator */
+DW_AT (DW_AT_GNU_discriminator, 0x2136)
/* VMS extensions. */
DW_AT (DW_AT_VMS_rtnbeg_pd_address, 0x2201)
/* GNAT extensions. */
--- a/include/floatformat.h
+++ b/include/floatformat.h
@@ -128,7 +128,8 @@ extern const struct floatformat floatfor
extern const struct floatformat floatformat_ia64_quad_big;
extern const struct floatformat floatformat_ia64_quad_little;
/* IBM long double (double+double). */
-extern const struct floatformat floatformat_ibm_long_double;
+extern const struct floatformat floatformat_ibm_long_double_big;
+extern const struct floatformat floatformat_ibm_long_double_little;
/* Convert from FMT to a double.
FROM is the address of the extended float.
--- a/libiberty/ChangeLog
+++ b/libiberty/ChangeLog
@@ -1,3 +1,9 @@
+2013-08-20 Alan Modra <amodra@gmail.com>
+
+ * floatformat.c (floatformat_ibm_long_double): Rename to..
+ (floatformat_ibm_long_double_big): ..this.
+ (floatformat_ibm_long_double_little): New.
+
2013-03-01 Andreas Schwab <schwab@linux-m68k.org>
* obstacks.texi (Obstacks): Trim @node to only contain the
--- a/libiberty/floatformat.c
+++ b/libiberty/floatformat.c
@@ -371,14 +371,23 @@ floatformat_ibm_long_double_is_valid (co
}
}
-const struct floatformat floatformat_ibm_long_double =
+const struct floatformat floatformat_ibm_long_double_big =
{
floatformat_big, 128, 0, 1, 11, 1023, 2047, 12, 52,
floatformat_intbit_no,
- "floatformat_ibm_long_double",
+ "floatformat_ibm_long_double_big",
floatformat_ibm_long_double_is_valid,
&floatformat_ieee_double_big
};
+
+const struct floatformat floatformat_ibm_long_double_little =
+{
+ floatformat_little, 128, 0, 1, 11, 1023, 2047, 12, 52,
+ floatformat_intbit_no,
+ "floatformat_ibm_long_double_little",
+ floatformat_ibm_long_double_is_valid,
+ &floatformat_ieee_double_little
+};
#ifndef min
#
# gdb-7.6-ppc64-ELFv2-trampoline-match.patch
#
From: Alan Modra <amodra@gmail.com>
Date: Mon Nov 11 14:14:40 2013 +1030
Git-commit: ef1bc9e72fd2f0310ac3113acc41e1c115e3ac79
References: ppc64le enablement
PowerPC64 ELFv2 trampoline match
ELFv2 needs different plt call stubs to ELFv1, register usage differs
too. When I added these to ld I changed register usage in the ELFv1
stubs as well, simplifying the linker code and (perhaps) future
maintenance. All well and good, but this means gdb needs to cope with
more stub variants. This patch also handles skipping over addis/addi
setting up r2 in ELFv2 global entry code. We want breakpoints to be
set past this point to catch calls via the local entry point.
* ppc64-tdep.c (ppc64_plt_entry_point): Renamed from..
(ppc64_desc_entry_point): ..this. Update comments here and at
call points.
(ppc64_standard_linkage1, ppc64_standard_linkage2,
ppc64_standard_linkage3): Update comments.
(ppc64_standard_linkage4, ppc64_standard_linkage5,
(ppc64_standard_linkage6, ppc64_standard_linkage7): New insn
patterns.
(ppc64_standard_linkage4_target): New function.
(ppc64_skip_trampoline_code): Skip ELFv2 patterns too.
* rs6000-tdep.c (skip_prologue): Skip ELFv2 r2 setup. Correct
nop match. Fix comment wrap.
Acked-by: Petr Tesarik <ptesarik@suse.cz>
---
gdb/ChangeLog | 15 ++++
gdb/ppc64-tdep.c | 201 ++++++++++++++++++++++++++++++++++++++++++++++--------
gdb/rs6000-tdep.c | 20 ++++-
3 files changed, 203 insertions(+), 33 deletions(-)
--- a/gdb/ChangeLog
+++ b/gdb/ChangeLog
@@ -1,3 +1,18 @@
+2013-11-15 Alan Modra <amodra@gmail.com>
+
+ * ppc64-tdep.c (ppc64_plt_entry_point): Renamed from..
+ (ppc64_desc_entry_point): ..this. Update comments here and at
+ call points.
+ (ppc64_standard_linkage1, ppc64_standard_linkage2,
+ ppc64_standard_linkage3): Update comments.
+ (ppc64_standard_linkage4, ppc64_standard_linkage5,
+ (ppc64_standard_linkage6, ppc64_standard_linkage7): New insn
+ patterns.
+ (ppc64_standard_linkage4_target): New function.
+ (ppc64_skip_trampoline_code): Skip ELFv2 patterns too.
+ * rs6000-tdep.c (skip_prologue): Skip ELFv2 r2 setup. Correct
+ nop match. Fix comment wrap.
+
2013-06-04 Alan Modra <amodra@gmail.com>
* ppc-tdep.h (ppc_insns_match_pattern): Update prototype.
--- a/gdb/ppc64-tdep.c
+++ b/gdb/ppc64-tdep.c
@@ -48,21 +48,21 @@
| (((spr) & 0x3e0) << 6) \
| (((xo) & 0x3ff) << 1))
-/* If DESC is the address of a 64-bit PowerPC FreeBSD function
- descriptor, return the descriptor's entry point. */
+/* If PLT is the address of a 64-bit PowerPC PLT entry,
+ return the function's entry point. */
static CORE_ADDR
-ppc64_desc_entry_point (struct gdbarch *gdbarch, CORE_ADDR desc)
+ppc64_plt_entry_point (struct gdbarch *gdbarch, CORE_ADDR plt)
{
enum bfd_endian byte_order = gdbarch_byte_order (gdbarch);
- /* The first word of the descriptor is the entry point. */
- return (CORE_ADDR) read_memory_unsigned_integer (desc, 8, byte_order);
+ /* The first word of the PLT entry is the function entry point. */
+ return (CORE_ADDR) read_memory_unsigned_integer (plt, 8, byte_order);
}
/* Patterns for the standard linkage functions. These are built by
build_plt_stub in bfd/elf64-ppc.c. */
-/* Old PLT call stub. */
+/* Old ELFv1 PLT call stub. */
static struct ppc_insn_pattern ppc64_standard_linkage1[] =
{
@@ -96,7 +96,7 @@ static struct ppc_insn_pattern ppc64_sta
{ 0, 0, 0 }
};
-/* Current PLT call stub to access PLT entries more than +/- 32k from r2.
+/* ELFv1 PLT call stub to access PLT entries more than +/- 32k from r2.
Also supports older stub with different placement of std 2,40(1),
a stub that omits the std 2,40(1), and both versions of power7
thread safety read barriers. Note that there are actually two more
@@ -144,7 +144,7 @@ static struct ppc_insn_pattern ppc64_sta
{ 0, 0, 0 }
};
-/* Current PLT call stub to access PLT entries within +/- 32k of r2. */
+/* ELFv1 PLT call stub to access PLT entries within +/- 32k of r2. */
static struct ppc_insn_pattern ppc64_standard_linkage3[] =
{
@@ -181,6 +181,128 @@ static struct ppc_insn_pattern ppc64_sta
{ 0, 0, 0 }
};
+/* ELFv1 PLT call stub to access PLT entries more than +/- 32k from r2.
+ A more modern variant of ppc64_standard_linkage2 differing in
+ register usage. */
+
+static struct ppc_insn_pattern ppc64_standard_linkage4[] =
+ {
+ /* std r2, 40(r1) <optional> */
+ { -1, insn_ds (62, 2, 1, 40, 0), 1 },
+
+ /* addis r11, r2, <any> */
+ { insn_d (-1, -1, -1, 0), insn_d (15, 11, 2, 0), 0 },
+
+ /* ld r12, <any>(r11) */
+ { insn_ds (-1, -1, -1, 0, -1), insn_ds (58, 12, 11, 0, 0), 0 },
+
+ /* addi r11, r11, <any> <optional> */
+ { insn_d (-1, -1, -1, 0), insn_d (14, 11, 11, 0), 1 },
+
+ /* mtctr r12 */
+ { insn_xfx (-1, -1, -1, -1), insn_xfx (31, 12, 9, 467), 0 },
+
+ /* xor r2, r12, r12 <optional> */
+ { -1, 0x7d826278, 1 },
+
+ /* add r11, r11, r2 <optional> */
+ { -1, 0x7d6b1214, 1 },
+
+ /* ld r2, <any>(r11) */
+ { insn_ds (-1, -1, -1, 0, -1), insn_ds (58, 2, 11, 0, 0), 0 },
+
+ /* ld r11, <any>(r11) <optional> */
+ { insn_ds (-1, -1, -1, 0, -1), insn_ds (58, 11, 11, 0, 0), 1 },
+
+ /* bctr <optional> */
+ { -1, 0x4e800420, 1 },
+
+ /* cmpldi r2, 0 <optional> */
+ { -1, 0x28220000, 1 },
+
+ { 0, 0, 0 }
+ };
+
+/* ELFv1 PLT call stub to access PLT entries within +/- 32k of r2.
+ A more modern variant of ppc64_standard_linkage3 differing in
+ register usage. */
+
+static struct ppc_insn_pattern ppc64_standard_linkage5[] =
+ {
+ /* std r2, 40(r1) <optional> */
+ { -1, insn_ds (62, 2, 1, 40, 0), 1 },
+
+ /* ld r12, <any>(r2) */
+ { insn_ds (-1, -1, -1, 0, -1), insn_ds (58, 12, 2, 0, 0), 0 },
+
+ /* addi r2, r2, <any> <optional> */
+ { insn_d (-1, -1, -1, 0), insn_d (14, 2, 2, 0), 1 },
+
+ /* mtctr r12 */
+ { insn_xfx (-1, -1, -1, -1), insn_xfx (31, 12, 9, 467), 0 },
+
+ /* xor r11, r12, r12 <optional> */
+ { -1, 0x7d8b6278, 1 },
+
+ /* add r2, r2, r11 <optional> */
+ { -1, 0x7c425a14, 1 },
+
+ /* ld r11, <any>(r2) <optional> */
+ { insn_ds (-1, -1, -1, 0, -1), insn_ds (58, 11, 2, 0, 0), 1 },
+
+ /* ld r2, <any>(r2) */
+ { insn_ds (-1, -1, -1, 0, -1), insn_ds (58, 2, 2, 0, 0), 0 },
+
+ /* bctr <optional> */
+ { -1, 0x4e800420, 1 },
+
+ /* cmpldi r2, 0 <optional> */
+ { -1, 0x28220000, 1 },
+
+ { 0, 0, 0 }
+ };
+
+/* ELFv2 PLT call stub to access PLT entries more than +/- 32k from r2. */
+
+static struct ppc_insn_pattern ppc64_standard_linkage6[] =
+ {
+ /* std r2, 24(r1) <optional> */
+ { -1, insn_ds (62, 2, 1, 24, 0), 1 },
+
+ /* addis r11, r2, <any> */
+ { insn_d (-1, -1, -1, 0), insn_d (15, 11, 2, 0), 0 },
+
+ /* ld r12, <any>(r11) */
+ { insn_ds (-1, -1, -1, 0, -1), insn_ds (58, 12, 11, 0, 0), 0 },
+
+ /* mtctr r12 */
+ { insn_xfx (-1, -1, -1, -1), insn_xfx (31, 12, 9, 467), 0 },
+
+ /* bctr */
+ { -1, 0x4e800420, 0 },
+
+ { 0, 0, 0 }
+ };
+
+/* ELFv2 PLT call stub to access PLT entries within +/- 32k of r2. */
+
+static struct ppc_insn_pattern ppc64_standard_linkage7[] =
+ {
+ /* std r2, 24(r1) <optional> */
+ { -1, insn_ds (62, 2, 1, 40, 0), 1 },
+
+ /* ld r12, <any>(r2) */
+ { insn_ds (-1, -1, -1, 0, -1), insn_ds (58, 12, 2, 0, 0), 0 },
+
+ /* mtctr r12 */
+ { insn_xfx (-1, -1, -1, -1), insn_xfx (31, 12, 9, 467), 0 },
+
+ /* bctr */
+ { -1, 0x4e800420, 0 },
+
+ { 0, 0, 0 }
+ };
+
/* When the dynamic linker is doing lazy symbol resolution, the first
call to a function in another object will go like this:
@@ -243,16 +365,14 @@ ppc64_standard_linkage1_target (struct f
struct gdbarch *gdbarch = get_frame_arch (frame);
struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
- /* The address of the function descriptor this linkage function
- references. */
- CORE_ADDR desc
+ /* The address of the PLT entry this linkage function references. */
+ CORE_ADDR plt
= ((CORE_ADDR) get_frame_register_unsigned (frame,
tdep->ppc_gp0_regnum + 2)
+ (ppc_insn_d_field (insn[0]) << 16)
+ ppc_insn_ds_field (insn[2]));
- /* The first word of the descriptor is the entry point. Return that. */
- return ppc64_desc_entry_point (gdbarch, desc);
+ return ppc64_plt_entry_point (gdbarch, plt);
}
static CORE_ADDR
@@ -262,16 +382,14 @@ ppc64_standard_linkage2_target (struct f
struct gdbarch *gdbarch = get_frame_arch (frame);
struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
- /* The address of the function descriptor this linkage function
- references. */
- CORE_ADDR desc
+ /* The address of the PLT entry this linkage function references. */
+ CORE_ADDR plt
= ((CORE_ADDR) get_frame_register_unsigned (frame,
tdep->ppc_gp0_regnum + 2)
+ (ppc_insn_d_field (insn[1]) << 16)
+ ppc_insn_ds_field (insn[3]));
- /* The first word of the descriptor is the entry point. Return that. */
- return ppc64_desc_entry_point (gdbarch, desc);
+ return ppc64_plt_entry_point (gdbarch, plt);
}
static CORE_ADDR
@@ -281,15 +399,28 @@ ppc64_standard_linkage3_target (struct f
struct gdbarch *gdbarch = get_frame_arch (frame);
struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
- /* The address of the function descriptor this linkage function
- references. */
- CORE_ADDR desc
+ /* The address of the PLT entry this linkage function references. */
+ CORE_ADDR plt
= ((CORE_ADDR) get_frame_register_unsigned (frame,
tdep->ppc_gp0_regnum + 2)
+ ppc_insn_ds_field (insn[1]));
- /* The first word of the descriptor is the entry point. Return that. */
- return ppc64_desc_entry_point (gdbarch, desc);
+ return ppc64_plt_entry_point (gdbarch, plt);
+}
+
+static CORE_ADDR
+ppc64_standard_linkage4_target (struct frame_info *frame,
+ CORE_ADDR pc, unsigned int *insn)
+{
+ struct gdbarch *gdbarch = get_frame_arch (frame);
+ struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
+
+ CORE_ADDR plt
+ = ((CORE_ADDR) get_frame_register_unsigned (frame, tdep->ppc_gp0_regnum + 2)
+ + (ppc_insn_d_field (insn[1]) << 16)
+ + ppc_insn_ds_field (insn[2]));
+
+ return ppc64_plt_entry_point (gdbarch, plt);
}
@@ -300,13 +431,27 @@ CORE_ADDR
ppc64_skip_trampoline_code (struct frame_info *frame, CORE_ADDR pc)
{
#define MAX(a,b) ((a) > (b) ? (a) : (b))
- unsigned int insns[MAX (MAX (ARRAY_SIZE (ppc64_standard_linkage1),
- ARRAY_SIZE (ppc64_standard_linkage2)),
- ARRAY_SIZE (ppc64_standard_linkage3)) - 1];
+ unsigned int insns[MAX (MAX (MAX (ARRAY_SIZE (ppc64_standard_linkage1),
+ ARRAY_SIZE (ppc64_standard_linkage2)),
+ MAX (ARRAY_SIZE (ppc64_standard_linkage3),
+ ARRAY_SIZE (ppc64_standard_linkage4))),
+ MAX (MAX (ARRAY_SIZE (ppc64_standard_linkage5),
+ ARRAY_SIZE (ppc64_standard_linkage6)),
+ ARRAY_SIZE (ppc64_standard_linkage7))) - 1];
CORE_ADDR target;
- if (ppc_insns_match_pattern (frame, pc, ppc64_standard_linkage3, insns)
- && (insns[8] != 0 || insns[9] != 0))
+ if (ppc_insns_match_pattern (frame, pc, ppc64_standard_linkage7, insns))
+ pc = ppc64_standard_linkage3_target (frame, pc, insns);
+ else if (ppc_insns_match_pattern (frame, pc, ppc64_standard_linkage6, insns))
+ pc = ppc64_standard_linkage4_target (frame, pc, insns);
+ else if (ppc_insns_match_pattern (frame, pc, ppc64_standard_linkage5, insns)
+ && (insns[8] != 0 || insns[9] != 0))
+ pc = ppc64_standard_linkage3_target (frame, pc, insns);
+ else if (ppc_insns_match_pattern (frame, pc, ppc64_standard_linkage4, insns)
+ && (insns[9] != 0 || insns[10] != 0))
+ pc = ppc64_standard_linkage4_target (frame, pc, insns);
+ else if (ppc_insns_match_pattern (frame, pc, ppc64_standard_linkage3, insns)
+ && (insns[8] != 0 || insns[9] != 0))
pc = ppc64_standard_linkage3_target (frame, pc, insns);
else if (ppc_insns_match_pattern (frame, pc, ppc64_standard_linkage2, insns)
&& (insns[10] != 0 || insns[11] != 0))
--- a/gdb/rs6000-tdep.c
+++ b/gdb/rs6000-tdep.c
@@ -1616,7 +1616,19 @@ skip_prologue (struct gdbarch *gdbarch,
continue;
}
- else if ((op & 0xffff0000) == 0x60000000)
+ else if ((op & 0xffff0000) == 0x3c4c0000
+ || (op & 0xffff0000) == 0x3c400000
+ || (op & 0xffff0000) == 0x38420000)
+ {
+ /* . 0: addis 2,12,.TOC.-0b@ha
+ . addi 2,2,.TOC.-0b@l
+ or
+ . lis 2,.TOC.@ha
+ . addi 2,2,.TOC.@l
+ used by ELFv2 global entry points to set up r2. */
+ continue;
+ }
+ else if (op == 0x60000000)
{
/* nop */
/* Allow nops in the prologue, but do not consider them to
@@ -1627,8 +1639,7 @@ skip_prologue (struct gdbarch *gdbarch,
}
else if ((op & 0xffff0000) == 0x3c000000)
- { /* addis 0,0,NUM, used
- for >= 32k frames */
+ { /* addis 0,0,NUM, used for >= 32k frames */
fdata->offset = (op & 0x0000ffff) << 16;
fdata->frameless = 0;
r0_contains_arg = 0;
@@ -1636,8 +1647,7 @@ skip_prologue (struct gdbarch *gdbarch,
}
else if ((op & 0xffff0000) == 0x60000000)
- { /* ori 0,0,NUM, 2nd ha
- lf of >= 32k frames */
+ { /* ori 0,0,NUM, 2nd half of >= 32k frames */
fdata->offset |= (op & 0x0000ffff);
fdata->frameless = 0;
r0_contains_arg = 0;
#
# gdb-7.6-update-autoconf-2013-06-10.patch
#
From: Alan Modra <amodra@gmail.com>
Date: Sat Nov 23 08:55:31 2013 +1030
Git-commit: f3f51a69187bd04f61373f54afd359e595d18011
References: ppc64le enablement
Import config.sub and config.guess from upstream.
Acked-by: Petr Tesarik <ptesarik@suse.cz>
---
ChangeLog | 4 +
config.guess | 144 ++++++++++++++++++++++++++++++++---------------------------
config.sub | 17 ++++--
3 files changed, 94 insertions(+), 71 deletions(-)
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,7 @@
+2013-11-23 Alan Modra <amodra@gmail.com>
+
+ * config.sub, config.guess: Import from upstream.
+
2013-04-29 Jan-Benedict Glaw <jbglaw@lug-owl.de>
* config.guess: Update from config repo.
--- a/config.guess
+++ b/config.guess
@@ -2,7 +2,7 @@
# Attempt to guess a canonical system name.
# Copyright 1992-2013 Free Software Foundation, Inc.
-timestamp='2013-04-24'
+timestamp='2013-06-10'
# This file is free software; you can redistribute it and/or modify it
# under the terms of the GNU General Public License as published by
@@ -132,6 +132,27 @@ UNAME_RELEASE=`(uname -r) 2>/dev/null` |
UNAME_SYSTEM=`(uname -s) 2>/dev/null` || UNAME_SYSTEM=unknown
UNAME_VERSION=`(uname -v) 2>/dev/null` || UNAME_VERSION=unknown
+case "${UNAME_SYSTEM}" in
+Linux|GNU|GNU/*)
+ # If the system lacks a compiler, then just pick glibc.
+ # We could probably try harder.
+ LIBC=gnu
+
+ eval $set_cc_for_build
+ cat <<-EOF > $dummy.c
+ #include <features.h>
+ #if defined(__UCLIBC__)
+ LIBC=uclibc
+ #elif defined(__dietlibc__)
+ LIBC=dietlibc
+ #else
+ LIBC=gnu
+ #endif
+ EOF
+ eval `$CC_FOR_BUILD -E $dummy.c 2>/dev/null | grep '^LIBC'`
+ ;;
+esac
+
# Note: order is significant - the case branches are not exclusive.
case "${UNAME_MACHINE}:${UNAME_SYSTEM}:${UNAME_RELEASE}:${UNAME_VERSION}" in
@@ -853,21 +874,21 @@ EOF
exit ;;
*:GNU:*:*)
# the GNU system
- echo `echo ${UNAME_MACHINE}|sed -e 's,[-/].*$,,'`-unknown-gnu`echo ${UNAME_RELEASE}|sed -e 's,/.*$,,'`
+ echo `echo ${UNAME_MACHINE}|sed -e 's,[-/].*$,,'`-unknown-${LIBC}`echo ${UNAME_RELEASE}|sed -e 's,/.*$,,'`
exit ;;
*:GNU/*:*:*)
# other systems with GNU libc and userland
- echo ${UNAME_MACHINE}-unknown-`echo ${UNAME_SYSTEM} | sed 's,^[^/]*/,,' | tr '[A-Z]' '[a-z]'``echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'`-gnu
+ echo ${UNAME_MACHINE}-unknown-`echo ${UNAME_SYSTEM} | sed 's,^[^/]*/,,' | tr '[A-Z]' '[a-z]'``echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'`-${LIBC}
exit ;;
i*86:Minix:*:*)
echo ${UNAME_MACHINE}-pc-minix
exit ;;
aarch64:Linux:*:*)
- echo ${UNAME_MACHINE}-unknown-linux-gnu
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
exit ;;
aarch64_be:Linux:*:*)
UNAME_MACHINE=aarch64_be
- echo ${UNAME_MACHINE}-unknown-linux-gnu
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
exit ;;
alpha:Linux:*:*)
case `sed -n '/^cpu model/s/^.*: \(.*\)/\1/p' < /proc/cpuinfo` in
@@ -880,67 +901,54 @@ EOF
EV68*) UNAME_MACHINE=alphaev68 ;;
esac
objdump --private-headers /bin/sh | grep -q ld.so.1
- if test "$?" = 0 ; then LIBC="libc1" ; else LIBC="" ; fi
- echo ${UNAME_MACHINE}-unknown-linux-gnu${LIBC}
+ if test "$?" = 0 ; then LIBC="gnulibc1" ; fi
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
exit ;;
arc:Linux:*:* | arceb:Linux:*:*)
- echo ${UNAME_MACHINE}-unknown-linux-gnu
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
exit ;;
arm*:Linux:*:*)
eval $set_cc_for_build
if echo __ARM_EABI__ | $CC_FOR_BUILD -E - 2>/dev/null \
| grep -q __ARM_EABI__
then
- echo ${UNAME_MACHINE}-unknown-linux-gnu
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
else
if echo __ARM_PCS_VFP | $CC_FOR_BUILD -E - 2>/dev/null \
| grep -q __ARM_PCS_VFP
then
- echo ${UNAME_MACHINE}-unknown-linux-gnueabi
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}eabi
else
- echo ${UNAME_MACHINE}-unknown-linux-gnueabihf
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}eabihf
fi
fi
exit ;;
avr32*:Linux:*:*)
- echo ${UNAME_MACHINE}-unknown-linux-gnu
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
exit ;;
cris:Linux:*:*)
- echo ${UNAME_MACHINE}-axis-linux-gnu
+ echo ${UNAME_MACHINE}-axis-linux-${LIBC}
exit ;;
crisv32:Linux:*:*)
- echo ${UNAME_MACHINE}-axis-linux-gnu
+ echo ${UNAME_MACHINE}-axis-linux-${LIBC}
exit ;;
frv:Linux:*:*)
- echo ${UNAME_MACHINE}-unknown-linux-gnu
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
exit ;;
hexagon:Linux:*:*)
- echo ${UNAME_MACHINE}-unknown-linux-gnu
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
exit ;;
i*86:Linux:*:*)
- LIBC=gnu
- eval $set_cc_for_build
- sed 's/^ //' << EOF >$dummy.c
- #ifdef __dietlibc__
- LIBC=dietlibc
- #endif
- #else
- #include <features.h>
- #ifdef __UCLIBC__
- LIBC=uclibc
- #endif
-EOF
- eval `$CC_FOR_BUILD -E $dummy.c 2>/dev/null | grep '^LIBC'`
- echo "${UNAME_MACHINE}-pc-linux-${LIBC}"
+ echo ${UNAME_MACHINE}-pc-linux-${LIBC}
exit ;;
ia64:Linux:*:*)
- echo ${UNAME_MACHINE}-unknown-linux-gnu
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
exit ;;
m32r*:Linux:*:*)
- echo ${UNAME_MACHINE}-unknown-linux-gnu
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
exit ;;
m68*:Linux:*:*)
- echo ${UNAME_MACHINE}-unknown-linux-gnu
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
exit ;;
mips:Linux:*:* | mips64:Linux:*:*)
eval $set_cc_for_build
@@ -959,59 +967,63 @@ EOF
#endif
EOF
eval `$CC_FOR_BUILD -E $dummy.c 2>/dev/null | grep '^CPU'`
- test x"${CPU}" != x && { echo "${CPU}-unknown-linux-gnu"; exit; }
+ test x"${CPU}" != x && { echo "${CPU}-unknown-linux-${LIBC}"; exit; }
;;
or1k:Linux:*:*)
- echo ${UNAME_MACHINE}-unknown-linux-gnu
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
exit ;;
or32:Linux:*:*)
- echo ${UNAME_MACHINE}-unknown-linux-gnu
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
exit ;;
padre:Linux:*:*)
- echo sparc-unknown-linux-gnu
+ echo sparc-unknown-linux-${LIBC}
exit ;;
parisc64:Linux:*:* | hppa64:Linux:*:*)
- echo hppa64-unknown-linux-gnu
+ echo hppa64-unknown-linux-${LIBC}
exit ;;
parisc:Linux:*:* | hppa:Linux:*:*)
# Look for CPU level
case `grep '^cpu[^a-z]*:' /proc/cpuinfo 2>/dev/null | cut -d' ' -f2` in
- PA7*) echo hppa1.1-unknown-linux-gnu ;;
- PA8*) echo hppa2.0-unknown-linux-gnu ;;
- *) echo hppa-unknown-linux-gnu ;;
+ PA7*) echo hppa1.1-unknown-linux-${LIBC} ;;
+ PA8*) echo hppa2.0-unknown-linux-${LIBC} ;;
+ *) echo hppa-unknown-linux-${LIBC} ;;
esac
exit ;;
ppc64:Linux:*:*)
- echo powerpc64-unknown-linux-gnu
+ echo powerpc64-unknown-linux-${LIBC}
exit ;;
ppc:Linux:*:*)
- echo powerpc-unknown-linux-gnu
+ echo powerpc-unknown-linux-${LIBC}
+ exit ;;
+ ppc64le:Linux:*:*)
+ echo powerpc64le-unknown-linux-${LIBC}
+ exit ;;
+ ppcle:Linux:*:*)
+ echo powerpcle-unknown-linux-${LIBC}
exit ;;
s390:Linux:*:* | s390x:Linux:*:*)
- echo ${UNAME_MACHINE}-ibm-linux
+ echo ${UNAME_MACHINE}-ibm-linux-${LIBC}
exit ;;
sh64*:Linux:*:*)
- echo ${UNAME_MACHINE}-unknown-linux-gnu
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
exit ;;
sh*:Linux:*:*)
- echo ${UNAME_MACHINE}-unknown-linux-gnu
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
exit ;;
sparc:Linux:*:* | sparc64:Linux:*:*)
- echo ${UNAME_MACHINE}-unknown-linux-gnu
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
exit ;;
tile*:Linux:*:*)
- echo ${UNAME_MACHINE}-unknown-linux-gnu
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
exit ;;
vax:Linux:*:*)
- echo ${UNAME_MACHINE}-dec-linux-gnu
+ echo ${UNAME_MACHINE}-dec-linux-${LIBC}
exit ;;
x86_64:Linux:*:*)
- LIBC=gnu
- test -r /lib/libc.so && od -An -S13 /lib/libc.so | grep -q __uClibc_main && LIBC=uclibc
echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
exit ;;
xtensa*:Linux:*:*)
- echo ${UNAME_MACHINE}-unknown-linux-gnu
+ echo ${UNAME_MACHINE}-unknown-linux-${LIBC}
exit ;;
i*86:DYNIX/ptx:4*:*)
# ptx 4.0 does uname -s correctly, with DYNIX/ptx in there.
@@ -1244,19 +1256,21 @@ EOF
exit ;;
*:Darwin:*:*)
UNAME_PROCESSOR=`uname -p` || UNAME_PROCESSOR=unknown
- case $UNAME_PROCESSOR in
- i386)
- eval $set_cc_for_build
- if [ "$CC_FOR_BUILD" != 'no_compiler_found' ]; then
- if (echo '#ifdef __LP64__'; echo IS_64BIT_ARCH; echo '#endif') | \
- (CCOPTS= $CC_FOR_BUILD -E - 2>/dev/null) | \
- grep IS_64BIT_ARCH >/dev/null
- then
- UNAME_PROCESSOR="x86_64"
- fi
- fi ;;
- unknown) UNAME_PROCESSOR=powerpc ;;
- esac
+ eval $set_cc_for_build
+ if test "$UNAME_PROCESSOR" = unknown ; then
+ UNAME_PROCESSOR=powerpc
+ fi
+ if [ "$CC_FOR_BUILD" != 'no_compiler_found' ]; then
+ if (echo '#ifdef __LP64__'; echo IS_64BIT_ARCH; echo '#endif') | \
+ (CCOPTS= $CC_FOR_BUILD -E - 2>/dev/null) | \
+ grep IS_64BIT_ARCH >/dev/null
+ then
+ case $UNAME_PROCESSOR in
+ i386) UNAME_PROCESSOR=x86_64 ;;
+ powerpc) UNAME_PROCESSOR=powerpc64 ;;
+ esac
+ fi
+ fi
echo ${UNAME_PROCESSOR}-apple-darwin${UNAME_RELEASE}
exit ;;
*:procnto*:*:* | *:QNX:[0123456789]*:*)
--- a/config.sub
+++ b/config.sub
@@ -2,7 +2,7 @@
# Configuration validation subroutine script.
# Copyright 1992-2013 Free Software Foundation, Inc.
-timestamp='2013-04-24'
+timestamp='2013-10-01'
# This file is free software; you can redistribute it and/or modify it
# under the terms of the GNU General Public License as published by
@@ -257,7 +257,7 @@ case $basic_machine in
| avr | avr32 \
| be32 | be64 \
| bfin \
- | c4x | clipper \
+ | c4x | c8051 | clipper \
| d10v | d30v | dlx | dsp16xx \
| epiphany \
| fido | fr30 | frv \
@@ -265,6 +265,7 @@ case $basic_machine in
| hexagon \
| i370 | i860 | i960 | ia64 \
| ip2k | iq2000 \
+ | k1om \
| le32 | le64 \
| lm32 \
| m32c | m32r | m32rle | m68000 | m68k | m88k \
@@ -324,7 +325,7 @@ case $basic_machine in
c6x)
basic_machine=tic6x-unknown
;;
- m6811 | m68hc11 | m6812 | m68hc12 | m68hcs12x | picochip)
+ m6811 | m68hc11 | m6812 | m68hc12 | m68hcs12x | nvptx | picochip)
basic_machine=$basic_machine-unknown
os=-none
;;
@@ -372,7 +373,7 @@ case $basic_machine in
| be32-* | be64-* \
| bfin-* | bs2000-* \
| c[123]* | c30-* | [cjt]90-* | c4x-* \
- | clipper-* | craynv-* | cydra-* \
+ | c8051-* | clipper-* | craynv-* | cydra-* \
| d10v-* | d30v-* | dlx-* \
| elxsi-* \
| f30[01]-* | f700-* | fido-* | fr30-* | frv-* | fx80-* \
@@ -381,6 +382,7 @@ case $basic_machine in
| hexagon-* \
| i*86-* | i860-* | i960-* | ia64-* \
| ip2k-* | iq2000-* \
+ | k1om-* \
| le32-* | le64-* \
| lm32-* \
| m32c-* | m32r-* | m32rle-* \
@@ -794,7 +796,7 @@ case $basic_machine in
os=-mingw64
;;
mingw32)
- basic_machine=i386-pc
+ basic_machine=i686-pc
os=-mingw32
;;
mingw32ce)
@@ -830,7 +832,7 @@ case $basic_machine in
basic_machine=`echo $basic_machine | sed -e 's/ms1-/mt-/'`
;;
msys)
- basic_machine=i386-pc
+ basic_machine=i686-pc
os=-msys
;;
mvs)
@@ -1546,6 +1548,9 @@ case $basic_machine in
c4x-* | tic4x-*)
os=-coff
;;
+ c8051-*)
+ os=-elf
+ ;;
hexagon-*)
os=-elf
;;
#
# gdb-7.6-ppc64le.patch
#
From: Ulrich Weigand <uweigand@de.ibm.com>
References: ppc64le enablement
Patch-mainline: not yet
Signed-off-by: Ulrich Weigand <uweigand@de.ibm.com>
Signed-off-by: Petr Tesarik <ptesarik@suse.cz>
---
gdb/auxv.c | 1
gdb/configure.host | 4
gdb/configure.tgt | 2
gdb/doublest.c | 49 +-
gdb/gdbarch.c | 33 +
gdb/gdbarch.h | 6
gdb/gdbarch.sh | 1
gdb/gdbtypes.c | 4
gdb/infrun.c | 4
gdb/ppc-linux-tdep.c | 60 ++-
gdb/ppc-sysv-tdep.c | 534 ++++++++++++++++++++++++---
gdb/ppc-tdep.h | 11
gdb/ppc64-tdep.c | 2
gdb/rs6000-tdep.c | 43 +-
gdb/symtab.c | 2
gdb/testsuite/gdb.arch/altivec-regs.exp | 2
gdb/testsuite/gdb.arch/powerpc-d128-regs.exp | 2
gdb/testsuite/gdb.arch/vsx-regs.exp | 39 +
gdb/testsuite/gdb.base/sigbpt.exp | 2
gdb/testsuite/gdb.base/step-bt.exp | 2
include/elf/common.h | 1
include/elf/ppc64.h | 54 ++
22 files changed, 752 insertions(+), 106 deletions(-)
--- a/gdb/ppc64-tdep.c
+++ b/gdb/ppc64-tdep.c
@@ -289,7 +289,7 @@ static struct ppc_insn_pattern ppc64_sta
static struct ppc_insn_pattern ppc64_standard_linkage7[] =
{
/* std r2, 24(r1) <optional> */
- { -1, insn_ds (62, 2, 1, 40, 0), 1 },
+ { -1, insn_ds (62, 2, 1, 24, 0), 1 },
/* ld r12, <any>(r2) */
{ insn_ds (-1, -1, -1, 0, -1), insn_ds (58, 12, 2, 0, 0), 0 },
--- a/gdb/rs6000-tdep.c
+++ b/gdb/rs6000-tdep.c
@@ -48,6 +48,7 @@
#include "elf-bfd.h"
#include "elf/ppc.h"
+#include "elf/ppc64.h"
#include "solib-svr4.h"
#include "ppc-tdep.h"
@@ -2672,10 +2673,10 @@ dfp_pseudo_register_read (struct gdbarch
else
{
status = regcache_raw_read (regcache, tdep->ppc_fp0_regnum +
- 2 * reg_index + 1, buffer + 8);
+ 2 * reg_index + 1, buffer);
if (status == REG_VALID)
status = regcache_raw_read (regcache, tdep->ppc_fp0_regnum +
- 2 * reg_index, buffer);
+ 2 * reg_index, buffer + 8);
}
return status;
@@ -2701,9 +2702,9 @@ dfp_pseudo_register_write (struct gdbarc
else
{
regcache_raw_write (regcache, tdep->ppc_fp0_regnum +
- 2 * reg_index + 1, buffer + 8);
+ 2 * reg_index + 1, buffer);
regcache_raw_write (regcache, tdep->ppc_fp0_regnum +
- 2 * reg_index, buffer);
+ 2 * reg_index, buffer + 8);
}
}
@@ -2781,7 +2782,8 @@ efpr_pseudo_register_read (struct gdbarc
int reg_index = reg_nr - tdep->ppc_efpr0_regnum;
/* Read the portion that overlaps the VMX register. */
- return regcache_raw_read_part (regcache, tdep->ppc_vr0_regnum + reg_index, 0,
+ int offset = gdbarch_byte_order (gdbarch) == BFD_ENDIAN_BIG ? 0 : 8;
+ return regcache_raw_read_part (regcache, tdep->ppc_vr0_regnum + reg_index, offset,
register_size (gdbarch, reg_nr), buffer);
}
@@ -2794,7 +2796,8 @@ efpr_pseudo_register_write (struct gdbar
int reg_index = reg_nr - tdep->ppc_efpr0_regnum;
/* Write the portion that overlaps the VMX register. */
- regcache_raw_write_part (regcache, tdep->ppc_vr0_regnum + reg_index, 0,
+ int offset = gdbarch_byte_order (gdbarch) == BFD_ENDIAN_BIG ? 0 : 8;
+ regcache_raw_write_part (regcache, tdep->ppc_vr0_regnum + reg_index, offset,
register_size (gdbarch, reg_nr), buffer);
}
@@ -3550,6 +3553,7 @@ rs6000_gdbarch_init (struct gdbarch_info
enum auto_boolean soft_float_flag = powerpc_soft_float_global;
int soft_float;
enum powerpc_vector_abi vector_abi = powerpc_vector_abi_global;
+ enum powerpc_elf_abi elf_abi = POWERPC_ELF_AUTO;
int have_fpu = 1, have_spe = 0, have_mq = 0, have_altivec = 0, have_dfp = 0,
have_vsx = 0;
int tdesc_wordsize = -1;
@@ -3856,6 +3860,21 @@ rs6000_gdbarch_init (struct gdbarch_info
}
#ifdef HAVE_ELF
+ if (from_elf_exec)
+ {
+ switch (elf_elfheader (info.abfd)->e_flags & EF_PPC64_ABI)
+ {
+ case 1:
+ elf_abi = POWERPC_ELF_V1;
+ break;
+ case 2:
+ elf_abi = POWERPC_ELF_V2;
+ break;
+ default:
+ break;
+ }
+ }
+
if (soft_float_flag == AUTO_BOOLEAN_AUTO && from_elf_exec)
{
switch (bfd_elf_get_obj_attr_int (info.abfd, OBJ_ATTR_GNU,
@@ -3892,6 +3911,15 @@ rs6000_gdbarch_init (struct gdbarch_info
}
#endif
+ /* Default to ELFv2 ABI on 64-bit little-endian, and ELFv1 otherwise. */
+ if (elf_abi == POWERPC_ELF_AUTO)
+ {
+ if (wordsize == 8 && info.byte_order == BFD_ENDIAN_LITTLE)
+ elf_abi = POWERPC_ELF_V2;
+ else
+ elf_abi = POWERPC_ELF_V1;
+ }
+
if (soft_float_flag == AUTO_BOOLEAN_TRUE)
soft_float = 1;
else if (soft_float_flag == AUTO_BOOLEAN_FALSE)
@@ -3934,6 +3962,8 @@ rs6000_gdbarch_init (struct gdbarch_info
meaningful, because 64-bit CPUs can run in 32-bit mode. So, perform
separate word size check. */
tdep = gdbarch_tdep (arches->gdbarch);
+ if (tdep && tdep->elf_abi != elf_abi)
+ continue;
if (tdep && tdep->soft_float != soft_float)
continue;
if (tdep && tdep->vector_abi != vector_abi)
@@ -3956,6 +3986,7 @@ rs6000_gdbarch_init (struct gdbarch_info
tdep = XCALLOC (1, struct gdbarch_tdep);
tdep->wordsize = wordsize;
+ tdep->elf_abi = elf_abi;
tdep->soft_float = soft_float;
tdep->vector_abi = vector_abi;
--- a/gdb/auxv.c
+++ b/gdb/auxv.c
@@ -441,6 +441,7 @@ fprint_target_auxv (struct ui_file *file
TAG (AT_IGNOREPPC, _("Entry should be ignored"), dec);
TAG (AT_BASE_PLATFORM, _("String identifying base platform"), str);
TAG (AT_RANDOM, _("Address of 16 random bytes"), hex);
+ TAG (AT_HWCAP2, _("Extension of AT_HWCAP"), hex);
TAG (AT_EXECFN, _("File name of executable"), str);
TAG (AT_SECURE, _("Boolean, was exec setuid-like?"), dec);
TAG (AT_SYSINFO, _("Special system info/entry points"), hex);
--- a/gdb/configure.host
+++ b/gdb/configure.host
@@ -129,18 +129,18 @@ mips64*-*-openbsd*) gdb_host=obsd64 ;;
powerpc-*-aix* | rs6000-*-*)
gdb_host=aix ;;
powerpc*-*-freebsd*) gdb_host=fbsd ;;
-powerpc-*-linux*) gdb_host=linux ;;
powerpc-*-netbsd* | powerpc-*-knetbsd*-gnu)
gdb_host=nbsd ;;
powerpc-*-openbsd*) gdb_host=obsd ;;
-powerpc64-*-linux*) gdb_host=ppc64-linux
+powerpc64*-*-linux*) gdb_host=ppc64-linux
# Support 'pseudo-native' debugging on the Cell BE
if test "${target_cpu}" = "spu"; then
gdb_host=spu-linux
gdb_native=yes
fi
;;
+powerpc*-*-linux*) gdb_host=linux ;;
s390*-*-*) gdb_host=s390 ;;
--- a/gdb/configure.tgt
+++ b/gdb/configure.tgt
@@ -421,7 +421,7 @@ powerpc-*-aix* | rs6000-*-*)
ppc-sysv-tdep.o solib-svr4.o \
ravenscar-thread.o ppc-ravenscar-thread.o"
;;
-powerpc-*-linux* | powerpc64-*-linux*)
+powerpc*-*-linux*)
# Target: PowerPC running Linux
gdb_target_obs="rs6000-tdep.o ppc-linux-tdep.o ppc-sysv-tdep.o \
ppc64-tdep.o solib-svr4.o solib-spu.o \
--- a/gdb/doublest.c
+++ b/gdb/doublest.c
@@ -190,7 +190,8 @@ convert_floatformat_to_doublest (const s
{
double dto;
- floatformat_to_double (fmt, from, &dto);
+ floatformat_to_double (fmt->split_half ? fmt->split_half : fmt,
+ from, &dto);
*to = (DOUBLEST) dto;
return;
}
@@ -561,6 +562,11 @@ floatformat_is_negative (const struct fl
gdb_assert (fmt->totalsize
<= FLOATFORMAT_LARGEST_BYTES * FLOATFORMAT_CHAR_BIT);
+ /* An IBM long double (a two element array of double) always takes the
+ sign of the first double. */
+ if (fmt->split_half)
+ fmt = fmt->split_half;
+
order = floatformat_normalize_byteorder (fmt, uval, newfrom);
if (order != fmt->byteorder)
@@ -587,6 +593,13 @@ floatformat_classify (const struct float
gdb_assert (fmt->totalsize
<= FLOATFORMAT_LARGEST_BYTES * FLOATFORMAT_CHAR_BIT);
+ /* An IBM long double (a two element array of double) can be classified
+ by looking at the first double. inf and nan are specified as
+ ignoring the second double. zero and subnormal will always have
+ the second double 0.0 if the long double is correctly rounded. */
+ if (fmt->split_half)
+ fmt = fmt->split_half;
+
order = floatformat_normalize_byteorder (fmt, uval, newfrom);
if (order != fmt->byteorder)
@@ -669,6 +682,16 @@ floatformat_mantissa (const struct float
gdb_assert (fmt->totalsize
<= FLOATFORMAT_LARGEST_BYTES * FLOATFORMAT_CHAR_BIT);
+ /* For IBM long double (a two element array of double), return the
+ mantissa of the first double. The problem with returning the
+ actual mantissa from both doubles is that there can be an
+ arbitrary number of implied 0's or 1's between the mantissas
+ of the first and second double. In any case, this function
+ is only used for dumping out nans, and a nan is specified to
+ ignore the value in the second double. */
+ if (fmt->split_half)
+ fmt = fmt->split_half;
+
order = floatformat_normalize_byteorder (fmt, uval, newfrom);
if (order != fmt->byteorder)
@@ -926,27 +949,3 @@ convert_typed_floating (const void *from
floatformat_from_doublest (to_fmt, &d, to);
}
}
-
-const struct floatformat *floatformat_ieee_single[BFD_ENDIAN_UNKNOWN];
-const struct floatformat *floatformat_ieee_double[BFD_ENDIAN_UNKNOWN];
-const struct floatformat *floatformat_ieee_quad[BFD_ENDIAN_UNKNOWN];
-const struct floatformat *floatformat_arm_ext[BFD_ENDIAN_UNKNOWN];
-const struct floatformat *floatformat_ia64_spill[BFD_ENDIAN_UNKNOWN];
-
-extern void _initialize_doublest (void);
-
-extern void
-_initialize_doublest (void)
-{
- floatformat_ieee_single[BFD_ENDIAN_LITTLE] = &floatformat_ieee_single_little;
- floatformat_ieee_single[BFD_ENDIAN_BIG] = &floatformat_ieee_single_big;
- floatformat_ieee_double[BFD_ENDIAN_LITTLE] = &floatformat_ieee_double_little;
- floatformat_ieee_double[BFD_ENDIAN_BIG] = &floatformat_ieee_double_big;
- floatformat_arm_ext[BFD_ENDIAN_LITTLE]
- = &floatformat_arm_ext_littlebyte_bigword;
- floatformat_arm_ext[BFD_ENDIAN_BIG] = &floatformat_arm_ext_big;
- floatformat_ia64_spill[BFD_ENDIAN_LITTLE] = &floatformat_ia64_spill_little;
- floatformat_ia64_spill[BFD_ENDIAN_BIG] = &floatformat_ia64_spill_big;
- floatformat_ieee_quad[BFD_ENDIAN_LITTLE] = &floatformat_ia64_quad_little;
- floatformat_ieee_quad[BFD_ENDIAN_BIG] = &floatformat_ia64_quad_big;
-}
--- a/gdb/gdbarch.c
+++ b/gdb/gdbarch.c
@@ -200,6 +200,7 @@ struct gdbarch
gdbarch_return_in_first_hidden_param_p_ftype *return_in_first_hidden_param_p;
gdbarch_skip_prologue_ftype *skip_prologue;
gdbarch_skip_main_prologue_ftype *skip_main_prologue;
+ gdbarch_skip_entrypoint_ftype *skip_entrypoint;
gdbarch_inner_than_ftype *inner_than;
gdbarch_breakpoint_from_pc_ftype *breakpoint_from_pc;
gdbarch_remote_breakpoint_from_pc_ftype *remote_breakpoint_from_pc;
@@ -371,6 +372,7 @@ struct gdbarch startup_gdbarch =
default_return_in_first_hidden_param_p, /* return_in_first_hidden_param_p */
0, /* skip_prologue */
0, /* skip_main_prologue */
+ 0, /* skip_entrypoint */
0, /* inner_than */
0, /* breakpoint_from_pc */
default_remote_breakpoint_from_pc, /* remote_breakpoint_from_pc */
@@ -672,6 +674,7 @@ verify_gdbarch (struct gdbarch *gdbarch)
if (gdbarch->skip_prologue == 0)
fprintf_unfiltered (log, "\n\tskip_prologue");
/* Skip verify of skip_main_prologue, has predicate. */
+ /* Skip verify of skip_entrypoint, has predicate. */
if (gdbarch->inner_than == 0)
fprintf_unfiltered (log, "\n\tinner_than");
if (gdbarch->breakpoint_from_pc == 0)
@@ -1285,6 +1288,12 @@ gdbarch_dump (struct gdbarch *gdbarch, s
"gdbarch_dump: single_step_through_delay = <%s>\n",
host_address_to_string (gdbarch->single_step_through_delay));
fprintf_unfiltered (file,
+ "gdbarch_dump: gdbarch_skip_entrypoint_p() = %d\n",
+ gdbarch_skip_entrypoint_p (gdbarch));
+ fprintf_unfiltered (file,
+ "gdbarch_dump: skip_entrypoint = <%s>\n",
+ host_address_to_string (gdbarch->skip_entrypoint));
+ fprintf_unfiltered (file,
"gdbarch_dump: gdbarch_skip_main_prologue_p() = %d\n",
gdbarch_skip_main_prologue_p (gdbarch));
fprintf_unfiltered (file,
@@ -2635,6 +2644,30 @@ set_gdbarch_skip_main_prologue (struct g
}
int
+gdbarch_skip_entrypoint_p (struct gdbarch *gdbarch)
+{
+ gdb_assert (gdbarch != NULL);
+ return gdbarch->skip_entrypoint != NULL;
+}
+
+CORE_ADDR
+gdbarch_skip_entrypoint (struct gdbarch *gdbarch, CORE_ADDR ip)
+{
+ gdb_assert (gdbarch != NULL);
+ gdb_assert (gdbarch->skip_entrypoint != NULL);
+ if (gdbarch_debug >= 2)
+ fprintf_unfiltered (gdb_stdlog, "gdbarch_skip_entrypoint called\n");
+ return gdbarch->skip_entrypoint (gdbarch, ip);
+}
+
+void
+set_gdbarch_skip_entrypoint (struct gdbarch *gdbarch,
+ gdbarch_skip_entrypoint_ftype skip_entrypoint)
+{
+ gdbarch->skip_entrypoint = skip_entrypoint;
+}
+
+int
gdbarch_inner_than (struct gdbarch *gdbarch, CORE_ADDR lhs, CORE_ADDR rhs)
{
gdb_assert (gdbarch != NULL);
--- a/gdb/gdbarch.h
+++ b/gdb/gdbarch.h
@@ -487,6 +487,12 @@ typedef CORE_ADDR (gdbarch_skip_main_pro
extern CORE_ADDR gdbarch_skip_main_prologue (struct gdbarch *gdbarch, CORE_ADDR ip);
extern void set_gdbarch_skip_main_prologue (struct gdbarch *gdbarch, gdbarch_skip_main_prologue_ftype *skip_main_prologue);
+extern int gdbarch_skip_entrypoint_p (struct gdbarch *gdbarch);
+
+typedef CORE_ADDR (gdbarch_skip_entrypoint_ftype) (struct gdbarch *gdbarch, CORE_ADDR ip);
+extern CORE_ADDR gdbarch_skip_entrypoint (struct gdbarch *gdbarch, CORE_ADDR ip);
+extern void set_gdbarch_skip_entrypoint (struct gdbarch *gdbarch, gdbarch_skip_entrypoint_ftype *skip_entrypoint);
+
typedef int (gdbarch_inner_than_ftype) (CORE_ADDR lhs, CORE_ADDR rhs);
extern int gdbarch_inner_than (struct gdbarch *gdbarch, CORE_ADDR lhs, CORE_ADDR rhs);
extern void set_gdbarch_inner_than (struct gdbarch *gdbarch, gdbarch_inner_than_ftype *inner_than);
--- a/gdb/gdbarch.sh
+++ b/gdb/gdbarch.sh
@@ -527,6 +527,7 @@ m:int:return_in_first_hidden_param_p:str
m:CORE_ADDR:skip_prologue:CORE_ADDR ip:ip:0:0
M:CORE_ADDR:skip_main_prologue:CORE_ADDR ip:ip
+M:CORE_ADDR:skip_entrypoint:CORE_ADDR ip:ip
f:int:inner_than:CORE_ADDR lhs, CORE_ADDR rhs:lhs, rhs:0:0
m:const gdb_byte *:breakpoint_from_pc:CORE_ADDR *pcptr, int *lenptr:pcptr, lenptr::0:
# Return the adjusted address and kind to use for Z0/Z1 packets.
--- a/gdb/gdbtypes.c
+++ b/gdb/gdbtypes.c
@@ -107,8 +107,8 @@ const struct floatformat *floatformats_v
&floatformat_vax_d
};
const struct floatformat *floatformats_ibm_long_double[BFD_ENDIAN_UNKNOWN] = {
- &floatformat_ibm_long_double,
- &floatformat_ibm_long_double
+ &floatformat_ibm_long_double_big,
+ &floatformat_ibm_long_double_little
};
/* Should opaque types be resolved? */
--- a/gdb/infrun.c
+++ b/gdb/infrun.c
@@ -3139,6 +3139,10 @@ fill_in_stop_func (struct gdbarch *gdbar
ecs->stop_func_start
+= gdbarch_deprecated_function_start_offset (gdbarch);
+ if (gdbarch_skip_entrypoint_p (gdbarch))
+ ecs->stop_func_start = gdbarch_skip_entrypoint (gdbarch,
+ ecs->stop_func_start);
+
ecs->stop_func_filled_in = 1;
}
}
--- a/gdb/ppc-linux-tdep.c
+++ b/gdb/ppc-linux-tdep.c
@@ -44,6 +44,7 @@
#include "observer.h"
#include "auxv.h"
#include "elf/common.h"
+#include "elf/ppc64.h"
#include "exceptions.h"
#include "arch-utils.h"
#include "spu-tdep.h"
@@ -876,6 +877,43 @@ ppc_linux_core_read_description (struct
}
}
+/* If the ELF symbol has a local entry point, use it as SYMBOL_VALUE_ADDRESS
+ for the msymbol. This matches the DWARF function start if present. */
+
+static void
+ppc_elfv2_elf_make_msymbol_special (asymbol *sym, struct minimal_symbol *msym)
+{
+ elf_symbol_type *elf_sym = (elf_symbol_type *)sym;
+ switch (PPC64_LOCAL_ENTRY_OFFSET (elf_sym->internal_elf_sym.st_other))
+ {
+ default:
+ break;
+ case 8:
+ MSYMBOL_TARGET_FLAG_1 (msym) = 1;
+ break;
+ }
+}
+
+static CORE_ADDR
+ppc_elfv2_skip_entrypoint (struct gdbarch *gdbarch, CORE_ADDR pc)
+{
+ struct bound_minimal_symbol fun;
+ int local_entry_offset = 0;
+
+ fun = lookup_minimal_symbol_by_pc (pc);
+ if (fun.minsym == NULL)
+ return pc;
+
+ if (MSYMBOL_TARGET_FLAG_1 (fun.minsym))
+ local_entry_offset = 8;
+
+ if (SYMBOL_VALUE_ADDRESS (fun.minsym) <= pc
+ && pc < SYMBOL_VALUE_ADDRESS (fun.minsym) + local_entry_offset)
+ return SYMBOL_VALUE_ADDRESS (fun.minsym) + local_entry_offset;
+
+ return pc;
+}
+
/* Implementation of `gdbarch_stap_is_single_operand', as defined in
gdbarch.h. */
@@ -1332,13 +1370,23 @@ ppc_linux_init_abi (struct gdbarch_info
if (tdep->wordsize == 8)
{
- /* Handle PPC GNU/Linux 64-bit function pointers (which are really
- function descriptors). */
- set_gdbarch_convert_from_func_ptr_addr
- (gdbarch, ppc64_convert_from_func_ptr_addr);
+ if (tdep->elf_abi == POWERPC_ELF_V1)
+ {
+ /* Handle PPC GNU/Linux 64-bit function pointers (which are really
+ function descriptors). */
+ set_gdbarch_convert_from_func_ptr_addr
+ (gdbarch, ppc64_convert_from_func_ptr_addr);
- set_gdbarch_elf_make_msymbol_special (gdbarch,
- ppc64_elf_make_msymbol_special);
+ set_gdbarch_elf_make_msymbol_special
+ (gdbarch, ppc64_elf_make_msymbol_special);
+ }
+ else
+ {
+ set_gdbarch_elf_make_msymbol_special
+ (gdbarch, ppc_elfv2_elf_make_msymbol_special);
+
+ set_gdbarch_skip_entrypoint (gdbarch, ppc_elfv2_skip_entrypoint);
+ }
/* Shared library handling. */
set_gdbarch_skip_trampoline_code (gdbarch, ppc64_skip_trampoline_code);
--- a/gdb/ppc-sysv-tdep.c
+++ b/gdb/ppc-sysv-tdep.c
@@ -610,42 +610,48 @@ ppc_sysv_abi_push_dummy_call (struct gdb
}
/* Handle the return-value conventions for Decimal Floating Point values
- in both ppc32 and ppc64, which are the same. */
-static int
+ in both ppc32 and ppc64, which are the same. INDEX specifies which
+ part of a multi-part return value is to be handled. */
+static void
get_decimal_float_return_value (struct gdbarch *gdbarch, struct type *valtype,
struct regcache *regcache, gdb_byte *readbuf,
- const gdb_byte *writebuf)
+ const gdb_byte *writebuf, int index)
{
struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
+ int offset = index * TYPE_LENGTH (valtype);
gdb_assert (TYPE_CODE (valtype) == TYPE_CODE_DECFLOAT);
/* 32-bit and 64-bit decimal floats in f1. */
if (TYPE_LENGTH (valtype) <= 8)
{
+ int regnum = tdep->ppc_fp0_regnum + 1 + index;
+
if (writebuf != NULL)
{
gdb_byte regval[MAX_REGISTER_SIZE];
const gdb_byte *p;
/* 32-bit decimal float is right aligned in the doubleword. */
- if (TYPE_LENGTH (valtype) == 4)
+ if (TYPE_LENGTH (valtype) == 4
+ && gdbarch_byte_order (gdbarch) == BFD_ENDIAN_BIG)
{
- memcpy (regval + 4, writebuf, 4);
+ memcpy (regval + 4, writebuf + offset, 4);
p = regval;
}
else
- p = writebuf;
+ p = writebuf + offset;
- regcache_cooked_write (regcache, tdep->ppc_fp0_regnum + 1, p);
+ regcache_cooked_write (regcache, regnum, p);
}
if (readbuf != NULL)
{
- regcache_cooked_read (regcache, tdep->ppc_fp0_regnum + 1, readbuf);
+ regcache_cooked_read (regcache, regnum, readbuf);
/* Left align 32-bit decimal float. */
- if (TYPE_LENGTH (valtype) == 4)
- memcpy (readbuf, readbuf + 4, 4);
+ if (TYPE_LENGTH (valtype) == 4
+ && gdbarch_byte_order (gdbarch) == BFD_ENDIAN_BIG)
+ memcpy (readbuf + offset, readbuf + offset + 4, 4);
}
}
/* 128-bit decimal floats in f2,f3. */
@@ -653,24 +659,27 @@ get_decimal_float_return_value (struct g
{
if (writebuf != NULL || readbuf != NULL)
{
- int i;
+ int i, regnum;
for (i = 0; i < 2; i++)
{
+ if (gdbarch_byte_order (gdbarch) == BFD_ENDIAN_BIG)
+ regnum = tdep->ppc_fp0_regnum + 2 + i + 2 * index;
+ else
+ regnum = tdep->ppc_fp0_regnum + 3 - i + 2 * index;
+
if (writebuf != NULL)
- regcache_cooked_write (regcache, tdep->ppc_fp0_regnum + 2 + i,
- writebuf + i * 8);
+ regcache_cooked_write (regcache, regnum,
+ writebuf + offset + i * 8);
if (readbuf != NULL)
- regcache_cooked_read (regcache, tdep->ppc_fp0_regnum + 2 + i,
- readbuf + i * 8);
+ regcache_cooked_read (regcache, regnum,
+ readbuf + offset + i * 8);
}
}
}
else
/* Can't happen. */
internal_error (__FILE__, __LINE__, _("Unknown decimal float size."));
-
- return RETURN_VALUE_REGISTER_CONVENTION;
}
/* Handle the return-value conventions specified by the SysV 32-bit
@@ -802,8 +811,11 @@ do_ppc_sysv_return_value (struct gdbarch
return RETURN_VALUE_REGISTER_CONVENTION;
}
if (TYPE_CODE (type) == TYPE_CODE_DECFLOAT && !tdep->soft_float)
- return get_decimal_float_return_value (gdbarch, type, regcache, readbuf,
- writebuf);
+ {
+ get_decimal_float_return_value (gdbarch, type, regcache,
+ readbuf, writebuf, 0);
+ return RETURN_VALUE_REGISTER_CONVENTION;
+ }
else if ((TYPE_CODE (type) == TYPE_CODE_INT
|| TYPE_CODE (type) == TYPE_CODE_CHAR
|| TYPE_CODE (type) == TYPE_CODE_BOOL
@@ -1102,6 +1114,156 @@ convert_code_addr_to_desc_addr (CORE_ADD
return 1;
}
+/* Walk down the type tree of TYPE counting consecutive base elements.
+ If *FIELD_TYPE is NULL, then set it to the first valid floating point
+ or vector type. If a non-floating point or vector type is found, or
+ if a floating point or vector type that doesn't match a non-NULL
+ *FIELD_TYPE is found, then return -1, otherwise return the count in the
+ sub-tree. */
+
+static LONGEST
+ppc64_aggregate_candidate (struct type *type,
+ struct type **field_type)
+{
+ type = check_typedef (type);
+
+ switch (TYPE_CODE (type))
+ {
+ case TYPE_CODE_FLT:
+ case TYPE_CODE_DECFLOAT:
+ if (!*field_type)
+ *field_type = type;
+ if (TYPE_CODE (*field_type) == TYPE_CODE (type)
+ && TYPE_LENGTH (*field_type) == TYPE_LENGTH (type))
+ return 1;
+ break;
+
+ case TYPE_CODE_COMPLEX:
+ type = TYPE_TARGET_TYPE (type);
+ if (TYPE_CODE (type) == TYPE_CODE_FLT
+ || TYPE_CODE (type) == TYPE_CODE_DECFLOAT)
+ {
+ if (!*field_type)
+ *field_type = type;
+ if (TYPE_CODE (*field_type) == TYPE_CODE (type)
+ && TYPE_LENGTH (*field_type) == TYPE_LENGTH (type))
+ return 2;
+ }
+ break;
+
+ case TYPE_CODE_ARRAY:
+ if (TYPE_VECTOR (type))
+ {
+ if (!*field_type)
+ *field_type = type;
+ if (TYPE_CODE (*field_type) == TYPE_CODE (type)
+ && TYPE_LENGTH (*field_type) == TYPE_LENGTH (type))
+ return 1;
+ }
+ else
+ {
+ LONGEST count, low_bound, high_bound;
+
+ count = ppc64_aggregate_candidate
+ (TYPE_TARGET_TYPE (type), field_type);
+ if (count == -1)
+ return -1;
+
+ if (!get_array_bounds (type, &low_bound, &high_bound))
+ return -1;
+ count *= high_bound - low_bound;
+
+ /* There must be no padding. */
+ if (count == 0)
+ return TYPE_LENGTH (type) == 0 ? 0 : -1;
+ else if (TYPE_LENGTH (type) != count * TYPE_LENGTH (*field_type))
+ return -1;
+
+ return count;
+ }
+ break;
+
+ case TYPE_CODE_STRUCT:
+ case TYPE_CODE_UNION:
+ {
+ LONGEST count = 0;
+ int i;
+
+ for (i = 0; i < TYPE_NFIELDS (type); i++)
+ {
+ LONGEST sub_count;
+
+ if (field_is_static (&TYPE_FIELD (type, i)))
+ continue;
+
+ sub_count = ppc64_aggregate_candidate
+ (TYPE_FIELD_TYPE (type, i), field_type);
+ if (sub_count == -1)
+ return -1;
+
+ if (TYPE_CODE (type) == TYPE_CODE_STRUCT)
+ count += sub_count;
+ else
+ count = max (count, sub_count);
+ }
+
+ /* There must be no padding. */
+ if (count == 0)
+ return TYPE_LENGTH (type) == 0 ? 0 : -1;
+ else if (TYPE_LENGTH (type) != count * TYPE_LENGTH (*field_type))
+ return -1;
+
+ return count;
+ }
+ break;
+
+ default:
+ break;
+ }
+
+ return -1;
+}
+
+/* If an argument of type TYPE is a homogeneous float or vector aggregate
+ that shall be passed in FP/vector registers according to the ELFv2 ABI,
+ return the homogeneous element type in *ELT_TYPE and the number of
+ elements in *N_ELTS, and return non-zero. Otherwise, return zero. */
+
+static int
+ppc64_elfv2_abi_homogeneous_aggregate (struct type *type,
+ struct type **elt_type, int *n_elts)
+{
+ /* Complex types at the top level are treated separately. However,
+ complex types can be elements of homogeneous aggregates. */
+ if (TYPE_CODE (type) == TYPE_CODE_STRUCT
+ || TYPE_CODE (type) == TYPE_CODE_UNION
+ || (TYPE_CODE (type) == TYPE_CODE_ARRAY && !TYPE_VECTOR (type)))
+ {
+ struct type *field_type = NULL;
+ LONGEST field_count = ppc64_aggregate_candidate (type, &field_type);
+
+ if (field_count > 0)
+ {
+ int n_regs = ((TYPE_CODE (field_type) == TYPE_CODE_FLT
+ || TYPE_CODE (field_type) == TYPE_CODE_DECFLOAT)?
+ (TYPE_LENGTH (field_type) + 7) >> 3 : 1);
+
+ /* The ELFv2 ABI allows homogeneous aggregates to occupy
+ up to 8 registers. */
+ if (field_count * n_regs <= 8)
+ {
+ if (elt_type)
+ *elt_type = field_type;
+ if (n_elts)
+ *n_elts = (int) field_count;
+ return 1;
+ }
+ }
+ }
+
+ return 0;
+}
+
/* Push a float in either registers, or in the stack. Using the ppc 64 bit
SysV ABI.
@@ -1143,6 +1305,8 @@ ppc64_sysv_abi_push_float (struct gdbarc
/* Write value in the stack's parameter save area. */
write_memory (gparam, p, 8);
+ if (greg <= 10)
+ regcache_cooked_write (regcache, tdep->ppc_gp0_regnum + greg, p);
/* Floats and Doubles go in f1 .. f13. They also consume a left aligned
GREG, and can end up in memory. */
@@ -1154,8 +1318,6 @@ ppc64_sysv_abi_push_float (struct gdbarc
convert_typed_floating (val, type, regval, regtype);
regcache_cooked_write (regcache, tdep->ppc_fp0_regnum + freg, regval);
}
- if (greg <= 10)
- regcache_cooked_write (regcache, tdep->ppc_gp0_regnum + greg, regval);
}
else
{
@@ -1268,9 +1430,13 @@ ppc64_sysv_abi_push_dummy_call (struct g
to their corresponding regions. */
refparam = align_down (sp - refparam_size, 16);
gparam = align_down (refparam - gparam_size, 16);
- /* Add in space for the TOC, link editor double word,
- compiler double word, LR save area, CR save area. */
- sp = align_down (gparam - 48, 16);
+ /* Add in space for the TOC, link editor double word (v1 only),
+ compiler double word (v1 only), LR save area, CR save area,
+ and backchain. */
+ if (tdep->elf_abi == POWERPC_ELF_V1)
+ sp = align_down (gparam - 48, 16);
+ else
+ sp = align_down (gparam - 32, 16);
}
/* If the function is returning a `struct', then there is an
@@ -1375,7 +1541,8 @@ ppc64_sysv_abi_push_dummy_call (struct g
/* 32-bit decimal floats are right aligned in the
doubleword. */
- if (TYPE_LENGTH (type) == 4)
+ if (TYPE_LENGTH (type) == 4
+ && byte_order == BFD_ENDIAN_BIG)
{
memcpy (regval + 4, val, 4);
p = regval;
@@ -1407,10 +1574,21 @@ ppc64_sysv_abi_push_dummy_call (struct g
{
/* Make sure freg is even. */
freg += freg & 1;
- regcache_cooked_write (regcache,
- tdep->ppc_fp0_regnum + freg, val);
- regcache_cooked_write (regcache,
- tdep->ppc_fp0_regnum + freg + 1, val + 8);
+
+ if (byte_order == BFD_ENDIAN_BIG)
+ {
+ regcache_cooked_write (regcache,
+ tdep->ppc_fp0_regnum + freg, val);
+ regcache_cooked_write (regcache,
+ tdep->ppc_fp0_regnum + freg + 1, val + 8);
+ }
+ else
+ {
+ regcache_cooked_write (regcache,
+ tdep->ppc_fp0_regnum + freg + 1, val);
+ regcache_cooked_write (regcache,
+ tdep->ppc_fp0_regnum + freg, val + 8);
+ }
}
write_memory (gparam, val, TYPE_LENGTH (type));
@@ -1587,8 +1765,9 @@ ppc64_sysv_abi_push_dummy_call (struct g
ULONGEST word = unpack_long (type, val);
/* Convert any function code addresses into
descriptors. */
- if (TYPE_CODE (type) == TYPE_CODE_PTR
- || TYPE_CODE (type) == TYPE_CODE_REF)
+ if (tdep->elf_abi == POWERPC_ELF_V1
+ && (TYPE_CODE (type) == TYPE_CODE_PTR
+ || TYPE_CODE (type) == TYPE_CODE_REF))
{
struct type *target_type;
target_type = check_typedef (TYPE_TARGET_TYPE (type));
@@ -1613,6 +1792,9 @@ ppc64_sysv_abi_push_dummy_call (struct g
}
else
{
+ struct type *elt_type;
+ int n_elts;
+
int byte;
for (byte = 0; byte < TYPE_LENGTH (type);
byte += tdep->wordsize)
@@ -1630,7 +1812,7 @@ ppc64_sysv_abi_push_dummy_call (struct g
versions before 3.4 implemented this
incorrectly; see
<http://gcc.gnu.org/gcc-3.4/powerpc-abi.html>. */
- if (byte == 0)
+ if (byte_order == BFD_ENDIAN_BIG && byte == 0)
memcpy (regval + tdep->wordsize - len,
val + byte, len);
else
@@ -1649,7 +1831,7 @@ ppc64_sysv_abi_push_dummy_call (struct g
value to memory. Fortunately, doing this
simplifies the code. */
int len = TYPE_LENGTH (type);
- if (len < tdep->wordsize)
+ if (byte_order == BFD_ENDIAN_BIG && len < tdep->wordsize)
write_memory (gparam + tdep->wordsize - len, val, len);
else
write_memory (gparam, val, len);
@@ -1705,6 +1887,132 @@ ppc64_sysv_abi_push_dummy_call (struct g
}
}
}
+ /* In the ELFv2 ABI, homogeneous floating-point or vector
+ aggregates are passed in registers. */
+ if (tdep->elf_abi == POWERPC_ELF_V2
+ && ppc64_elfv2_abi_homogeneous_aggregate (type,
+ &elt_type, &n_elts))
+ {
+ int i;
+ for (i = 0; i < n_elts; i++)
+ {
+ const gdb_byte *elt_val
+ = val + i * TYPE_LENGTH (elt_type);
+
+ switch (TYPE_CODE (elt_type))
+ {
+ case TYPE_CODE_FLT:
+ if (TYPE_LENGTH (elt_type) <= 8)
+ {
+ if (write_pass && freg <= 13)
+ {
+ int fregnum = tdep->ppc_fp0_regnum + freg;
+ gdb_byte regval[MAX_REGISTER_SIZE];
+ struct type *regtype
+ = register_type (gdbarch, fregnum);
+ convert_typed_floating (elt_val, elt_type,
+ regval, regtype);
+ regcache_cooked_write (regcache,
+ fregnum, regval);
+ }
+ freg++;
+ }
+ else if (TYPE_LENGTH (elt_type) == 16
+ && (gdbarch_long_double_format (gdbarch)
+ == floatformats_ibm_long_double))
+ {
+ if (write_pass && freg <= 13)
+ {
+ int fregnum = tdep->ppc_fp0_regnum + freg;
+ regcache_cooked_write (regcache,
+ fregnum, elt_val);
+ if (freg <= 12)
+ regcache_cooked_write (regcache,
+ fregnum + 1,
+ elt_val + 8);
+ }
+ freg += 2;
+ }
+ break;
+
+ case TYPE_CODE_DECFLOAT:
+ if (TYPE_LENGTH (elt_type) <= 8)
+ {
+ if (write_pass && freg <= 13)
+ {
+ int fregnum = tdep->ppc_fp0_regnum + freg;
+ gdb_byte regval[MAX_REGISTER_SIZE];
+ const gdb_byte *p;
+
+ /* 32-bit decimal floats are right aligned
+ in the doubleword. */
+ if (TYPE_LENGTH (elt_type) == 4
+ && byte_order == BFD_ENDIAN_BIG)
+ {
+ memcpy (regval + 4, elt_val, 4);
+ p = regval;
+ }
+ else
+ p = elt_val;
+
+ regcache_cooked_write (regcache, fregnum, p);
+ }
+ freg++;
+ }
+ else if (TYPE_LENGTH (elt_type) == 16)
+ {
+ /* Make sure freg is even. */
+ freg += freg & 1;
+
+ if (write_pass && freg <= 12)
+ {
+ int fregnum = tdep->ppc_fp0_regnum + freg;
+ if (byte_order == BFD_ENDIAN_BIG)
+ {
+ regcache_cooked_write (regcache,
+ fregnum,
+ elt_val);
+ regcache_cooked_write (regcache,
+ fregnum + 1,
+ elt_val + 8);
+ }
+ else
+ {
+ regcache_cooked_write (regcache,
+ fregnum + 1,
+ elt_val);
+ regcache_cooked_write (regcache,
+ fregnum,
+ elt_val + 8);
+ }
+ }
+ freg += 2;
+ }
+ break;
+
+ case TYPE_CODE_ARRAY:
+ gdb_assert (TYPE_VECTOR (type));
+
+ if (tdep->vector_abi == POWERPC_VEC_ALTIVEC
+ && TYPE_LENGTH (elt_type) == 16)
+ {
+ if (write_pass && vreg <= 13)
+ {
+ int vregnum = tdep->ppc_vr0_regnum + vreg;
+ regcache_cooked_write (regcache,
+ vregnum, elt_val);
+ }
+ vreg++;
+ }
+ break;
+
+ default:
+ internal_error (__FILE__, __LINE__,
+ _("Unknown element type."));
+ break;
+ }
+ }
+ }
/* Always consume parameter stack space. */
gparam = align_up (gparam + TYPE_LENGTH (type), tdep->wordsize);
}
@@ -1733,24 +2041,31 @@ ppc64_sysv_abi_push_dummy_call (struct g
breakpoint. */
regcache_cooked_write_signed (regcache, tdep->ppc_lr_regnum, bp_addr);
- /* Use the func_addr to find the descriptor, and use that to find
- the TOC. If we're calling via a function pointer, the pointer
- itself identifies the descriptor. */
- {
- struct type *ftype = check_typedef (value_type (function));
- CORE_ADDR desc_addr = value_as_address (function);
-
- if (TYPE_CODE (ftype) == TYPE_CODE_PTR
- || convert_code_addr_to_desc_addr (func_addr, &desc_addr))
- {
- /* The TOC is the second double word in the descriptor. */
- CORE_ADDR toc =
- read_memory_unsigned_integer (desc_addr + tdep->wordsize,
- tdep->wordsize, byte_order);
- regcache_cooked_write_unsigned (regcache,
- tdep->ppc_gp0_regnum + 2, toc);
- }
- }
+ /* In the ELFv1 ABI, use the func_addr to find the descriptor, and use
+ that to find the TOC. If we're calling via a function pointer,
+ the pointer itself identifies the descriptor. */
+ if (tdep->elf_abi == POWERPC_ELF_V1)
+ {
+ struct type *ftype = check_typedef (value_type (function));
+ CORE_ADDR desc_addr = value_as_address (function);
+
+ if (TYPE_CODE (ftype) == TYPE_CODE_PTR
+ || convert_code_addr_to_desc_addr (func_addr, &desc_addr))
+ {
+ /* The TOC is the second double word in the descriptor. */
+ CORE_ADDR toc =
+ read_memory_unsigned_integer (desc_addr + tdep->wordsize,
+ tdep->wordsize, byte_order);
+ regcache_cooked_write_unsigned (regcache,
+ tdep->ppc_gp0_regnum + 2, toc);
+ }
+ }
+
+ /* In the ELFv2 ABI, we need to pass the target address in r12 since
+ we may be calling a global entry point. */
+ if (tdep->elf_abi == POWERPC_ELF_V2)
+ regcache_cooked_write_unsigned (regcache,
+ tdep->ppc_gp0_regnum + 12, func_addr);
return sp;
}
@@ -1775,6 +2090,8 @@ ppc64_sysv_abi_return_value (struct gdba
enum bfd_endian byte_order = gdbarch_byte_order (gdbarch);
struct type *func_type = function ? value_type (function) : NULL;
int opencl_abi = func_type? ppc_sysv_use_opencl_abi (func_type) : 0;
+ struct type *elt_type;
+ int n_elts;
/* This function exists to support a calling convention that
requires floating-point registers. It shouldn't be used on
@@ -1799,8 +2116,11 @@ ppc64_sysv_abi_return_value (struct gdba
return RETURN_VALUE_REGISTER_CONVENTION;
}
if (TYPE_CODE (valtype) == TYPE_CODE_DECFLOAT)
- return get_decimal_float_return_value (gdbarch, valtype, regcache, readbuf,
- writebuf);
+ {
+ get_decimal_float_return_value (gdbarch, valtype, regcache,
+ readbuf, writebuf, 0);
+ return RETURN_VALUE_REGISTER_CONVENTION;
+ }
/* Integers in r3. */
if ((TYPE_CODE (valtype) == TYPE_CODE_INT
|| TYPE_CODE (valtype) == TYPE_CODE_ENUM
@@ -2019,6 +2339,114 @@ ppc64_sysv_abi_return_value (struct gdba
}
}
return RETURN_VALUE_REGISTER_CONVENTION;
+ }
+ /* In the ELFv2 ABI, homogeneous floating-point or vector
+ aggregates are returned in registers. */
+ if (tdep->elf_abi == POWERPC_ELF_V2
+ && ppc64_elfv2_abi_homogeneous_aggregate (valtype, &elt_type, &n_elts))
+ {
+ int i;
+ for (i = 0; i < n_elts; i++)
+ {
+ int offset = i * TYPE_LENGTH (elt_type);
+
+ switch (TYPE_CODE (elt_type))
+ {
+ case TYPE_CODE_FLT:
+ if (TYPE_LENGTH (elt_type) <= 8)
+ {
+ int regnum = tdep->ppc_fp0_regnum + 1 + i;
+ gdb_byte regval[MAX_REGISTER_SIZE];
+ struct type *regtype = register_type (gdbarch, regnum);
+ if (writebuf != NULL)
+ {
+ convert_typed_floating (writebuf + offset, elt_type,
+ regval, regtype);
+ regcache_cooked_write (regcache, regnum, regval);
+ }
+ if (readbuf != NULL)
+ {
+ regcache_cooked_read (regcache, regnum, regval);
+ convert_typed_floating (regval, regtype,
+ readbuf + offset, elt_type);
+ }
+ }
+ else
+ {
+ int j, nregs = (TYPE_LENGTH (elt_type) + 7) / 8;
+ for (j = 0; j < nregs; j++)
+ {
+ int regnum = tdep->ppc_fp0_regnum + 1 + nregs * i + j;
+
+ if (writebuf != NULL)
+ regcache_cooked_write (regcache, regnum,
+ writebuf + offset + j * 8);
+ if (readbuf != NULL)
+ regcache_cooked_read (regcache, regnum,
+ readbuf + offset + j * 8);
+ }
+ }
+ break;
+
+ case TYPE_CODE_DECFLOAT:
+ get_decimal_float_return_value (gdbarch, elt_type, regcache,
+ readbuf, writebuf, i);
+ break;
+
+ case TYPE_CODE_ARRAY:
+ {
+ int regnum = tdep->ppc_vr0_regnum + 2 + i;
+ gdb_assert (TYPE_VECTOR (elt_type));
+
+ if (writebuf != NULL)
+ regcache_cooked_write (regcache, regnum, writebuf + offset);
+ if (readbuf != NULL)
+ regcache_cooked_read (regcache, regnum, readbuf + offset);
+ }
+ break;
+ }
+ }
+ return RETURN_VALUE_REGISTER_CONVENTION;
+ }
+ /* In the ELFv2 ABI, aggregate types of up to 16 bytes are
+ returned in registers r3:r4. */
+ if (tdep->elf_abi == POWERPC_ELF_V2
+ && TYPE_LENGTH (valtype) <= 16
+ && (TYPE_CODE (valtype) == TYPE_CODE_STRUCT
+ || TYPE_CODE (valtype) == TYPE_CODE_UNION
+ || (TYPE_CODE (valtype) == TYPE_CODE_ARRAY && !TYPE_VECTOR (valtype))))
+ {
+ int n_regs = (TYPE_LENGTH (valtype) + tdep->wordsize - 1) / tdep->wordsize;
+ int i;
+
+ for (i = 0; i < n_regs; i++)
+ {
+ gdb_byte regval[MAX_REGISTER_SIZE];
+ int regnum = tdep->ppc_gp0_regnum + 3 + i;
+ int offset = i * tdep->wordsize;
+ int len = TYPE_LENGTH (valtype) - offset;
+ if (len > tdep->wordsize)
+ len = tdep->wordsize;
+
+ if (writebuf != NULL)
+ {
+ memset (regval, 0, sizeof regval);
+ if (byte_order == BFD_ENDIAN_BIG && offset == 0)
+ memcpy (regval + tdep->wordsize - len, writebuf, len);
+ else
+ memcpy (regval, writebuf + offset, len);
+ regcache_cooked_write (regcache, regnum, regval);
+ }
+ if (readbuf != NULL)
+ {
+ regcache_cooked_read (regcache, regnum, regval);
+ if (byte_order == BFD_ENDIAN_BIG && offset == 0)
+ memcpy (readbuf, regval + tdep->wordsize - len, len);
+ else
+ memcpy (readbuf + offset, regval, len);
+ }
+ }
+ return RETURN_VALUE_REGISTER_CONVENTION;
}
return RETURN_VALUE_STRUCT_CONVENTION;
}
--- a/gdb/ppc-tdep.h
+++ b/gdb/ppc-tdep.h
@@ -182,6 +182,15 @@ extern void ppc_collect_vsxregset (const
/* Private data that this module attaches to struct gdbarch. */
+/* ELF ABI version used by the inferior. */
+enum powerpc_elf_abi
+{
+ POWERPC_ELF_AUTO,
+ POWERPC_ELF_V1,
+ POWERPC_ELF_V2,
+ POWERPC_ELF_LAST
+};
+
/* Vector ABI used by the inferior. */
enum powerpc_vector_abi
{
@@ -197,6 +206,8 @@ struct gdbarch_tdep
int wordsize; /* Size in bytes of fixed-point word. */
int soft_float; /* Avoid FP registers for arguments? */
+ enum powerpc_elf_abi elf_abi; /* ELF ABI version. */
+
/* How to pass vector arguments. Never set to AUTO or LAST. */
enum powerpc_vector_abi vector_abi;
--- a/gdb/symtab.c
+++ b/gdb/symtab.c
@@ -2881,6 +2881,8 @@ skip_prologue_sal (struct symtab_and_lin
/* Skip "first line" of function (which is actually its prologue). */
pc += gdbarch_deprecated_function_start_offset (gdbarch);
+ if (gdbarch_skip_entrypoint_p (gdbarch))
+ pc = gdbarch_skip_entrypoint (gdbarch, pc);
if (skip)
pc = gdbarch_skip_prologue (gdbarch, pc);
--- a/gdb/testsuite/gdb.arch/altivec-regs.exp
+++ b/gdb/testsuite/gdb.arch/altivec-regs.exp
@@ -118,7 +118,7 @@ gdb_test "info reg vscr" "vscr.*0x1\t1"
if {$endianness == "big"} {
set decimal_vector ".uint128 = 0x00000001000000010000000100000001, v4_float = .1.*e-45, 1.*e-45, 1.*e-45, 1.*e-45., v4_int32 = .1, 1, 1, 1., v8_int16 = .0, 1, 0, 1, 0, 1, 0, 1., v16_int8 = .0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 1.."
} else {
- set decimal_vector ".uint128 = 0x00000001000000010000000100000001, v4_float = .1.*e-45, 1.*e-45, 1.*e-45, 1.*e-45., v4_int32 = .1, 1, 1, 1., v8_int16 = .1, 0, 1, 0, 1, 0, 1, 0., v16_int8 = .1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0.."
+ set decimal_vector ".uint128 = 0x00000001000000010000000100000001, v4_float = .1.*e-45, 1.*e-45, 1.*e-45, 1.*e-45., v4_int32 = .1, 1, 1, 1., v8_int16 = .1, 0, 1, 0, 1, 0, 1, 0., v16_int8 = .1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0.."
}
for {set i 0} {$i < 32} {incr i 1} {
--- a/gdb/testsuite/gdb.arch/powerpc-d128-regs.exp
+++ b/gdb/testsuite/gdb.arch/powerpc-d128-regs.exp
@@ -20,7 +20,7 @@
# Testcase for ppc decimal128 pseudo-registers.
-if ![istarget "powerpc64-*"] then {
+if ![istarget "powerpc64*-*"] then {
verbose "Skipping powerpc Decimal128 pseudo-registers testcase."
return
}
--- a/gdb/testsuite/gdb.arch/vsx-regs.exp
+++ b/gdb/testsuite/gdb.arch/vsx-regs.exp
@@ -58,19 +58,46 @@ if ![runto_main] then {
gdb_suppress_tests
}
+send_gdb "show endian\n"
+set endianness ""
+gdb_expect {
+ -re "(The target endianness is set automatically .currently )(big|little)( endian.*)$gdb_prompt $" {
+ pass "endianness"
+ set endianness $expect_out(2,string)
+ }
+ -re ".*$gdb_prompt $" {
+ fail "couldn't get endianness"
+ }
+ timeout { fail "(timeout) endianness" }
+}
+
# Data sets used throughout the test
-set vector_register1 ".uint128 = 0x3ff4cccccccccccc0000000000000000, v2_double = .0x1, 0x0., v4_float = .0x1, 0xf99999a0, 0x0, 0x0., v4_int32 = .0x3ff4cccc, 0xcccccccc, 0x0, 0x0., v8_int16 = .0x3ff4, 0xcccc, 0xcccc, 0xcccc, 0x0, 0x0, 0x0, 0x0., v16_int8 = .0x3f, 0xf4, 0xcc, 0xcc, 0xcc, 0xcc, 0xcc, 0xcc, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0.."
+if {$endianness == "big"} {
+ set vector_register1 ".uint128 = 0x3ff4cccccccccccc0000000000000000, v2_double = .0x1, 0x0., v4_float = .0x1, 0xf99999a0, 0x0, 0x0., v4_int32 = .0x3ff4cccc, 0xcccccccc, 0x0, 0x0., v8_int16 = .0x3ff4, 0xcccc, 0xcccc, 0xcccc, 0x0, 0x0, 0x0, 0x0., v16_int8 = .0x3f, 0xf4, 0xcc, 0xcc, 0xcc, 0xcc, 0xcc, 0xcc, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0.."
+
+ set vector_register1_vr ".uint128 = 0x3ff4cccccccccccc0000000100000001, v4_float = .0x1, 0xf99999a0, 0x0, 0x0., v4_int32 = .0x3ff4cccc, 0xcccccccc, 0x1, 0x1., v8_int16 = .0x3ff4, 0xcccc, 0xcccc, 0xcccc, 0x0, 0x1, 0x0, 0x1., v16_int8 = .0x3f, 0xf4, 0xcc, 0xcc, 0xcc, 0xcc, 0xcc, 0xcc, 0x0, 0x0, 0x0, 0x1, 0x0, 0x0, 0x0, 0x1.."
+
+ set vector_register2 "uint128 = 0xdeadbeefdeadbeefdeadbeefdeadbeef, v2_double = .0x1, 0x1., v4_float = .0x0, 0x0, 0x0, 0x0., v4_int32 = .0xdeadbeef, 0xdeadbeef, 0xdeadbeef, 0xdeadbeef., v8_int16 = .0xdead, 0xbeef, 0xdead, 0xbeef, 0xdead, 0xbeef, 0xdead, 0xbeef., v16_int8 = .0xde, 0xad, 0xbe, 0xef, 0xde, 0xad, 0xbe, 0xef, 0xde, 0xad, 0xbe, 0xef, 0xde, 0xad, 0xbe, 0xef.."
-set vector_register1_vr ".uint128 = 0x3ff4cccccccccccc0000000100000001, v4_float = .0x1, 0xf99999a0, 0x0, 0x0., v4_int32 = .0x3ff4cccc, 0xcccccccc, 0x1, 0x1., v8_int16 = .0x3ff4, 0xcccc, 0xcccc, 0xcccc, 0x0, 0x1, 0x0, 0x1., v16_int8 = .0x3f, 0xf4, 0xcc, 0xcc, 0xcc, 0xcc, 0xcc, 0xcc, 0x0, 0x0, 0x0, 0x1, 0x0, 0x0, 0x0, 0x1.."
+ set vector_register2_vr "uint128 = 0xdeadbeefdeadbeefdeadbeefdeadbeef, v4_float = .0x0, 0x0, 0x0, 0x0., v4_int32 = .0xdeadbeef, 0xdeadbeef, 0xdeadbeef, 0xdeadbeef., v8_int16 = .0xdead, 0xbeef, 0xdead, 0xbeef, 0xdead, 0xbeef, 0xdead, 0xbeef., v16_int8 = .0xde, 0xad, 0xbe, 0xef, 0xde, 0xad, 0xbe, 0xef, 0xde, 0xad, 0xbe, 0xef, 0xde, 0xad, 0xbe, 0xef.."
-set vector_register2 "uint128 = 0xdeadbeefdeadbeefdeadbeefdeadbeef, v2_double = .0x1, 0x1., v4_float = .0x0, 0x0, 0x0, 0x0., v4_int32 = .0xdeadbeef, 0xdeadbeef, 0xdeadbeef, 0xdeadbeef., v8_int16 = .0xdead, 0xbeef, 0xdead, 0xbeef, 0xdead, 0xbeef, 0xdead, 0xbeef., v16_int8 = .0xde, 0xad, 0xbe, 0xef, 0xde, 0xad, 0xbe, 0xef, 0xde, 0xad, 0xbe, 0xef, 0xde, 0xad, 0xbe, 0xef.."
+ set vector_register3 ".uint128 = 0x00000001000000010000000100000001, v2_double = .0x0, 0x0., v4_float = .0x0, 0x0, 0x0, 0x0., v4_int32 = .0x1, 0x1, 0x1, 0x1., v8_int16 = .0x0, 0x1, 0x0, 0x1, 0x0, 0x1, 0x0, 0x1., v16_int8 = .0x0, 0x0, 0x0, 0x1, 0x0, 0x0, 0x0, 0x1, 0x0, 0x0, 0x0, 0x1, 0x0, 0x0, 0x0, 0x1.."
-set vector_register2_vr "uint128 = 0xdeadbeefdeadbeefdeadbeefdeadbeef, v4_float = .0x0, 0x0, 0x0, 0x0., v4_int32 = .0xdeadbeef, 0xdeadbeef, 0xdeadbeef, 0xdeadbeef., v8_int16 = .0xdead, 0xbeef, 0xdead, 0xbeef, 0xdead, 0xbeef, 0xdead, 0xbeef., v16_int8 = .0xde, 0xad, 0xbe, 0xef, 0xde, 0xad, 0xbe, 0xef, 0xde, 0xad, 0xbe, 0xef, 0xde, 0xad, 0xbe, 0xef.."
+ set vector_register3_vr ".uint128 = 0x00000001000000010000000100000001, v4_float = .0x0, 0x0, 0x0, 0x0., v4_int32 = .0x1, 0x1, 0x1, 0x1., v8_int16 = .0x0, 0x1, 0x0, 0x1, 0x0, 0x1, 0x0, 0x1., v16_int8 = .0x0, 0x0, 0x0, 0x1, 0x0, 0x0, 0x0, 0x1, 0x0, 0x0, 0x0, 0x1, 0x0, 0x0, 0x0, 0x1.."
+} else {
+ set vector_register1 ".uint128 = 0x3ff4cccccccccccc0000000000000000, v2_double = .0x0, 0x1., v4_float = .0x0, 0x0, 0xf99999a0, 0x1., v4_int32 = .0x0, 0x0, 0xcccccccc, 0x3ff4cccc., v8_int16 = .0x0, 0x0, 0x0, 0x0, 0xcccc, 0xcccc, 0xcccc, 0x3ff4., v16_int8 = .0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0xcc, 0xcc, 0xcc, 0xcc, 0xcc, 0xcc, 0xf4, 0x3f.."
-set vector_register3 ".uint128 = 0x00000001000000010000000100000001, v2_double = .0x0, 0x0., v4_float = .0x0, 0x0, 0x0, 0x0., v4_int32 = .0x1, 0x1, 0x1, 0x1., v8_int16 = .0x0, 0x1, 0x0, 0x1, 0x0, 0x1, 0x0, 0x1., v16_int8 = .0x0, 0x0, 0x0, 0x1, 0x0, 0x0, 0x0, 0x1, 0x0, 0x0, 0x0, 0x1, 0x0, 0x0, 0x0, 0x1.."
+ set vector_register1_vr ".uint128 = 0x3ff4cccccccccccc0000000100000001, v4_float = .0x0, 0x0, 0xf99999a0, 0x1., v4_int32 = .0x1, 0x1, 0xcccccccc, 0x3ff4cccc., v8_int16 = .0x1, 0x0, 0x1, 0x0, 0xcccc, 0xcccc, 0xcccc, 0x3ff4., v16_int8 = .0x1, 0x0, 0x0, 0x0, 0x1, 0x0, 0x0, 0x0, 0xcc, 0xcc, 0xcc, 0xcc, 0xcc, 0xcc, 0xf4, 0x3f.."
-set vector_register3_vr ".uint128 = 0x00000001000000010000000100000001, v4_float = .0x0, 0x0, 0x0, 0x0., v4_int32 = .0x1, 0x1, 0x1, 0x1., v8_int16 = .0x0, 0x1, 0x0, 0x1, 0x0, 0x1, 0x0, 0x1., v16_int8 = .0x0, 0x0, 0x0, 0x1, 0x0, 0x0, 0x0, 0x1, 0x0, 0x0, 0x0, 0x1, 0x0, 0x0, 0x0, 0x1.."
+ set vector_register2 "uint128 = 0xdeadbeefdeadbeefdeadbeefdeadbeef, v2_double = .0x1, 0x1., v4_float = .0x0, 0x0, 0x0, 0x0., v4_int32 = .0xdeadbeef, 0xdeadbeef, 0xdeadbeef, 0xdeadbeef., v8_int16 = .0xbeef, 0xdead, 0xbeef, 0xdead, 0xbeef, 0xdead, 0xbeef, 0xdead., v16_int8 = .0xef, 0xbe, 0xad, 0xde, 0xef, 0xbe, 0xad, 0xde, 0xef, 0xbe, 0xad, 0xde, 0xef, 0xbe, 0xad, 0xde.."
+
+ set vector_register2_vr "uint128 = 0xdeadbeefdeadbeefdeadbeefdeadbeef, v4_float = .0x0, 0x0, 0x0, 0x0., v4_int32 = .0xdeadbeef, 0xdeadbeef, 0xdeadbeef, 0xdeadbeef., v8_int16 = .0xbeef, 0xdead, 0xbeef, 0xdead, 0xbeef, 0xdead, 0xbeef, 0xdead., v16_int8 = .0xef, 0xbe, 0xad, 0xde, 0xef, 0xbe, 0xad, 0xde, 0xef, 0xbe, 0xad, 0xde, 0xef, 0xbe, 0xad, 0xde.."
+
+ set vector_register3 ".uint128 = 0x00000001000000010000000100000001, v2_double = .0x0, 0x0., v4_float = .0x0, 0x0, 0x0, 0x0., v4_int32 = .0x1, 0x1, 0x1, 0x1., v8_int16 = .0x1, 0x0, 0x1, 0x0, 0x1, 0x0, 0x1, 0x0., v16_int8 = .0x1, 0x0, 0x0, 0x0, 0x1, 0x0, 0x0, 0x0, 0x1, 0x0, 0x0, 0x0, 0x1, 0x0, 0x0, 0x0.."
+
+ set vector_register3_vr ".uint128 = 0x00000001000000010000000100000001, v4_float = .0x0, 0x0, 0x0, 0x0., v4_int32 = .0x1, 0x1, 0x1, 0x1., v8_int16 = .0x1, 0x0, 0x1, 0x0, 0x1, 0x0, 0x1, 0x0., v16_int8 = .0x1, 0x0, 0x0, 0x0, 0x1, 0x0, 0x0, 0x0, 0x1, 0x0, 0x0, 0x0, 0x1, 0x0, 0x0, 0x0.."
+}
set float_register ".raw 0xdeadbeefdeadbeef."
--- a/gdb/testsuite/gdb.base/sigbpt.exp
+++ b/gdb/testsuite/gdb.base/sigbpt.exp
@@ -82,7 +82,7 @@ gdb_test "break keeper"
set bowler_addrs bowler
set segv_addr none
gdb_test {display/i $pc}
-gdb_test "advance *bowler" "bowler.*" "advance to the bowler"
+gdb_test "advance bowler" "bowler.*" "advance to the bowler"
set test "stepping to fault"
set signame "SIGSEGV"
gdb_test_multiple "stepi" "$test" {
--- a/gdb/testsuite/gdb.base/step-bt.exp
+++ b/gdb/testsuite/gdb.base/step-bt.exp
@@ -32,7 +32,7 @@ gdb_start
gdb_reinitialize_dir $srcdir/$subdir
gdb_load ${binfile}
-gdb_test "break *hello" \
+gdb_test "break hello" \
"Breakpoint.*at.* file .*$srcfile, line .*" \
"breakpoint at first instruction of hello()"
--- a/include/elf/common.h
+++ b/include/elf/common.h
@@ -954,6 +954,7 @@
#define AT_BASE_PLATFORM 24 /* String identifying real platform,
may differ from AT_PLATFORM. */
#define AT_RANDOM 25 /* Address of 16 random bytes. */
+#define AT_HWCAP2 26 /* Extension of AT_HWCAP. */
#define AT_EXECFN 31 /* Filename of executable. */
/* Pointer to the global system page used for system calls and other
nice things. */
--- a/include/elf/ppc64.h
+++ b/include/elf/ppc64.h
@@ -164,6 +164,60 @@ END_RELOC_NUMBERS (R_PPC64_max)
#define IS_PPC64_TLS_RELOC(R) \
((R) >= R_PPC64_TLS && (R) <= R_PPC64_DTPREL16_HIGHESTA)
+
+/* e_flags bits specifying ABI.
+ 1 for original function descriptor using ABI,
+ 2 for revised ABI without function descriptors,
+ 0 for unspecified or not using any features affected by the differences. */
+#define EF_PPC64_ABI 3
+
+/* The ELFv2 ABI uses three bits in the symbol st_other field of a
+ function definition to specify the number of instructions between a
+ function's global entry point and local entry point.
+ The global entry point is used when it is necessary to set up the
+ toc pointer (r2) for the function. Callers must enter the global
+ entry point with r12 set to the global entry point address. On
+ return from the function, r2 may have a different value to that
+ which it had on entry.
+ The local entry point is used when r2 is known to already be valid
+ for the function. There is no requirement on r12 when using the
+ local entry point, and on return r2 will contain the same value as
+ at entry.
+ A value of zero in these bits means that the function has a single
+ entry point with no requirement on r12 or r2, and that on return r2
+ will contain the same value as at entry.
+ Values of one and seven are reserved. */
+#define STO_PPC64_LOCAL_BIT 5
+#define STO_PPC64_LOCAL_MASK (7 << STO_PPC64_LOCAL_BIT)
+
+// 3 bit other field to bytes.
+static inline unsigned int
+ppc64_decode_local_entry(unsigned int other)
+{
+ return ((1 << other) >> 2) << 2;
+}
+
+// bytes to field value.
+static inline unsigned int
+ppc64_encode_local_entry(unsigned int val)
+{
+ return (val >= 4 * 4
+ ? (val >= 8 * 4
+ ? (val >= 16 * 4 ? 6 : 5)
+ : 4)
+ : (val >= 2 * 4
+ ? 3
+ : (val >= 1 * 4 ? 2 : 0)));
+}
+
+/* st_other to number of bytes. */
+#define PPC64_LOCAL_ENTRY_OFFSET(other) \
+ ppc64_decode_local_entry (((other) & STO_PPC64_LOCAL_MASK) \
+ >> STO_PPC64_LOCAL_BIT)
+/* number of bytes to st_other. */
+#define PPC64_SET_LOCAL_ENTRY_OFFSET(val) \
+ ppc64_encode_local_entry (val) << STO_PPC64_LOCAL_BIT
+
/* Specify the start of the .glink section. */
#define DT_PPC64_GLINK DT_LOPROC