diff options
author | kmacy <kmacy@FreeBSD.org> | 2008-09-26 05:29:39 +0000 |
---|---|---|
committer | kmacy <kmacy@FreeBSD.org> | 2008-09-26 05:29:39 +0000 |
commit | 3d2b6bb54b8a411bb970da8c076cad33f16eba7a (patch) | |
tree | c6c485e78e0fbd30ce865ac6ee34c847120931a3 /sys/xen/interface | |
parent | 966196697e0d67be61d85d4d9f9039a772c7cc2c (diff) | |
download | FreeBSD-src-3d2b6bb54b8a411bb970da8c076cad33f16eba7a.zip FreeBSD-src-3d2b6bb54b8a411bb970da8c076cad33f16eba7a.tar.gz |
Update xen/interface includes to the latest in mercurial
MFC after: 1 month
Diffstat (limited to 'sys/xen/interface')
31 files changed, 1919 insertions, 704 deletions
diff --git a/sys/xen/interface/arch-ia64.h b/sys/xen/interface/arch-ia64.h index a9afa3b..0c43cee 100644 --- a/sys/xen/interface/arch-ia64.h +++ b/sys/xen/interface/arch-ia64.h @@ -23,18 +23,28 @@ * */ +#include "xen.h" + #ifndef __HYPERVISOR_IF_IA64_H__ #define __HYPERVISOR_IF_IA64_H__ +#if !defined(__GNUC__) || defined(__STRICT_ANSI__) +#error "Anonymous structs/unions are a GNU extension." +#endif + /* Structural guest handles introduced in 0x00030201. */ #if __XEN_INTERFACE_VERSION__ >= 0x00030201 -#define __DEFINE_XEN_GUEST_HANDLE(name, type) \ +#define ___DEFINE_XEN_GUEST_HANDLE(name, type) \ typedef struct { type *p; } __guest_handle_ ## name #else -#define __DEFINE_XEN_GUEST_HANDLE(name, type) \ +#define ___DEFINE_XEN_GUEST_HANDLE(name, type) \ typedef type * __guest_handle_ ## name #endif +#define __DEFINE_XEN_GUEST_HANDLE(name, type) \ + ___DEFINE_XEN_GUEST_HANDLE(name, type); \ + ___DEFINE_XEN_GUEST_HANDLE(const_##name, const type) + #define DEFINE_XEN_GUEST_HANDLE(name) __DEFINE_XEN_GUEST_HANDLE(name, name) #define XEN_GUEST_HANDLE(name) __guest_handle_ ## name #define XEN_GUEST_HANDLE_64(name) XEN_GUEST_HANDLE(name) @@ -45,18 +55,7 @@ #endif #ifndef __ASSEMBLY__ -/* Guest handles for primitive C types. */ -__DEFINE_XEN_GUEST_HANDLE(uchar, unsigned char); -__DEFINE_XEN_GUEST_HANDLE(uint, unsigned int); -__DEFINE_XEN_GUEST_HANDLE(ulong, unsigned long); -__DEFINE_XEN_GUEST_HANDLE(u64, unsigned long); -DEFINE_XEN_GUEST_HANDLE(char); -DEFINE_XEN_GUEST_HANDLE(int); -DEFINE_XEN_GUEST_HANDLE(long); -DEFINE_XEN_GUEST_HANDLE(void); - typedef unsigned long xen_pfn_t; -DEFINE_XEN_GUEST_HANDLE(xen_pfn_t); #define PRI_xen_pfn "lx" #endif @@ -69,55 +68,21 @@ DEFINE_XEN_GUEST_HANDLE(xen_pfn_t); /* WARNING: before changing this, check that shared_info fits on a page */ #define MAX_VIRT_CPUS 64 +/* IO ports location for PV. */ +#define IO_PORTS_PADDR 0x00000ffffc000000UL +#define IO_PORTS_SIZE 0x0000000004000000UL + #ifndef __ASSEMBLY__ typedef unsigned long xen_ulong_t; -#define INVALID_MFN (~0UL) - -#define MEM_G (1UL << 30) -#define MEM_M (1UL << 20) -#define MEM_K (1UL << 10) - -#define MMIO_START (3 * MEM_G) -#define MMIO_SIZE (512 * MEM_M) - -#define VGA_IO_START 0xA0000UL -#define VGA_IO_SIZE 0x20000 - -#define LEGACY_IO_START (MMIO_START + MMIO_SIZE) -#define LEGACY_IO_SIZE (64*MEM_M) - -#define IO_PAGE_START (LEGACY_IO_START + LEGACY_IO_SIZE) -#define IO_PAGE_SIZE PAGE_SIZE - -#define STORE_PAGE_START (IO_PAGE_START + IO_PAGE_SIZE) -#define STORE_PAGE_SIZE PAGE_SIZE - -#define BUFFER_IO_PAGE_START (STORE_PAGE_START+STORE_PAGE_SIZE) -#define BUFFER_IO_PAGE_SIZE PAGE_SIZE - -#define BUFFER_PIO_PAGE_START (BUFFER_IO_PAGE_START+BUFFER_IO_PAGE_SIZE) -#define BUFFER_PIO_PAGE_SIZE PAGE_SIZE - -#define IO_SAPIC_START 0xfec00000UL -#define IO_SAPIC_SIZE 0x100000 - -#define PIB_START 0xfee00000UL -#define PIB_SIZE 0x200000 - -#define GFW_START (4*MEM_G -16*MEM_M) -#define GFW_SIZE (16*MEM_M) - -/* Nvram belongs to GFW memory space */ -#define NVRAM_SIZE (MEM_K * 64) -#define NVRAM_START (GFW_START + 10 * MEM_M) +#ifdef __XEN_TOOLS__ +#define XEN_PAGE_SIZE XC_PAGE_SIZE +#else +#define XEN_PAGE_SIZE PAGE_SIZE +#endif -#define NVRAM_VALID_SIG 0x4650494e45584948 // "HIXENIPF" -struct nvram_save_addr { - unsigned long addr; - unsigned long signature; -}; +#define INVALID_MFN (~0UL) struct pt_fpreg { union { @@ -126,83 +91,6 @@ struct pt_fpreg { } u; }; -struct cpu_user_regs { - /* The following registers are saved by SAVE_MIN: */ - unsigned long b6; /* scratch */ - unsigned long b7; /* scratch */ - - unsigned long ar_csd; /* used by cmp8xchg16 (scratch) */ - unsigned long ar_ssd; /* reserved for future use (scratch) */ - - unsigned long r8; /* scratch (return value register 0) */ - unsigned long r9; /* scratch (return value register 1) */ - unsigned long r10; /* scratch (return value register 2) */ - unsigned long r11; /* scratch (return value register 3) */ - - unsigned long cr_ipsr; /* interrupted task's psr */ - unsigned long cr_iip; /* interrupted task's instruction pointer */ - unsigned long cr_ifs; /* interrupted task's function state */ - - unsigned long ar_unat; /* interrupted task's NaT register (preserved) */ - unsigned long ar_pfs; /* prev function state */ - unsigned long ar_rsc; /* RSE configuration */ - /* The following two are valid only if cr_ipsr.cpl > 0: */ - unsigned long ar_rnat; /* RSE NaT */ - unsigned long ar_bspstore; /* RSE bspstore */ - - unsigned long pr; /* 64 predicate registers (1 bit each) */ - unsigned long b0; /* return pointer (bp) */ - unsigned long loadrs; /* size of dirty partition << 16 */ - - unsigned long r1; /* the gp pointer */ - unsigned long r12; /* interrupted task's memory stack pointer */ - unsigned long r13; /* thread pointer */ - - unsigned long ar_fpsr; /* floating point status (preserved) */ - unsigned long r15; /* scratch */ - - /* The remaining registers are NOT saved for system calls. */ - - unsigned long r14; /* scratch */ - unsigned long r2; /* scratch */ - unsigned long r3; /* scratch */ - unsigned long r16; /* scratch */ - unsigned long r17; /* scratch */ - unsigned long r18; /* scratch */ - unsigned long r19; /* scratch */ - unsigned long r20; /* scratch */ - unsigned long r21; /* scratch */ - unsigned long r22; /* scratch */ - unsigned long r23; /* scratch */ - unsigned long r24; /* scratch */ - unsigned long r25; /* scratch */ - unsigned long r26; /* scratch */ - unsigned long r27; /* scratch */ - unsigned long r28; /* scratch */ - unsigned long r29; /* scratch */ - unsigned long r30; /* scratch */ - unsigned long r31; /* scratch */ - unsigned long ar_ccv; /* compare/exchange value (scratch) */ - - /* - * Floating point registers that the kernel considers scratch: - */ - struct pt_fpreg f6; /* scratch */ - struct pt_fpreg f7; /* scratch */ - struct pt_fpreg f8; /* scratch */ - struct pt_fpreg f9; /* scratch */ - struct pt_fpreg f10; /* scratch */ - struct pt_fpreg f11; /* scratch */ - unsigned long r4; /* preserved */ - unsigned long r5; /* preserved */ - unsigned long r6; /* preserved */ - unsigned long r7; /* preserved */ - unsigned long eml_unat; /* used for emulating instruction */ - unsigned long pad0; /* alignment pad */ - -}; -typedef struct cpu_user_regs cpu_user_regs_t; - union vac { unsigned long value; struct { @@ -309,8 +197,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) }; }; }; @@ -328,6 +215,21 @@ struct arch_vcpu_info { }; typedef struct arch_vcpu_info arch_vcpu_info_t; +/* + * This structure is used for magic page in domain pseudo physical address + * space and the result of XENMEM_machine_memory_map. + * As the XENMEM_machine_memory_map result, + * xen_memory_map::nr_entries indicates the size in bytes + * including struct xen_ia64_memmap_info. Not the number of entries. + */ +struct xen_ia64_memmap_info { + uint64_t efi_memmap_size; /* size of EFI memory map */ + uint64_t efi_memdesc_size; /* size of an EFI memory map descriptor */ + uint32_t efi_memdesc_version; /* memory descriptor version */ + void *memdesc[0]; /* array of efi_memory_desc_t */ +}; +typedef struct xen_ia64_memmap_info xen_ia64_memmap_info_t; + struct arch_shared_info { /* PFN of the start_info page. */ unsigned long start_info_pfn; @@ -335,7 +237,12 @@ struct arch_shared_info { /* Interrupt vector for event channel. */ int evtchn_vector; - uint64_t pad[32]; + /* PFN of memmap_info page */ + unsigned int memmap_info_num_pages;/* currently only = 1 case is + supported. */ + unsigned long memmap_info_pfn; + + uint64_t pad[31]; }; typedef struct arch_shared_info arch_shared_info_t; @@ -347,21 +254,154 @@ 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_extra_regs { - struct ia64_tr_entry itrs[8]; - struct ia64_tr_entry dtrs[8]; - unsigned long iva; - unsigned long dcr; - unsigned long event_callback_ip; +struct vcpu_tr_regs { + struct ia64_tr_entry itrs[12]; + struct ia64_tr_entry dtrs[12]; +}; + +union vcpu_ar_regs { + unsigned long ar[128]; + struct { + unsigned long kr[8]; + unsigned long rsv1[8]; + unsigned long rsc; + unsigned long bsp; + unsigned long bspstore; + unsigned long rnat; + unsigned long rsv2; + unsigned long fcr; + unsigned long rsv3[2]; + unsigned long eflag; + unsigned long csd; + unsigned long ssd; + unsigned long cflg; + unsigned long fsr; + unsigned long fir; + unsigned long fdr; + unsigned long rsv4; + unsigned long ccv; /* 32 */ + unsigned long rsv5[3]; + unsigned long unat; + unsigned long rsv6[3]; + unsigned long fpsr; + unsigned long rsv7[3]; + unsigned long itc; + unsigned long rsv8[3]; + unsigned long ign1[16]; + unsigned long pfs; /* 64 */ + unsigned long lc; + unsigned long ec; + unsigned long rsv9[45]; + unsigned long ign2[16]; + }; +}; + +union vcpu_cr_regs { + unsigned long cr[128]; + struct { + unsigned long dcr; // CR0 + unsigned long itm; + unsigned long iva; + unsigned long rsv1[5]; + unsigned long pta; // CR8 + unsigned long rsv2[7]; + unsigned long ipsr; // CR16 + unsigned long isr; + unsigned long rsv3; + unsigned long iip; + unsigned long ifa; + unsigned long itir; + unsigned long iipa; + unsigned long ifs; + unsigned long iim; // CR24 + unsigned long iha; + unsigned long rsv4[38]; + unsigned long lid; // CR64 + unsigned long ivr; + unsigned long tpr; + unsigned long eoi; + unsigned long irr[4]; + unsigned long itv; // CR72 + unsigned long pmv; + unsigned long cmcv; + unsigned long rsv5[5]; + unsigned long lrr0; // CR80 + unsigned long lrr1; + unsigned long rsv6[46]; + }; +}; + +struct vcpu_guest_context_regs { + unsigned long r[32]; + unsigned long b[8]; + unsigned long bank[16]; + unsigned long ip; + unsigned long psr; + unsigned long cfm; + unsigned long pr; + unsigned int nats; /* NaT bits for r1-r31. */ + unsigned int bnats; /* Nat bits for banked registers. */ + union vcpu_ar_regs ar; + union vcpu_cr_regs cr; + struct pt_fpreg f[128]; + unsigned long dbr[8]; + unsigned long ibr[8]; + unsigned long rr[8]; + unsigned long pkr[16]; + + /* FIXME: cpuid,pmd,pmc */ + + unsigned long xip; + unsigned long xpsr; + unsigned long xfs; + unsigned long xr[4]; + + struct vcpu_tr_regs tr; + + /* Physical registers in case of debug event. */ + unsigned long excp_iipa; + unsigned long excp_ifa; + unsigned long excp_isr; + unsigned int excp_vector; + + /* + * The rbs is intended to be the image of the stacked registers still + * in the cpu (not yet stored in memory). It is laid out as if it + * were written in memory at a 512 (64*8) aligned address + offset. + * rbs_voff is (offset / 8). rbs_nat contains NaT bits for the + * remaining rbs registers. rbs_rnat contains NaT bits for in memory + * rbs registers. + * Note: loadrs is 2**14 bytes == 2**11 slots. + */ + unsigned int rbs_voff; + unsigned long rbs[2048]; + unsigned long rbs_rnat; + + /* + * RSE.N_STACKED_PHYS via PAL_RSE_INFO + * Strictly this isn't cpu context, but this value is necessary + * for domain save/restore. So is here. + */ + unsigned long num_phys_stacked; }; struct vcpu_guest_context { -#define VGCF_EXTRA_REGS (1<<1) /* Get/Set extra regs. */ +#define VGCF_EXTRA_REGS (1UL << 1) /* Set extra regs. */ +#define VGCF_SET_CR_IRR (1UL << 2) /* Set cr_irr[0:3]. */ +#define VGCF_online (1UL << 3) /* make this vcpu online */ unsigned long flags; /* VGCF_* flags */ - struct cpu_user_regs user_regs; - struct vcpu_extra_regs extra_regs; + struct vcpu_guest_context_regs regs; + + unsigned long event_callback_ip; + + /* xen doesn't share privregs pages with hvm domain so that this member + * doesn't make sense for hvm domain. + * ~0UL is already used for INVALID_P2M_ENTRY. */ +#define VGC_PRIVREGS_HVM (~(-2UL)) unsigned long privregs_pfn; }; typedef struct vcpu_guest_context vcpu_guest_context_t; @@ -400,9 +440,19 @@ DEFINE_XEN_GUEST_HANDLE(vcpu_guest_context_t); /* gmfn version of IA64_DOM0VP_add_physmap */ #define IA64_DOM0VP_add_physmap_with_gmfn 9 +/* get fpswa revision */ +#define IA64_DOM0VP_fpswa_revision 10 + /* Add an I/O port space range */ #define IA64_DOM0VP_add_io_space 11 +/* expose the foreign domain's p2m table into privileged domain */ +#define IA64_DOM0VP_expose_foreign_p2m 12 +#define IA64_DOM0VP_EFP_ALLOC_PTE 0x1 /* allocate p2m table */ + +/* unexpose the foreign domain's p2m table into privileged domain */ +#define IA64_DOM0VP_unexpose_foreign_p2m 13 + // flags for page assignement to pseudo physical address space #define _ASSIGN_readonly 0 #define ASSIGN_readonly (1UL << _ASSIGN_readonly) @@ -416,6 +466,9 @@ DEFINE_XEN_GUEST_HANDLE(vcpu_guest_context_t); /* Internal only: associated with PGC_allocated bit */ #define _ASSIGN_pgc_allocated 3 #define ASSIGN_pgc_allocated (1UL << _ASSIGN_pgc_allocated) +/* Page is an IO page. */ +#define _ASSIGN_io 4 +#define ASSIGN_io (1UL << _ASSIGN_io) /* This structure has the same layout of struct ia64_boot_param, defined in <asm/system.h>. It is redefined here to ease use. */ @@ -477,19 +530,61 @@ struct xen_ia64_boot_param { #define HYPERPRIVOP_SET_EFLAG (HYPERPRIVOP_START + 0x16) #define HYPERPRIVOP_RSM_BE (HYPERPRIVOP_START + 0x17) #define HYPERPRIVOP_GET_PSR (HYPERPRIVOP_START + 0x18) -#define HYPERPRIVOP_MAX (0x19) +#define HYPERPRIVOP_SET_RR0_TO_RR4 (HYPERPRIVOP_START + 0x19) +#define HYPERPRIVOP_MAX (0x1a) /* Fast and light hypercalls. */ #define __HYPERVISOR_ia64_fast_eoi __HYPERVISOR_arch_1 +/* Extra debug features. */ +#define __HYPERVISOR_ia64_debug_op __HYPERVISOR_arch_2 + /* 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__ + +/* + * Optimization features. + * The hypervisor may do some special optimizations for guests. This hypercall + * can be used to switch on/of these special optimizations. + */ +#define __HYPERVISOR_opt_feature 0x700UL + +#define XEN_IA64_OPTF_OFF 0x0 +#define XEN_IA64_OPTF_ON 0x1 + +/* + * If this feature is switched on, the hypervisor inserts the + * tlb entries without calling the guests traphandler. + * This is useful in guests using region 7 for identity mapping + * like the linux kernel does. + */ +#define XEN_IA64_OPTF_IDENT_MAP_REG7 1 + +/* Identity mapping of region 4 addresses in HVM. */ +#define XEN_IA64_OPTF_IDENT_MAP_REG4 2 + +/* Identity mapping of region 5 addresses in HVM. */ +#define XEN_IA64_OPTF_IDENT_MAP_REG5 3 + +#define XEN_IA64_OPTF_IDENT_MAP_NOT_SET (0) + +struct xen_ia64_opt_feature { + unsigned long cmd; /* Which feature */ + unsigned char on; /* Switch feature on/off */ + union { + struct { + /* The page protection bit mask of the pte. + * This will be or'ed with the pte. */ + unsigned long pgprot; + unsigned long key; /* A protection key for itir. */ + }; + }; +}; + +#endif /* __ASSEMBLY__ */ /* xen perfmon */ #ifdef XEN @@ -509,6 +604,10 @@ DEFINE_XEN_GUEST_HANDLE(pfarg_load_t); #endif /* __ASSEMBLY__ */ #endif /* XEN */ +#ifndef __ASSEMBLY__ +#include "arch-ia64/hvm/memmap.h" +#endif + #endif /* __HYPERVISOR_IF_IA64_H__ */ /* diff --git a/sys/xen/interface/arch-powerpc.h b/sys/xen/interface/arch-powerpc.h index 82854d7..d92532f 100644 --- a/sys/xen/interface/arch-powerpc.h +++ b/sys/xen/interface/arch-powerpc.h @@ -22,15 +22,20 @@ * Authors: Hollis Blanchard <hollisb@us.ibm.com> */ +#include "xen.h" + #ifndef __XEN_PUBLIC_ARCH_PPC_64_H__ #define __XEN_PUBLIC_ARCH_PPC_64_H__ -#define __DEFINE_XEN_GUEST_HANDLE(name, type) \ +#define ___DEFINE_XEN_GUEST_HANDLE(name, type) \ typedef struct { \ int __pad[(sizeof (long long) - sizeof (void *)) / sizeof (int)]; \ type *p; \ } __attribute__((__aligned__(8))) __guest_handle_ ## name +#define __DEFINE_XEN_GUEST_HANDLE(name, type) \ + ___DEFINE_XEN_GUEST_HANDLE(name, type); \ + ___DEFINE_XEN_GUEST_HANDLE(const_##name, const type) #define DEFINE_XEN_GUEST_HANDLE(name) __DEFINE_XEN_GUEST_HANDLE(name, name) #define XEN_GUEST_HANDLE(name) __guest_handle_ ## name #define set_xen_guest_handle(hnd, val) \ @@ -45,17 +50,7 @@ #endif #ifndef __ASSEMBLY__ -/* Guest handles for primitive C types. */ -__DEFINE_XEN_GUEST_HANDLE(uchar, unsigned char); -__DEFINE_XEN_GUEST_HANDLE(uint, unsigned int); -__DEFINE_XEN_GUEST_HANDLE(ulong, unsigned long); -DEFINE_XEN_GUEST_HANDLE(char); -DEFINE_XEN_GUEST_HANDLE(int); -DEFINE_XEN_GUEST_HANDLE(long); -DEFINE_XEN_GUEST_HANDLE(void); - typedef unsigned long long xen_pfn_t; -DEFINE_XEN_GUEST_HANDLE(xen_pfn_t); #define PRI_xen_pfn "llx" #endif diff --git a/sys/xen/interface/arch-x86/cpuid.h b/sys/xen/interface/arch-x86/cpuid.h new file mode 100644 index 0000000..34fd72d --- /dev/null +++ b/sys/xen/interface/arch-x86/cpuid.h @@ -0,0 +1,68 @@ +/****************************************************************************** + * arch-x86/cpuid.h + * + * CPUID interface to Xen. + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to + * deal in the Software without restriction, including without limitation the + * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or + * sell copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER + * DEALINGS IN THE SOFTWARE. + * + * Copyright (c) 2007 Citrix Systems, Inc. + * + * Authors: + * Keir Fraser <keir.fraser@citrix.com> + */ + +#ifndef __XEN_PUBLIC_ARCH_X86_CPUID_H__ +#define __XEN_PUBLIC_ARCH_X86_CPUID_H__ + +/* Xen identification leaves start at 0x40000000. */ +#define XEN_CPUID_FIRST_LEAF 0x40000000 +#define XEN_CPUID_LEAF(i) (XEN_CPUID_FIRST_LEAF + (i)) + +/* + * Leaf 1 (0x40000000) + * EAX: Largest Xen-information leaf. All leaves up to an including @EAX + * are supported by the Xen host. + * EBX-EDX: "XenVMMXenVMM" signature, allowing positive identification + * of a Xen host. + */ +#define XEN_CPUID_SIGNATURE_EBX 0x566e6558 /* "XenV" */ +#define XEN_CPUID_SIGNATURE_ECX 0x65584d4d /* "MMXe" */ +#define XEN_CPUID_SIGNATURE_EDX 0x4d4d566e /* "nVMM" */ + +/* + * Leaf 2 (0x40000001) + * EAX[31:16]: Xen major version. + * EAX[15: 0]: Xen minor version. + * EBX-EDX: Reserved (currently all zeroes). + */ + +/* + * Leaf 3 (0x40000002) + * EAX: Number of hypercall transfer pages. This register is always guaranteed + * to specify one hypercall page. + * EBX: Base address of Xen-specific MSRs. + * ECX: Features 1. Unused bits are set to zero. + * EDX: Features 2. Unused bits are set to zero. + */ + +/* Does the host support MMU_PT_UPDATE_PRESERVE_AD for this guest? */ +#define _XEN_CPUID_FEAT1_MMU_PT_UPDATE_PRESERVE_AD 0 +#define XEN_CPUID_FEAT1_MMU_PT_UPDATE_PRESERVE_AD (1u<<0) + +#endif /* __XEN_PUBLIC_ARCH_X86_CPUID_H__ */ diff --git a/sys/xen/interface/arch-x86/hvm/save.h b/sys/xen/interface/arch-x86/hvm/save.h new file mode 100644 index 0000000..73b3909 --- /dev/null +++ b/sys/xen/interface/arch-x86/hvm/save.h @@ -0,0 +1,429 @@ +/* + * Structure definitions for HVM state that is held by Xen and must + * be saved along with the domain's memory and device-model state. + * + * Copyright (c) 2007 XenSource Ltd. + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to + * deal in the Software without restriction, including without limitation the + * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or + * sell copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER + * DEALINGS IN THE SOFTWARE. + */ + +#ifndef __XEN_PUBLIC_HVM_SAVE_X86_H__ +#define __XEN_PUBLIC_HVM_SAVE_X86_H__ + +/* + * Save/restore header: general info about the save file. + */ + +#define HVM_FILE_MAGIC 0x54381286 +#define HVM_FILE_VERSION 0x00000001 + +struct hvm_save_header { + uint32_t magic; /* Must be HVM_FILE_MAGIC */ + uint32_t version; /* File format version */ + uint64_t changeset; /* Version of Xen that saved this file */ + uint32_t cpuid; /* CPUID[0x01][%eax] on the saving machine */ + uint32_t pad0; +}; + +DECLARE_HVM_SAVE_TYPE(HEADER, 1, struct hvm_save_header); + + +/* + * Processor + */ + +struct hvm_hw_cpu { + uint8_t fpu_regs[512]; + + uint64_t rax; + uint64_t rbx; + uint64_t rcx; + uint64_t rdx; + uint64_t rbp; + uint64_t rsi; + uint64_t rdi; + uint64_t rsp; + uint64_t r8; + uint64_t r9; + uint64_t r10; + uint64_t r11; + uint64_t r12; + uint64_t r13; + uint64_t r14; + uint64_t r15; + + uint64_t rip; + uint64_t rflags; + + uint64_t cr0; + uint64_t cr2; + uint64_t cr3; + uint64_t cr4; + + uint64_t dr0; + uint64_t dr1; + uint64_t dr2; + uint64_t dr3; + uint64_t dr6; + uint64_t dr7; + + uint32_t cs_sel; + uint32_t ds_sel; + uint32_t es_sel; + uint32_t fs_sel; + uint32_t gs_sel; + uint32_t ss_sel; + uint32_t tr_sel; + uint32_t ldtr_sel; + + uint32_t cs_limit; + uint32_t ds_limit; + uint32_t es_limit; + uint32_t fs_limit; + uint32_t gs_limit; + uint32_t ss_limit; + uint32_t tr_limit; + uint32_t ldtr_limit; + uint32_t idtr_limit; + uint32_t gdtr_limit; + + uint64_t cs_base; + uint64_t ds_base; + uint64_t es_base; + uint64_t fs_base; + uint64_t gs_base; + uint64_t ss_base; + uint64_t tr_base; + uint64_t ldtr_base; + uint64_t idtr_base; + uint64_t gdtr_base; + + uint32_t cs_arbytes; + uint32_t ds_arbytes; + uint32_t es_arbytes; + uint32_t fs_arbytes; + uint32_t gs_arbytes; + uint32_t ss_arbytes; + uint32_t tr_arbytes; + uint32_t ldtr_arbytes; + + uint32_t sysenter_cs; + uint32_t padding0; + + uint64_t sysenter_esp; + uint64_t sysenter_eip; + + /* msr for em64t */ + uint64_t shadow_gs; + + /* msr content saved/restored. */ + uint64_t msr_flags; + uint64_t msr_lstar; + uint64_t msr_star; + uint64_t msr_cstar; + uint64_t msr_syscall_mask; + uint64_t msr_efer; + + /* guest's idea of what rdtsc() would return */ + uint64_t tsc; + + /* pending event, if any */ + union { + uint32_t pending_event; + struct { + uint8_t pending_vector:8; + uint8_t pending_type:3; + uint8_t pending_error_valid:1; + uint32_t pending_reserved:19; + uint8_t pending_valid:1; + }; + }; + /* error code for pending event */ + uint32_t error_code; +}; + +DECLARE_HVM_SAVE_TYPE(CPU, 2, struct hvm_hw_cpu); + + +/* + * PIC + */ + +struct hvm_hw_vpic { + /* IR line bitmasks. */ + uint8_t irr; + uint8_t imr; + uint8_t isr; + + /* Line IRx maps to IRQ irq_base+x */ + uint8_t irq_base; + + /* + * Where are we in ICW2-4 initialisation (0 means no init in progress)? + * Bits 0-1 (=x): Next write at A=1 sets ICW(x+1). + * Bit 2: ICW1.IC4 (1 == ICW4 included in init sequence) + * Bit 3: ICW1.SNGL (0 == ICW3 included in init sequence) + */ + uint8_t init_state:4; + + /* IR line with highest priority. */ + uint8_t priority_add:4; + + /* Reads from A=0 obtain ISR or IRR? */ + uint8_t readsel_isr:1; + + /* Reads perform a polling read? */ + uint8_t poll:1; + + /* Automatically clear IRQs from the ISR during INTA? */ + uint8_t auto_eoi:1; + + /* Automatically rotate IRQ priorities during AEOI? */ + uint8_t rotate_on_auto_eoi:1; + + /* Exclude slave inputs when considering in-service IRQs? */ + uint8_t special_fully_nested_mode:1; + + /* Special mask mode excludes masked IRs from AEOI and priority checks. */ + uint8_t special_mask_mode:1; + + /* Is this a master PIC or slave PIC? (NB. This is not programmable.) */ + uint8_t is_master:1; + + /* Edge/trigger selection. */ + uint8_t elcr; + + /* Virtual INT output. */ + uint8_t int_output; +}; + +DECLARE_HVM_SAVE_TYPE(PIC, 3, struct hvm_hw_vpic); + + +/* + * IO-APIC + */ + +#ifdef __ia64__ +#define VIOAPIC_IS_IOSAPIC 1 +#define VIOAPIC_NUM_PINS 24 +#else +#define VIOAPIC_NUM_PINS 48 /* 16 ISA IRQs, 32 non-legacy PCI IRQS. */ +#endif + +struct hvm_hw_vioapic { + uint64_t base_address; + uint32_t ioregsel; + uint32_t id; + union vioapic_redir_entry + { + uint64_t bits; + struct { + uint8_t vector; + uint8_t delivery_mode:3; + uint8_t dest_mode:1; + uint8_t delivery_status:1; + uint8_t polarity:1; + uint8_t remote_irr:1; + uint8_t trig_mode:1; + uint8_t mask:1; + uint8_t reserve:7; +#if !VIOAPIC_IS_IOSAPIC + uint8_t reserved[4]; + uint8_t dest_id; +#else + uint8_t reserved[3]; + uint16_t dest_id; +#endif + } fields; + } redirtbl[VIOAPIC_NUM_PINS]; +}; + +DECLARE_HVM_SAVE_TYPE(IOAPIC, 4, struct hvm_hw_vioapic); + + +/* + * LAPIC + */ + +struct hvm_hw_lapic { + uint64_t apic_base_msr; + uint32_t disabled; /* VLAPIC_xx_DISABLED */ + uint32_t timer_divisor; +}; + +DECLARE_HVM_SAVE_TYPE(LAPIC, 5, struct hvm_hw_lapic); + +struct hvm_hw_lapic_regs { + uint8_t data[1024]; +}; + +DECLARE_HVM_SAVE_TYPE(LAPIC_REGS, 6, struct hvm_hw_lapic_regs); + + +/* + * IRQs + */ + +struct hvm_hw_pci_irqs { + /* + * Virtual interrupt wires for a single PCI bus. + * Indexed by: device*4 + INTx#. + */ + union { + DECLARE_BITMAP(i, 32*4); + uint64_t pad[2]; + }; +}; + +DECLARE_HVM_SAVE_TYPE(PCI_IRQ, 7, struct hvm_hw_pci_irqs); + +struct hvm_hw_isa_irqs { + /* + * Virtual interrupt wires for ISA devices. + * Indexed by ISA IRQ (assumes no ISA-device IRQ sharing). + */ + union { + DECLARE_BITMAP(i, 16); + uint64_t pad[1]; + }; +}; + +DECLARE_HVM_SAVE_TYPE(ISA_IRQ, 8, struct hvm_hw_isa_irqs); + +struct hvm_hw_pci_link { + /* + * PCI-ISA interrupt router. + * Each PCI <device:INTx#> is 'wire-ORed' into one of four links using + * the traditional 'barber's pole' mapping ((device + INTx#) & 3). + * The router provides a programmable mapping from each link to a GSI. + */ + uint8_t route[4]; + uint8_t pad0[4]; +}; + +DECLARE_HVM_SAVE_TYPE(PCI_LINK, 9, struct hvm_hw_pci_link); + +/* + * PIT + */ + +struct hvm_hw_pit { + struct hvm_hw_pit_channel { + uint32_t count; /* can be 65536 */ + uint16_t latched_count; + uint8_t count_latched; + uint8_t status_latched; + uint8_t status; + uint8_t read_state; + uint8_t write_state; + uint8_t write_latch; + uint8_t rw_mode; + uint8_t mode; + uint8_t bcd; /* not supported */ + uint8_t gate; /* timer start */ + } channels[3]; /* 3 x 16 bytes */ + uint32_t speaker_data_on; + uint32_t pad0; +}; + +DECLARE_HVM_SAVE_TYPE(PIT, 10, struct hvm_hw_pit); + + +/* + * RTC + */ + +#define RTC_CMOS_SIZE 14 +struct hvm_hw_rtc { + /* CMOS bytes */ + uint8_t cmos_data[RTC_CMOS_SIZE]; + /* Index register for 2-part operations */ + uint8_t cmos_index; + uint8_t pad0; +}; + +DECLARE_HVM_SAVE_TYPE(RTC, 11, struct hvm_hw_rtc); + + +/* + * HPET + */ + +#define HPET_TIMER_NUM 3 /* 3 timers supported now */ +struct hvm_hw_hpet { + /* Memory-mapped, software visible registers */ + uint64_t capability; /* capabilities */ + uint64_t res0; /* reserved */ + uint64_t config; /* configuration */ + uint64_t res1; /* reserved */ + uint64_t isr; /* interrupt status reg */ + uint64_t res2[25]; /* reserved */ + uint64_t mc64; /* main counter */ + uint64_t res3; /* reserved */ + struct { /* timers */ + uint64_t config; /* configuration/cap */ + uint64_t cmp; /* comparator */ + uint64_t fsb; /* FSB route, not supported now */ + uint64_t res4; /* reserved */ + } timers[HPET_TIMER_NUM]; + uint64_t res5[4*(24-HPET_TIMER_NUM)]; /* reserved, up to 0x3ff */ + + /* Hidden register state */ + uint64_t period[HPET_TIMER_NUM]; /* Last value written to comparator */ +}; + +DECLARE_HVM_SAVE_TYPE(HPET, 12, struct hvm_hw_hpet); + + +/* + * PM timer + */ + +struct hvm_hw_pmtimer { + uint32_t tmr_val; /* PM_TMR_BLK.TMR_VAL: 32bit free-running counter */ + uint16_t pm1a_sts; /* PM1a_EVT_BLK.PM1a_STS: status register */ + uint16_t pm1a_en; /* PM1a_EVT_BLK.PM1a_EN: enable register */ +}; + +DECLARE_HVM_SAVE_TYPE(PMTIMER, 13, struct hvm_hw_pmtimer); + +/* + * MTRR MSRs + */ + +struct hvm_hw_mtrr { +#define MTRR_VCNT 8 +#define NUM_FIXED_MSR 11 + uint64_t msr_pat_cr; + /* mtrr physbase & physmask msr pair*/ + uint64_t msr_mtrr_var[MTRR_VCNT*2]; + uint64_t msr_mtrr_fixed[NUM_FIXED_MSR]; + uint64_t msr_mtrr_cap; + uint64_t msr_mtrr_def_type; +}; + +DECLARE_HVM_SAVE_TYPE(MTRR, 14, struct hvm_hw_mtrr); + +/* + * Largest type-code in use + */ +#define HVM_SAVE_CODE_MAX 14 + +#endif /* __XEN_PUBLIC_HVM_SAVE_X86_H__ */ diff --git a/sys/xen/interface/arch-x86/xen-mca.h b/sys/xen/interface/arch-x86/xen-mca.h new file mode 100644 index 0000000..103d41f --- /dev/null +++ b/sys/xen/interface/arch-x86/xen-mca.h @@ -0,0 +1,279 @@ +/****************************************************************************** + * arch-x86/mca.h + * + * Contributed by Advanced Micro Devices, Inc. + * Author: Christoph Egger <Christoph.Egger@amd.com> + * + * Guest OS machine check interface to x86 Xen. + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to + * deal in the Software without restriction, including without limitation the + * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or + * sell copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER + * DEALINGS IN THE SOFTWARE. + */ + +/* Full MCA functionality has the following Usecases from the guest side: + * + * Must have's: + * 1. Dom0 and DomU register machine check trap callback handlers + * (already done via "set_trap_table" hypercall) + * 2. Dom0 registers machine check event callback handler + * (doable via EVTCHNOP_bind_virq) + * 3. Dom0 and DomU fetches machine check data + * 4. Dom0 wants Xen to notify a DomU + * 5. Dom0 gets DomU ID from physical address + * 6. Dom0 wants Xen to kill DomU (already done for "xm destroy") + * + * Nice to have's: + * 7. Dom0 wants Xen to deactivate a physical CPU + * This is better done as separate task, physical CPU hotplugging, + * and hypercall(s) should be sysctl's + * 8. Page migration proposed from Xen NUMA work, where Dom0 can tell Xen to + * move a DomU (or Dom0 itself) away from a malicious page + * producing correctable errors. + * 9. offlining physical page: + * Xen free's and never re-uses a certain physical page. + * 10. Testfacility: Allow Dom0 to write values into machine check MSR's + * and tell Xen to trigger a machine check + */ + +#ifndef __XEN_PUBLIC_ARCH_X86_MCA_H__ +#define __XEN_PUBLIC_ARCH_X86_MCA_H__ + +/* Hypercall */ +#define __HYPERVISOR_mca __HYPERVISOR_arch_0 + +#define XEN_MCA_INTERFACE_VERSION 0x03000001 + +/* IN: Dom0 calls hypercall from MC event handler. */ +#define XEN_MC_CORRECTABLE 0x0 +/* IN: Dom0/DomU calls hypercall from MC trap handler. */ +#define XEN_MC_TRAP 0x1 +/* XEN_MC_CORRECTABLE and XEN_MC_TRAP are mutually exclusive. */ + +/* OUT: All is ok */ +#define XEN_MC_OK 0x0 +/* OUT: Domain could not fetch data. */ +#define XEN_MC_FETCHFAILED 0x1 +/* OUT: There was no machine check data to fetch. */ +#define XEN_MC_NODATA 0x2 +/* OUT: Between notification time and this hypercall an other + * (most likely) correctable error happened. The fetched data, + * does not match the original machine check data. */ +#define XEN_MC_NOMATCH 0x4 + +/* OUT: DomU did not register MC NMI handler. Try something else. */ +#define XEN_MC_CANNOTHANDLE 0x8 +/* OUT: Notifying DomU failed. Retry later or try something else. */ +#define XEN_MC_NOTDELIVERED 0x10 +/* Note, XEN_MC_CANNOTHANDLE and XEN_MC_NOTDELIVERED are mutually exclusive. */ + + +#ifndef __ASSEMBLY__ + +#define VIRQ_MCA VIRQ_ARCH_0 /* G. (DOM0) Machine Check Architecture */ + +/* + * Machine Check Architecure: + * structs are read-only and used to report all kinds of + * correctable and uncorrectable errors detected by the HW. + * Dom0 and DomU: register a handler to get notified. + * Dom0 only: Correctable errors are reported via VIRQ_MCA + * Dom0 and DomU: Uncorrectable errors are reported via nmi handlers + */ +#define MC_TYPE_GLOBAL 0 +#define MC_TYPE_BANK 1 +#define MC_TYPE_EXTENDED 2 + +struct mcinfo_common { + uint16_t type; /* structure type */ + uint16_t size; /* size of this struct in bytes */ +}; + + +#define MC_FLAG_CORRECTABLE (1 << 0) +#define MC_FLAG_UNCORRECTABLE (1 << 1) + +/* contains global x86 mc information */ +struct mcinfo_global { + struct mcinfo_common common; + + /* running domain at the time in error (most likely the impacted one) */ + uint16_t mc_domid; + uint32_t mc_socketid; /* physical socket of the physical core */ + uint16_t mc_coreid; /* physical impacted core */ + uint16_t mc_core_threadid; /* core thread of physical core */ + uint16_t mc_vcpuid; /* virtual cpu scheduled for mc_domid */ + uint64_t mc_gstatus; /* global status */ + uint32_t mc_flags; +}; + +/* contains bank local x86 mc information */ +struct mcinfo_bank { + struct mcinfo_common common; + + uint16_t mc_bank; /* bank nr */ + uint16_t mc_domid; /* Usecase 5: domain referenced by mc_addr on dom0 + * and if mc_addr is valid. Never valid on DomU. */ + uint64_t mc_status; /* bank status */ + uint64_t mc_addr; /* bank address, only valid + * if addr bit is set in mc_status */ + uint64_t mc_misc; +}; + + +struct mcinfo_msr { + uint64_t reg; /* MSR */ + uint64_t value; /* MSR value */ +}; + +/* contains mc information from other + * or additional mc MSRs */ +struct mcinfo_extended { + struct mcinfo_common common; + + /* You can fill up to five registers. + * If you need more, then use this structure + * multiple times. */ + + uint32_t mc_msrs; /* Number of msr with valid values. */ + struct mcinfo_msr mc_msr[5]; +}; + +#define MCINFO_HYPERCALLSIZE 1024 +#define MCINFO_MAXSIZE 768 + +struct mc_info { + /* Number of mcinfo_* entries in mi_data */ + uint32_t mi_nentries; + + uint8_t mi_data[MCINFO_MAXSIZE - sizeof(uint32_t)]; +}; +typedef struct mc_info mc_info_t; + + + +/* + * OS's should use these instead of writing their own lookup function + * each with its own bugs and drawbacks. + * We use macros instead of static inline functions to allow guests + * to include this header in assembly files (*.S). + */ +/* Prototype: + * uint32_t x86_mcinfo_nentries(struct mc_info *mi); + */ +#define x86_mcinfo_nentries(_mi) \ + (_mi)->mi_nentries +/* Prototype: + * struct mcinfo_common *x86_mcinfo_first(struct mc_info *mi); + */ +#define x86_mcinfo_first(_mi) \ + (struct mcinfo_common *)((_mi)->mi_data) +/* Prototype: + * struct mcinfo_common *x86_mcinfo_next(struct mcinfo_common *mic); + */ +#define x86_mcinfo_next(_mic) \ + (struct mcinfo_common *)((uint8_t *)(_mic) + (_mic)->size) + +/* Prototype: + * void x86_mcinfo_lookup(void *ret, struct mc_info *mi, uint16_t type); + */ +#define x86_mcinfo_lookup(_ret, _mi, _type) \ + do { \ + uint32_t found, i; \ + struct mcinfo_common *_mic; \ + \ + found = 0; \ + (_ret) = NULL; \ + if (_mi == NULL) break; \ + _mic = x86_mcinfo_first(_mi); \ + for (i = 0; i < x86_mcinfo_nentries(_mi); i++) { \ + if (_mic->type == (_type)) { \ + found = 1; \ + break; \ + } \ + _mic = x86_mcinfo_next(_mic); \ + } \ + (_ret) = found ? _mic : NULL; \ + } while (0) + + +/* Usecase 1 + * Register machine check trap callback handler + * (already done via "set_trap_table" hypercall) + */ + +/* Usecase 2 + * Dom0 registers machine check event callback handler + * done by EVTCHNOP_bind_virq + */ + +/* Usecase 3 + * Fetch machine check data from hypervisor. + * Note, this hypercall is special, because both Dom0 and DomU must use this. + */ +#define XEN_MC_fetch 1 +struct xen_mc_fetch { + /* IN/OUT variables. */ + uint32_t flags; + +/* IN: XEN_MC_CORRECTABLE, XEN_MC_TRAP */ +/* OUT: XEN_MC_OK, XEN_MC_FETCHFAILED, XEN_MC_NODATA, XEN_MC_NOMATCH */ + + /* OUT variables. */ + uint32_t fetch_idx; /* only useful for Dom0 for the notify hypercall */ + struct mc_info mc_info; +}; +typedef struct xen_mc_fetch xen_mc_fetch_t; +DEFINE_XEN_GUEST_HANDLE(xen_mc_fetch_t); + + +/* Usecase 4 + * This tells the hypervisor to notify a DomU about the machine check error + */ +#define XEN_MC_notifydomain 2 +struct xen_mc_notifydomain { + /* IN variables. */ + uint16_t mc_domid; /* The unprivileged domain to notify. */ + uint16_t mc_vcpuid; /* The vcpu in mc_domid to notify. + * Usually echo'd value from the fetch hypercall. */ + uint32_t fetch_idx; /* echo'd value from the fetch hypercall. */ + + /* IN/OUT variables. */ + uint32_t flags; + +/* IN: XEN_MC_CORRECTABLE, XEN_MC_TRAP */ +/* OUT: XEN_MC_OK, XEN_MC_CANNOTHANDLE, XEN_MC_NOTDELIVERED, XEN_MC_NOMATCH */ +}; +typedef struct xen_mc_notifydomain xen_mc_notifydomain_t; +DEFINE_XEN_GUEST_HANDLE(xen_mc_notifydomain_t); + + +struct xen_mc { + uint32_t cmd; + uint32_t interface_version; /* XEN_MCA_INTERFACE_VERSION */ + union { + struct xen_mc_fetch mc_fetch; + struct xen_mc_notifydomain mc_notifydomain; + uint8_t pad[MCINFO_HYPERCALLSIZE]; + } u; +}; +typedef struct xen_mc xen_mc_t; +DEFINE_XEN_GUEST_HANDLE(xen_mc_t); + +#endif /* __ASSEMBLY__ */ + +#endif /* __XEN_PUBLIC_ARCH_X86_MCA_H__ */ diff --git a/sys/xen/interface/domctl.h b/sys/xen/interface/domctl.h index a23bc78..e7ddd5f 100644 --- a/sys/xen/interface/domctl.h +++ b/sys/xen/interface/domctl.h @@ -376,7 +376,7 @@ DEFINE_XEN_GUEST_HANDLE(xen_domctl_hypercall_init_t); #define XEN_DOMAINSETUP_hvm_guest (1UL<<_XEN_DOMAINSETUP_hvm_guest) #define _XEN_DOMAINSETUP_query 1 /* Get parameters (for save) */ #define XEN_DOMAINSETUP_query (1UL<<_XEN_DOMAINSETUP_query) -define _XEN_DOMAINSETUP_sioemu_guest 2 +#define _XEN_DOMAINSETUP_sioemu_guest 2 #define XEN_DOMAINSETUP_sioemu_guest (1UL<<_XEN_DOMAINSETUP_sioemu_guest) typedef struct xen_domctl_arch_setup { uint64_aligned_t flags; /* XEN_DOMAINSETUP_* */ diff --git a/sys/xen/interface/foreign/mkchecker.py b/sys/xen/interface/foreign/mkchecker.py index b30e82a..9da1e2b 100644 --- a/sys/xen/interface/foreign/mkchecker.py +++ b/sys/xen/interface/foreign/mkchecker.py @@ -29,14 +29,14 @@ for a in archs: f.write('int main(int argc, char *argv[])\n{\n'); f.write('\tprintf("\\n");'); -f.write('printf("%-20s |", "structs");\n'); +f.write('printf("%-25s |", "structs");\n'); for a in archs: f.write('\tprintf("%%8s", "%s");\n' % a); f.write('\tprintf("\\n");'); f.write('\tprintf("\\n");'); for struct in structs: - f.write('\tprintf("%%-20s |", "%s");\n' % struct); + f.write('\tprintf("%%-25s |", "%s");\n' % struct); for a in archs: if a == arch: s = struct; # native diff --git a/sys/xen/interface/foreign/mkheader.py b/sys/xen/interface/foreign/mkheader.py index a5310eb..3d75a7a 100644 --- a/sys/xen/interface/foreign/mkheader.py +++ b/sys/xen/interface/foreign/mkheader.py @@ -1,7 +1,7 @@ #!/usr/bin/python import sys, re; -from structs import structs, defines; +from structs import unions, structs, defines; # command line arguments arch = sys.argv[1]; @@ -110,6 +110,16 @@ input = re.sub("#define[^\n]+\n", "", input); input = re.compile("/\*(.*?)\*/", re.S).sub("", input) input = re.compile("\n\s*\n", re.S).sub("\n", input); +# add unions to output +for union in unions: + regex = "union\s+%s\s*\{(.*?)\n\};" % union; + match = re.search(regex, input, re.S) + if None == match: + output += "#define %s_has_no_%s 1\n" % (arch, union); + else: + output += "union %s_%s {%s\n};\n" % (union, arch, match.group(1)); + output += "\n"; + # add structs to output for struct in structs: regex = "struct\s+%s\s*\{(.*?)\n\};" % struct; @@ -135,6 +145,10 @@ for define in defines: replace = define + "_" + arch; output = re.sub("\\b%s\\b" % define, replace, output); +# replace: unions +for union in unions: + output = re.sub("\\b(union\s+%s)\\b" % union, "\\1_%s" % arch, output); + # replace: structs + struct typedefs for struct in structs: output = re.sub("\\b(struct\s+%s)\\b" % struct, "\\1_%s" % arch, output); diff --git a/sys/xen/interface/foreign/structs.py b/sys/xen/interface/foreign/structs.py index 6ecd1aa..7d51ca8 100644 --- a/sys/xen/interface/foreign/structs.py +++ b/sys/xen/interface/foreign/structs.py @@ -1,12 +1,16 @@ # configuration: what needs translation +unions = [ "vcpu_cr_regs", + "vcpu_ar_regs" ]; + structs = [ "start_info", "trap_info", "pt_fpreg", "cpu_user_regs", "xen_ia64_boot_param", "ia64_tr_entry", - "vcpu_extra_regs", + "vcpu_tr_regs", + "vcpu_guest_context_regs", "vcpu_guest_context", "arch_vcpu_info", "vcpu_time_info", diff --git a/sys/xen/interface/grant_table.h b/sys/xen/interface/grant_table.h index 7dcba2b..26f2c35 100644 --- a/sys/xen/interface/grant_table.h +++ b/sys/xen/interface/grant_table.h @@ -235,11 +235,7 @@ struct gnttab_setup_table { uint32_t nr_frames; /* OUT parameters. */ int16_t status; /* GNTST_* */ -#ifdef __LP64__ - XEN_GUEST_HANDLE(uint64_t) frame_list; -#else - XEN_GUEST_HANDLE(uint32_t) frame_list; -#endif + XEN_GUEST_HANDLE(ulong) frame_list; }; typedef struct gnttab_setup_table gnttab_setup_table_t; DEFINE_XEN_GUEST_HANDLE(gnttab_setup_table_t); diff --git a/sys/xen/interface/hvm/hvm_op.h b/sys/xen/interface/hvm/hvm_op.h index b21b0f7..f0ada2d 100644 --- a/sys/xen/interface/hvm/hvm_op.h +++ b/sys/xen/interface/hvm/hvm_op.h @@ -73,4 +73,59 @@ DEFINE_XEN_GUEST_HANDLE(xen_hvm_set_pci_link_route_t); /* Flushes all VCPU TLBs: @arg must be NULL. */ #define HVMOP_flush_tlbs 5 +/* Following tools-only interfaces may change in future. */ +#if defined(__XEN__) || defined(__XEN_TOOLS__) + +/* Track dirty VRAM. */ +#define HVMOP_track_dirty_vram 6 +struct xen_hvm_track_dirty_vram { + /* Domain to be tracked. */ + domid_t domid; + /* First pfn to track. */ + uint64_aligned_t first_pfn; + /* Number of pages to track. */ + uint64_aligned_t nr; + /* OUT variable. */ + /* Dirty bitmap buffer. */ + XEN_GUEST_HANDLE_64(uint8) dirty_bitmap; +}; +typedef struct xen_hvm_track_dirty_vram xen_hvm_track_dirty_vram_t; +DEFINE_XEN_GUEST_HANDLE(xen_hvm_track_dirty_vram_t); + +/* Notify that some pages got modified by the Device Model. */ +#define HVMOP_modified_memory 7 +struct xen_hvm_modified_memory { + /* Domain to be updated. */ + domid_t domid; + /* First pfn. */ + uint64_aligned_t first_pfn; + /* Number of pages. */ + uint64_aligned_t nr; +}; +typedef struct xen_hvm_modified_memory xen_hvm_modified_memory_t; +DEFINE_XEN_GUEST_HANDLE(xen_hvm_modified_memory_t); + +#define HVMOP_set_mem_type 8 +typedef enum { + HVMMEM_ram_rw, /* Normal read/write guest RAM */ + HVMMEM_ram_ro, /* Read-only; writes are discarded */ + HVMMEM_mmio_dm, /* Reads and write go to the device model */ +} hvmmem_type_t; +/* Notify that a region of memory is to be treated in a specific way. */ +struct xen_hvm_set_mem_type { + /* Domain to be updated. */ + domid_t domid; + /* Memory type */ + hvmmem_type_t hvmmem_type; + /* First pfn. */ + uint64_aligned_t first_pfn; + /* Number of pages. */ + uint64_aligned_t nr; +}; +typedef struct xen_hvm_set_mem_type xen_hvm_set_mem_type_t; +DEFINE_XEN_GUEST_HANDLE(xen_hvm_set_mem_type_t); + + +#endif /* defined(__XEN__) || defined(__XEN_TOOLS__) */ + #endif /* __XEN_PUBLIC_HVM_HVM_OP_H__ */ diff --git a/sys/xen/interface/hvm/ioreq.h b/sys/xen/interface/hvm/ioreq.h index 91a4cef..5b68730 100644 --- a/sys/xen/interface/hvm/ioreq.h +++ b/sys/xen/interface/hvm/ioreq.h @@ -34,14 +34,8 @@ #define IOREQ_TYPE_PIO 0 /* pio */ #define IOREQ_TYPE_COPY 1 /* mmio ops */ -#define IOREQ_TYPE_AND 2 -#define IOREQ_TYPE_OR 3 -#define IOREQ_TYPE_XOR 4 -#define IOREQ_TYPE_XCHG 5 -#define IOREQ_TYPE_ADD 6 #define IOREQ_TYPE_TIMEOFFSET 7 #define IOREQ_TYPE_INVALIDATE 8 /* mapcache */ -#define IOREQ_TYPE_SUB 9 /* * VMExit dispatcher should cooperate with instruction decoder to @@ -58,6 +52,7 @@ struct ioreq { * of the real data to use. */ uint8_t dir:1; /* 1=read, 0=write */ uint8_t df:1; + uint8_t pad:1; uint8_t type; /* I/O type */ uint8_t _pad0[6]; uint64_t io_count; /* How many IO done on a vcpu */ @@ -77,11 +72,21 @@ struct shared_iopage { }; typedef struct shared_iopage shared_iopage_t; -#define IOREQ_BUFFER_SLOT_NUM 80 +struct buf_ioreq { + uint8_t type; /* I/O type */ + uint8_t pad:1; + uint8_t dir:1; /* 1=read, 0=write */ + uint8_t size:2; /* 0=>1, 1=>2, 2=>4, 3=>8. If 8, use two buf_ioreqs */ + uint32_t addr:20;/* physical address */ + uint32_t data; /* data */ +}; +typedef struct buf_ioreq buf_ioreq_t; + +#define IOREQ_BUFFER_SLOT_NUM 511 /* 8 bytes each, plus 2 4-byte indexes */ struct buffered_iopage { - unsigned int read_pointer; - unsigned int write_pointer; - ioreq_t ioreq[IOREQ_BUFFER_SLOT_NUM]; + unsigned int read_pointer; + unsigned int write_pointer; + buf_ioreq_t buf_ioreq[IOREQ_BUFFER_SLOT_NUM]; }; /* NB. Size of this structure must be no greater than one page. */ typedef struct buffered_iopage buffered_iopage_t; @@ -103,11 +108,11 @@ struct buffered_piopage { }; #endif /* defined(__ia64__) */ -#if defined(__i386__) || defined(__x86_64__) #define ACPI_PM1A_EVT_BLK_ADDRESS 0x0000000000001f40 #define ACPI_PM1A_CNT_BLK_ADDRESS (ACPI_PM1A_EVT_BLK_ADDRESS + 0x04) #define ACPI_PM_TMR_BLK_ADDRESS (ACPI_PM1A_EVT_BLK_ADDRESS + 0x08) -#endif /* defined(__i386__) || defined(__x86_64__) */ +#define ACPI_GPE0_BLK_ADDRESS (ACPI_PM_TMR_BLK_ADDRESS + 0x20) +#define ACPI_GPE0_BLK_LEN 0x08 #endif /* _IOREQ_H_ */ diff --git a/sys/xen/interface/hvm/params.h b/sys/xen/interface/hvm/params.h index 9657654..5f75ed7 100644 --- a/sys/xen/interface/hvm/params.h +++ b/sys/xen/interface/hvm/params.h @@ -52,9 +52,47 @@ #ifdef __ia64__ #define HVM_PARAM_NVRAM_FD 7 -#define HVM_NR_PARAMS 8 -#else -#define HVM_NR_PARAMS 7 +#define HVM_PARAM_VHPT_SIZE 8 +#define HVM_PARAM_BUFPIOREQ_PFN 9 #endif +/* + * Set mode for virtual timers (currently x86 only): + * delay_for_missed_ticks (default): + * Do not advance a vcpu's time beyond the correct delivery time for + * interrupts that have been missed due to preemption. Deliver missed + * interrupts when the vcpu is rescheduled and advance the vcpu's virtual + * time stepwise for each one. + * no_delay_for_missed_ticks: + * As above, missed interrupts are delivered, but guest time always tracks + * wallclock (i.e., real) time while doing so. + * no_missed_ticks_pending: + * No missed interrupts are held pending. Instead, to ensure ticks are + * delivered at some non-zero rate, if we detect missed ticks then the + * internal tick alarm is not disabled if the VCPU is preempted during the + * next tick period. + * one_missed_tick_pending: + * Missed interrupts are collapsed together and delivered as one 'late tick'. + * Guest time always tracks wallclock (i.e., real) time. + */ +#define HVM_PARAM_TIMER_MODE 10 +#define HVMPTM_delay_for_missed_ticks 0 +#define HVMPTM_no_delay_for_missed_ticks 1 +#define HVMPTM_no_missed_ticks_pending 2 +#define HVMPTM_one_missed_tick_pending 3 + +/* Boolean: Enable virtual HPET (high-precision event timer)? (x86-only) */ +#define HVM_PARAM_HPET_ENABLED 11 + +/* Identity-map page directory used by Intel EPT when CR0.PG=0. */ +#define HVM_PARAM_IDENT_PT 12 + +/* Device Model domain, defaults to 0. */ +#define HVM_PARAM_DM_DOMAIN 13 + +/* ACPI S state: currently support S0 and S3 on x86. */ +#define HVM_PARAM_ACPI_S_STATE 14 + +#define HVM_NR_PARAMS 15 + #endif /* __XEN_PUBLIC_HVM_PARAMS_H__ */ diff --git a/sys/xen/interface/hvm/save.h b/sys/xen/interface/hvm/save.h index e01218a..d45f0c1 100644 --- a/sys/xen/interface/hvm/save.h +++ b/sys/xen/interface/hvm/save.h @@ -3,7 +3,6 @@ * * Structure definitions for HVM state that is held by Xen and must * be saved along with the domain's memory and device-model state. - * * * Copyright (c) 2007 XenSource Ltd. * @@ -40,6 +39,10 @@ * Internal mechanisms should be kept in Xen-private headers. */ +#if !defined(__GNUC__) || defined(__STRICT_ANSI__) +#error "Anonymous structs/unions are a GNU extension." +#endif + /* * Each entry is preceded by a descriptor giving its type and length */ @@ -67,391 +70,6 @@ struct hvm_save_descriptor { /* - * Save/restore header: general info about the save file. - */ - -#define HVM_FILE_MAGIC 0x54381286 -#define HVM_FILE_VERSION 0x00000001 - -struct hvm_save_header { - uint32_t magic; /* Must be HVM_FILE_MAGIC */ - uint32_t version; /* File format version */ - uint64_t changeset; /* Version of Xen that saved this file */ - uint32_t cpuid; /* CPUID[0x01][%eax] on the saving machine */ - uint32_t pad0; -}; - -DECLARE_HVM_SAVE_TYPE(HEADER, 1, struct hvm_save_header); - - -/* - * Processor - */ - -struct hvm_hw_cpu { - uint8_t fpu_regs[512]; - - uint64_t rax; - uint64_t rbx; - uint64_t rcx; - uint64_t rdx; - uint64_t rbp; - uint64_t rsi; - uint64_t rdi; - uint64_t rsp; - uint64_t r8; - uint64_t r9; - uint64_t r10; - uint64_t r11; - uint64_t r12; - uint64_t r13; - uint64_t r14; - uint64_t r15; - - uint64_t rip; - uint64_t rflags; - - uint64_t cr0; - uint64_t cr2; - uint64_t cr3; - uint64_t cr4; - - uint64_t dr0; - uint64_t dr1; - uint64_t dr2; - uint64_t dr3; - uint64_t dr6; - uint64_t dr7; - - uint32_t cs_sel; - uint32_t ds_sel; - uint32_t es_sel; - uint32_t fs_sel; - uint32_t gs_sel; - uint32_t ss_sel; - uint32_t tr_sel; - uint32_t ldtr_sel; - - uint32_t cs_limit; - uint32_t ds_limit; - uint32_t es_limit; - uint32_t fs_limit; - uint32_t gs_limit; - uint32_t ss_limit; - uint32_t tr_limit; - uint32_t ldtr_limit; - uint32_t idtr_limit; - uint32_t gdtr_limit; - - uint64_t cs_base; - uint64_t ds_base; - uint64_t es_base; - uint64_t fs_base; - uint64_t gs_base; - uint64_t ss_base; - uint64_t tr_base; - uint64_t ldtr_base; - uint64_t idtr_base; - uint64_t gdtr_base; - - uint32_t cs_arbytes; - uint32_t ds_arbytes; - uint32_t es_arbytes; - uint32_t fs_arbytes; - uint32_t gs_arbytes; - uint32_t ss_arbytes; - uint32_t tr_arbytes; - uint32_t ldtr_arbytes; - - uint32_t sysenter_cs; - uint32_t padding0; - - uint64_t sysenter_esp; - uint64_t sysenter_eip; - - /* msr for em64t */ - uint64_t shadow_gs; - - /* msr content saved/restored. */ - uint64_t msr_flags; - uint64_t msr_lstar; - uint64_t msr_star; - uint64_t msr_cstar; - uint64_t msr_syscall_mask; - uint64_t msr_efer; - - /* guest's idea of what rdtsc() would return */ - uint64_t tsc; - - /* pending event, if any */ - union { - uint32_t pending_event; - struct { - uint8_t pending_vector:8; - uint8_t pending_type:3; - uint8_t pending_error_valid:1; - uint32_t pending_reserved:19; - uint8_t pending_valid:1; - }; - }; - /* error code for pending event */ - uint32_t error_code; -}; - -DECLARE_HVM_SAVE_TYPE(CPU, 2, struct hvm_hw_cpu); - - -/* - * PIC - */ - -struct hvm_hw_vpic { - /* IR line bitmasks. */ - uint8_t irr; - uint8_t imr; - uint8_t isr; - - /* Line IRx maps to IRQ irq_base+x */ - uint8_t irq_base; - - /* - * Where are we in ICW2-4 initialisation (0 means no init in progress)? - * Bits 0-1 (=x): Next write at A=1 sets ICW(x+1). - * Bit 2: ICW1.IC4 (1 == ICW4 included in init sequence) - * Bit 3: ICW1.SNGL (0 == ICW3 included in init sequence) - */ - uint8_t init_state:4; - - /* IR line with highest priority. */ - uint8_t priority_add:4; - - /* Reads from A=0 obtain ISR or IRR? */ - uint8_t readsel_isr:1; - - /* Reads perform a polling read? */ - uint8_t poll:1; - - /* Automatically clear IRQs from the ISR during INTA? */ - uint8_t auto_eoi:1; - - /* Automatically rotate IRQ priorities during AEOI? */ - uint8_t rotate_on_auto_eoi:1; - - /* Exclude slave inputs when considering in-service IRQs? */ - uint8_t special_fully_nested_mode:1; - - /* Special mask mode excludes masked IRs from AEOI and priority checks. */ - uint8_t special_mask_mode:1; - - /* Is this a master PIC or slave PIC? (NB. This is not programmable.) */ - uint8_t is_master:1; - - /* Edge/trigger selection. */ - uint8_t elcr; - - /* Virtual INT output. */ - uint8_t int_output; -}; - -DECLARE_HVM_SAVE_TYPE(PIC, 3, struct hvm_hw_vpic); - - -/* - * IO-APIC - */ - -#ifdef __ia64__ -#define VIOAPIC_IS_IOSAPIC 1 -#define VIOAPIC_NUM_PINS 24 -#else -#define VIOAPIC_NUM_PINS 48 /* 16 ISA IRQs, 32 non-legacy PCI IRQS. */ -#endif - -struct hvm_hw_vioapic { - uint64_t base_address; - uint32_t ioregsel; - uint32_t id; - union vioapic_redir_entry - { - uint64_t bits; - struct { - uint8_t vector; - uint8_t delivery_mode:3; - uint8_t dest_mode:1; - uint8_t delivery_status:1; - uint8_t polarity:1; - uint8_t remote_irr:1; - uint8_t trig_mode:1; - uint8_t mask:1; - uint8_t reserve:7; -#if !VIOAPIC_IS_IOSAPIC - uint8_t reserved[4]; - uint8_t dest_id; -#else - uint8_t reserved[3]; - uint16_t dest_id; -#endif - } fields; - } redirtbl[VIOAPIC_NUM_PINS]; -}; - -DECLARE_HVM_SAVE_TYPE(IOAPIC, 4, struct hvm_hw_vioapic); - - -/* - * LAPIC - */ - -struct hvm_hw_lapic { - uint64_t apic_base_msr; - uint32_t disabled; /* VLAPIC_xx_DISABLED */ - uint32_t timer_divisor; -}; - -DECLARE_HVM_SAVE_TYPE(LAPIC, 5, struct hvm_hw_lapic); - -struct hvm_hw_lapic_regs { - /* A 4k page of register state */ - uint8_t data[0x400]; -}; - -DECLARE_HVM_SAVE_TYPE(LAPIC_REGS, 6, struct hvm_hw_lapic_regs); - - -/* - * IRQs - */ - -struct hvm_hw_pci_irqs { - /* - * Virtual interrupt wires for a single PCI bus. - * Indexed by: device*4 + INTx#. - */ - union { - DECLARE_BITMAP(i, 32*4); - uint64_t pad[2]; - }; -}; - -DECLARE_HVM_SAVE_TYPE(PCI_IRQ, 7, struct hvm_hw_pci_irqs); - -struct hvm_hw_isa_irqs { - /* - * Virtual interrupt wires for ISA devices. - * Indexed by ISA IRQ (assumes no ISA-device IRQ sharing). - */ - union { - DECLARE_BITMAP(i, 16); - uint64_t pad[1]; - }; -}; - -DECLARE_HVM_SAVE_TYPE(ISA_IRQ, 8, struct hvm_hw_isa_irqs); - -struct hvm_hw_pci_link { - /* - * PCI-ISA interrupt router. - * Each PCI <device:INTx#> is 'wire-ORed' into one of four links using - * the traditional 'barber's pole' mapping ((device + INTx#) & 3). - * The router provides a programmable mapping from each link to a GSI. - */ - uint8_t route[4]; - uint8_t pad0[4]; -}; - -DECLARE_HVM_SAVE_TYPE(PCI_LINK, 9, struct hvm_hw_pci_link); - -/* - * PIT - */ - -struct hvm_hw_pit { - struct hvm_hw_pit_channel { - uint32_t count; /* can be 65536 */ - uint16_t latched_count; - uint8_t count_latched; - uint8_t status_latched; - uint8_t status; - uint8_t read_state; - uint8_t write_state; - uint8_t write_latch; - uint8_t rw_mode; - uint8_t mode; - uint8_t bcd; /* not supported */ - uint8_t gate; /* timer start */ - } channels[3]; /* 3 x 16 bytes */ - uint32_t speaker_data_on; - uint32_t pad0; -}; - -DECLARE_HVM_SAVE_TYPE(PIT, 10, struct hvm_hw_pit); - - -/* - * RTC - */ - -#define RTC_CMOS_SIZE 14 -struct hvm_hw_rtc { - /* CMOS bytes */ - uint8_t cmos_data[RTC_CMOS_SIZE]; - /* Index register for 2-part operations */ - uint8_t cmos_index; - uint8_t pad0; -}; - -DECLARE_HVM_SAVE_TYPE(RTC, 11, struct hvm_hw_rtc); - - -/* - * HPET - */ - -#define HPET_TIMER_NUM 3 /* 3 timers supported now */ -struct hvm_hw_hpet { - /* Memory-mapped, software visible registers */ - uint64_t capability; /* capabilities */ - uint64_t res0; /* reserved */ - uint64_t config; /* configuration */ - uint64_t res1; /* reserved */ - uint64_t isr; /* interrupt status reg */ - uint64_t res2[25]; /* reserved */ - uint64_t mc64; /* main counter */ - uint64_t res3; /* reserved */ - struct { /* timers */ - uint64_t config; /* configuration/cap */ - uint64_t cmp; /* comparator */ - uint64_t fsb; /* FSB route, not supported now */ - uint64_t res4; /* reserved */ - } timers[HPET_TIMER_NUM]; - uint64_t res5[4*(24-HPET_TIMER_NUM)]; /* reserved, up to 0x3ff */ - - /* Hidden register state */ - uint64_t period[HPET_TIMER_NUM]; /* Last value written to comparator */ -}; - -DECLARE_HVM_SAVE_TYPE(HPET, 12, struct hvm_hw_hpet); - - -/* - * PM timer - */ - -struct hvm_hw_pmtimer { - uint32_t tmr_val; /* PM_TMR_BLK.TMR_VAL: 32bit free-running counter */ - uint16_t pm1a_sts; /* PM1a_EVT_BLK.PM1a_STS: status register */ - uint16_t pm1a_en; /* PM1a_EVT_BLK.PM1a_EN: enable register */ -}; - -DECLARE_HVM_SAVE_TYPE(PMTIMER, 13, struct hvm_hw_pmtimer); - -/* - * Largest type-code in use - */ -#define HVM_SAVE_CODE_MAX 13 - - -/* * The series of save records is teminated by a zero-type, zero-length * descriptor. */ @@ -459,4 +77,12 @@ DECLARE_HVM_SAVE_TYPE(PMTIMER, 13, struct hvm_hw_pmtimer); struct hvm_save_end {}; DECLARE_HVM_SAVE_TYPE(END, 0, struct hvm_save_end); +#if defined(__i386__) || defined(__x86_64__) +#include "../arch-x86/hvm/save.h" +#elif defined(__ia64__) +#include "../arch-ia64/hvm/save.h" +#else +#error "unsupported architecture" +#endif + #endif /* __XEN_PUBLIC_HVM_SAVE_H__ */ diff --git a/sys/xen/interface/io/blkif.h b/sys/xen/interface/io/blkif.h index d2bd652..9e2d3d0 100644 --- a/sys/xen/interface/io/blkif.h +++ b/sys/xen/interface/io/blkif.h @@ -54,7 +54,7 @@ #define BLKIF_OP_WRITE 1 /* * Recognised only if "feature-barrier" is present in backend xenbus info. - * The "feature_barrier" node contains a boolean indicating whether barrier + * The "feature-barrier" node contains a boolean indicating whether barrier * requests are likely to succeed or fail. Either way, a barrier request * may fail at any time with BLKIF_RSP_EOPNOTSUPP if it is unsupported by * the underlying block-device hardware. The boolean simply indicates whether @@ -63,6 +63,19 @@ * create the "feature-barrier" node! */ #define BLKIF_OP_WRITE_BARRIER 2 +/* + * Recognised if "feature-flush-cache" is present in backend xenbus + * info. A flush will ask the underlying storage hardware to flush its + * non-volatile caches as appropriate. The "feature-flush-cache" node + * contains a boolean indicating whether flush requests are likely to + * succeed or fail. Either way, a flush request may fail at any time + * with BLKIF_RSP_EOPNOTSUPP if it is unsupported by the underlying + * block-device hardware. The boolean simply indicates whether or not it + * is worthwhile for the frontend to attempt flushes. If a backend does + * not recognise BLKIF_OP_WRITE_FLUSH_CACHE, it should *not* create the + * "feature-flush-cache" node! + */ +#define BLKIF_OP_FLUSH_DISKCACHE 3 /* * Maximum scatter/gather segments per request. diff --git a/sys/xen/interface/io/fbif.h b/sys/xen/interface/io/fbif.h index 261d756..95377a0 100644 --- a/sys/xen/interface/io/fbif.h +++ b/sys/xen/interface/io/fbif.h @@ -50,12 +50,29 @@ struct xenfb_update int32_t height; /* rect height */ }; +/* + * Framebuffer resize notification event + * Capable backend sets feature-resize in xenstore. + */ +#define XENFB_TYPE_RESIZE 3 + +struct xenfb_resize +{ + uint8_t type; /* XENFB_TYPE_RESIZE */ + int32_t width; /* width in pixels */ + int32_t height; /* height in pixels */ + int32_t stride; /* stride in bytes */ + int32_t depth; /* depth in bits */ + int32_t offset; /* offset of the framebuffer in bytes */ +}; + #define XENFB_OUT_EVENT_SIZE 40 union xenfb_out_event { uint8_t type; struct xenfb_update update; + struct xenfb_resize resize; char pad[XENFB_OUT_EVENT_SIZE]; }; @@ -63,14 +80,33 @@ union xenfb_out_event /* * Frontends should ignore unknown in events. - * No in events currently defined. */ +/* + * Framebuffer refresh period advice + * Backend sends it to advise the frontend their preferred period of + * refresh. Frontends that keep the framebuffer constantly up-to-date + * just ignore it. Frontends that use the advice should immediately + * refresh the framebuffer (and send an update notification event if + * those have been requested), then use the update frequency to guide + * their periodical refreshs. + */ +#define XENFB_TYPE_REFRESH_PERIOD 1 +#define XENFB_NO_REFRESH 0 + +struct xenfb_refresh_period +{ + uint8_t type; /* XENFB_TYPE_UPDATE_PERIOD */ + uint32_t period; /* period of refresh, in ms, + * XENFB_NO_REFRESH if no refresh is needed */ +}; + #define XENFB_IN_EVENT_SIZE 40 union xenfb_in_event { uint8_t type; + struct xenfb_refresh_period refresh_period; char pad[XENFB_IN_EVENT_SIZE]; }; @@ -109,15 +145,17 @@ struct xenfb_page * Each directory page holds PAGE_SIZE / sizeof(*pd) * framebuffer pages, and can thus map up to PAGE_SIZE * * PAGE_SIZE / sizeof(*pd) bytes. With PAGE_SIZE == 4096 and - * sizeof(unsigned long) == 4, that's 4 Megs. Two directory - * pages should be enough for a while. + * sizeof(unsigned long) == 4/8, that's 4 Megs 32 bit and 2 Megs + * 64 bit. 256 directories give enough room for a 512 Meg + * framebuffer with a max resolution of 12,800x10,240. Should + * be enough for a while with room leftover for expansion. */ - unsigned long pd[2]; + unsigned long pd[256]; }; /* - * Wart: xenkbd needs to know resolution. Put it here until a better - * solution is found, but don't leak it to the backend. + * Wart: xenkbd needs to know default resolution. Put it here until a + * better solution is found, but don't leak it to the backend. */ #ifdef __KERNEL__ #define XENFB_WIDTH 800 diff --git a/sys/xen/interface/io/kbdif.h b/sys/xen/interface/io/kbdif.h index 38193c8..e1d66a5 100644 --- a/sys/xen/interface/io/kbdif.h +++ b/sys/xen/interface/io/kbdif.h @@ -50,6 +50,7 @@ struct xenkbd_motion uint8_t type; /* XENKBD_TYPE_MOTION */ int32_t rel_x; /* relative X motion */ int32_t rel_y; /* relative Y motion */ + int32_t rel_z; /* relative Z motion (wheel) */ }; struct xenkbd_key @@ -64,6 +65,7 @@ struct xenkbd_position uint8_t type; /* XENKBD_TYPE_POS */ int32_t abs_x; /* absolute X position (in FB pixels) */ int32_t abs_y; /* absolute Y position (in FB pixels) */ + int32_t rel_z; /* relative Z motion (wheel) */ }; #define XENKBD_IN_EVENT_SIZE 40 diff --git a/sys/xen/interface/io/netif.h b/sys/xen/interface/io/netif.h index a2e885c..fbb5c27 100644 --- a/sys/xen/interface/io/netif.h +++ b/sys/xen/interface/io/netif.h @@ -75,9 +75,11 @@ struct netif_tx_request { typedef struct netif_tx_request netif_tx_request_t; /* Types of netif_extra_info descriptors. */ -#define XEN_NETIF_EXTRA_TYPE_NONE (0) /* Never used - invalid */ -#define XEN_NETIF_EXTRA_TYPE_GSO (1) /* u.gso */ -#define XEN_NETIF_EXTRA_TYPE_MAX (2) +#define XEN_NETIF_EXTRA_TYPE_NONE (0) /* Never used - invalid */ +#define XEN_NETIF_EXTRA_TYPE_GSO (1) /* u.gso */ +#define XEN_NETIF_EXTRA_TYPE_MCAST_ADD (2) /* u.mcast */ +#define XEN_NETIF_EXTRA_TYPE_MCAST_DEL (3) /* u.mcast */ +#define XEN_NETIF_EXTRA_TYPE_MAX (4) /* netif_extra_info flags. */ #define _XEN_NETIF_EXTRA_FLAG_MORE (0) @@ -95,6 +97,9 @@ struct netif_extra_info { uint8_t flags; /* XEN_NETIF_EXTRA_FLAG_* */ union { + /* + * XEN_NETIF_EXTRA_TYPE_GSO: + */ struct { /* * Maximum payload size of each segment. For example, for TCP this @@ -118,9 +123,25 @@ struct netif_extra_info { uint16_t features; /* XEN_NETIF_GSO_FEAT_* */ } gso; + /* + * XEN_NETIF_EXTRA_TYPE_MCAST_{ADD,DEL}: + * Backend advertises availability via 'feature-multicast-control' + * xenbus node containing value '1'. + * Frontend requests this feature by advertising + * 'request-multicast-control' xenbus node containing value '1'. + * If multicast control is requested then multicast flooding is + * disabled and the frontend must explicitly register its interest + * in multicast groups using dummy transmit requests containing + * MCAST_{ADD,DEL} extra-info fragments. + */ + struct { + uint8_t addr[6]; /* Address to add/remove. */ + } mcast; + uint16_t pad[3]; } u; }; +typedef struct netif_extra_info netif_extra_info_t; struct netif_tx_response { uint16_t id; diff --git a/sys/xen/interface/io/pciif.h b/sys/xen/interface/io/pciif.h index 42dcfdb..0a0ffcc 100644 --- a/sys/xen/interface/io/pciif.h +++ b/sys/xen/interface/io/pciif.h @@ -34,6 +34,10 @@ /* xen_pci_op commands */ #define XEN_PCI_OP_conf_read (0) #define XEN_PCI_OP_conf_write (1) +#define XEN_PCI_OP_enable_msi (2) +#define XEN_PCI_OP_disable_msi (3) +#define XEN_PCI_OP_enable_msix (4) +#define XEN_PCI_OP_disable_msix (5) /* xen_pci_op error numbers */ #define XEN_PCI_ERR_success (0) @@ -44,6 +48,16 @@ /* XEN_PCI_ERR_op_failed - backend failed to complete the operation */ #define XEN_PCI_ERR_op_failed (-5) +/* + * it should be PAGE_SIZE-sizeof(struct xen_pci_op))/sizeof(struct msix_entry)) + * Should not exceed 128 + */ +#define SH_INFO_MAX_VEC 128 + +struct xen_msix_entry { + uint16_t vector; + uint16_t entry; +}; struct xen_pci_op { /* IN: what action to perform: XEN_PCI_OP_* */ uint32_t cmd; @@ -62,6 +76,10 @@ struct xen_pci_op { /* IN/OUT: Contains the result after a READ or the value to WRITE */ uint32_t value; + /* IN: Contains extra infor for this operation */ + uint32_t info; + /*IN: param for msi-x */ + struct xen_msix_entry msix_entries[SH_INFO_MAX_VEC]; }; struct xen_pci_sharedinfo { diff --git a/sys/xen/interface/io/protocols.h b/sys/xen/interface/io/protocols.h index 01fc8ae..77bd1bd 100644 --- a/sys/xen/interface/io/protocols.h +++ b/sys/xen/interface/io/protocols.h @@ -1,10 +1,31 @@ +/****************************************************************************** + * protocols.h + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to + * deal in the Software without restriction, including without limitation the + * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or + * sell copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER + * DEALINGS IN THE SOFTWARE. + */ + #ifndef __XEN_PROTOCOLS_H__ #define __XEN_PROTOCOLS_H__ #define XEN_IO_PROTO_ABI_X86_32 "x86_32-abi" #define XEN_IO_PROTO_ABI_X86_64 "x86_64-abi" #define XEN_IO_PROTO_ABI_IA64 "ia64-abi" -#define XEN_IO_PROTO_ABI_POWERPC64 "powerpc64-abi" #if defined(__i386__) # define XEN_IO_PROTO_ABI_NATIVE XEN_IO_PROTO_ABI_X86_32 @@ -12,8 +33,6 @@ # define XEN_IO_PROTO_ABI_NATIVE XEN_IO_PROTO_ABI_X86_64 #elif defined(__ia64__) # define XEN_IO_PROTO_ABI_NATIVE XEN_IO_PROTO_ABI_IA64 -#elif defined(__powerpc64__) -# define XEN_IO_PROTO_ABI_NATIVE XEN_IO_PROTO_ABI_POWERPC64 #else # error arch fixup needed here #endif diff --git a/sys/xen/interface/io/ring.h b/sys/xen/interface/io/ring.h index 355eba5..6ce1d0d 100644 --- a/sys/xen/interface/io/ring.h +++ b/sys/xen/interface/io/ring.h @@ -27,6 +27,14 @@ #ifndef __XEN_PUBLIC_IO_RING_H__ #define __XEN_PUBLIC_IO_RING_H__ +#include "../xen-compat.h" + +#if __XEN_INTERFACE_VERSION__ < 0x00030208 +#define xen_mb() mb() +#define xen_rmb() rmb() +#define xen_wmb() wmb() +#endif + typedef unsigned int RING_IDX; /* Round a 32-bit unsigned constant down to the nearest power of two. */ @@ -211,12 +219,12 @@ typedef struct __name##_back_ring __name##_back_ring_t (((_cons) - (_r)->rsp_prod_pvt) >= RING_SIZE(_r)) #define RING_PUSH_REQUESTS(_r) do { \ - wmb(); /* back sees requests /before/ updated producer index */ \ + xen_wmb(); /* back sees requests /before/ updated producer index */ \ (_r)->sring->req_prod = (_r)->req_prod_pvt; \ } while (0) #define RING_PUSH_RESPONSES(_r) do { \ - wmb(); /* front sees responses /before/ updated producer index */ \ + xen_wmb(); /* front sees resps /before/ updated producer index */ \ (_r)->sring->rsp_prod = (_r)->rsp_prod_pvt; \ } while (0) @@ -253,9 +261,9 @@ typedef struct __name##_back_ring __name##_back_ring_t #define RING_PUSH_REQUESTS_AND_CHECK_NOTIFY(_r, _notify) do { \ RING_IDX __old = (_r)->sring->req_prod; \ RING_IDX __new = (_r)->req_prod_pvt; \ - wmb(); /* back sees requests /before/ updated producer index */ \ + xen_wmb(); /* back sees requests /before/ updated producer index */ \ (_r)->sring->req_prod = __new; \ - mb(); /* back sees new requests /before/ we check req_event */ \ + xen_mb(); /* back sees new requests /before/ we check req_event */ \ (_notify) = ((RING_IDX)(__new - (_r)->sring->req_event) < \ (RING_IDX)(__new - __old)); \ } while (0) @@ -263,9 +271,9 @@ typedef struct __name##_back_ring __name##_back_ring_t #define RING_PUSH_RESPONSES_AND_CHECK_NOTIFY(_r, _notify) do { \ RING_IDX __old = (_r)->sring->rsp_prod; \ RING_IDX __new = (_r)->rsp_prod_pvt; \ - wmb(); /* front sees responses /before/ updated producer index */ \ + xen_wmb(); /* front sees resps /before/ updated producer index */ \ (_r)->sring->rsp_prod = __new; \ - mb(); /* front sees new responses /before/ we check rsp_event */ \ + xen_mb(); /* front sees new resps /before/ we check rsp_event */ \ (_notify) = ((RING_IDX)(__new - (_r)->sring->rsp_event) < \ (RING_IDX)(__new - __old)); \ } while (0) @@ -274,7 +282,7 @@ typedef struct __name##_back_ring __name##_back_ring_t (_work_to_do) = RING_HAS_UNCONSUMED_REQUESTS(_r); \ if (_work_to_do) break; \ (_r)->sring->req_event = (_r)->req_cons + 1; \ - mb(); \ + xen_mb(); \ (_work_to_do) = RING_HAS_UNCONSUMED_REQUESTS(_r); \ } while (0) @@ -282,7 +290,7 @@ typedef struct __name##_back_ring __name##_back_ring_t (_work_to_do) = RING_HAS_UNCONSUMED_RESPONSES(_r); \ if (_work_to_do) break; \ (_r)->sring->rsp_event = (_r)->rsp_cons + 1; \ - mb(); \ + xen_mb(); \ (_work_to_do) = RING_HAS_UNCONSUMED_RESPONSES(_r); \ } while (0) diff --git a/sys/xen/interface/io/xenbus.h b/sys/xen/interface/io/xenbus.h index 28584e5..4a053df 100644 --- a/sys/xen/interface/io/xenbus.h +++ b/sys/xen/interface/io/xenbus.h @@ -56,7 +56,14 @@ enum xenbus_state { */ XenbusStateClosing = 5, - XenbusStateClosed = 6 + XenbusStateClosed = 6, + + /* + * Reconfiguring: The device is being reconfigured. + */ + XenbusStateReconfiguring = 7, + + XenbusStateReconfigured = 8 }; typedef enum xenbus_state XenbusState; diff --git a/sys/xen/interface/io/xs_wire.h b/sys/xen/interface/io/xs_wire.h index 927ed8c..f6a49ab 100644 --- a/sys/xen/interface/io/xs_wire.h +++ b/sys/xen/interface/io/xs_wire.h @@ -46,7 +46,8 @@ enum xsd_sockmsg_type XS_WATCH_EVENT, XS_ERROR, XS_IS_DOMAIN_INTRODUCED, - XS_RESUME + XS_RESUME, + XS_SET_TARGET }; #define XS_WRITE_NONE "NONE" @@ -60,6 +61,7 @@ struct xsd_errors const char *errstring; }; #define XSD_ERROR(x) { x, #x } +/* LINTED: static unused */ static struct xsd_errors xsd_errors[] #if defined(__GNUC__) __attribute__((unused)) @@ -108,6 +110,13 @@ struct xenstore_domain_interface { XENSTORE_RING_IDX rsp_cons, rsp_prod; }; +/* Violating this is very bad. See docs/misc/xenstore.txt. */ +#define XENSTORE_PAYLOAD_MAX 4096 + +/* Violating these just gets you an error back */ +#define XENSTORE_ABS_PATH_MAX 3072 +#define XENSTORE_REL_PATH_MAX 2048 + #endif /* _XS_WIRE_H */ /* diff --git a/sys/xen/interface/kexec.h b/sys/xen/interface/kexec.h index ca6e85b..fc19f2f 100644 --- a/sys/xen/interface/kexec.h +++ b/sys/xen/interface/kexec.h @@ -1,6 +1,24 @@ /****************************************************************************** * kexec.h - Public portion * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to + * deal in the Software without restriction, including without limitation the + * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or + * sell copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER + * DEALINGS IN THE SOFTWARE. + * * Xen port written by: * - Simon 'Horms' Horman <horms@verge.net.au> * - Magnus Damm <magnus@valinux.co.jp> @@ -79,6 +97,9 @@ typedef struct xen_kexec_image { #if defined(__i386__) || defined(__x86_64__) unsigned long page_list[KEXEC_XEN_NO_PAGES]; #endif +#if defined(__ia64__) + unsigned long reboot_code_buffer; +#endif unsigned long indirection_page; unsigned long start_address; } xen_kexec_image_t; @@ -105,9 +126,19 @@ typedef struct xen_kexec_load { xen_kexec_image_t image; } xen_kexec_load_t; -#define KEXEC_RANGE_MA_CRASH 0 /* machine address and size of crash area */ -#define KEXEC_RANGE_MA_XEN 1 /* machine address and size of Xen itself */ -#define KEXEC_RANGE_MA_CPU 2 /* machine address and size of a CPU note */ +#define KEXEC_RANGE_MA_CRASH 0 /* machine address and size of crash area */ +#define KEXEC_RANGE_MA_XEN 1 /* machine address and size of Xen itself */ +#define KEXEC_RANGE_MA_CPU 2 /* machine address and size of a CPU note */ +#define KEXEC_RANGE_MA_XENHEAP 3 /* machine address and size of xenheap + * Note that although this is adjacent + * to Xen it exists in a separate EFI + * region on ia64, and thus needs to be + * inserted into iomem_machine separately */ +#define KEXEC_RANGE_MA_BOOT_PARAM 4 /* machine address and size of + * the ia64_boot_param */ +#define KEXEC_RANGE_MA_EFI_MEMMAP 5 /* machine address and size of + * of the EFI Memory Map */ +#define KEXEC_RANGE_MA_VMCOREINFO 6 /* machine address and size of vmcoreinfo */ /* * Find the address and size of certain memory areas @@ -124,6 +155,27 @@ typedef struct xen_kexec_range { unsigned long start; } xen_kexec_range_t; +/* vmcoreinfo stuff */ +#define VMCOREINFO_BYTES (4096) +#define VMCOREINFO_NOTE_NAME "VMCOREINFO_XEN" +void arch_crash_save_vmcoreinfo(void); +void vmcoreinfo_append_str(const char *fmt, ...) + __attribute__ ((format (printf, 1, 2))); +#define VMCOREINFO_PAGESIZE(value) \ + vmcoreinfo_append_str("PAGESIZE=%ld\n", value) +#define VMCOREINFO_SYMBOL(name) \ + vmcoreinfo_append_str("SYMBOL(%s)=%lx\n", #name, (unsigned long)&name) +#define VMCOREINFO_SYMBOL_ALIAS(alias, name) \ + vmcoreinfo_append_str("SYMBOL(%s)=%lx\n", #alias, (unsigned long)&name) +#define VMCOREINFO_STRUCT_SIZE(name) \ + vmcoreinfo_append_str("SIZE(%s)=%zu\n", #name, sizeof(struct name)) +#define VMCOREINFO_OFFSET(name, field) \ + vmcoreinfo_append_str("OFFSET(%s.%s)=%lu\n", #name, #field, \ + (unsigned long)offsetof(struct name, field)) +#define VMCOREINFO_OFFSET_ALIAS(name, field, alias) \ + vmcoreinfo_append_str("OFFSET(%s.%s)=%lu\n", #name, #alias, \ + (unsigned long)offsetof(struct name, field)) + #endif /* _XEN_PUBLIC_KEXEC_H */ /* diff --git a/sys/xen/interface/libelf.h b/sys/xen/interface/libelf.h index 4a580e0..d238330 100644 --- a/sys/xen/interface/libelf.h +++ b/sys/xen/interface/libelf.h @@ -1,10 +1,30 @@ +/****************************************************************************** + * libelf.h + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to + * deal in the Software without restriction, including without limitation the + * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or + * sell copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER + * DEALINGS IN THE SOFTWARE. + */ + #ifndef __XC_LIBELF__ #define __XC_LIBELF__ 1 -#if defined(__i386__) || defined(__x86_64) || defined(__ia64__) +#if defined(__i386__) || defined(__x86_64__) || defined(__ia64__) #define XEN_ELF_LITTLE_ENDIAN -#elif defined(__powerpc__) -#define XEN_ELF_BIG_ENDIAN #else #error define architectural endianness #endif @@ -69,6 +89,9 @@ struct elf_binary { uint64_t pend; uint64_t reloc_offset; + uint64_t bsd_symtab_pstart; + uint64_t bsd_symtab_pend; + #ifndef __XEN__ /* misc */ FILE *log; @@ -91,33 +114,32 @@ struct elf_binary { #define elf_lsb(elf) (ELFDATA2LSB == (elf)->data) #define elf_swap(elf) (NATIVE_ELFDATA != (elf)->data) -#define elf_uval(elf, str, elem) \ - ((ELFCLASS64 == (elf)->class) \ - ? elf_access_unsigned((elf), (str), \ - offsetof(typeof(*(str)),e64.elem), \ - sizeof((str)->e64.elem)) \ - : elf_access_unsigned((elf), (str), \ - offsetof(typeof(*(str)),e32.elem), \ - sizeof((str)->e32.elem))) - -#define elf_sval(elf, str, elem) \ - ((ELFCLASS64 == (elf)->class) \ - ? elf_access_signed((elf), (str), \ - offsetof(typeof(*(str)),e64.elem), \ - sizeof((str)->e64.elem)) \ - : elf_access_signed((elf), (str), \ - offsetof(typeof(*(str)),e32.elem), \ - sizeof((str)->e32.elem))) - -#define elf_size(elf, str) \ - ((ELFCLASS64 == (elf)->class) \ - ? sizeof((str)->e64) \ - : sizeof((str)->e32)) +#define elf_uval(elf, str, elem) \ + ((ELFCLASS64 == (elf)->class) \ + ? elf_access_unsigned((elf), (str), \ + offsetof(typeof(*(str)),e64.elem), \ + sizeof((str)->e64.elem)) \ + : elf_access_unsigned((elf), (str), \ + offsetof(typeof(*(str)),e32.elem), \ + sizeof((str)->e32.elem))) + +#define elf_sval(elf, str, elem) \ + ((ELFCLASS64 == (elf)->class) \ + ? elf_access_signed((elf), (str), \ + offsetof(typeof(*(str)),e64.elem), \ + sizeof((str)->e64.elem)) \ + : elf_access_signed((elf), (str), \ + offsetof(typeof(*(str)),e32.elem), \ + sizeof((str)->e32.elem))) + +#define elf_size(elf, str) \ + ((ELFCLASS64 == (elf)->class) \ + ? sizeof((str)->e64) : sizeof((str)->e32)) uint64_t elf_access_unsigned(struct elf_binary *elf, const void *ptr, - uint64_t offset, size_t size); + uint64_t offset, size_t size); int64_t elf_access_signed(struct elf_binary *elf, const void *ptr, - uint64_t offset, size_t size); + uint64_t offset, size_t size); uint64_t elf_round_up(struct elf_binary *elf, uint64_t addr); @@ -165,6 +187,8 @@ void elf_load_binary(struct elf_binary *elf); void *elf_get_ptr(struct elf_binary *elf, unsigned long addr); uint64_t elf_lookup_addr(struct elf_binary *elf, const char *symbol); +void elf_parse_bsdsyms(struct elf_binary *elf, uint64_t pstart); /* private */ + /* ------------------------------------------------------------------------ */ /* xc_libelf_relocate.c */ @@ -185,8 +209,8 @@ struct xen_elfnote { enum xen_elfnote_type type; const char *name; union { - const char *str; - uint64_t num; + const char *str; + uint64_t num; } data; }; @@ -228,14 +252,14 @@ static inline int elf_xen_feature_get(int nr, uint32_t * addr) } int elf_xen_parse_features(const char *features, - uint32_t *supported, - uint32_t *required); + uint32_t *supported, + uint32_t *required); int elf_xen_parse_note(struct elf_binary *elf, - struct elf_dom_parms *parms, - const elf_note *note); + struct elf_dom_parms *parms, + const elf_note *note); int elf_xen_parse_guest_info(struct elf_binary *elf, - struct elf_dom_parms *parms); + struct elf_dom_parms *parms); int elf_xen_parse(struct elf_binary *elf, - struct elf_dom_parms *parms); + struct elf_dom_parms *parms); #endif /* __XC_LIBELF__ */ diff --git a/sys/xen/interface/memory.h b/sys/xen/interface/memory.h index 73815fd..d7b9fff 100644 --- a/sys/xen/interface/memory.h +++ b/sys/xen/interface/memory.h @@ -35,6 +35,21 @@ #define XENMEM_increase_reservation 0 #define XENMEM_decrease_reservation 1 #define XENMEM_populate_physmap 6 + +#if __XEN_INTERFACE_VERSION__ >= 0x00030209 +/* + * Maximum # bits addressable by the user of the allocated region (e.g., I/O + * devices often have a 32-bit limitation even in 64-bit systems). If zero + * then the user has no addressing restriction. This field is not used by + * XENMEM_decrease_reservation. + */ +#define XENMEMF_address_bits(x) (x) +#define XENMEMF_get_address_bits(x) ((x) & 0xffu) +/* NUMA node to allocate from. */ +#define XENMEMF_node(x) (((x) + 1) << 8) +#define XENMEMF_get_node(x) ((((x) >> 8) - 1) & 0xffu) +#endif + struct xen_memory_reservation { /* @@ -47,19 +62,18 @@ struct xen_memory_reservation { * OUT: GMFN bases of extents that were allocated * (NB. This command also updates the mach_to_phys translation table) */ - xen_pfn_t *extent_start; + XEN_GUEST_HANDLE(xen_pfn_t) extent_start; /* Number of extents, and size/alignment of each (2^extent_order pages). */ xen_ulong_t nr_extents; unsigned int extent_order; - /* - * Maximum # bits addressable by the user of the allocated region (e.g., - * I/O devices often have a 32-bit limitation even in 64-bit systems). If - * zero then the user has no addressing restriction. - * This field is not used by XENMEM_decrease_reservation. - */ +#if __XEN_INTERFACE_VERSION__ >= 0x00030209 + /* XENMEMF flags. */ + unsigned int mem_flags; +#else unsigned int address_bits; +#endif /* * Domain whose reservation is being changed. @@ -152,7 +166,7 @@ struct xen_machphys_mfn_list { * any large discontiguities in the machine address space, 2MB gaps in * the machphys table will be represented by an MFN base of zero. */ - xen_pfn_t extent_start; + XEN_GUEST_HANDLE(xen_pfn_t) extent_start; /* * Number of extents written to the above array. This will be smaller @@ -190,6 +204,7 @@ struct xen_add_to_physmap { /* Source mapping space. */ #define XENMAPSPACE_shared_info 0 /* shared info page */ #define XENMAPSPACE_grant_table 1 /* grant table page */ +#define XENMAPSPACE_mfn 2 /* usual MFN */ unsigned int space; /* Index into source mapping space. */ @@ -202,6 +217,22 @@ typedef struct xen_add_to_physmap xen_add_to_physmap_t; DEFINE_XEN_GUEST_HANDLE(xen_add_to_physmap_t); /* + * Unmaps the page appearing at a particular GPFN from the specified guest's + * pseudophysical address space. + * arg == addr of xen_remove_from_physmap_t. + */ +#define XENMEM_remove_from_physmap 15 +struct xen_remove_from_physmap { + /* Which domain to change the mapping for. */ + domid_t domid; + + /* GPFN of the current mapping of the page. */ + xen_pfn_t gpfn; +}; +typedef struct xen_remove_from_physmap xen_remove_from_physmap_t; +DEFINE_XEN_GUEST_HANDLE(xen_remove_from_physmap_t); + +/* * Translates a list of domain-specific GPFNs into MFNs. Returns a -ve error * code on failure. This call only works for auto-translated guests. */ @@ -214,13 +245,13 @@ struct xen_translate_gpfn_list { xen_ulong_t nr_gpfns; /* List of GPFNs to translate. */ - xen_pfn_t gpfn_list; + XEN_GUEST_HANDLE(xen_pfn_t) gpfn_list; /* * Output list to contain MFN translations. May be the same as the input * list (in which case each input GPFN is overwritten with the output MFN). */ - xen_pfn_t mfn_list; + XEN_GUEST_HANDLE(xen_pfn_t) mfn_list; }; typedef struct xen_translate_gpfn_list xen_translate_gpfn_list_t; DEFINE_XEN_GUEST_HANDLE(xen_translate_gpfn_list_t); @@ -243,7 +274,7 @@ struct xen_memory_map { * Entries in the buffer are in the same format as returned by the * BIOS INT 0x15 EAX=0xE820 call. */ - void *buffer; + XEN_GUEST_HANDLE(void) buffer; }; typedef struct xen_memory_map xen_memory_map_t; DEFINE_XEN_GUEST_HANDLE(xen_memory_map_t); diff --git a/sys/xen/interface/platform.h b/sys/xen/interface/platform.h index dd3acb2..c69fdab 100644 --- a/sys/xen/interface/platform.h +++ b/sys/xen/interface/platform.h @@ -97,7 +97,7 @@ DEFINE_XEN_GUEST_HANDLE(xenpf_read_memtype_t); #define XENPF_microcode_update 35 struct xenpf_microcode_update { /* IN variables. */ - void * data; /* Pointer to microcode data */ + XEN_GUEST_HANDLE(const_void) data;/* Pointer to microcode data */ uint32_t length; /* Length of microcode data. */ }; typedef struct xenpf_microcode_update xenpf_microcode_update_t; @@ -135,7 +135,7 @@ struct xenpf_firmware_info { uint8_t legacy_sectors_per_track; /* %cl[5:0]: max sector # */ /* Int13, Fn41: Get Device Parameters (as filled into %ds:%esi). */ /* NB. First uint16_t of buffer must be set to buffer size. */ - void * edd_params; + XEN_GUEST_HANDLE(void) edd_params; } disk_info; /* XEN_FW_DISK_INFO */ struct { uint8_t device; /* bios device number */ @@ -146,13 +146,172 @@ struct xenpf_firmware_info { uint8_t capabilities; uint8_t edid_transfer_time; /* must refer to 128-byte buffer */ - XEN_GUEST_HANDLE(uint8_t) edid; + XEN_GUEST_HANDLE(uint8) edid; } vbeddc_info; /* XEN_FW_VBEDDC_INFO */ } u; }; typedef struct xenpf_firmware_info xenpf_firmware_info_t; DEFINE_XEN_GUEST_HANDLE(xenpf_firmware_info_t); +#define XENPF_enter_acpi_sleep 51 +struct xenpf_enter_acpi_sleep { + /* IN variables */ + uint16_t pm1a_cnt_val; /* PM1a control value. */ + uint16_t pm1b_cnt_val; /* PM1b control value. */ + uint32_t sleep_state; /* Which state to enter (Sn). */ + uint32_t flags; /* Must be zero. */ +}; +typedef struct xenpf_enter_acpi_sleep xenpf_enter_acpi_sleep_t; +DEFINE_XEN_GUEST_HANDLE(xenpf_enter_acpi_sleep_t); + +#define XENPF_change_freq 52 +struct xenpf_change_freq { + /* IN variables */ + uint32_t flags; /* Must be zero. */ + uint32_t cpu; /* Physical cpu. */ + uint64_t freq; /* New frequency (Hz). */ +}; +typedef struct xenpf_change_freq xenpf_change_freq_t; +DEFINE_XEN_GUEST_HANDLE(xenpf_change_freq_t); + +/* + * Get idle times (nanoseconds since boot) for physical CPUs specified in the + * @cpumap_bitmap with range [0..@cpumap_nr_cpus-1]. The @idletime array is + * indexed by CPU number; only entries with the corresponding @cpumap_bitmap + * bit set are written to. On return, @cpumap_bitmap is modified so that any + * non-existent CPUs are cleared. Such CPUs have their @idletime array entry + * cleared. + */ +#define XENPF_getidletime 53 +struct xenpf_getidletime { + /* IN/OUT variables */ + /* IN: CPUs to interrogate; OUT: subset of IN which are present */ + XEN_GUEST_HANDLE(uint8) cpumap_bitmap; + /* IN variables */ + /* Size of cpumap bitmap. */ + uint32_t cpumap_nr_cpus; + /* Must be indexable for every cpu in cpumap_bitmap. */ + XEN_GUEST_HANDLE(uint64) idletime; + /* OUT variables */ + /* System time when the idletime snapshots were taken. */ + uint64_t now; +}; +typedef struct xenpf_getidletime xenpf_getidletime_t; +DEFINE_XEN_GUEST_HANDLE(xenpf_getidletime_t); + +#define XENPF_set_processor_pminfo 54 + +/* ability bits */ +#define XEN_PROCESSOR_PM_CX 1 +#define XEN_PROCESSOR_PM_PX 2 +#define XEN_PROCESSOR_PM_TX 4 + +/* cmd type */ +#define XEN_PM_CX 0 +#define XEN_PM_PX 1 +#define XEN_PM_TX 2 + +/* Px sub info type */ +#define XEN_PX_PCT 1 +#define XEN_PX_PSS 2 +#define XEN_PX_PPC 4 +#define XEN_PX_PSD 8 + +struct xen_power_register { + uint32_t space_id; + uint32_t bit_width; + uint32_t bit_offset; + uint32_t access_size; + uint64_t address; +}; + +struct xen_processor_csd { + uint32_t domain; /* domain number of one dependent group */ + uint32_t coord_type; /* coordination type */ + uint32_t num; /* number of processors in same domain */ +}; +typedef struct xen_processor_csd xen_processor_csd_t; +DEFINE_XEN_GUEST_HANDLE(xen_processor_csd_t); + +struct xen_processor_cx { + struct xen_power_register reg; /* GAS for Cx trigger register */ + uint8_t type; /* cstate value, c0: 0, c1: 1, ... */ + uint32_t latency; /* worst latency (ms) to enter/exit this cstate */ + uint32_t power; /* average power consumption(mW) */ + uint32_t dpcnt; /* number of dependency entries */ + XEN_GUEST_HANDLE(xen_processor_csd_t) dp; /* NULL if no dependency */ +}; +typedef struct xen_processor_cx xen_processor_cx_t; +DEFINE_XEN_GUEST_HANDLE(xen_processor_cx_t); + +struct xen_processor_flags { + uint32_t bm_control:1; + uint32_t bm_check:1; + uint32_t has_cst:1; + uint32_t power_setup_done:1; + uint32_t bm_rld_set:1; +}; + +struct xen_processor_power { + uint32_t count; /* number of C state entries in array below */ + struct xen_processor_flags flags; /* global flags of this processor */ + XEN_GUEST_HANDLE(xen_processor_cx_t) states; /* supported c states */ +}; + +struct xen_pct_register { + uint8_t descriptor; + uint16_t length; + uint8_t space_id; + uint8_t bit_width; + uint8_t bit_offset; + uint8_t reserved; + uint64_t address; +}; + +struct xen_processor_px { + uint64_t core_frequency; /* megahertz */ + uint64_t power; /* milliWatts */ + uint64_t transition_latency; /* microseconds */ + uint64_t bus_master_latency; /* microseconds */ + uint64_t control; /* control value */ + uint64_t status; /* success indicator */ +}; +typedef struct xen_processor_px xen_processor_px_t; +DEFINE_XEN_GUEST_HANDLE(xen_processor_px_t); + +struct xen_psd_package { + uint64_t num_entries; + uint64_t revision; + uint64_t domain; + uint64_t coord_type; + uint64_t num_processors; +}; + +struct xen_processor_performance { + uint32_t flags; /* flag for Px sub info type */ + uint32_t platform_limit; /* Platform limitation on freq usage */ + struct xen_pct_register control_register; + struct xen_pct_register status_register; + uint32_t state_count; /* total available performance states */ + XEN_GUEST_HANDLE(xen_processor_px_t) states; + struct xen_psd_package domain_info; + uint32_t shared_type; /* coordination type of this processor */ +}; +typedef struct xen_processor_performance xen_processor_performance_t; +DEFINE_XEN_GUEST_HANDLE(xen_processor_performance_t); + +struct xenpf_set_processor_pminfo { + /* IN variables */ + uint32_t id; /* ACPI CPU ID */ + uint32_t type; /* {XEN_PM_CX, XEN_PM_PX} */ + union { + struct xen_processor_power power;/* Cx: _CST/_CSD */ + struct xen_processor_performance perf; /* Px: _PPC/_PCT/_PSS/_PSD */ + } u; +}; +typedef struct xenpf_set_processor_pminfo xenpf_set_processor_pminfo_t; +DEFINE_XEN_GUEST_HANDLE(xenpf_set_processor_pminfo_t); + struct xen_platform_op { uint32_t cmd; uint32_t interface_version; /* XENPF_INTERFACE_VERSION */ @@ -164,6 +323,10 @@ struct xen_platform_op { struct xenpf_microcode_update microcode; struct xenpf_platform_quirk platform_quirk; struct xenpf_firmware_info firmware_info; + struct xenpf_enter_acpi_sleep enter_acpi_sleep; + struct xenpf_change_freq change_freq; + struct xenpf_getidletime getidletime; + struct xenpf_set_processor_pminfo set_pminfo; uint8_t pad[128]; } u; }; diff --git a/sys/xen/interface/sysctl.h b/sys/xen/interface/sysctl.h index d51052a..6b10954 100644 --- a/sys/xen/interface/sysctl.h +++ b/sys/xen/interface/sysctl.h @@ -34,18 +34,27 @@ #include "xen.h" #include "domctl.h" -#define XEN_SYSCTL_INTERFACE_VERSION 0x00000003 +#define XEN_SYSCTL_INTERFACE_VERSION 0x00000006 /* * Read console content from Xen buffer ring. */ #define XEN_SYSCTL_readconsole 1 struct xen_sysctl_readconsole { - /* IN variables. */ - uint32_t clear; /* Non-zero -> clear after reading. */ - XEN_GUEST_HANDLE_64(char) buffer; /* Buffer start */ - /* IN/OUT variables. */ - uint32_t count; /* In: Buffer size; Out: Used buffer size */ + /* IN: Non-zero -> clear after reading. */ + uint8_t clear; + /* IN: Non-zero -> start index specified by @index field. */ + uint8_t incremental; + uint8_t pad0, pad1; + /* + * IN: Start index for consuming from ring buffer (if @incremental); + * OUT: End index after consuming from ring buffer. + */ + uint32_t index; + /* IN: Virtual address to write console data. */ + XEN_GUEST_HANDLE_64(char) buffer; + /* IN: Size of buffer; OUT: Bytes written to buffer. */ + uint32_t count; }; typedef struct xen_sysctl_readconsole xen_sysctl_readconsole_t; DEFINE_XEN_GUEST_HANDLE(xen_sysctl_readconsole_t); @@ -75,16 +84,41 @@ DEFINE_XEN_GUEST_HANDLE(xen_sysctl_tbuf_op_t); * Get physical information about the host machine */ #define XEN_SYSCTL_physinfo 3 + /* (x86) The platform supports HVM guests. */ +#define _XEN_SYSCTL_PHYSCAP_hvm 0 +#define XEN_SYSCTL_PHYSCAP_hvm (1u<<_XEN_SYSCTL_PHYSCAP_hvm) + /* (x86) The platform supports HVM-guest direct access to I/O devices. */ +#define _XEN_SYSCTL_PHYSCAP_hvm_directio 1 +#define XEN_SYSCTL_PHYSCAP_hvm_directio (1u<<_XEN_SYSCTL_PHYSCAP_hvm_directio) struct xen_sysctl_physinfo { uint32_t threads_per_core; uint32_t cores_per_socket; - uint32_t sockets_per_node; + uint32_t nr_cpus; uint32_t nr_nodes; uint32_t cpu_khz; uint64_aligned_t total_pages; uint64_aligned_t free_pages; uint64_aligned_t scrub_pages; uint32_t hw_cap[8]; + + /* + * IN: maximum addressable entry in the caller-provided cpu_to_node array. + * OUT: largest cpu identifier in the system. + * If OUT is greater than IN then the cpu_to_node array is truncated! + */ + uint32_t max_cpu_id; + /* + * If not NULL, this array is filled with node identifier for each cpu. + * If a cpu has no node information (e.g., cpu not present) then the + * sentinel value ~0u is written. + * The size of this array is specified by the caller in @max_cpu_id. + * If the actual @max_cpu_id is smaller than the array then the trailing + * elements of the array will not be written by the sysctl. + */ + XEN_GUEST_HANDLE_64(uint32) cpu_to_node; + + /* XEN_SYSCTL_PHYSCAP_??? */ + uint32_t capabilities; }; typedef struct xen_sysctl_physinfo xen_sysctl_physinfo_t; DEFINE_XEN_GUEST_HANDLE(xen_sysctl_physinfo_t); @@ -153,7 +187,7 @@ DEFINE_XEN_GUEST_HANDLE(xen_sysctl_debug_keys_t); /* Get physical CPU information. */ #define XEN_SYSCTL_getcpuinfo 8 struct xen_sysctl_cpuinfo { - uint64_t idletime; + uint64_aligned_t idletime; }; typedef struct xen_sysctl_cpuinfo xen_sysctl_cpuinfo_t; DEFINE_XEN_GUEST_HANDLE(xen_sysctl_cpuinfo_t); @@ -167,6 +201,79 @@ struct xen_sysctl_getcpuinfo { typedef struct xen_sysctl_getcpuinfo xen_sysctl_getcpuinfo_t; DEFINE_XEN_GUEST_HANDLE(xen_sysctl_getcpuinfo_t); +#define XEN_SYSCTL_availheap 9 +struct xen_sysctl_availheap { + /* IN variables. */ + uint32_t min_bitwidth; /* Smallest address width (zero if don't care). */ + uint32_t max_bitwidth; /* Largest address width (zero if don't care). */ + int32_t node; /* NUMA node of interest (-1 for all nodes). */ + /* OUT variables. */ + uint64_aligned_t avail_bytes;/* Bytes available in the specified region. */ +}; +typedef struct xen_sysctl_availheap xen_sysctl_availheap_t; +DEFINE_XEN_GUEST_HANDLE(xen_sysctl_availheap_t); + +#define XEN_SYSCTL_get_pmstat 10 +struct pm_px_val { + uint64_aligned_t freq; /* Px core frequency */ + uint64_aligned_t residency; /* Px residency time */ + uint64_aligned_t count; /* Px transition count */ +}; +typedef struct pm_px_val pm_px_val_t; +DEFINE_XEN_GUEST_HANDLE(pm_px_val_t); + +struct pm_px_stat { + uint8_t total; /* total Px states */ + uint8_t usable; /* usable Px states */ + uint8_t last; /* last Px state */ + uint8_t cur; /* current Px state */ + XEN_GUEST_HANDLE_64(uint64) trans_pt; /* Px transition table */ + XEN_GUEST_HANDLE_64(pm_px_val_t) pt; +}; +typedef struct pm_px_stat pm_px_stat_t; +DEFINE_XEN_GUEST_HANDLE(pm_px_stat_t); + +struct pm_cx_stat { + uint32_t nr; /* entry nr in triggers & residencies, including C0 */ + uint32_t last; /* last Cx state */ + uint64_aligned_t idle_time; /* idle time from boot */ + XEN_GUEST_HANDLE_64(uint64) triggers; /* Cx trigger counts */ + XEN_GUEST_HANDLE_64(uint64) residencies; /* Cx residencies */ +}; + +struct xen_sysctl_get_pmstat { +#define PMSTAT_CATEGORY_MASK 0xf0 +#define PMSTAT_PX 0x10 +#define PMSTAT_CX 0x20 +#define PMSTAT_get_max_px (PMSTAT_PX | 0x1) +#define PMSTAT_get_pxstat (PMSTAT_PX | 0x2) +#define PMSTAT_reset_pxstat (PMSTAT_PX | 0x3) +#define PMSTAT_get_max_cx (PMSTAT_CX | 0x1) +#define PMSTAT_get_cxstat (PMSTAT_CX | 0x2) +#define PMSTAT_reset_cxstat (PMSTAT_CX | 0x3) + uint32_t type; + uint32_t cpuid; + union { + struct pm_px_stat getpx; + struct pm_cx_stat getcx; + /* other struct for tx, etc */ + } u; +}; +typedef struct xen_sysctl_get_pmstat xen_sysctl_get_pmstat_t; +DEFINE_XEN_GUEST_HANDLE(xen_sysctl_get_pmstat_t); + +#define XEN_SYSCTL_cpu_hotplug 11 +struct xen_sysctl_cpu_hotplug { + /* IN variables */ + uint32_t cpu; /* Physical cpu. */ +#define XEN_SYSCTL_CPU_HOTPLUG_ONLINE 0 +#define XEN_SYSCTL_CPU_HOTPLUG_OFFLINE 1 + uint32_t op; /* hotplug opcode */ +}; +typedef struct xen_sysctl_cpu_hotplug xen_sysctl_cpu_hotplug_t; +DEFINE_XEN_GUEST_HANDLE(xen_sysctl_cpu_hotplug_t); + + struct xen_sysctl { uint32_t cmd; uint32_t interface_version; /* XEN_SYSCTL_INTERFACE_VERSION */ @@ -179,6 +286,9 @@ struct xen_sysctl { struct xen_sysctl_getdomaininfolist getdomaininfolist; struct xen_sysctl_debug_keys debug_keys; struct xen_sysctl_getcpuinfo getcpuinfo; + struct xen_sysctl_availheap availheap; + struct xen_sysctl_get_pmstat get_pmstat; + struct xen_sysctl_cpu_hotplug cpu_hotplug; uint8_t pad[128]; } u; }; diff --git a/sys/xen/interface/trace.h b/sys/xen/interface/trace.h index 33654e4..a11b30f 100644 --- a/sys/xen/interface/trace.h +++ b/sys/xen/interface/trace.h @@ -26,14 +26,23 @@ #ifndef __XEN_PUBLIC_TRACE_H__ #define __XEN_PUBLIC_TRACE_H__ +#define TRACE_EXTRA_MAX 7 +#define TRACE_EXTRA_SHIFT 28 + /* Trace classes */ #define TRC_CLS_SHIFT 16 -#define TRC_GEN 0x0001f000 /* General trace */ -#define TRC_SCHED 0x0002f000 /* Xen Scheduler trace */ -#define TRC_DOM0OP 0x0004f000 /* Xen DOM0 operation trace */ -#define TRC_HVM 0x0008f000 /* Xen HVM trace */ -#define TRC_MEM 0x0010f000 /* Xen memory trace */ -#define TRC_ALL 0xfffff000 +#define TRC_GEN 0x0001f000 /* General trace */ +#define TRC_SCHED 0x0002f000 /* Xen Scheduler trace */ +#define TRC_DOM0OP 0x0004f000 /* Xen DOM0 operation trace */ +#define TRC_HVM 0x0008f000 /* Xen HVM trace */ +#define TRC_MEM 0x0010f000 /* Xen memory trace */ +#define TRC_PV 0x0020f000 /* Xen PV traces */ +#define TRC_SHADOW 0x0040f000 /* Xen shadow tracing */ +#define TRC_ALL 0x0ffff000 +#define TRC_HD_TO_EVENT(x) ((x)&0x0fffffff) +#define TRC_HD_CYCLE_FLAG (1UL<<31) +#define TRC_HD_INCLUDES_CYCLE_COUNT(x) ( !!( (x) & TRC_HD_CYCLE_FLAG ) ) +#define TRC_HD_EXTRA(x) (((x)>>TRACE_EXTRA_SHIFT)&TRACE_EXTRA_MAX) /* Trace subclasses */ #define TRC_SUBCLS_SHIFT 12 @@ -42,41 +51,82 @@ #define TRC_HVM_ENTRYEXIT 0x00081000 /* VMENTRY and #VMEXIT */ #define TRC_HVM_HANDLER 0x00082000 /* various HVM handlers */ +#define TRC_SCHED_MIN 0x00021000 /* Just runstate changes */ +#define TRC_SCHED_VERBOSE 0x00028000 /* More inclusive scheduling */ + /* Trace events per class */ #define TRC_LOST_RECORDS (TRC_GEN + 1) +#define TRC_TRACE_WRAP_BUFFER (TRC_GEN + 2) +#define TRC_TRACE_CPU_CHANGE (TRC_GEN + 3) -#define TRC_SCHED_DOM_ADD (TRC_SCHED + 1) -#define TRC_SCHED_DOM_REM (TRC_SCHED + 2) -#define TRC_SCHED_SLEEP (TRC_SCHED + 3) -#define TRC_SCHED_WAKE (TRC_SCHED + 4) -#define TRC_SCHED_YIELD (TRC_SCHED + 5) -#define TRC_SCHED_BLOCK (TRC_SCHED + 6) -#define TRC_SCHED_SHUTDOWN (TRC_SCHED + 7) -#define TRC_SCHED_CTL (TRC_SCHED + 8) -#define TRC_SCHED_ADJDOM (TRC_SCHED + 9) -#define TRC_SCHED_SWITCH (TRC_SCHED + 10) -#define TRC_SCHED_S_TIMER_FN (TRC_SCHED + 11) -#define TRC_SCHED_T_TIMER_FN (TRC_SCHED + 12) -#define TRC_SCHED_DOM_TIMER_FN (TRC_SCHED + 13) -#define TRC_SCHED_SWITCH_INFPREV (TRC_SCHED + 14) -#define TRC_SCHED_SWITCH_INFNEXT (TRC_SCHED + 15) +#define TRC_SCHED_RUNSTATE_CHANGE (TRC_SCHED_MIN + 1) +#define TRC_SCHED_DOM_ADD (TRC_SCHED_VERBOSE + 1) +#define TRC_SCHED_DOM_REM (TRC_SCHED_VERBOSE + 2) +#define TRC_SCHED_SLEEP (TRC_SCHED_VERBOSE + 3) +#define TRC_SCHED_WAKE (TRC_SCHED_VERBOSE + 4) +#define TRC_SCHED_YIELD (TRC_SCHED_VERBOSE + 5) +#define TRC_SCHED_BLOCK (TRC_SCHED_VERBOSE + 6) +#define TRC_SCHED_SHUTDOWN (TRC_SCHED_VERBOSE + 7) +#define TRC_SCHED_CTL (TRC_SCHED_VERBOSE + 8) +#define TRC_SCHED_ADJDOM (TRC_SCHED_VERBOSE + 9) +#define TRC_SCHED_SWITCH (TRC_SCHED_VERBOSE + 10) +#define TRC_SCHED_S_TIMER_FN (TRC_SCHED_VERBOSE + 11) +#define TRC_SCHED_T_TIMER_FN (TRC_SCHED_VERBOSE + 12) +#define TRC_SCHED_DOM_TIMER_FN (TRC_SCHED_VERBOSE + 13) +#define TRC_SCHED_SWITCH_INFPREV (TRC_SCHED_VERBOSE + 14) +#define TRC_SCHED_SWITCH_INFNEXT (TRC_SCHED_VERBOSE + 15) #define TRC_MEM_PAGE_GRANT_MAP (TRC_MEM + 1) #define TRC_MEM_PAGE_GRANT_UNMAP (TRC_MEM + 2) #define TRC_MEM_PAGE_GRANT_TRANSFER (TRC_MEM + 3) +#define TRC_PV_HYPERCALL (TRC_PV + 1) +#define TRC_PV_TRAP (TRC_PV + 3) +#define TRC_PV_PAGE_FAULT (TRC_PV + 4) +#define TRC_PV_FORCED_INVALID_OP (TRC_PV + 5) +#define TRC_PV_EMULATE_PRIVOP (TRC_PV + 6) +#define TRC_PV_EMULATE_4GB (TRC_PV + 7) +#define TRC_PV_MATH_STATE_RESTORE (TRC_PV + 8) +#define TRC_PV_PAGING_FIXUP (TRC_PV + 9) +#define TRC_PV_GDT_LDT_MAPPING_FAULT (TRC_PV + 10) +#define TRC_PV_PTWR_EMULATION (TRC_PV + 11) +#define TRC_PV_PTWR_EMULATION_PAE (TRC_PV + 12) + /* Indicates that addresses in trace record are 64 bits */ +#define TRC_64_FLAG (0x100) + +#define TRC_SHADOW_NOT_SHADOW (TRC_SHADOW + 1) +#define TRC_SHADOW_FAST_PROPAGATE (TRC_SHADOW + 2) +#define TRC_SHADOW_FAST_MMIO (TRC_SHADOW + 3) +#define TRC_SHADOW_FALSE_FAST_PATH (TRC_SHADOW + 4) +#define TRC_SHADOW_MMIO (TRC_SHADOW + 5) +#define TRC_SHADOW_FIXUP (TRC_SHADOW + 6) +#define TRC_SHADOW_DOMF_DYING (TRC_SHADOW + 7) +#define TRC_SHADOW_EMULATE (TRC_SHADOW + 8) +#define TRC_SHADOW_EMULATE_UNSHADOW_USER (TRC_SHADOW + 9) +#define TRC_SHADOW_EMULATE_UNSHADOW_EVTINJ (TRC_SHADOW + 10) +#define TRC_SHADOW_EMULATE_UNSHADOW_UNHANDLED (TRC_SHADOW + 11) +#define TRC_SHADOW_WRMAP_BF (TRC_SHADOW + 12) +#define TRC_SHADOW_PREALLOC_UNPIN (TRC_SHADOW + 13) +#define TRC_SHADOW_RESYNC_FULL (TRC_SHADOW + 14) +#define TRC_SHADOW_RESYNC_ONLY (TRC_SHADOW + 15) + /* trace events per subclass */ #define TRC_HVM_VMENTRY (TRC_HVM_ENTRYEXIT + 0x01) #define TRC_HVM_VMEXIT (TRC_HVM_ENTRYEXIT + 0x02) +#define TRC_HVM_VMEXIT64 (TRC_HVM_ENTRYEXIT + TRC_64_FLAG + 0x02) #define TRC_HVM_PF_XEN (TRC_HVM_HANDLER + 0x01) +#define TRC_HVM_PF_XEN64 (TRC_HVM_HANDLER + TRC_64_FLAG + 0x01) #define TRC_HVM_PF_INJECT (TRC_HVM_HANDLER + 0x02) +#define TRC_HVM_PF_INJECT64 (TRC_HVM_HANDLER + TRC_64_FLAG + 0x02) #define TRC_HVM_INJ_EXC (TRC_HVM_HANDLER + 0x03) #define TRC_HVM_INJ_VIRQ (TRC_HVM_HANDLER + 0x04) #define TRC_HVM_REINJ_VIRQ (TRC_HVM_HANDLER + 0x05) #define TRC_HVM_IO_READ (TRC_HVM_HANDLER + 0x06) #define TRC_HVM_IO_WRITE (TRC_HVM_HANDLER + 0x07) #define TRC_HVM_CR_READ (TRC_HVM_HANDLER + 0x08) +#define TRC_HVM_CR_READ64 (TRC_HVM_HANDLER + TRC_64_FLAG + 0x08) #define TRC_HVM_CR_WRITE (TRC_HVM_HANDLER + 0x09) +#define TRC_HVM_CR_WRITE64 (TRC_HVM_HANDLER + TRC_64_FLAG + 0x09) #define TRC_HVM_DR_READ (TRC_HVM_HANDLER + 0x0A) #define TRC_HVM_DR_WRITE (TRC_HVM_HANDLER + 0x0B) #define TRC_HVM_MSR_READ (TRC_HVM_HANDLER + 0x0C) @@ -88,13 +138,28 @@ #define TRC_HVM_VMMCALL (TRC_HVM_HANDLER + 0x12) #define TRC_HVM_HLT (TRC_HVM_HANDLER + 0x13) #define TRC_HVM_INVLPG (TRC_HVM_HANDLER + 0x14) +#define TRC_HVM_INVLPG64 (TRC_HVM_HANDLER + TRC_64_FLAG + 0x14) #define TRC_HVM_MCE (TRC_HVM_HANDLER + 0x15) +#define TRC_HVM_IO_ASSIST (TRC_HVM_HANDLER + 0x16) +#define TRC_HVM_MMIO_ASSIST (TRC_HVM_HANDLER + 0x17) +#define TRC_HVM_CLTS (TRC_HVM_HANDLER + 0x18) +#define TRC_HVM_LMSW (TRC_HVM_HANDLER + 0x19) +#define TRC_HVM_LMSW64 (TRC_HVM_HANDLER + TRC_64_FLAG + 0x19) /* This structure represents a single trace buffer record. */ struct t_rec { - uint64_t cycles; /* cycle counter timestamp */ - uint32_t event; /* event ID */ - unsigned long data[5]; /* event data items */ + uint32_t event:28; + uint32_t extra_u32:3; /* # entries in trailing extra_u32[] array */ + uint32_t cycles_included:1; /* u.cycles or u.no_cycles? */ + union { + struct { + uint32_t cycles_lo, cycles_hi; /* cycle counter timestamp */ + uint32_t extra_u32[7]; /* event data items */ + } cycles; + struct { + uint32_t extra_u32[7]; /* event data items */ + } nocycles; + } u; }; /* @@ -102,9 +167,17 @@ struct t_rec { * field, indexes into an array of struct t_rec's. */ struct t_buf { - uint32_t cons; /* Next item to be consumed by control tools. */ - uint32_t prod; /* Next item to be produced by Xen. */ - /* 'nr_recs' records follow immediately after the meta-data header. */ + /* Assume the data buffer size is X. X is generally not a power of 2. + * CONS and PROD are incremented modulo (2*X): + * 0 <= cons < 2*X + * 0 <= prod < 2*X + * This is done because addition modulo X breaks at 2^32 when X is not a + * power of 2: + * (((2^32 - 1) % X) + 1) % X != (2^32) % X + */ + uint32_t cons; /* Offset of next item to be consumed by control tools. */ + uint32_t prod; /* Offset of next item to be produced by Xen. */ + /* Records follow immediately after the meta-data header. */ }; #endif /* __XEN_PUBLIC_TRACE_H__ */ diff --git a/sys/xen/interface/xen-compat.h b/sys/xen/interface/xen-compat.h index 19b0a2c..329be07 100644 --- a/sys/xen/interface/xen-compat.h +++ b/sys/xen/interface/xen-compat.h @@ -27,7 +27,7 @@ #ifndef __XEN_PUBLIC_XEN_COMPAT_H__ #define __XEN_PUBLIC_XEN_COMPAT_H__ -#define __XEN_LATEST_INTERFACE_VERSION__ 0x00030205 +#define __XEN_LATEST_INTERFACE_VERSION__ 0x00030209 #if defined(__XEN__) || defined(__XEN_TOOLS__) /* Xen is built with matching headers and implements the latest interface. */ @@ -41,11 +41,4 @@ #error "These header files do not support the requested interface version." #endif -/* Fields defined as a Xen guest handle since 0x00030205. */ -#if __XEN_INTERFACE_VERSION__ >= 0x00030205 -#define XEN_GUEST_HANDLE_00030205(type) XEN_GUEST_HANDLE(type) -#else -#define XEN_GUEST_HANDLE_00030205(type) type * -#endif - #endif /* __XEN_PUBLIC_XEN_COMPAT_H__ */ diff --git a/sys/xen/interface/xen.h b/sys/xen/interface/xen.h index 0606dbe..4b444b4 100644 --- a/sys/xen/interface/xen.h +++ b/sys/xen/interface/xen.h @@ -27,18 +27,29 @@ #ifndef __XEN_PUBLIC_XEN_H__ #define __XEN_PUBLIC_XEN_H__ -#include <xen/interface/xen-compat.h> +#include "xen-compat.h" #if defined(__i386__) || defined(__x86_64__) -#include <xen/interface/arch-x86/xen.h> +#include "arch-x86/xen.h" #elif defined(__ia64__) #include "arch-ia64.h" -#elif defined(__powerpc__) -#include "arch-powerpc.h" #else #error "Unsupported architecture" #endif +#ifndef __ASSEMBLY__ +/* Guest handles for primitive C types. */ +DEFINE_XEN_GUEST_HANDLE(char); +__DEFINE_XEN_GUEST_HANDLE(uchar, unsigned char); +DEFINE_XEN_GUEST_HANDLE(int); +__DEFINE_XEN_GUEST_HANDLE(uint, unsigned int); +DEFINE_XEN_GUEST_HANDLE(long); +__DEFINE_XEN_GUEST_HANDLE(ulong, unsigned long); +DEFINE_XEN_GUEST_HANDLE(void); + +DEFINE_XEN_GUEST_HANDLE(xen_pfn_t); +#endif + /* * HYPERCALLS */ @@ -69,7 +80,7 @@ #define __HYPERVISOR_vcpu_op 24 #define __HYPERVISOR_set_segment_base 25 /* x86/64 only */ #define __HYPERVISOR_mmuext_op 26 -#define __HYPERVISOR_acm_op 27 +#define __HYPERVISOR_xsm_op 27 #define __HYPERVISOR_nmi_op 28 #define __HYPERVISOR_sched_op 29 #define __HYPERVISOR_callback_op 30 @@ -103,7 +114,6 @@ /* New event-channel and physdev hypercalls introduced in 0x00030202. */ #if __XEN_INTERFACE_VERSION__ < 0x00030202 -#warning using compat ops #undef __HYPERVISOR_event_channel_op #define __HYPERVISOR_event_channel_op __HYPERVISOR_event_channel_op_compat #undef __HYPERVISOR_physdev_op @@ -169,9 +179,14 @@ * ptr[:2] -- Machine address within the frame whose mapping to modify. * The frame must belong to the FD, if one is specified. * val -- Value to write into the mapping entry. + * + * ptr[1:0] == MMU_PT_UPDATE_PRESERVE_AD: + * As MMU_NORMAL_PT_UPDATE above, but A/D bits currently in the PTE are ORed + * with those in @val. */ -#define MMU_NORMAL_PT_UPDATE 0 /* checked '*ptr = val'. ptr is MA. */ -#define MMU_MACHPHYS_UPDATE 1 /* ptr = MA of frame to modify entry for */ +#define MMU_NORMAL_PT_UPDATE 0 /* checked '*ptr = val'. ptr is MA. */ +#define MMU_MACHPHYS_UPDATE 1 /* ptr = MA of frame to modify entry for */ +#define MMU_PT_UPDATE_PRESERVE_AD 2 /* atomically: *ptr = val | (*ptr&(A|D)) */ /* * MMU EXTENDED OPERATIONS @@ -246,7 +261,11 @@ struct mmuext_op { /* SET_LDT */ unsigned int nr_ents; /* TLB_FLUSH_MULTI, INVLPG_MULTI */ - XEN_GUEST_HANDLE_00030205(void) vcpumask; +#if __XEN_INTERFACE_VERSION__ >= 0x00030205 + XEN_GUEST_HANDLE(void) vcpumask; +#else + void *vcpumask; +#endif } arg2; }; typedef struct mmuext_op mmuext_op_t; @@ -535,6 +554,7 @@ typedef struct start_info start_info_t; /* These flags are passed in the 'flags' field of start_info_t. */ #define SIF_PRIVILEGED (1<<0) /* Is the domain privileged? */ #define SIF_INITDOMAIN (1<<1) /* Is this the initial control domain? */ +#define SIF_PM_MASK (0xFF<<8) /* reserve 1 byte for xen-pm options */ typedef struct dom0_vga_console_info { uint8_t video_type; /* DOM0_VGA_CONSOLE_??? */ @@ -566,6 +586,12 @@ typedef struct dom0_vga_console_info { uint8_t green_pos, green_size; uint8_t blue_pos, blue_size; uint8_t rsvd_pos, rsvd_size; +#if __XEN_INTERFACE_VERSION__ >= 0x00030206 + /* VESA capabilities (offset 0xa, VESA command 0x4f00). */ + uint32_t gbl_caps; + /* Mode attributes (offset 0x0, VESA command 0x4f01). */ + uint16_t mode_attrs; +#endif } vesa_lfb; } u; } dom0_vga_console_info_t; @@ -578,10 +604,10 @@ typedef uint8_t xen_domain_handle_t[16]; #define __mk_unsigned_long(x) x ## UL #define mk_unsigned_long(x) __mk_unsigned_long(x) -DEFINE_XEN_GUEST_HANDLE(uint8_t); -DEFINE_XEN_GUEST_HANDLE(uint16_t); -DEFINE_XEN_GUEST_HANDLE(uint32_t); -DEFINE_XEN_GUEST_HANDLE(uint64_t); +__DEFINE_XEN_GUEST_HANDLE(uint8, uint8_t); +__DEFINE_XEN_GUEST_HANDLE(uint16, uint16_t); +__DEFINE_XEN_GUEST_HANDLE(uint32, uint32_t); +__DEFINE_XEN_GUEST_HANDLE(uint64, uint64_t); #else /* __ASSEMBLY__ */ |