|
dvander@367
|
1 |
/** |
|
ds@653
|
2 |
* vim: set ts=4 : |
|
ds@1330
|
3 |
* ============================================================================= |
|
ds@1330
|
4 |
* SourcePawn JIT |
|
ds@1330
|
5 |
* Copyright (C)2004-2007 AlliedModders LLC. All rights reserved. |
|
ds@1330
|
6 |
* ============================================================================= |
|
dvander@367
|
7 |
* |
|
ds@1330
|
8 |
* This file is not open source and may not be copied without explicit wriiten |
|
ds@1330
|
9 |
* permission of AlliedModders LLC. This file may not be redistributed in whole |
|
ds@1330
|
10 |
* or significant part. |
|
dvander@367
|
11 |
* For information, see LICENSE.txt or http://www.sourcemod.net/license.php |
|
dvander@367
|
12 |
* |
|
dvander@367
|
13 |
* Version: $Id$ |
|
dvander@367
|
14 |
*/ |
|
dvander@367
|
15 |
|
|
dvander@157
|
16 |
#ifndef _INCLUDE_SOURCEPAWN_JIT_X86_H_ |
|
dvander@157
|
17 |
#define _INCLUDE_SOURCEPAWN_JIT_X86_H_ |
|
dvander@157
|
18 |
|
|
dvander@157
|
19 |
#include <sp_vm_types.h> |
|
dvander@157
|
20 |
#include <sp_vm_api.h> |
|
dvander@706
|
21 |
#include <jit_helpers.h> |
|
dvander@157
|
22 |
|
|
dvander@157
|
23 |
using namespace SourcePawn; |
|
dvander@157
|
24 |
|
|
dvander@157
|
25 |
#define JIT_INLINE_ERRORCHECKS (1<<0) |
|
dvander@157
|
26 |
#define JIT_INLINE_NATIVES (1<<1) |
|
dvander@175
|
27 |
#define STACK_MARGIN 64 //8 parameters of safety, I guess |
|
dvander@175
|
28 |
#define JIT_FUNCMAGIC 0x214D4148 //magic function offset |
|
dvander@157
|
29 |
|
|
dvander@157
|
30 |
#define JITVARS_TRACKER 0 //important: don't change this to avoid trouble |
|
dvander@175
|
31 |
#define JITVARS_FUNCINFO 1 //important: don't change this aWOAWOGJQG I LIKE HAM |
|
dvander@344
|
32 |
#define JITVARS_REBASE 2 //important: hi, i'm bail |
|
dvander@157
|
33 |
|
|
dvander@1396
|
34 |
#define sDIMEN_MAX 5 //this must mirror what the compiler has. |
|
dvander@1396
|
35 |
|
|
dvander@157
|
36 |
typedef struct tracker_s |
|
dvander@157
|
37 |
{ |
|
dvander@157
|
38 |
size_t size; |
|
dvander@157
|
39 |
ucell_t *pBase; |
|
dvander@157
|
40 |
ucell_t *pCur; |
|
dvander@157
|
41 |
} tracker_t; |
|
dvander@157
|
42 |
|
|
dvander@175
|
43 |
typedef struct funcinfo_s |
|
dvander@175
|
44 |
{ |
|
dvander@175
|
45 |
unsigned int magic; |
|
dvander@175
|
46 |
unsigned int index; |
|
dvander@175
|
47 |
} funcinfo_t; |
|
dvander@175
|
48 |
|
|
dvander@175
|
49 |
typedef struct functracker_s |
|
dvander@175
|
50 |
{ |
|
dvander@175
|
51 |
unsigned int num_functions; |
|
dvander@175
|
52 |
unsigned int code_size; |
|
dvander@175
|
53 |
} functracker_t; |
|
dvander@175
|
54 |
|
|
faluco@831
|
55 |
struct floattbl_t |
|
faluco@831
|
56 |
{ |
|
faluco@831
|
57 |
floattbl_t() |
|
faluco@831
|
58 |
{ |
|
faluco@831
|
59 |
found = false; |
|
faluco@831
|
60 |
index = 0; |
|
faluco@831
|
61 |
} |
|
faluco@831
|
62 |
bool found; |
|
faluco@831
|
63 |
unsigned int index; |
|
faluco@831
|
64 |
}; |
|
faluco@831
|
65 |
|
|
dvander@157
|
66 |
class CompData : public ICompilation |
|
dvander@157
|
67 |
{ |
|
dvander@157
|
68 |
public: |
|
dvander@157
|
69 |
CompData() : plugin(NULL), |
|
dvander@1930
|
70 |
debug(false), profile(0), inline_level(0), rebase(NULL), |
|
dvander@175
|
71 |
error_set(SP_ERROR_NONE), func_idx(0) |
|
dvander@157
|
72 |
{ |
|
dvander@157
|
73 |
}; |
|
dvander@157
|
74 |
public: |
|
dvander@157
|
75 |
sp_plugin_t *plugin; /* plugin handle */ |
|
dvander@350
|
76 |
bool debug; /* whether to compile debug mode */ |
|
dvander@1930
|
77 |
int profile; /* profiling flags */ |
|
dvander@350
|
78 |
int inline_level; /* inline optimization level */ |
|
dvander@157
|
79 |
jitcode_t rebase; /* relocation map */ |
|
dvander@350
|
80 |
int error_set; /* error code to halt process */ |
|
dvander@350
|
81 |
unsigned int func_idx; /* current function index */ |
|
dvander@157
|
82 |
jitoffs_t jit_return; /* point in main call to return to */ |
|
dvander@157
|
83 |
jitoffs_t jit_verify_addr_eax; |
|
dvander@157
|
84 |
jitoffs_t jit_verify_addr_edx; |
|
dvander@157
|
85 |
jitoffs_t jit_break; /* call to op.break */ |
|
dvander@157
|
86 |
jitoffs_t jit_sysreq_n; /* call version of op.sysreq.n */ |
|
dvander@157
|
87 |
jitoffs_t jit_genarray; /* call to genarray intrinsic */ |
|
dvander@157
|
88 |
jitoffs_t jit_error_bounds; |
|
dvander@157
|
89 |
jitoffs_t jit_error_divzero; |
|
dvander@157
|
90 |
jitoffs_t jit_error_stacklow; |
|
dvander@157
|
91 |
jitoffs_t jit_error_stackmin; |
|
dvander@157
|
92 |
jitoffs_t jit_error_memaccess; |
|
dvander@157
|
93 |
jitoffs_t jit_error_heaplow; |
|
dvander@157
|
94 |
jitoffs_t jit_error_heapmin; |
|
dvander@157
|
95 |
jitoffs_t jit_error_array_too_big; |
|
dvander@157
|
96 |
jitoffs_t jit_extern_error; /* returning generic error */ |
|
dvander@157
|
97 |
jitoffs_t jit_sysreq_c; /* old version! */ |
|
faluco@831
|
98 |
jitoffs_t jit_rounding_table; |
|
faluco@831
|
99 |
floattbl_t *jit_float_table; |
|
dvander@157
|
100 |
uint32_t codesize; /* total codesize */ |
|
dvander@157
|
101 |
}; |
|
dvander@157
|
102 |
|
|
dvander@157
|
103 |
class JITX86 : public IVirtualMachine |
|
dvander@157
|
104 |
{ |
|
dvander@157
|
105 |
public: |
|
dvander@157
|
106 |
const char *GetVMName(); |
|
dvander@157
|
107 |
ICompilation *StartCompilation(sp_plugin_t *plugin); |
|
dvander@157
|
108 |
bool SetCompilationOption(ICompilation *co, const char *key, const char *val); |
|
dvander@157
|
109 |
sp_context_t *CompileToContext(ICompilation *co, int *err); |
|
dvander@157
|
110 |
void AbortCompilation(ICompilation *co); |
|
dvander@157
|
111 |
void FreeContext(sp_context_t *ctx); |
|
dvander@157
|
112 |
int ContextExecute(sp_context_t *ctx, uint32_t code_idx, cell_t *result); |
|
dvander@175
|
113 |
unsigned int GetAPIVersion(); |
|
dvander@175
|
114 |
bool FunctionLookup(const sp_context_t *ctx, uint32_t code_addr, unsigned int *result); |
|
dvander@344
|
115 |
bool FunctionPLookup(const sp_context_t *ctx, uint32_t code_addr, unsigned int *result); |
|
dvander@175
|
116 |
unsigned int FunctionCount(const sp_context_t *ctx); |
|
dvander@253
|
117 |
const char *GetVersionString(); |
|
dvander@253
|
118 |
const char *GetCPUOptimizations(); |
|
dvander@601
|
119 |
SPVM_NATIVE_FUNC CreateFakeNative(SPVM_FAKENATIVE_FUNC callback, void *pData); |
|
dvander@605
|
120 |
void DestroyFakeNative(SPVM_NATIVE_FUNC func); |
|
dvander@157
|
121 |
}; |
|
dvander@157
|
122 |
|
|
dvander@157
|
123 |
cell_t NativeCallback(sp_context_t *ctx, ucell_t native_idx, cell_t *params); |
|
dvander@157
|
124 |
cell_t NativeCallback_Debug(sp_context_t *ctx, ucell_t native_idx, cell_t *params); |
|
dvander@1930
|
125 |
cell_t NativeCallback_Debug_Profile(sp_context_t *ctx, ucell_t native_idx, cell_t *params); |
|
dvander@1930
|
126 |
cell_t NativeCallback_Profile(sp_context_t *ctx, ucell_t native_idx, cell_t *params); |
|
dvander@157
|
127 |
jitoffs_t RelocLookup(JitWriter *jit, cell_t pcode_offs, bool relative=false); |
|
dvander@157
|
128 |
|
|
dvander@157
|
129 |
#define AMX_REG_PRI REG_EAX |
|
dvander@157
|
130 |
#define AMX_REG_ALT REG_EDX |
|
dvander@157
|
131 |
#define AMX_REG_STK REG_EDI |
|
dvander@157
|
132 |
#define AMX_REG_DAT REG_EBP |
|
dvander@157
|
133 |
#define AMX_REG_TMP REG_ECX |
|
dvander@157
|
134 |
#define AMX_REG_INFO REG_ESI |
|
dvander@157
|
135 |
#define AMX_REG_FRM REG_EBX |
|
dvander@157
|
136 |
|
|
dvander@157
|
137 |
#define AMX_INFO_FRM AMX_REG_INFO //not relocated |
|
dvander@157
|
138 |
#define AMX_INFO_FRAME 0 //(same thing as above) |
|
dvander@157
|
139 |
#define AMX_INFO_HEAP 4 //not relocated |
|
dvander@157
|
140 |
#define AMX_INFO_RETVAL 8 //physical |
|
dvander@157
|
141 |
#define AMX_INFO_CONTEXT 12 //physical |
|
dvander@157
|
142 |
#define AMX_INFO_STACKTOP 16 //relocated |
|
dvander@157
|
143 |
|
|
dvander@157
|
144 |
extern ISourcePawnEngine *engine; |
|
dvander@157
|
145 |
|
|
dvander@157
|
146 |
#endif //_INCLUDE_SOURCEPAWN_JIT_X86_H_ |