static int sparc64nbsd_supply_pcb (struct regcache *regcache, struct pcb *pcb) { u_int64_t state; int regnum; /* The following is true for NetBSD 1.6.2: The pcb contains %sp and %pc, %pstate and %cwp. From this information we reconstruct the register state as it would look when we just returned from cpu_switch(). */ /* The stack pointer shouldn't be zero. */ if (pcb->pcb_sp == 0) return 0; /* If the program counter is zero, this is probably a core dump, and we can get %pc from the stack. */ if (pcb->pcb_pc == 0) read_memory(pcb->pcb_sp + BIAS - 176 + (11 * 8), (gdb_byte *)&pcb->pcb_pc, sizeof pcb->pcb_pc); regcache_raw_supply (regcache, SPARC_SP_REGNUM, &pcb->pcb_sp); regcache_raw_supply (regcache, SPARC64_PC_REGNUM, &pcb->pcb_pc); state = pcb->pcb_pstate << 8 | pcb->pcb_cwp; regcache_raw_supply (regcache, SPARC64_STATE_REGNUM, &state); sparc_supply_rwindow (regcache, pcb->pcb_sp, -1); return 1; }
static int sparc64fbsd_kvm_supply_pcb (struct regcache *regcache, struct pcb *pcb) { /* The following is true for FreeBSD 5.4: The pcb contains %sp and %pc. Since the register windows are explicitly flushed, we can find the `local' and `in' registers on the stack. */ /* The stack pointer shouldn't be zero. */ if (pcb->pcb_sp == 0) return 0; regcache_raw_supply (regcache, SPARC_SP_REGNUM, &pcb->pcb_sp); regcache_raw_supply (regcache, SPARC64_PC_REGNUM, &pcb->pcb_pc); /* Synthesize %npc. */ pcb->pcb_pc += 4; regcache_raw_supply (regcache, SPARC64_NPC_REGNUM, &pcb->pcb_pc); /* Read `local' and `in' registers from the stack. */ sparc_supply_rwindow (regcache, pcb->pcb_sp, -1); return 1; }
static void sparc64fbsd_supply_pcb(struct regcache *regcache, CORE_ADDR pcb_addr) { struct pcb pcb; if (target_read_memory(pcb_addr, &pcb, sizeof(pcb)) != 0) memset(&pcb, 0, sizeof(pcb)); regcache_raw_supply(regcache, SPARC_SP_REGNUM, (char *)&pcb.pcb_sp); sparc_supply_rwindow(regcache, pcb.pcb_sp, -1); regcache_raw_supply(regcache, SPARC64_PC_REGNUM, (char *)&pcb.pcb_pc); pcb.pcb_pc += 4; regcache_raw_supply(regcache, SPARC64_NPC_REGNUM, (char *)&pcb.pcb_pc); }
static void sparc32obsd_supply_uthread (struct regcache *regcache, int regnum, CORE_ADDR addr) { struct gdbarch *gdbarch = get_regcache_arch (regcache); enum bfd_endian byte_order = gdbarch_byte_order (gdbarch); CORE_ADDR fp, fp_addr = addr + SPARC32OBSD_UTHREAD_FP_OFFSET; gdb_byte buf[4]; gdb_assert (regnum >= -1); fp = read_memory_unsigned_integer (fp_addr, 4, byte_order); if (regnum == SPARC_SP_REGNUM || regnum == -1) { store_unsigned_integer (buf, 4, byte_order, fp); regcache_raw_supply (regcache, SPARC_SP_REGNUM, buf); if (regnum == SPARC_SP_REGNUM) return; } if (regnum == SPARC32_PC_REGNUM || regnum == SPARC32_NPC_REGNUM || regnum == -1) { CORE_ADDR i7, i7_addr = addr + SPARC32OBSD_UTHREAD_PC_OFFSET; i7 = read_memory_unsigned_integer (i7_addr, 4, byte_order); if (regnum == SPARC32_PC_REGNUM || regnum == -1) { store_unsigned_integer (buf, 4, byte_order, i7 + 8); regcache_raw_supply (regcache, SPARC32_PC_REGNUM, buf); } if (regnum == SPARC32_NPC_REGNUM || regnum == -1) { store_unsigned_integer (buf, 4, byte_order, i7 + 12); regcache_raw_supply (regcache, SPARC32_NPC_REGNUM, buf); } if (regnum == SPARC32_PC_REGNUM || regnum == SPARC32_NPC_REGNUM) return; } sparc_supply_rwindow (regcache, fp, regnum); }
static void sparc64obsd_supply_uthread (struct regcache *regcache, int regnum, CORE_ADDR addr) { CORE_ADDR fp, fp_addr = addr + SPARC64OBSD_UTHREAD_FP_OFFSET; gdb_byte buf[8]; gdb_assert (regnum >= -1); fp = read_memory_unsigned_integer (fp_addr, 8); if (regnum == SPARC_SP_REGNUM || regnum == -1) { store_unsigned_integer (buf, 8, fp); regcache_raw_supply (regcache, SPARC_SP_REGNUM, buf); if (regnum == SPARC_SP_REGNUM) return; } if (regnum == SPARC64_PC_REGNUM || regnum == SPARC64_NPC_REGNUM || regnum == -1) { CORE_ADDR i7, i7_addr = addr + SPARC64OBSD_UTHREAD_PC_OFFSET; i7 = read_memory_unsigned_integer (i7_addr, 8); if (regnum == SPARC64_PC_REGNUM || regnum == -1) { store_unsigned_integer (buf, 8, i7 + 8); regcache_raw_supply (regcache, SPARC64_PC_REGNUM, buf); } if (regnum == SPARC64_NPC_REGNUM || regnum == -1) { store_unsigned_integer (buf, 8, i7 + 12); regcache_raw_supply (regcache, SPARC64_NPC_REGNUM, buf); } if (regnum == SPARC64_PC_REGNUM || regnum == SPARC64_NPC_REGNUM) return; } sparc_supply_rwindow (regcache, fp, regnum); }
void kgdb_trgt_fetch_registers(int regno __unused) { struct kthr *kt; struct pcb pcb; kt = kgdb_thr_lookup_tid(ptid_get_pid(inferior_ptid)); if (kt == NULL) return; if (kvm_read(kvm, kt->pcb, &pcb, sizeof(pcb)) != sizeof(pcb)) { warnx("kvm_read: %s", kvm_geterr(kvm)); memset(&pcb, 0, sizeof(pcb)); } supply_register(SPARC_SP_REGNUM, (char *)&pcb.pcb_sp); sparc_supply_rwindow(current_regcache, pcb.pcb_sp, -1); supply_register(SPARC64_PC_REGNUM, (char *)&pcb.pcb_pc); pcb.pcb_pc += 4; supply_register(SPARC64_NPC_REGNUM, (char *)&pcb.pcb_pc); }
static int sparc32nbsd_supply_pcb (struct regcache *regcache, struct pcb *pcb) { /* The following is true for NetBSD 1.6.2: The pcb contains %sp, %pc, %psr and %wim. From this information we reconstruct the register state as it would look when we just returned from cpu_switch(). */ /* The stack pointer shouldn't be zero. */ if (pcb->pcb_sp == 0) return 0; regcache_raw_supply (regcache, SPARC_SP_REGNUM, &pcb->pcb_sp); regcache_raw_supply (regcache, SPARC_O7_REGNUM, &pcb->pcb_pc); regcache_raw_supply (regcache, SPARC32_PSR_REGNUM, &pcb->pcb_psr); regcache_raw_supply (regcache, SPARC32_WIM_REGNUM, &pcb->pcb_wim); regcache_raw_supply (regcache, SPARC32_PC_REGNUM, &pcb->pcb_pc); sparc_supply_rwindow (regcache, pcb->pcb_sp, -1); return 1; }
void sparc32_supply_gregset (const struct sparc_gregset *gregset, struct regcache *regcache, int regnum, const void *gregs) { const gdb_byte *regs = gregs; int i; if (regnum == SPARC32_PSR_REGNUM || regnum == -1) regcache_raw_supply (regcache, SPARC32_PSR_REGNUM, regs + gregset->r_psr_offset); if (regnum == SPARC32_PC_REGNUM || regnum == -1) regcache_raw_supply (regcache, SPARC32_PC_REGNUM, regs + gregset->r_pc_offset); if (regnum == SPARC32_NPC_REGNUM || regnum == -1) regcache_raw_supply (regcache, SPARC32_NPC_REGNUM, regs + gregset->r_npc_offset); if (regnum == SPARC32_Y_REGNUM || regnum == -1) regcache_raw_supply (regcache, SPARC32_Y_REGNUM, regs + gregset->r_y_offset); if (regnum == SPARC_G0_REGNUM || regnum == -1) regcache_raw_supply (regcache, SPARC_G0_REGNUM, NULL); if ((regnum >= SPARC_G1_REGNUM && regnum <= SPARC_O7_REGNUM) || regnum == -1) { int offset = gregset->r_g1_offset; for (i = SPARC_G1_REGNUM; i <= SPARC_O7_REGNUM; i++) { if (regnum == i || regnum == -1) regcache_raw_supply (regcache, i, regs + offset); offset += 4; } } if ((regnum >= SPARC_L0_REGNUM && regnum <= SPARC_I7_REGNUM) || regnum == -1) { /* Not all of the register set variants include Locals and Inputs. For those that don't, we read them off the stack. */ if (gregset->r_l0_offset == -1) { ULONGEST sp; regcache_cooked_read_unsigned (regcache, SPARC_SP_REGNUM, &sp); sparc_supply_rwindow (regcache, sp, regnum); } else { int offset = gregset->r_l0_offset; for (i = SPARC_L0_REGNUM; i <= SPARC_I7_REGNUM; i++) { if (regnum == i || regnum == -1) regcache_raw_supply (regcache, i, regs + offset); offset += 4; } } } }