void gdb_arch_read_reg(unsigned long regnum, struct cpu_user_regs *regs, struct gdb_context *ctx) { struct gdb_callback_arg arg; unsigned long reg; struct pt_fpreg freg; char buf[16 * 2 + 1]; if (regnum >= NUM_REGS) { dbg_printk("%s: regnum %ld\n", __func__, regnum); goto out_err; } arg.regs = regs; arg.regnum = regnum; arg.reg = ® arg.freg = &freg; arg.error = 0; unw_init_running(&gdb_get_reg_callback, (void*)&arg); if (arg.error < 0) { dbg_printk("%s: gdb_get_reg_callback failed\n", __func__); goto out_err; } if (arg.error > 0) { // notify gdb that this register is not supported. // see fetch_register_using_p() in gdb/remote.c. safe_strcpy(buf, "x"); } else if (IA64_FR0_REGNUM <= regnum && regnum <= IA64_FR0_REGNUM + 127) { snprintf(buf, sizeof(buf), "%.016lx", swab64(freg.u.bits[0])); snprintf(buf + 16, sizeof(buf) - 16, "%.016lx", swab64(freg.u.bits[1])); } else { snprintf(buf, sizeof(buf), "%.016lx", swab64(reg)); } out: return gdb_send_reply(buf, ctx); out_err: dbg_printk("Register read unsupported regnum = 0x%lx\n", regnum); safe_strcpy(buf, "E0"); goto out; }
irqreturn_t handle_IPI (int irq, void *dev_id) { int this_cpu = get_cpu(); unsigned long *pending_ipis = &__ia64_per_cpu_var(ipi_operation); unsigned long ops; mb(); /* */ while ((ops = xchg(pending_ipis, 0)) != 0) { mb(); /* */ do { unsigned long which; which = ffz(~ops); ops &= ~(1 << which); switch (which) { case IPI_CPU_STOP: stop_this_cpu(); break; case IPI_CALL_FUNC: generic_smp_call_function_interrupt(); break; case IPI_CALL_FUNC_SINGLE: generic_smp_call_function_single_interrupt(); break; #ifdef CONFIG_KEXEC case IPI_KDUMP_CPU_STOP: unw_init_running(kdump_cpu_freeze, NULL); break; #endif default: printk(KERN_CRIT "Unknown IPI on CPU %d: %lu\n", this_cpu, which); break; } } while (ops); mb(); /* */ } put_cpu(); return IRQ_HANDLED; }
void ia64_backtrace(struct pt_regs * const regs, unsigned int depth) { ia64_backtrace_t bt; unsigned long flags; /* */ if (user_mode(regs)) return; bt.depth = depth; bt.regs = regs; bt.prev_pfs_loc = NULL; local_irq_save(flags); unw_init_running(do_ia64_backtrace, &bt); local_irq_restore(flags); }
void ia64_backtrace(struct pt_regs * const regs, unsigned int depth) { ia64_backtrace_t bt; unsigned long flags; /* * On IA64 there is little hope of getting backtraces from * user space programs -- the problems of getting the unwind * information from arbitrary user programs are extreme. */ if (user_mode(regs)) return; bt.depth = depth; bt.regs = regs; bt.prev_pfs_loc = NULL; local_irq_save(flags); unw_init_running(do_ia64_backtrace, &bt); local_irq_restore(flags); }
void machine_kexec(struct kimage *image) { BUG_ON(!image); unw_init_running(ia64_machine_kexec, image); for(;;); }
/* * Save stack-backtrace addresses into a stack_trace buffer. */ void save_stack_trace(struct stack_trace *trace) { unw_init_running(ia64_do_save_stack, trace); }
void machine_kexec(xen_kexec_image_t *image) { machine_shutdown(); unw_init_running(ia64_machine_kexec, image); for(;;); }