From 315615555c28855516a8a2e77dc8317190a1894d Mon Sep 17 00:00:00 2001 From: Nate Williams Date: Thu, 1 Jul 1993 00:17:55 +0000 Subject: [PATCH] Bruce Evans: The enclosed diffs implement printing of the floating point state for the version of gdb-3.5 in 386BSD-0.0. I don't have gdb for 386BSD-0.1 but I've been told that it is also missing this feature. The changes are small. Code to read the FP state from the kernel was #ifdef'ed out, but it essentially works. Code to change the FP regs is still #ifdef'ed out. It is close to working too. Printing of the FP regs was broken because hard reg numbers were confused with stack offsets. 4. The emulator does not handle FP errors right, and it does not communicate the emulated FP state to the rest of the kernel, so "info float" shows garbage. --- gnu/usr.bin/gdb/config/i386bsd-dep.c | 31 +++++++++++++++++++++------- 1 file changed, 24 insertions(+), 7 deletions(-) diff --git a/gnu/usr.bin/gdb/config/i386bsd-dep.c b/gnu/usr.bin/gdb/config/i386bsd-dep.c index 6172cf7c308..d298fb02ac0 100644 --- a/gnu/usr.bin/gdb/config/i386bsd-dep.c +++ b/gnu/usr.bin/gdb/config/i386bsd-dep.c @@ -1748,12 +1748,18 @@ print_387_status (status, ep) top = (ep->status >> 11) & 7; - printf ("regno tag msb lsb value\n"); + printf (" regno tag msb lsb value\n"); for (fpreg = 7; fpreg >= 0; fpreg--) { + int st_regno; double val; - printf ("%s %d: ", fpreg == top ? "=>" : " ", fpreg); + /* The physical regno `fpreg' is only relevant as an index into the + * tag word. Logical `%st' numbers are required for indexing `p->regs. + */ + st_regno = (fpreg + 8 - top) & 0x7; + + printf ("%%st(%d) %s ", st_regno, fpreg == top ? "=>" : " "); switch ((ep->tag >> (fpreg * 2)) & 3) { @@ -1763,11 +1769,12 @@ print_387_status (status, ep) case 3: printf ("empty "); break; } for (i = 9; i >= 0; i--) - printf ("%02x", ep->regs[fpreg][i]); + printf ("%02x", ep->regs[st_regno][i]); - i387_to_double (ep->regs[fpreg], (char *)&val); + i387_to_double (ep->regs[st_regno], (char *)&val); printf (" %g\n", val); } +#if 0 /* reserved fields are always 0xffff on 486's */ if (ep->r0) printf ("warning: reserved0 is 0x%x\n", ep->r0); if (ep->r1) @@ -1776,8 +1783,14 @@ print_387_status (status, ep) printf ("warning: reserved2 is 0x%x\n", ep->r2); if (ep->r3) printf ("warning: reserved3 is 0x%x\n", ep->r3); +#endif } +#ifdef __386BSD__ +#define fpstate save87 +#define U_FPSTATE(u) u.u_pcb.pcb_savefpu +#endif + #ifndef U_FPSTATE #define U_FPSTATE(u) u.u_fpstate #endif @@ -1786,7 +1799,6 @@ i386_float_info () { struct user u; /* just for address computations */ int i; -#ifndef __386BSD__ /* fpstate defined in */ struct fpstate *fpstatep; char buf[sizeof (struct fpstate) + 2 * sizeof (int)]; @@ -1797,6 +1809,7 @@ i386_float_info () extern int corechan; int skip; +#ifndef __386BSD__ /* XXX - look at pcb flags */ uaddr = (char *)&u.u_fpvalid - (char *)&u; if (have_inferior_p()) { @@ -1804,7 +1817,7 @@ i386_float_info () unsigned int mask; rounded_addr = uaddr & -sizeof (int); - data = ptrace (3, inferior_pid, rounded_addr, 0); + data = ptrace (PT_READ_U, inferior_pid, (caddr_t)rounded_addr, 0); mask = 0xff << ((uaddr - rounded_addr) * 8); fpvalid = ((data & mask) != 0); @@ -1823,6 +1836,7 @@ i386_float_info () printf ("no floating point status saved\n"); return; } +#endif /* not __386BSD__ */ uaddr = (char *)&U_FPSTATE(u) - (char *)&u; if (have_inferior_p ()) @@ -1837,7 +1851,7 @@ i386_float_info () ip = (int *)buf; for (i = 0; i < rounded_size; i++) { - *ip++ = ptrace (3, inferior_pid, rounded_addr, 0); + *ip++ = ptrace (PT_READ_U, inferior_pid, (caddr_t)rounded_addr, 0); rounded_addr += sizeof (int); } } @@ -1850,6 +1864,9 @@ i386_float_info () skip = 0; } +#ifdef __386BSD__ + print_387_status (0, (struct env387 *)buf); +#else fpstatep = (struct fpstate *)(buf + skip); print_387_status (fpstatep->status, (struct env387 *)fpstatep->state); #endif