1 /******************************************************************************
2  * hvm/emulate.h
3  *
4  * HVM instruction emulation. Used for MMIO and VMX real mode.
5  *
6  * Copyright (c) 2008 Citrix Systems, Inc.
7  *
8  * Authors:
9  *    Keir Fraser <keir@xen.org>
10  */
11 
12 #ifndef __ASM_X86_HVM_EMULATE_H__
13 #define __ASM_X86_HVM_EMULATE_H__
14 
15 #include <xen/err.h>
16 #include <asm/hvm/hvm.h>
17 #include <asm/x86_emulate.h>
18 
19 typedef bool hvm_emulate_validate_t(const struct x86_emulate_state *state,
20                                     const struct x86_emulate_ctxt *ctxt);
21 
22 struct hvm_emulate_ctxt {
23     struct x86_emulate_ctxt ctxt;
24 
25     /*
26      * validate: Post-decode, pre-emulate hook to allow caller controlled
27      * filtering.
28      */
29     hvm_emulate_validate_t *validate;
30 
31     /* Cache of 16 bytes of instruction. */
32     uint8_t insn_buf[16];
33     unsigned long insn_buf_eip;
34     unsigned int insn_buf_bytes;
35 
36     struct segment_register seg_reg[10];
37     unsigned long seg_reg_accessed;
38     unsigned long seg_reg_dirty;
39 
40     /*
41      * MFNs behind temporary mappings in the write callback.  The length is
42      * arbitrary, and can be increased if writes longer than PAGE_SIZE+1 are
43      * needed.
44      */
45     mfn_t mfn[2];
46 
47     uint32_t intr_shadow;
48 
49     bool_t set_context;
50 };
51 
52 enum emul_kind {
53     EMUL_KIND_NORMAL,
54     EMUL_KIND_NOWRITE,
55     EMUL_KIND_SET_CONTEXT_DATA,
56     EMUL_KIND_SET_CONTEXT_INSN
57 };
58 
59 bool __nonnull(1, 2) hvm_emulate_one_insn(
60     hvm_emulate_validate_t *validate,
61     const char *descr);
62 int hvm_emulate_one(
63     struct hvm_emulate_ctxt *hvmemul_ctxt);
64 void hvm_emulate_one_vm_event(enum emul_kind kind,
65     unsigned int trapnr,
66     unsigned int errcode);
67 /* Must be called once to set up hvmemul state. */
68 void hvm_emulate_init_once(
69     struct hvm_emulate_ctxt *hvmemul_ctxt,
70     hvm_emulate_validate_t *validate,
71     struct cpu_user_regs *regs);
72 /* Must be called once before each instruction emulated. */
73 void hvm_emulate_init_per_insn(
74     struct hvm_emulate_ctxt *hvmemul_ctxt,
75     const unsigned char *insn_buf,
76     unsigned int insn_bytes);
77 void hvm_emulate_writeback(
78     struct hvm_emulate_ctxt *hvmemul_ctxt);
79 int hvmemul_cpuid(uint32_t leaf, uint32_t subleaf,
80                   struct cpuid_leaf *res, struct x86_emulate_ctxt *ctxt);
81 struct segment_register *hvmemul_get_seg_reg(
82     enum x86_segment seg,
83     struct hvm_emulate_ctxt *hvmemul_ctxt);
84 int hvm_emulate_one_mmio(unsigned long mfn, unsigned long gla);
85 
handle_mmio(void)86 static inline bool handle_mmio(void)
87 {
88     return hvm_emulate_one_insn(x86_insn_is_mem_access, "MMIO");
89 }
90 
91 int hvmemul_insn_fetch(enum x86_segment seg,
92                        unsigned long offset,
93                        void *p_data,
94                        unsigned int bytes,
95                        struct x86_emulate_ctxt *ctxt);
96 int hvmemul_do_pio_buffer(uint16_t port,
97                           unsigned int size,
98                           uint8_t dir,
99                           void *buffer);
100 
101 void hvm_dump_emulation_state(const char *loglvl, const char *prefix,
102                               struct hvm_emulate_ctxt *hvmemul_ctxt, int rc);
103 
104 #endif /* __ASM_X86_HVM_EMULATE_H__ */
105 
106 /*
107  * Local variables:
108  * mode: C
109  * c-file-style: "BSD"
110  * c-basic-offset: 4
111  * tab-width: 4
112  * indent-tabs-mode: nil
113  * End:
114  */
115