int cmd_set(char **arg) { char *reg_text = get_arg(arg); char *val_text = get_arg(arg); int reg; address_t value = 0; address_t regs[DEVICE_NUM_REGS]; if (!(reg_text && val_text)) { printc_err("set: must specify a register and a value\n"); return -1; } reg = dis_reg_from_name(reg_text); if (reg < 0) { printc_err("set: unknown register: %s\n", reg_text); return -1; } if (expr_eval(val_text, &value) < 0) { printc_err("set: can't parse value: %s\n", val_text); return -1; } if (device_getregs(regs) < 0) return -1; regs[reg] = value; if (device_setregs(regs) < 0) return -1; show_regs(regs); return 0; }
static int run_final_status(struct gdb_data *data) { address_t regs[DEVICE_NUM_REGS]; int i; if (device_getregs(regs) < 0) return gdb_send(data, "E00"); gdb_packet_start(data); gdb_printf(data, "T05"); for (i = 0; i < 16; i++) { address_t value = regs[i]; int j; /* NOTE: this only gives GDB the lower 16 bits of each * register. It complains if we give the full data. */ gdb_printf(data, "%02x:", i); for (j = 0; j < 2; j++) { gdb_printf(data, "%02x", value & 0xff); value >>= 8; } gdb_printf(data, ";"); } gdb_packet_end(data); return gdb_flush_ack(data); }
static int run_set_pc(struct gdb_data *data, char *buf) { address_t regs[DEVICE_NUM_REGS]; if (!*buf) return 0; if (device_getregs(regs) < 0) return -1; regs[0] = strtoul(buf, NULL, 16); return device_setregs(regs); }
int cmd_run(char **arg) { device_status_t status; address_t regs[DEVICE_NUM_REGS]; (void)arg; if (device_getregs(regs) < 0) { printc_err("warning: device: can't fetch registers\n"); } else { int i; for (i = 0; i < device_default->max_breakpoints; i++) { struct device_breakpoint *bp = &device_default->breakpoints[i]; if ((bp->flags & DEVICE_BP_ENABLED) && bp->type == DEVICE_BPTYPE_BREAK && bp->addr == regs[0]) break; } if (i < device_default->max_breakpoints) { printc("Stepping over breakpoint #%d at 0x%04x\n", i, regs[0]); device_ctl(DEVICE_CTL_STEP); } } if (device_ctl(DEVICE_CTL_RUN) < 0) { printc_err("run: failed to start CPU\n"); return -1; } printc("Running. Press Ctrl+C to interrupt...\n"); do { status = device_poll(); } while (status == DEVICE_STATUS_RUNNING); if (status == DEVICE_STATUS_INTR) printc("\n"); if (status == DEVICE_STATUS_ERROR) return -1; if (device_ctl(DEVICE_CTL_HALT) < 0) return -1; return cmd_regs(NULL); }
static int read_registers(struct gdb_data *data) { address_t regs[DEVICE_NUM_REGS]; int i; printc("Reading registers\n"); if (device_getregs(regs) < 0) return gdb_send(data, "E00"); gdb_packet_start(data); for (i = 0; i < DEVICE_NUM_REGS; i++) gdb_printf(data, "%02x%02x", regs[i] & 0xff, (regs[i] >> 8) & 0xff); gdb_packet_end(data); return gdb_flush_ack(data); }
int cmd_regs(char **arg) { address_t regs[DEVICE_NUM_REGS]; uint8_t code[16]; int len = sizeof(code); (void)arg; if (device_getregs(regs) < 0) return -1; show_regs(regs); /* Try to disassemble the instruction at PC */ if (len > 0x10000 - regs[0]) len = 0x10000 - regs[0]; if (device_readmem(regs[0], code, len) < 0) return 0; disassemble(regs[0], (uint8_t *)code, len, device_default->power_buf); return 0; }