1 /*
2 ===========================================================================
3 Copyright (C) 1999-2005 Id Software, Inc.
4 
5 This file is part of Quake III Arena source code.
6 
7 Quake III Arena source code is free software; you can redistribute it
8 and/or modify it under the terms of the GNU General Public License as
9 published by the Free Software Foundation; either version 2 of the License,
10 or (at your option) any later version.
11 
12 Quake III Arena source code is distributed in the hope that it will be
13 useful, but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15 GNU General Public License for more details.
16 
17 You should have received a copy of the GNU General Public License
18 along with Quake III Arena source code; if not, write to the Free Software
19 Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
20 ===========================================================================
21 */
22 #include "q_shared.h"
23 #include "qcommon.h"
24 
25 typedef enum {
26 	OP_UNDEF,
27 
28 	OP_IGNORE,
29 
30 	OP_BREAK,
31 
32 	OP_ENTER,
33 	OP_LEAVE,
34 	OP_CALL,
35 	OP_PUSH,
36 	OP_POP,
37 
38 	OP_CONST,
39 	OP_LOCAL,
40 
41 	OP_JUMP,
42 
43 	//-------------------
44 
45 	OP_EQ,
46 	OP_NE,
47 
48 	OP_LTI,
49 	OP_LEI,
50 	OP_GTI,
51 	OP_GEI,
52 
53 	OP_LTU,
54 	OP_LEU,
55 	OP_GTU,
56 	OP_GEU,
57 
58 	OP_EQF,
59 	OP_NEF,
60 
61 	OP_LTF,
62 	OP_LEF,
63 	OP_GTF,
64 	OP_GEF,
65 
66 	//-------------------
67 
68 	OP_LOAD1,
69 	OP_LOAD2,
70 	OP_LOAD4,
71 	OP_STORE1,
72 	OP_STORE2,
73 	OP_STORE4,				// *(stack[top-1]) = stack[top]
74 	OP_ARG,
75 
76 	OP_BLOCK_COPY,
77 
78 	//-------------------
79 
80 	OP_SEX8,
81 	OP_SEX16,
82 
83 	OP_NEGI,
84 	OP_ADD,
85 	OP_SUB,
86 	OP_DIVI,
87 	OP_DIVU,
88 	OP_MODI,
89 	OP_MODU,
90 	OP_MULI,
91 	OP_MULU,
92 
93 	OP_BAND,
94 	OP_BOR,
95 	OP_BXOR,
96 	OP_BCOM,
97 
98 	OP_LSH,
99 	OP_RSHI,
100 	OP_RSHU,
101 
102 	OP_NEGF,
103 	OP_ADDF,
104 	OP_SUBF,
105 	OP_DIVF,
106 	OP_MULF,
107 
108 	OP_CVIF,
109 	OP_CVFI
110 } opcode_t;
111 
112 
113 
114 typedef int	vmptr_t;
115 
116 typedef struct vmSymbol_s {
117 	struct vmSymbol_s	*next;
118 	int		symValue;
119 	int		profileCount;
120 	char	symName[1];		// variable sized
121 } vmSymbol_t;
122 
123 #define	VM_OFFSET_PROGRAM_STACK		0
124 #define	VM_OFFSET_SYSTEM_CALL		4
125 
126 struct vm_s {
127     // DO NOT MOVE OR CHANGE THESE WITHOUT CHANGING THE VM_OFFSET_* DEFINES
128     // USED BY THE ASM CODE
129     int			programStack;		// the vm may be recursively entered
130     intptr_t			(*systemCall)( intptr_t *parms );
131 
132 	//------------------------------------
133 
134     char		name[MAX_QPATH];
135 
136 	// for dynamic linked modules
137 	void		*dllHandle;
138 	intptr_t			(QDECL *entryPoint)( int callNum, ... );
139 	void (*destroy)(vm_t* self);
140 
141 	// for interpreted modules
142 	qboolean	currentlyInterpreting;
143 
144 	qboolean	compiled;
145 	byte		*codeBase;
146 	int			codeLength;
147 
148 	int			*instructionPointers;
149 	int			instructionPointersLength;
150 
151 	byte		*dataBase;
152 	int			dataMask;
153 
154 	int			stackBottom;		// if programStack < stackBottom, error
155 
156 	int			numSymbols;
157 	struct vmSymbol_s	*symbols;
158 
159 	int			callLevel;		// counts recursive VM_Call
160 	int			breakFunction;		// increment breakCount on function entry to this
161 	int			breakCount;
162 
163 	char		fqpath[MAX_QPATH+1] ;
164 
165 	byte		*jumpTableTargets;
166 	int			numJumpTableTargets;
167 };
168 
169 
170 extern	vm_t	*currentVM;
171 extern	int		vm_debugLevel;
172 
173 void VM_Compile( vm_t *vm, vmHeader_t *header );
174 int	VM_CallCompiled( vm_t *vm, int *args );
175 
176 void VM_PrepareInterpreter( vm_t *vm, vmHeader_t *header );
177 int	VM_CallInterpreted( vm_t *vm, int *args );
178 
179 vmSymbol_t *VM_ValueToFunctionSymbol( vm_t *vm, int value );
180 int VM_SymbolToValue( vm_t *vm, const char *symbol );
181 const char *VM_ValueToSymbol( vm_t *vm, int value );
182 void VM_LogSyscalls( int *args );
183 
184