| Index: gdb/ia64-linux-nat.c
|
| diff --git a/gdb/ia64-linux-nat.c b/gdb/ia64-linux-nat.c
|
| index 5aaaed9fc57b9dd32fafd308c010599d0c2f37b0..9b5fbf3d8ae3471895d2aa4c560a6716968bbc05 100644
|
| --- a/gdb/ia64-linux-nat.c
|
| +++ b/gdb/ia64-linux-nat.c
|
| @@ -272,7 +272,7 @@ static int u_offsets[] =
|
| -1, -1, -1, -1, -1, -1, -1, -1, -1,
|
| PT_AR_PFS,
|
| PT_AR_LC,
|
| - -1, /* Not available: EC, the Epilog Count register. */
|
| + PT_AR_EC,
|
| -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
|
| -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
|
| -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
|
| @@ -447,8 +447,20 @@ supply_fpregset (struct regcache *regcache, const fpregset_t *fpregsetp)
|
| {
|
| int regi;
|
| const char *from;
|
| + const gdb_byte f_zero[16] = { 0 };
|
| + const gdb_byte f_one[16] =
|
| + { 0, 0, 0, 0, 0, 0, 0, 0x80, 0xff, 0xff, 0, 0, 0, 0, 0, 0 };
|
|
|
| - for (regi = IA64_FR0_REGNUM; regi <= IA64_FR127_REGNUM; regi++)
|
| + /* Kernel generated cores have fr1==0 instead of 1.0. Older GDBs
|
| + did the same. So ignore whatever might be recorded in fpregset_t
|
| + for fr0/fr1 and always supply their expected values. */
|
| +
|
| + /* fr0 is always read as zero. */
|
| + regcache_raw_supply (regcache, IA64_FR0_REGNUM, f_zero);
|
| + /* fr1 is always read as one (1.0). */
|
| + regcache_raw_supply (regcache, IA64_FR1_REGNUM, f_one);
|
| +
|
| + for (regi = IA64_FR2_REGNUM; regi <= IA64_FR127_REGNUM; regi++)
|
| {
|
| from = (const char *) &((*fpregsetp)[regi - IA64_FR0_REGNUM]);
|
| regcache_raw_supply (regcache, regi, from);
|
| @@ -617,7 +629,7 @@ ia64_linux_remove_watchpoint (CORE_ADDR addr, int len, int type,
|
| }
|
|
|
| static void
|
| -ia64_linux_new_thread (ptid_t ptid)
|
| +ia64_linux_new_thread (struct lwp_info *lp)
|
| {
|
| int i, any;
|
|
|
| @@ -626,24 +638,25 @@ ia64_linux_new_thread (ptid_t ptid)
|
| {
|
| if (debug_registers[i] != 0)
|
| any = 1;
|
| - store_debug_register (ptid, i, debug_registers[i]);
|
| + store_debug_register (lp->ptid, i, debug_registers[i]);
|
| }
|
|
|
| if (any)
|
| - enable_watchpoints_in_psr (ptid);
|
| + enable_watchpoints_in_psr (lp->ptid);
|
| }
|
|
|
| static int
|
| ia64_linux_stopped_data_address (struct target_ops *ops, CORE_ADDR *addr_p)
|
| {
|
| CORE_ADDR psr;
|
| - struct siginfo *siginfo_p;
|
| + siginfo_t siginfo;
|
| struct regcache *regcache = get_current_regcache ();
|
|
|
| - siginfo_p = linux_nat_get_siginfo (inferior_ptid);
|
| + if (!linux_nat_get_siginfo (inferior_ptid, &siginfo))
|
| + return 0;
|
|
|
| - if (siginfo_p->si_signo != SIGTRAP
|
| - || (siginfo_p->si_code & 0xffff) != 0x0004 /* TRAP_HWBKPT */)
|
| + if (siginfo.si_signo != SIGTRAP
|
| + || (siginfo.si_code & 0xffff) != 0x0004 /* TRAP_HWBKPT */)
|
| return 0;
|
|
|
| regcache_cooked_read_unsigned (regcache, IA64_PSR_REGNUM, &psr);
|
| @@ -651,7 +664,7 @@ ia64_linux_stopped_data_address (struct target_ops *ops, CORE_ADDR *addr_p)
|
| for the next instruction. */
|
| regcache_cooked_write_unsigned (regcache, IA64_PSR_REGNUM, psr);
|
|
|
| - *addr_p = (CORE_ADDR)siginfo_p->si_addr;
|
| + *addr_p = (CORE_ADDR) siginfo.si_addr;
|
| return 1;
|
| }
|
|
|
| @@ -680,6 +693,37 @@ ia64_linux_fetch_register (struct regcache *regcache, int regnum)
|
| PTRACE_TYPE_RET *buf;
|
| int pid, i;
|
|
|
| + /* r0 cannot be fetched but is always zero. */
|
| + if (regnum == IA64_GR0_REGNUM)
|
| + {
|
| + const gdb_byte zero[8] = { 0 };
|
| +
|
| + gdb_assert (sizeof (zero) == register_size (gdbarch, regnum));
|
| + regcache_raw_supply (regcache, regnum, zero);
|
| + return;
|
| + }
|
| +
|
| + /* fr0 cannot be fetched but is always zero. */
|
| + if (regnum == IA64_FR0_REGNUM)
|
| + {
|
| + const gdb_byte f_zero[16] = { 0 };
|
| +
|
| + gdb_assert (sizeof (f_zero) == register_size (gdbarch, regnum));
|
| + regcache_raw_supply (regcache, regnum, f_zero);
|
| + return;
|
| + }
|
| +
|
| + /* fr1 cannot be fetched but is always one (1.0). */
|
| + if (regnum == IA64_FR1_REGNUM)
|
| + {
|
| + const gdb_byte f_one[16] =
|
| + { 0, 0, 0, 0, 0, 0, 0, 0x80, 0xff, 0xff, 0, 0, 0, 0, 0, 0 };
|
| +
|
| + gdb_assert (sizeof (f_one) == register_size (gdbarch, regnum));
|
| + regcache_raw_supply (regcache, regnum, f_one);
|
| + return;
|
| + }
|
| +
|
| if (ia64_cannot_fetch_register (gdbarch, regnum))
|
| {
|
| regcache_raw_supply (regcache, regnum, NULL);
|
|
|