| #ifndef __SVM_H | 
 | #define __SVM_H | 
 |  | 
 | #include <uapi/asm/svm.h> | 
 |  | 
 |  | 
 | enum { | 
 | 	INTERCEPT_INTR, | 
 | 	INTERCEPT_NMI, | 
 | 	INTERCEPT_SMI, | 
 | 	INTERCEPT_INIT, | 
 | 	INTERCEPT_VINTR, | 
 | 	INTERCEPT_SELECTIVE_CR0, | 
 | 	INTERCEPT_STORE_IDTR, | 
 | 	INTERCEPT_STORE_GDTR, | 
 | 	INTERCEPT_STORE_LDTR, | 
 | 	INTERCEPT_STORE_TR, | 
 | 	INTERCEPT_LOAD_IDTR, | 
 | 	INTERCEPT_LOAD_GDTR, | 
 | 	INTERCEPT_LOAD_LDTR, | 
 | 	INTERCEPT_LOAD_TR, | 
 | 	INTERCEPT_RDTSC, | 
 | 	INTERCEPT_RDPMC, | 
 | 	INTERCEPT_PUSHF, | 
 | 	INTERCEPT_POPF, | 
 | 	INTERCEPT_CPUID, | 
 | 	INTERCEPT_RSM, | 
 | 	INTERCEPT_IRET, | 
 | 	INTERCEPT_INTn, | 
 | 	INTERCEPT_INVD, | 
 | 	INTERCEPT_PAUSE, | 
 | 	INTERCEPT_HLT, | 
 | 	INTERCEPT_INVLPG, | 
 | 	INTERCEPT_INVLPGA, | 
 | 	INTERCEPT_IOIO_PROT, | 
 | 	INTERCEPT_MSR_PROT, | 
 | 	INTERCEPT_TASK_SWITCH, | 
 | 	INTERCEPT_FERR_FREEZE, | 
 | 	INTERCEPT_SHUTDOWN, | 
 | 	INTERCEPT_VMRUN, | 
 | 	INTERCEPT_VMMCALL, | 
 | 	INTERCEPT_VMLOAD, | 
 | 	INTERCEPT_VMSAVE, | 
 | 	INTERCEPT_STGI, | 
 | 	INTERCEPT_CLGI, | 
 | 	INTERCEPT_SKINIT, | 
 | 	INTERCEPT_RDTSCP, | 
 | 	INTERCEPT_ICEBP, | 
 | 	INTERCEPT_WBINVD, | 
 | 	INTERCEPT_MONITOR, | 
 | 	INTERCEPT_MWAIT, | 
 | 	INTERCEPT_MWAIT_COND, | 
 | 	INTERCEPT_XSETBV, | 
 | }; | 
 |  | 
 |  | 
 | struct __attribute__ ((__packed__)) vmcb_control_area { | 
 | 	u32 intercept_cr; | 
 | 	u32 intercept_dr; | 
 | 	u32 intercept_exceptions; | 
 | 	u64 intercept; | 
 | 	u8 reserved_1[42]; | 
 | 	u16 pause_filter_count; | 
 | 	u64 iopm_base_pa; | 
 | 	u64 msrpm_base_pa; | 
 | 	u64 tsc_offset; | 
 | 	u32 asid; | 
 | 	u8 tlb_ctl; | 
 | 	u8 reserved_2[3]; | 
 | 	u32 int_ctl; | 
 | 	u32 int_vector; | 
 | 	u32 int_state; | 
 | 	u8 reserved_3[4]; | 
 | 	u32 exit_code; | 
 | 	u32 exit_code_hi; | 
 | 	u64 exit_info_1; | 
 | 	u64 exit_info_2; | 
 | 	u32 exit_int_info; | 
 | 	u32 exit_int_info_err; | 
 | 	u64 nested_ctl; | 
 | 	u64 avic_vapic_bar; | 
 | 	u8 reserved_4[8]; | 
 | 	u32 event_inj; | 
 | 	u32 event_inj_err; | 
 | 	u64 nested_cr3; | 
 | 	u64 virt_ext; | 
 | 	u32 clean; | 
 | 	u32 reserved_5; | 
 | 	u64 next_rip; | 
 | 	u8 insn_len; | 
 | 	u8 insn_bytes[15]; | 
 | 	u64 avic_backing_page;	/* Offset 0xe0 */ | 
 | 	u8 reserved_6[8];	/* Offset 0xe8 */ | 
 | 	u64 avic_logical_id;	/* Offset 0xf0 */ | 
 | 	u64 avic_physical_id;	/* Offset 0xf8 */ | 
 | 	u8 reserved_7[768]; | 
 | }; | 
 |  | 
 |  | 
 | #define TLB_CONTROL_DO_NOTHING 0 | 
 | #define TLB_CONTROL_FLUSH_ALL_ASID 1 | 
 | #define TLB_CONTROL_FLUSH_ASID 3 | 
 | #define TLB_CONTROL_FLUSH_ASID_LOCAL 7 | 
 |  | 
 | #define V_TPR_MASK 0x0f | 
 |  | 
 | #define V_IRQ_SHIFT 8 | 
 | #define V_IRQ_MASK (1 << V_IRQ_SHIFT) | 
 |  | 
 | #define V_INTR_PRIO_SHIFT 16 | 
 | #define V_INTR_PRIO_MASK (0x0f << V_INTR_PRIO_SHIFT) | 
 |  | 
 | #define V_IGN_TPR_SHIFT 20 | 
 | #define V_IGN_TPR_MASK (1 << V_IGN_TPR_SHIFT) | 
 |  | 
 | #define V_INTR_MASKING_SHIFT 24 | 
 | #define V_INTR_MASKING_MASK (1 << V_INTR_MASKING_SHIFT) | 
 |  | 
 | #define AVIC_ENABLE_SHIFT 31 | 
 | #define AVIC_ENABLE_MASK (1 << AVIC_ENABLE_SHIFT) | 
 |  | 
 | #define LBR_CTL_ENABLE_MASK BIT_ULL(0) | 
 | #define VIRTUAL_VMLOAD_VMSAVE_ENABLE_MASK BIT_ULL(1) | 
 |  | 
 | #define SVM_INTERRUPT_SHADOW_MASK 1 | 
 |  | 
 | #define SVM_IOIO_STR_SHIFT 2 | 
 | #define SVM_IOIO_REP_SHIFT 3 | 
 | #define SVM_IOIO_SIZE_SHIFT 4 | 
 | #define SVM_IOIO_ASIZE_SHIFT 7 | 
 |  | 
 | #define SVM_IOIO_TYPE_MASK 1 | 
 | #define SVM_IOIO_STR_MASK (1 << SVM_IOIO_STR_SHIFT) | 
 | #define SVM_IOIO_REP_MASK (1 << SVM_IOIO_REP_SHIFT) | 
 | #define SVM_IOIO_SIZE_MASK (7 << SVM_IOIO_SIZE_SHIFT) | 
 | #define SVM_IOIO_ASIZE_MASK (7 << SVM_IOIO_ASIZE_SHIFT) | 
 |  | 
 | #define SVM_VM_CR_VALID_MASK	0x001fULL | 
 | #define SVM_VM_CR_SVM_LOCK_MASK 0x0008ULL | 
 | #define SVM_VM_CR_SVM_DIS_MASK  0x0010ULL | 
 |  | 
 | struct __attribute__ ((__packed__)) vmcb_seg { | 
 | 	u16 selector; | 
 | 	u16 attrib; | 
 | 	u32 limit; | 
 | 	u64 base; | 
 | }; | 
 |  | 
 | struct __attribute__ ((__packed__)) vmcb_save_area { | 
 | 	struct vmcb_seg es; | 
 | 	struct vmcb_seg cs; | 
 | 	struct vmcb_seg ss; | 
 | 	struct vmcb_seg ds; | 
 | 	struct vmcb_seg fs; | 
 | 	struct vmcb_seg gs; | 
 | 	struct vmcb_seg gdtr; | 
 | 	struct vmcb_seg ldtr; | 
 | 	struct vmcb_seg idtr; | 
 | 	struct vmcb_seg tr; | 
 | 	u8 reserved_1[43]; | 
 | 	u8 cpl; | 
 | 	u8 reserved_2[4]; | 
 | 	u64 efer; | 
 | 	u8 reserved_3[112]; | 
 | 	u64 cr4; | 
 | 	u64 cr3; | 
 | 	u64 cr0; | 
 | 	u64 dr7; | 
 | 	u64 dr6; | 
 | 	u64 rflags; | 
 | 	u64 rip; | 
 | 	u8 reserved_4[88]; | 
 | 	u64 rsp; | 
 | 	u8 reserved_5[24]; | 
 | 	u64 rax; | 
 | 	u64 star; | 
 | 	u64 lstar; | 
 | 	u64 cstar; | 
 | 	u64 sfmask; | 
 | 	u64 kernel_gs_base; | 
 | 	u64 sysenter_cs; | 
 | 	u64 sysenter_esp; | 
 | 	u64 sysenter_eip; | 
 | 	u64 cr2; | 
 | 	u8 reserved_6[32]; | 
 | 	u64 g_pat; | 
 | 	u64 dbgctl; | 
 | 	u64 br_from; | 
 | 	u64 br_to; | 
 | 	u64 last_excp_from; | 
 | 	u64 last_excp_to; | 
 | }; | 
 |  | 
 | struct __attribute__ ((__packed__)) vmcb { | 
 | 	struct vmcb_control_area control; | 
 | 	struct vmcb_save_area save; | 
 | }; | 
 |  | 
 | #define SVM_CPUID_FUNC 0x8000000a | 
 |  | 
 | #define SVM_VM_CR_SVM_DISABLE 4 | 
 |  | 
 | #define SVM_SELECTOR_S_SHIFT 4 | 
 | #define SVM_SELECTOR_DPL_SHIFT 5 | 
 | #define SVM_SELECTOR_P_SHIFT 7 | 
 | #define SVM_SELECTOR_AVL_SHIFT 8 | 
 | #define SVM_SELECTOR_L_SHIFT 9 | 
 | #define SVM_SELECTOR_DB_SHIFT 10 | 
 | #define SVM_SELECTOR_G_SHIFT 11 | 
 |  | 
 | #define SVM_SELECTOR_TYPE_MASK (0xf) | 
 | #define SVM_SELECTOR_S_MASK (1 << SVM_SELECTOR_S_SHIFT) | 
 | #define SVM_SELECTOR_DPL_MASK (3 << SVM_SELECTOR_DPL_SHIFT) | 
 | #define SVM_SELECTOR_P_MASK (1 << SVM_SELECTOR_P_SHIFT) | 
 | #define SVM_SELECTOR_AVL_MASK (1 << SVM_SELECTOR_AVL_SHIFT) | 
 | #define SVM_SELECTOR_L_MASK (1 << SVM_SELECTOR_L_SHIFT) | 
 | #define SVM_SELECTOR_DB_MASK (1 << SVM_SELECTOR_DB_SHIFT) | 
 | #define SVM_SELECTOR_G_MASK (1 << SVM_SELECTOR_G_SHIFT) | 
 |  | 
 | #define SVM_SELECTOR_WRITE_MASK (1 << 1) | 
 | #define SVM_SELECTOR_READ_MASK SVM_SELECTOR_WRITE_MASK | 
 | #define SVM_SELECTOR_CODE_MASK (1 << 3) | 
 |  | 
 | #define INTERCEPT_CR0_READ	0 | 
 | #define INTERCEPT_CR3_READ	3 | 
 | #define INTERCEPT_CR4_READ	4 | 
 | #define INTERCEPT_CR8_READ	8 | 
 | #define INTERCEPT_CR0_WRITE	(16 + 0) | 
 | #define INTERCEPT_CR3_WRITE	(16 + 3) | 
 | #define INTERCEPT_CR4_WRITE	(16 + 4) | 
 | #define INTERCEPT_CR8_WRITE	(16 + 8) | 
 |  | 
 | #define INTERCEPT_DR0_READ	0 | 
 | #define INTERCEPT_DR1_READ	1 | 
 | #define INTERCEPT_DR2_READ	2 | 
 | #define INTERCEPT_DR3_READ	3 | 
 | #define INTERCEPT_DR4_READ	4 | 
 | #define INTERCEPT_DR5_READ	5 | 
 | #define INTERCEPT_DR6_READ	6 | 
 | #define INTERCEPT_DR7_READ	7 | 
 | #define INTERCEPT_DR0_WRITE	(16 + 0) | 
 | #define INTERCEPT_DR1_WRITE	(16 + 1) | 
 | #define INTERCEPT_DR2_WRITE	(16 + 2) | 
 | #define INTERCEPT_DR3_WRITE	(16 + 3) | 
 | #define INTERCEPT_DR4_WRITE	(16 + 4) | 
 | #define INTERCEPT_DR5_WRITE	(16 + 5) | 
 | #define INTERCEPT_DR6_WRITE	(16 + 6) | 
 | #define INTERCEPT_DR7_WRITE	(16 + 7) | 
 |  | 
 | #define SVM_EVTINJ_VEC_MASK 0xff | 
 |  | 
 | #define SVM_EVTINJ_TYPE_SHIFT 8 | 
 | #define SVM_EVTINJ_TYPE_MASK (7 << SVM_EVTINJ_TYPE_SHIFT) | 
 |  | 
 | #define SVM_EVTINJ_TYPE_INTR (0 << SVM_EVTINJ_TYPE_SHIFT) | 
 | #define SVM_EVTINJ_TYPE_NMI (2 << SVM_EVTINJ_TYPE_SHIFT) | 
 | #define SVM_EVTINJ_TYPE_EXEPT (3 << SVM_EVTINJ_TYPE_SHIFT) | 
 | #define SVM_EVTINJ_TYPE_SOFT (4 << SVM_EVTINJ_TYPE_SHIFT) | 
 |  | 
 | #define SVM_EVTINJ_VALID (1 << 31) | 
 | #define SVM_EVTINJ_VALID_ERR (1 << 11) | 
 |  | 
 | #define SVM_EXITINTINFO_VEC_MASK SVM_EVTINJ_VEC_MASK | 
 | #define SVM_EXITINTINFO_TYPE_MASK SVM_EVTINJ_TYPE_MASK | 
 |  | 
 | #define	SVM_EXITINTINFO_TYPE_INTR SVM_EVTINJ_TYPE_INTR | 
 | #define	SVM_EXITINTINFO_TYPE_NMI SVM_EVTINJ_TYPE_NMI | 
 | #define	SVM_EXITINTINFO_TYPE_EXEPT SVM_EVTINJ_TYPE_EXEPT | 
 | #define	SVM_EXITINTINFO_TYPE_SOFT SVM_EVTINJ_TYPE_SOFT | 
 |  | 
 | #define SVM_EXITINTINFO_VALID SVM_EVTINJ_VALID | 
 | #define SVM_EXITINTINFO_VALID_ERR SVM_EVTINJ_VALID_ERR | 
 |  | 
 | #define SVM_EXITINFOSHIFT_TS_REASON_IRET 36 | 
 | #define SVM_EXITINFOSHIFT_TS_REASON_JMP 38 | 
 | #define SVM_EXITINFOSHIFT_TS_HAS_ERROR_CODE 44 | 
 |  | 
 | #define SVM_EXITINFO_REG_MASK 0x0F | 
 |  | 
 | #define SVM_CR0_SELECTIVE_MASK (X86_CR0_TS | X86_CR0_MP) | 
 |  | 
 | #define SVM_VMLOAD ".byte 0x0f, 0x01, 0xda" | 
 | #define SVM_VMRUN  ".byte 0x0f, 0x01, 0xd8" | 
 | #define SVM_VMSAVE ".byte 0x0f, 0x01, 0xdb" | 
 | #define SVM_CLGI   ".byte 0x0f, 0x01, 0xdd" | 
 | #define SVM_STGI   ".byte 0x0f, 0x01, 0xdc" | 
 | #define SVM_INVLPGA ".byte 0x0f, 0x01, 0xdf" | 
 |  | 
 | #endif |