* config/i386/nm-i386sol2.h (CANNOT_STEP_HW_WATCHPOINTS): Define.

* config/i386/tm-i386sol2.h (HAVE_I387_REGS):  Define.
	* i386v4-nat.c (supply_fpregset, fill_fpregset):  Add code
	to handle floating point registers if NUM_FREGS is not zero.
This commit is contained in:
Peter Schauer 2000-04-13 18:11:41 +00:00
parent db348f2745
commit 14164c30b6
4 changed files with 102 additions and 4 deletions

View File

@ -1,3 +1,10 @@
2000-04-13 Peter Schauer <pes@regent.e-technik.tu-muenchen.de>
* config/i386/nm-i386sol2.h (CANNOT_STEP_HW_WATCHPOINTS): Define.
* config/i386/tm-i386sol2.h (HAVE_I387_REGS): Define.
* i386v4-nat.c (supply_fpregset, fill_fpregset): Add code
to handle floating point registers if NUM_FREGS is not zero.
2000-04-13 Nick Duffek <nsd@cygnus.com>
* sol-thread.c (init_sol_core_ops): Initialize to_thread_alive

View File

@ -34,6 +34,16 @@
It will *NOT* be necessary for GDB to step over the watchpoint. */
#define HAVE_CONTINUABLE_WATCHPOINT
/* Solaris x86 2.6 and 2.7 targets have a kernel bug when stepping
over an instruction that causes a page fault without triggering
a hardware watchpoint. The kernel properly notices that it shouldn't
stop, because the hardware watchpoint is not triggered, but it forgets
the step request and continues the program normally.
Work around the problem by removing hardware watchpoints if a step is
requested, GDB will check for a hardware watchpoint trigger after the
step anyway. */
#define CANNOT_STEP_HW_WATCHPOINTS
extern int procfs_stopped_by_watchpoint PARAMS ((int));
#define STOPPED_BY_WATCHPOINT(W) \
procfs_stopped_by_watchpoint(inferior_pid)

View File

@ -21,6 +21,7 @@
#ifndef TM_I386SOL2_H
#define TM_I386SOL2_H 1
#define HAVE_I387_REGS
#include "i386/tm-i386v4.h"
/* Signal handler frames under Solaris 2 are recognized by a return address

View File

@ -142,17 +142,65 @@ fill_gregset (gregsetp, regno)
#endif /* HAVE_GREGSET_T */
#if defined (FP0_REGNUM) && defined (HAVE_FPREGSET_T)
#if defined (HAVE_FPREGSET_T)
/* Given a pointer to a floating point register set in /proc format
(fpregset_t *), unpack the register contents and supply them as gdb's
idea of the current floating point register values. */
/* FIXME: Assumes that fpregsetp contains an i387 FSAVE area. */
static const int freg_offset_map[] =
{
#if !defined(FPREGSET_FSAVE_OFFSET)
#define FPREGSET_FSAVE_OFFSET 0
#endif
FPREGSET_FSAVE_OFFSET + 28 + 0 * 10,
FPREGSET_FSAVE_OFFSET + 28 + 1 * 10,
FPREGSET_FSAVE_OFFSET + 28 + 2 * 10,
FPREGSET_FSAVE_OFFSET + 28 + 3 * 10,
FPREGSET_FSAVE_OFFSET + 28 + 4 * 10,
FPREGSET_FSAVE_OFFSET + 28 + 5 * 10,
FPREGSET_FSAVE_OFFSET + 28 + 6 * 10,
FPREGSET_FSAVE_OFFSET + 28 + 7 * 10,
FPREGSET_FSAVE_OFFSET + 0,
FPREGSET_FSAVE_OFFSET + 4,
FPREGSET_FSAVE_OFFSET + 8,
FPREGSET_FSAVE_OFFSET + 16,
FPREGSET_FSAVE_OFFSET + 12,
FPREGSET_FSAVE_OFFSET + 24,
FPREGSET_FSAVE_OFFSET + 20,
FPREGSET_FSAVE_OFFSET + 16
};
void
supply_fpregset (fpregsetp)
fpregset_t *fpregsetp;
{
/* FIXME: see m68k-tdep.c for an example, for the m68k. */
int regi;
if (NUM_FREGS == 0)
return;
for (regi = FP0_REGNUM; regi <= LAST_FPU_CTRL_REGNUM; regi++)
{
char tbuf[4];
ULONGEST tval;
char *from = (char *) fpregsetp + freg_offset_map[regi - FP0_REGNUM];
if (regi == FCS_REGNUM)
{
tval = extract_unsigned_integer (from, 4) & 0xffff;
store_unsigned_integer (tbuf, 4, tval);
supply_register (regi, tbuf);
}
else if (regi == FOP_REGNUM)
{
tval = (extract_unsigned_integer (from, 4) >> 16) & ((1 << 11) - 1);
store_unsigned_integer (tbuf, 4, tval);
supply_register (regi, tbuf);
}
else
supply_register (regi, from);
}
}
/* Given a pointer to a floating point register set in /proc format
@ -165,9 +213,41 @@ fill_fpregset (fpregsetp, regno)
fpregset_t *fpregsetp;
int regno;
{
/* FIXME: see m68k-tdep.c for an example, for the m68k. */
int regi;
if (NUM_FREGS == 0)
return;
for (regi = FP0_REGNUM; regi <= LAST_FPU_CTRL_REGNUM; regi++)
{
if ((regno == -1) || (regno == regi))
{
char *to = (char *) fpregsetp + freg_offset_map[regi - FP0_REGNUM];
char *from = (char *) &registers[REGISTER_BYTE (regi)];
ULONGEST valto;
ULONGEST valfrom;
if (regi == FCS_REGNUM)
{
valto = extract_unsigned_integer (to, 4);
valfrom = extract_unsigned_integer (from, 4);
valto = (valto & ~0xffff) | (valfrom & 0xffff);
store_unsigned_integer (to, 4, valto);
}
else if (regi == FOP_REGNUM)
{
valto = extract_unsigned_integer (to, 4);
valfrom = extract_unsigned_integer (from, 4);
valto = (valto & 0xffff) | ((valfrom & ((1 << 11) - 1)) << 16);
store_unsigned_integer (to, 4, valto);
}
else
{
memcpy (to, from, REGISTER_RAW_SIZE (regi));
}
}
}
}
#endif /* defined (FP0_REGNUM) && defined (HAVE_FPREGSET_T) */
#endif /* defined (HAVE_FPREGSET_T) */
#endif /* HAVE_SYS_PROCFS_H */