]> de.git.xonotic.org Git - xonotic/gmqcc.git/blob - gmqcc.h
Fixed parsing issues, added some parser tests.
[xonotic/gmqcc.git] / gmqcc.h
1 /*
2  * Copyright (C) 2012 
3  *      Dale Weiler
4  *
5  * Permission is hereby granted, free of charge, to any person obtaining a copy of
6  * this software and associated documentation files (the "Software"), to deal in
7  * the Software without restriction, including without limitation the rights to
8  * use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
9  * of the Software, and to permit persons to whom the Software is furnished to do
10  * so, subject to the following conditions:
11  *
12  * The above copyright notice and this permission notice shall be included in all
13  * copies or substantial portions of the Software.
14  *
15  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18  * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19  * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20  * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21  * SOFTWARE.
22  */
23 #ifndef GMQCC_HDR
24 #define GMQCC_HDR
25 #include <stdio.h>
26
27 /* The types supported by the language */
28 #define TYPE_VOID     0
29 #define TYPE_STRING   1
30 #define TYPE_FLOAT    2
31 #define TYPE_VECTOR   3
32 #define TYPE_ENTITY   4
33 #define TYPE_FIELD    5
34 #define TYPE_FUNCTION 6
35 #define TYPE_POINTER  7
36
37 /*
38  * there are 3 accessible memory zones -
39  * globals
40  *     array of 32bit ints/floats, mixed, LE,
41  * entities
42  *     structure is up to the engine but the fields are a linear array
43  *     of mixed ints/floats, there are globals referring to the offsets
44  *     of these in the entity struct so there are ADDRESS and STOREP and
45  *     LOAD instructions that use globals containing field offsets.
46  * strings
47  *     a static array in the progs.dat, with file parsing creating
48  *     additional constants, and some engine fields are mapped by 
49  *     address as well to unique string offsets
50  */
51  
52 /* 
53  * Instructions 
54  * These are the external instructions supported by the interperter
55  * this is what things compile to (from the C code). This is not internal
56  * instructions for support like int, and such (which are translated)
57  */
58 #define INSTR_DONE      0
59 // math
60 #define INSTR_MUL_F     1 /* multiplication float         */
61 #define INSTR_MUL_V     2 /* multiplication vector        */
62 #define INSTR_MUL_FV    3 /* multiplication float->vector */
63 #define INSTR_MUL_VF    4 /* multiplication vector->float */
64 #define INSTR_DIV_F     5
65 #define INSTR_ADD_F     6
66 #define INSTR_ADD_V     7
67 #define INSTR_SUB_F     8
68 #define INSTR_SUB_V     9
69 // compare
70 #define INSTR_EQ_F      10
71 #define INSTR_EQ_V      11
72 #define INSTR_EQ_S      12
73 #define INSTR_EQ_E      13
74 #define INSTR_EQ_FNC    14
75 #define INSTR_NE_F      15
76 #define INSTR_NE_V      16
77 #define INSTR_NE_S      17
78 #define INSTR_NE_E      18
79 #define INSTR_NE_FNC    19
80 // multi compare
81 #define INSTR_LE        20
82 #define INSTR_GE        21
83 #define INSTR_LT        22
84 #define INSTR_GT        23
85 // load and store
86 #define INSTR_LOAD_F    24
87 #define INSTR_LOAD_V    25
88 #define INSTR_LOAD_S    26
89 #define INSTR_LOAD_ENT  27
90 #define INSTR_LOAD_FLD  28
91 #define INSTR_LOAD_FNC  29
92 #define INSTR_STORE_F   31
93 #define INSTR_STORE_V   32
94 #define INSTR_STORE_S   33
95 #define INSTR_STORE_ENT 34
96 #define INSTR_STORE_FLD 35
97 #define INSTR_STORE_FNC 36
98 // others
99 #define INSTR_ADDRESS   30
100 #define INSTR_RETURN    37
101 #define INSTR_NOT_F     38
102 #define INSTR_NOT_V     39
103 #define INSTR_NOT_S     40
104 #define INSTR_NOT_ENT   41
105 #define INSTR_NOT_FNC   42
106 #define INSTR_IF        43
107 #define INSTR_IFNOT     44
108 #define INSTR_CALL0     45
109 #define INSTR_CALL1     46
110 #define INSTR_CALL2     47
111 #define INSTR_CALL3     48
112 #define INSTR_CALL4     49
113 #define INSTR_CALL5     50
114 #define INSTR_CALL6     51
115 #define INSTR_CALL7     52
116 #define INSTR_CALL8     53
117 #define INSTR_STATE     54
118 #define INSTR_GOTO      55
119 #define INSTR_AND       56
120 #define INSTR_OR        57
121 #define INSTR_BITAND    59
122 #define INSTR_BITOR     60
123
124 /*
125  * This is the smallest lexer I've ever wrote: and I must say, it's quite
126  * more nicer than those large bulky complex parsers that most people write
127  * which has some sort of a complex state.
128  */
129 struct lex_file {
130         /*
131          * This is a simple state for lexing, no need to be complex for qc
132          * code.  It's trivial stuff.
133          */
134         FILE *file;
135         char  peek[5]; /* extend for depthier peeks */
136         int   last;
137         int   current;
138         int   length;
139         int   size;
140         long  line;         /* Line the lexer is on                     */
141         char  lastok[8192]; /* No token shall ever be bigger than this! */
142 };
143
144 /*
145  * It's important that this table never exceed 32 keywords, the ascii
146  * table starts at 33 (and we don't want conflicts)
147  */
148 #define TOKEN_DO       0
149 #define TOKEN_ELSE     1
150 #define TOKEN_IF       2
151 #define TOKEN_WHILE    3
152 #define TOKEN_BREAK    4
153 #define TOKEN_CONTINUE 5
154 #define TOKEN_RETURN   6
155 #define TOKEN_GOTO     7
156 #define TOKEN_FOR      8   // extension
157 #define TOKEN_TYPEDEF  9   // extension
158
159
160 #define TOKEN_FLOAT    110
161 #define TOKEN_VECTOR   111
162 #define TOKEN_STRING   112
163 #define TOKEN_ENTITY   113
164 #define TOKEN_VOID     114
165
166 /*
167  * Lexer state constants, these are numbers for where exactly in
168  * the lexing the lexer is at. Or where it decided to stop if a lexer
169  * error occurs.
170  */
171 #define LEX_COMMENT    1128 /* higher than ascii */
172 #define LEX_CHRLIT     1129
173 #define LEX_STRLIT     1130
174 #define LEX_IDENT      1131
175
176 int              lex_token(struct lex_file *);
177 void             lex_reset(struct lex_file *);
178 int              lex_close(struct lex_file *);
179 struct lex_file *lex_open (FILE *);
180
181 /* errors */
182 #define ERROR_LEX      (SHRT_MAX+0)
183 #define ERROR_PARSE    (SHRT_MAX+1)
184 #define ERROR_INTERNAL (SHRT_MAX+2)
185 #define ERROR_COMPILER (SHRT_MAX+3)
186 #define ERROR_PREPRO   (SHRT_MAX+4)
187 int error(int, const char *, ...);
188
189 /* parse.c */
190 int parse(struct lex_file *);
191 struct parsenode {
192         struct parsenode *next;
193         int               type; /* some token */
194 };
195
196 /* typedef.c */
197 typedef struct typedef_node_t {
198         char      *name; /* name of actual type */
199 } typedef_node;
200
201 void          typedef_init();
202 void          typedef_clear();
203 typedef_node *typedef_find(const char *);
204 int           typedef_add (const char *, const char *);
205
206 /* alloc.c */
207 void *memory_a(unsigned int, unsigned int, const char *);
208 void  memory_d(void       *, unsigned int, const char *);
209 #ifdef NOTRACK
210 #       define mem_a(x) malloc(x)
211 #       define mem_d(x) free  (x)
212 #else
213 #       define mem_a(x) memory_a((x), __LINE__, __FILE__)
214 #       define mem_d(x) memory_d((x), __LINE__, __FILE__)
215 #endif
216 #endif