void sparc_fetch_inferior_registers (struct target_ops *ops, struct regcache *regcache, int regnum) { struct gdbarch *gdbarch = get_regcache_arch (regcache); int pid; /* NOTE: cagney/2002-12-03: This code assumes that the currently selected light weight processes' registers can be written directly into the selected thread's register cache. This works fine when given an 1:1 LWP:thread model (such as found on GNU/Linux) but will, likely, have problems when used on an N:1 (userland threads) or N:M (userland multiple LWP) model. In the case of the latter two, the LWP's registers do not necessarily belong to the selected thread (the LWP could be in the middle of executing the thread switch code). These functions should instead be paramaterized with an explicit object (struct regcache, struct thread_info?) into which the LWPs registers can be written. */ pid = TIDGET (inferior_ptid); if (pid == 0) pid = PIDGET (inferior_ptid); if (regnum == SPARC_G0_REGNUM) { gdb_byte zero[8] = { 0 }; regcache_raw_supply (regcache, SPARC_G0_REGNUM, &zero); return; } if (regnum == -1 || sparc_gregset_supplies_p (gdbarch, regnum)) { gregset_t regs; if (ptrace (PTRACE_GETREGS, pid, (PTRACE_TYPE_ARG3) ®s, 0) == -1) perror_with_name (_("Couldn't get registers")); sparc_supply_gregset (sparc_gregset, regcache, -1, ®s); if (regnum != -1) return; } if (regnum == -1 || sparc_fpregset_supplies_p (gdbarch, regnum)) { fpregset_t fpregs; if (ptrace (PTRACE_GETFPREGS, pid, (PTRACE_TYPE_ARG3) &fpregs, 0) == -1) perror_with_name (_("Couldn't get floating point status")); sparc_supply_fpregset (regcache, -1, &fpregs); } }
void sparc_store_inferior_registers (struct target_ops *ops, struct regcache *regcache, int regnum) { struct gdbarch *gdbarch = get_regcache_arch (regcache); int pid; /* NOTE: cagney/2002-12-02: See comment in fetch_inferior_registers about threaded assumptions. */ pid = TIDGET (inferior_ptid); if (pid == 0) pid = PIDGET (inferior_ptid); if (regnum == -1 || sparc_gregset_supplies_p (gdbarch, regnum)) { gregset_t regs; if (ptrace (PTRACE_GETREGS, pid, (PTRACE_TYPE_ARG3) ®s, 0) == -1) perror_with_name (_("Couldn't get registers")); sparc_collect_gregset (sparc_gregset, regcache, regnum, ®s); if (ptrace (PTRACE_SETREGS, pid, (PTRACE_TYPE_ARG3) ®s, 0) == -1) perror_with_name (_("Couldn't write registers")); /* Deal with the stack regs. */ if (regnum == -1 || regnum == SPARC_SP_REGNUM || (regnum >= SPARC_L0_REGNUM && regnum <= SPARC_I7_REGNUM)) { ULONGEST sp; regcache_cooked_read_unsigned (regcache, SPARC_SP_REGNUM, &sp); sparc_collect_rwindow (regcache, sp, regnum); } if (regnum != -1) return; } if (regnum == -1 || sparc_fpregset_supplies_p (gdbarch, regnum)) { fpregset_t fpregs, saved_fpregs; if (ptrace (PTRACE_GETFPREGS, pid, (PTRACE_TYPE_ARG3) &fpregs, 0) == -1) perror_with_name (_("Couldn't get floating-point registers")); memcpy (&saved_fpregs, &fpregs, sizeof (fpregs)); sparc_collect_fpregset (regcache, regnum, &fpregs); /* Writing the floating-point registers will fail on NetBSD with EINVAL if the inferior process doesn't have an FPU state (i.e. if it didn't use the FPU yet). Therefore we don't try to write the registers if nothing changed. */ if (memcmp (&saved_fpregs, &fpregs, sizeof (fpregs)) != 0) { if (ptrace (PTRACE_SETFPREGS, pid, (PTRACE_TYPE_ARG3) &fpregs, 0) == -1) perror_with_name (_("Couldn't write floating-point registers")); } if (regnum != -1) return; } }