From 92106c7ab8218e88fc8ecb87b8564725e6f26e0c Mon Sep 17 00:00:00 2001 From: Alex Williamson Date: Fri, 21 Sep 2007 12:54:11 -0600 Subject: [PATCH] [IA64] Linux support for debug_op hypercall Signed-off-by: Tristan Gingold --- arch/ia64/xen/xcom_privcmd.c | 32 +++++++++++- include/asm-ia64/hypercall.h | 8 +++ include/xen/interface/arch-ia64.h | 86 ++++++++++++++++++++++++++++--- 3 files changed, 118 insertions(+), 8 deletions(-) diff --git a/arch/ia64/xen/xcom_privcmd.c b/arch/ia64/xen/xcom_privcmd.c index 641bb9ed..57cbf110 100644 --- a/arch/ia64/xen/xcom_privcmd.c +++ b/arch/ia64/xen/xcom_privcmd.c @@ -713,7 +713,7 @@ xencomm_privcmd_ia64_dom0vp_op(privcmd_hypercall_t *hypercall) { int cmd = hypercall->arg[0]; int ret; - + switch (cmd) { case IA64_DOM0VP_fpswa_revision: { unsigned int revision; @@ -745,6 +745,34 @@ xencomm_privcmd_ia64_dom0vp_op(privcmd_hypercall_t *hypercall) return ret; } +static int +xencomm_privcmd_ia64_debug_op(privcmd_hypercall_t *hypercall) +{ + int cmd = hypercall->arg[0]; + unsigned long domain = hypercall->arg[1]; + struct xencomm_handle *desc; + int ret; + + switch (cmd) { + case XEN_IA64_DEBUG_OP_SET_FLAGS: + case XEN_IA64_DEBUG_OP_GET_FLAGS: + break; + default: + printk("%s: unknown IA64 DEBUGOP %d\n", __func__, cmd); + return -EINVAL; + } + + desc = xencomm_map((void *)hypercall->arg[2], + sizeof(xen_ia64_debug_op_t)); + if (desc == NULL) + return -ENOMEM; + + ret = xencomm_arch_hypercall_ia64_debug_op(cmd, domain, desc); + + xencomm_free(desc); + return ret; +} + int privcmd_hypercall(privcmd_hypercall_t *hypercall) { @@ -769,6 +797,8 @@ privcmd_hypercall(privcmd_hypercall_t *hypercall) return xencomm_privcmd_sched_op(hypercall); case __HYPERVISOR_ia64_dom0vp_op: return xencomm_privcmd_ia64_dom0vp_op(hypercall); + case __HYPERVISOR_ia64_debug_op: + return xencomm_privcmd_ia64_debug_op(hypercall); default: printk("%s: unknown hcall (%ld)\n", __func__, hypercall->op); return -ENOSYS; diff --git a/include/asm-ia64/hypercall.h b/include/asm-ia64/hypercall.h index 917e5241..2dacdce3 100644 --- a/include/asm-ia64/hypercall.h +++ b/include/asm-ia64/hypercall.h @@ -409,6 +409,14 @@ xencomm_arch_hypercall_fpswa_revision(struct xencomm_handle *arg) IA64_DOM0VP_fpswa_revision, arg); } +static inline int +xencomm_arch_hypercall_ia64_debug_op(unsigned long cmd, + unsigned long domain, + struct xencomm_handle *arg) +{ + return _hypercall3(int, ia64_debug_op, cmd, domain, arg); +} + static inline int HYPERVISOR_add_io_space(unsigned long phys_base, unsigned long sparse, diff --git a/include/xen/interface/arch-ia64.h b/include/xen/interface/arch-ia64.h index 8d1da899..29e2fafd 100644 --- a/include/xen/interface/arch-ia64.h +++ b/include/xen/interface/arch-ia64.h @@ -236,8 +236,7 @@ struct mapped_regs { int banknum; // 0 or 1, which virtual register bank is active unsigned long rrs[8]; // region registers unsigned long krs[8]; // kernel registers - unsigned long pkrs[8]; // protection key registers - unsigned long tmp[8]; // temp registers (e.g. for hyperprivops) + unsigned long tmp[16]; // temp registers (e.g. for hyperprivops) }; }; }; @@ -294,6 +293,8 @@ struct ia64_tr_entry { unsigned long vadr; unsigned long rid; }; +typedef struct ia64_tr_entry ia64_tr_entry_t; +DEFINE_XEN_GUEST_HANDLE(ia64_tr_entry_t); struct vcpu_tr_regs { struct ia64_tr_entry itrs[8]; @@ -557,15 +558,86 @@ struct xen_ia64_boot_param { /* Fast and light hypercalls. */ #define __HYPERVISOR_ia64_fast_eoi __HYPERVISOR_arch_1 +/* Extra debug features. */ +#define __HYPERVISOR_ia64_debug_op __HYPERVISOR_arch_2 + +/* Set/Get extra conditions to break. */ +#define XEN_IA64_DEBUG_OP_SET_FLAGS 1 +#define XEN_IA64_DEBUG_OP_GET_FLAGS 2 + +/* Break on kernel single step. */ +#define XEN_IA64_DEBUG_ON_KERN_SSTEP (1 << 0) + +/* Break on kernel debug (breakpoint or watch point). */ +#define XEN_IA64_DEBUG_ON_KERN_DEBUG (1 << 1) + +/* Break on kernel taken branch. */ +#define XEN_IA64_DEBUG_ON_KERN_TBRANCH (1 << 2) + +/* Break on interrupt injection. */ +#define XEN_IA64_DEBUG_ON_EXTINT (1 << 3) + +/* Break on interrupt injection. */ +#define XEN_IA64_DEBUG_ON_EXCEPT (1 << 4) + +/* Break on event injection. */ +#define XEN_IA64_DEBUG_ON_EVENT (1 << 5) + +/* Break on privop/virtualized instruction (slow path only). */ +#define XEN_IA64_DEBUG_ON_PRIVOP (1 << 6) + +/* Break on emulated PAL call (at entry). */ +#define XEN_IA64_DEBUG_ON_PAL (1 << 7) + +/* Break on emulated SAL call (at entry). */ +#define XEN_IA64_DEBUG_ON_SAL (1 << 8) + +/* Break on emulated EFI call (at entry). */ +#define XEN_IA64_DEBUG_ON_EFI (1 << 9) + +/* Break on rfi emulation (slow path only, before exec). */ +#define XEN_IA64_DEBUG_ON_RFI (1 << 10) + +/* Break on address translation switch. */ +#define XEN_IA64_DEBUG_ON_MMU (1 << 11) + +/* Break on bad guest physical address. */ +#define XEN_IA64_DEBUG_ON_BAD_MPA (1 << 12) + +/* Force psr.ss bit. */ +#define XEN_IA64_DEBUG_FORCE_SS (1 << 13) + +/* Force psr.db bit. */ +#define XEN_IA64_DEBUG_FORCE_DB (1 << 14) + +/* Break on ITR/PTR. */ +#define XEN_IA64_DEBUG_ON_TR (1 << 15) + +/* Break on ITC/PTC.L/PTC.G/PTC.GA. */ +#define XEN_IA64_DEBUG_ON_TC (1 << 16) + +/* Get translation cache. */ +#define XEN_IA64_DEBUG_OP_GET_TC 3 + +/* Translate virtual address to guest physical address. */ +#define XEN_IA64_DEBUG_OP_TRANSLATE 4 + +#ifndef __ASSEMBLY__ +union xen_ia64_debug_op { + uint64_t flags; + struct xen_ia64_debug_vtlb { + uint64_t nbr; /* IN/OUT */ + XEN_GUEST_HANDLE_64(ia64_tr_entry_t) tr; /* IN/OUT */ + } vtlb; +}; +typedef union xen_ia64_debug_op xen_ia64_debug_op_t; +DEFINE_XEN_GUEST_HANDLE(xen_ia64_debug_op_t); +#endif /* __ASSEMBLY__ */ + /* Xencomm macros. */ #define XENCOMM_INLINE_MASK 0xf800000000000000UL #define XENCOMM_INLINE_FLAG 0x8000000000000000UL -#define XENCOMM_IS_INLINE(addr) \ - (((unsigned long)(addr) & XENCOMM_INLINE_MASK) == XENCOMM_INLINE_FLAG) -#define XENCOMM_INLINE_ADDR(addr) \ - ((unsigned long)(addr) & ~XENCOMM_INLINE_MASK) - #ifndef __ASSEMBLY__ /* -- 2.39.5