1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
|
/* $NetBSD: x86emu.h,v 1.1 2007/12/01 20:14:10 joerg Exp $ */
/* $OpenBSD: x86emu.h,v 1.3 2009/06/06 03:45:05 matthieu Exp $ */
/****************************************************************************
*
* Realmode X86 Emulator Library
*
* Copyright (C) 1996-1999 SciTech Software, Inc.
* Copyright (C) David Mosberger-Tang
* Copyright (C) 1999 Egbert Eich
* Copyright (C) 2007 Joerg Sonnenberger
*
* ========================================================================
*
* Permission to use, copy, modify, distribute, and sell this software and
* its documentation for any purpose is hereby granted without fee,
* provided that the above copyright notice appear in all copies and that
* both that copyright notice and this permission notice appear in
* supporting documentation, and that the name of the authors not be used
* in advertising or publicity pertaining to distribution of the software
* without specific, written prior permission. The authors makes no
* representations about the suitability of this software for any purpose.
* It is provided "as is" without express or implied warranty.
*
* THE AUTHORS DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
* INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO
* EVENT SHALL THE AUTHORS BE LIABLE FOR ANY SPECIAL, INDIRECT OR
* CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF
* USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR
* OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
* PERFORMANCE OF THIS SOFTWARE.
*
****************************************************************************/
#ifndef __X86EMU_X86EMU_H
#define __X86EMU_X86EMU_H
#include <sys/types.h>
#include <sys/endian.h>
#ifdef _KERNEL
#include <sys/systm.h>
#else
#include <setjmp.h>
#endif
/*
* General EAX, EBX, ECX, EDX type registers. Note that for
* portability, and speed, the issue of byte swapping is not addressed
* in the registers. All registers are stored in the default format
* available on the host machine. The only critical issue is that the
* registers should line up EXACTLY in the same manner as they do in
* the 386. That is:
*
* EAX & 0xff === AL
* EAX & 0xffff == AX
*
* etc. The result is that alot of the calculations can then be
* done using the native instruction set fully.
*/
#ifdef __BIG_ENDIAN__
struct x86emu_register32 {
uint32_t e_reg;
};
struct x86emu_register16 {
uint16_t filler0;
uint16_t x_reg;
};
struct x86emu_register8 {
uint8_t filler0, filler1;
uint8_t h_reg, l_reg;
};
#else /* !__BIG_ENDIAN__ */
struct x86emu_register32 {
uint32_t e_reg;
};
struct x86emu_register16 {
uint16_t x_reg;
};
struct x86emu_register8 {
uint8_t l_reg, h_reg;
};
#endif /* BIG_ENDIAN */
union x86emu_register {
struct x86emu_register32 I32_reg;
struct x86emu_register16 I16_reg;
struct x86emu_register8 I8_reg;
};
struct x86emu_regs {
uint16_t register_cs;
uint16_t register_ds;
uint16_t register_es;
uint16_t register_fs;
uint16_t register_gs;
uint16_t register_ss;
uint32_t register_flags;
union x86emu_register register_a;
union x86emu_register register_b;
union x86emu_register register_c;
union x86emu_register register_d;
union x86emu_register register_sp;
union x86emu_register register_bp;
union x86emu_register register_si;
union x86emu_register register_di;
union x86emu_register register_ip;
/*
* MODE contains information on:
* REPE prefix 2 bits repe,repne
* SEGMENT overrides 5 bits normal,DS,SS,CS,ES
* Delayed flag set 3 bits (zero, signed, parity)
* reserved 6 bits
* interrupt # 8 bits instruction raised interrupt
* BIOS video segregs 4 bits
* Interrupt Pending 1 bits
* Extern interrupt 1 bits
* Halted 1 bits
*/
uint32_t mode;
volatile int intr; /* mask of pending interrupts */
uint8_t intno;
uint8_t __pad[3];
};
struct x86emu {
char *mem_base;
size_t mem_size;
void *sys_private;
struct x86emu_regs x86;
#ifdef _KERNEL
label_t exec_state;
#else
jmp_buf exec_state;
#endif
uint64_t cur_cycles;
unsigned int cur_mod:2;
unsigned int cur_rl:3;
unsigned int cur_rh:3;
uint32_t cur_offset;
uint8_t (*emu_rdb)(struct x86emu *, uint32_t addr);
uint16_t (*emu_rdw)(struct x86emu *, uint32_t addr);
uint32_t (*emu_rdl)(struct x86emu *, uint32_t addr);
void (*emu_wrb)(struct x86emu *, uint32_t addr,uint8_t val);
void (*emu_wrw)(struct x86emu *, uint32_t addr, uint16_t val);
void (*emu_wrl)(struct x86emu *, uint32_t addr, uint32_t val);
uint8_t (*emu_inb)(struct x86emu *, uint16_t addr);
uint16_t (*emu_inw)(struct x86emu *, uint16_t addr);
uint32_t (*emu_inl)(struct x86emu *, uint16_t addr);
void (*emu_outb)(struct x86emu *, uint16_t addr, uint8_t val);
void (*emu_outw)(struct x86emu *, uint16_t addr, uint16_t val);
void (*emu_outl)(struct x86emu *, uint16_t addr, uint32_t val);
void (*_x86emu_intrTab[256])(struct x86emu *, int);
};
__BEGIN_DECLS
void x86emu_init_default(struct x86emu *);
/* decode.c */
void x86emu_exec(struct x86emu *);
void x86emu_exec_call(struct x86emu *, uint16_t, uint16_t);
void x86emu_exec_intr(struct x86emu *, uint8_t);
void x86emu_halt_sys(struct x86emu *) __dead;
__END_DECLS
#endif /* __X86EMU_X86EMU_H */
|