1 /*
2 * Copyright (c) 2006-2018, RT-Thread Development Team
3 *
4 * SPDX-License-Identifier: Apache-2.0
5 *
6 * Change Logs:
7 * Date Author Notes
8 * 2010-03-22 Bernard first version
9 */
10 #include <finsh.h>
11
12 #include "finsh_node.h"
13 #include "finsh_error.h"
14 #include "finsh_var.h"
15 #include "finsh_ops.h"
16
17 union finsh_value* finsh_compile_sp; /* stack pointer */
18 uint8_t* finsh_compile_pc; /* PC */
19
20 #define finsh_code_byte(x) do { *finsh_compile_pc = (x); finsh_compile_pc ++; } while(0)
21 #define finsh_code_word(x) do { FINSH_SET16(finsh_compile_pc, x); finsh_compile_pc +=2; } while(0)
22 #define finsh_code_dword(x) do { FINSH_SET32(finsh_compile_pc, x); finsh_compile_pc +=4; } while(0)
23
finsh_compile(struct finsh_node * node)24 static int finsh_compile(struct finsh_node* node)
25 {
26 if (node != NULL)
27 {
28 /* compile child node */
29 if (finsh_node_child(node) != NULL)
30 finsh_compile(finsh_node_child(node));
31
32 /* compile current node */
33 switch (node->node_type)
34 {
35 case FINSH_NODE_ID:
36 {
37 /* identifier::syscall */
38 if (node->idtype & FINSH_IDTYPE_SYSCALL)
39 {
40 /* load address */
41 finsh_code_byte(FINSH_OP_LD_DWORD);
42 finsh_code_dword((long)node->id.syscall->func);
43 }
44 /* identifier::sysvar */
45 else if (node->idtype & FINSH_IDTYPE_SYSVAR)
46 {
47 struct finsh_sysvar* sysvar;
48
49 sysvar = node->id.sysvar;
50 if (sysvar != NULL)
51 {
52 switch (sysvar->type)
53 {
54 case finsh_type_char:
55 case finsh_type_uchar:
56 if (node->idtype & FINSH_IDTYPE_ADDRESS)
57 {
58 /* load address */
59 finsh_code_byte(FINSH_OP_LD_DWORD);
60 }
61 else
62 {
63 /* load value */
64 finsh_code_byte(FINSH_OP_LD_VALUE_BYTE);
65 }
66
67 finsh_code_dword((long)(sysvar->var));
68 break;
69
70 case finsh_type_short:
71 case finsh_type_ushort:
72 if (node->idtype & FINSH_IDTYPE_ADDRESS)
73 {
74 /* load address */
75 finsh_code_byte(FINSH_OP_LD_DWORD);
76 }
77 else
78 {
79 /* load value */
80 finsh_code_byte(FINSH_OP_LD_VALUE_WORD);
81 }
82
83 finsh_code_dword((long)(sysvar->var));
84 break;
85
86 case finsh_type_int:
87 case finsh_type_uint:
88 case finsh_type_long:
89 case finsh_type_ulong:
90 case finsh_type_charp:
91 case finsh_type_shortp:
92 case finsh_type_intp:
93 case finsh_type_longp:
94 if (node->idtype & FINSH_IDTYPE_ADDRESS)
95 {
96 /* load address */
97 finsh_code_byte(FINSH_OP_LD_DWORD);
98 }
99 else
100 {
101 /* load value */
102 finsh_code_byte(FINSH_OP_LD_VALUE_DWORD);
103 }
104
105 finsh_code_dword((long)(sysvar->var));
106 break;
107 }
108 }
109 }
110 /* identifier::var */
111 else
112 {
113 struct finsh_var* var;
114
115 var = node->id.var;
116 if (var != NULL)
117 {
118 switch (var->type)
119 {
120 case finsh_type_char:
121 case finsh_type_uchar:
122 if (node->idtype & FINSH_IDTYPE_ADDRESS)
123 {
124 /* load address */
125 finsh_code_byte(FINSH_OP_LD_DWORD);
126 }
127 else
128 {
129 /* load value */
130 finsh_code_byte(FINSH_OP_LD_VALUE_BYTE);
131 }
132
133 finsh_code_dword((long)&(var->value.char_value));
134 break;
135
136 case finsh_type_short:
137 case finsh_type_ushort:
138 if (node->idtype & FINSH_IDTYPE_ADDRESS)
139 {
140 /* load address */
141 finsh_code_byte(FINSH_OP_LD_DWORD);
142 }
143 else
144 {
145 /* load value */
146 finsh_code_byte(FINSH_OP_LD_VALUE_WORD);
147 }
148
149 finsh_code_dword((long)&(var->value.short_value));
150 break;
151
152 case finsh_type_int:
153 case finsh_type_uint:
154 case finsh_type_long:
155 case finsh_type_ulong:
156 case finsh_type_charp:
157 case finsh_type_shortp:
158 case finsh_type_intp:
159 case finsh_type_longp:
160 if (node->idtype & FINSH_IDTYPE_ADDRESS)
161 {
162 /* load address */
163 finsh_code_byte(FINSH_OP_LD_DWORD);
164 }
165 else
166 {
167 /* load value */
168 finsh_code_byte(FINSH_OP_LD_VALUE_DWORD);
169 }
170
171 finsh_code_dword((long)&(var->value.long_value));
172 break;
173 }
174 }
175 }
176 }
177 break;
178
179 /* load const */
180 case FINSH_NODE_VALUE_CHAR:
181 finsh_code_byte(FINSH_OP_LD_BYTE);
182 finsh_code_byte(node->value.char_value);
183 break;
184
185 case FINSH_NODE_VALUE_INT:
186 case FINSH_NODE_VALUE_LONG:
187 finsh_code_byte(FINSH_OP_LD_DWORD);
188 finsh_code_dword(node->value.long_value);
189 break;
190
191 case FINSH_NODE_VALUE_NULL:
192 case FINSH_NODE_VALUE_STRING:
193 finsh_code_byte(FINSH_OP_LD_DWORD);
194 finsh_code_dword((uint32_t)node->value.ptr);
195 break;
196
197 /* arithmetic operation */
198 case FINSH_NODE_SYS_ADD:
199 if (node->data_type == FINSH_DATA_TYPE_BYTE) finsh_code_byte(FINSH_OP_ADD_BYTE);
200 else if (node->data_type == FINSH_DATA_TYPE_WORD) finsh_code_byte(FINSH_OP_ADD_WORD);
201 else if (node->data_type == FINSH_DATA_TYPE_DWORD) finsh_code_byte(FINSH_OP_ADD_DWORD);
202 break;
203
204 case FINSH_NODE_SYS_SUB:
205 if (node->data_type == FINSH_DATA_TYPE_BYTE) finsh_code_byte(FINSH_OP_SUB_BYTE);
206 else if (node->data_type == FINSH_DATA_TYPE_WORD) finsh_code_byte(FINSH_OP_SUB_WORD);
207 else if (node->data_type == FINSH_DATA_TYPE_DWORD) finsh_code_byte(FINSH_OP_SUB_DWORD);
208 break;
209
210 case FINSH_NODE_SYS_MUL:
211 if (node->data_type == FINSH_DATA_TYPE_BYTE) finsh_code_byte(FINSH_OP_MUL_BYTE);
212 else if (node->data_type == FINSH_DATA_TYPE_WORD) finsh_code_byte(FINSH_OP_MUL_WORD);
213 else if (node->data_type == FINSH_DATA_TYPE_DWORD) finsh_code_byte(FINSH_OP_MUL_DWORD);
214 break;
215
216 case FINSH_NODE_SYS_DIV:
217 if (node->data_type == FINSH_DATA_TYPE_BYTE) finsh_code_byte(FINSH_OP_DIV_BYTE);
218 else if (node->data_type == FINSH_DATA_TYPE_WORD) finsh_code_byte(FINSH_OP_DIV_WORD);
219 else if (node->data_type == FINSH_DATA_TYPE_DWORD) finsh_code_byte(FINSH_OP_DIV_DWORD);
220 break;
221
222 case FINSH_NODE_SYS_MOD:
223 if (node->data_type == FINSH_DATA_TYPE_BYTE) finsh_code_byte(FINSH_OP_MOD_BYTE);
224 else if (node->data_type == FINSH_DATA_TYPE_WORD) finsh_code_byte(FINSH_OP_MOD_WORD);
225 else if (node->data_type == FINSH_DATA_TYPE_DWORD) finsh_code_byte(FINSH_OP_MOD_DWORD);
226 break;
227
228 /* bit operation */
229 case FINSH_NODE_SYS_AND:
230 if (node->data_type == FINSH_DATA_TYPE_BYTE) finsh_code_byte(FINSH_OP_AND_BYTE);
231 else if (node->data_type == FINSH_DATA_TYPE_WORD) finsh_code_byte(FINSH_OP_AND_WORD);
232 else if (node->data_type == FINSH_DATA_TYPE_DWORD) finsh_code_byte(FINSH_OP_AND_DWORD);
233 break;
234
235 case FINSH_NODE_SYS_OR:
236 if (node->data_type == FINSH_DATA_TYPE_BYTE) finsh_code_byte(FINSH_OP_OR_BYTE);
237 else if (node->data_type == FINSH_DATA_TYPE_WORD) finsh_code_byte(FINSH_OP_OR_WORD);
238 else if (node->data_type == FINSH_DATA_TYPE_DWORD) finsh_code_byte(FINSH_OP_OR_DWORD);
239 break;
240
241 case FINSH_NODE_SYS_XOR:
242 if (node->data_type == FINSH_DATA_TYPE_BYTE) finsh_code_byte(FINSH_OP_XOR_BYTE);
243 else if (node->data_type == FINSH_DATA_TYPE_WORD) finsh_code_byte(FINSH_OP_XOR_WORD);
244 else if (node->data_type == FINSH_DATA_TYPE_DWORD) finsh_code_byte(FINSH_OP_XOR_DWORD);
245 break;
246
247 case FINSH_NODE_SYS_BITWISE:
248 if (node->data_type == FINSH_DATA_TYPE_BYTE) finsh_code_byte(FINSH_OP_BITWISE_BYTE);
249 else if (node->data_type == FINSH_DATA_TYPE_WORD) finsh_code_byte(FINSH_OP_BITWISE_WORD);
250 else if (node->data_type == FINSH_DATA_TYPE_DWORD) finsh_code_byte(FINSH_OP_BITWISE_DWORD);
251 break;
252
253 case FINSH_NODE_SYS_SHL:
254 if (node->data_type == FINSH_DATA_TYPE_BYTE) finsh_code_byte(FINSH_OP_SHL_BYTE);
255 else if (node->data_type == FINSH_DATA_TYPE_WORD) finsh_code_byte(FINSH_OP_SHL_WORD);
256 else if (node->data_type == FINSH_DATA_TYPE_DWORD) finsh_code_byte(FINSH_OP_SHL_DWORD);
257 break;
258
259 case FINSH_NODE_SYS_SHR:
260 if (node->data_type == FINSH_DATA_TYPE_BYTE) finsh_code_byte(FINSH_OP_SHR_BYTE);
261 else if (node->data_type == FINSH_DATA_TYPE_WORD) finsh_code_byte(FINSH_OP_SHR_WORD);
262 else if (node->data_type == FINSH_DATA_TYPE_DWORD) finsh_code_byte(FINSH_OP_SHR_DWORD);
263 break;
264
265 /* syscall */
266 case FINSH_NODE_SYS_FUNC:
267 {
268 int parameters;
269 struct finsh_node* sibling;
270
271 parameters = 0;
272 if (finsh_node_child(node) != NULL)
273 {
274 sibling = finsh_node_sibling(finsh_node_child(node));
275 while (sibling != NULL)
276 {
277 parameters ++;
278 sibling = finsh_node_sibling(sibling);
279 }
280
281 /* load address of function */
282 // finsh_code_dword((long)&(node->var->value.ptr));
283
284 /* syscall parameters */
285 finsh_code_byte(FINSH_OP_SYSCALL);
286 finsh_code_byte(parameters);
287 }
288 }
289 break;
290
291 /* assign expression */
292 case FINSH_NODE_SYS_ASSIGN:
293 if (finsh_node_child(node) && finsh_node_child(node)->node_type == FINSH_NODE_ID)
294 {
295 switch (finsh_node_child(node)->data_type)
296 {
297 case FINSH_DATA_TYPE_BYTE:
298 finsh_code_byte(FINSH_OP_ST_BYTE);
299
300 /* load value again */
301 finsh_code_byte(FINSH_OP_LD_VALUE_BYTE_STACK);
302 break;
303
304 case FINSH_DATA_TYPE_WORD:
305 finsh_code_byte(FINSH_OP_ST_WORD);
306
307 /* load value again */
308 finsh_code_byte(FINSH_OP_LD_VALUE_WORD_STACK);
309 break;
310
311 case FINSH_DATA_TYPE_DWORD:
312 finsh_code_byte(FINSH_OP_ST_DWORD);
313
314 /* load value again */
315 finsh_code_byte(FINSH_OP_LD_VALUE_DWORD_STACK);
316 break;
317
318 default:
319 finsh_error_set(FINSH_ERROR_UNKNOWN_TYPE);
320 }
321 }
322 else if (finsh_node_child(node)->node_type == FINSH_NODE_SYS_GETVALUE)
323 {
324 switch ((finsh_node_child(node)->data_type) & 0x0F)
325 {
326 case FINSH_DATA_TYPE_BYTE:
327 finsh_code_byte(FINSH_OP_ST_BYTE);
328
329 /* load value again */
330 finsh_code_byte(FINSH_OP_LD_VALUE_BYTE_STACK);
331 break;
332
333 case FINSH_DATA_TYPE_WORD:
334 finsh_code_byte(FINSH_OP_ST_WORD);
335
336 /* load value again */
337 finsh_code_byte(FINSH_OP_LD_VALUE_WORD_STACK);
338 break;
339
340 case FINSH_DATA_TYPE_DWORD:
341 finsh_code_byte(FINSH_OP_ST_DWORD);
342
343 /* load value again */
344 finsh_code_byte(FINSH_OP_LD_VALUE_DWORD_STACK);
345 break;
346
347 default:
348 finsh_error_set(FINSH_ERROR_UNKNOWN_TYPE);
349 }
350 }
351 break;
352
353 /* pre-increase */
354 case FINSH_NODE_SYS_PREINC:
355 if (finsh_node_child(node) && finsh_node_child(node)->node_type == FINSH_NODE_ID)
356 {
357 struct finsh_var* var;
358 var = finsh_node_child(node)->id.var;
359
360 /* ld_dword &id */
361 // finsh_code_byte(FINSH_OP_LD_DWORD);
362
363 switch (node->data_type)
364 {
365 case FINSH_DATA_TYPE_BYTE:
366 /* address */
367 // finsh_code_dword((long)&(var->value.char_value));
368
369 /* ld_value_byte &id */
370 finsh_code_byte(FINSH_OP_LD_VALUE_BYTE);
371 finsh_code_dword((long)&(var->value.char_value));
372
373 /* ld_byte 1 */
374 finsh_code_byte(FINSH_OP_LD_BYTE);
375 finsh_code_byte(1);
376
377 /* add_byte */
378 finsh_code_byte(FINSH_OP_ADD_BYTE);
379 /* st_byte */
380 finsh_code_byte(FINSH_OP_ST_BYTE);
381
382 /* load value again */
383 finsh_code_byte(FINSH_OP_LD_VALUE_DWORD_STACK);
384
385 break;
386
387 case FINSH_DATA_TYPE_WORD:
388 /* address */
389 // finsh_code_dword((long)&(var->value.short_value));
390
391 /* ld_value_word &id */
392 finsh_code_byte(FINSH_OP_LD_VALUE_WORD);
393 finsh_code_dword((long)&(var->value.short_value));
394
395 /* ld_word 1 */
396 finsh_code_byte(FINSH_OP_LD_WORD);
397 finsh_code_word(1);
398
399 /* add_word */
400 finsh_code_byte(FINSH_OP_ADD_WORD);
401 /* st_word */
402 finsh_code_byte(FINSH_OP_ST_WORD);
403
404 /* load value again */
405 finsh_code_byte(FINSH_OP_LD_VALUE_DWORD_STACK);
406
407 break;
408
409 case FINSH_DATA_TYPE_DWORD:
410 /* address */
411 // finsh_code_dword((long)&(var->value.long_value));
412
413 /* ld_dword &id */
414 finsh_code_byte(FINSH_OP_LD_VALUE_DWORD);
415 finsh_code_dword((long)&(var->value.long_value));
416
417 /* ld_dword 1 */
418 finsh_code_byte(FINSH_OP_LD_DWORD);
419 finsh_code_dword(1);
420
421 /* add_dword */
422 finsh_code_byte(FINSH_OP_ADD_DWORD);
423 /* st_dword */
424 finsh_code_byte(FINSH_OP_ST_DWORD);
425
426 /* load value again */
427 finsh_code_byte(FINSH_OP_LD_VALUE_DWORD_STACK);
428
429 break;
430 }
431 }
432 break;
433
434 /* pre-decrease */
435 case FINSH_NODE_SYS_PREDEC:
436 if (finsh_node_child(node) && finsh_node_child(node)->node_type == FINSH_NODE_ID)
437 {
438 struct finsh_var* var;
439 var = finsh_node_child(node)->id.var;
440
441 /* ld_dword &id */
442 // finsh_code_byte(FINSH_OP_LD_DWORD);
443
444 switch (node->data_type)
445 {
446 case FINSH_DATA_TYPE_BYTE:
447 /* address */
448 // finsh_code_dword((long)&(var->value.char_value));
449
450 /* ld_value_byte &id */
451 finsh_code_byte(FINSH_OP_LD_VALUE_BYTE);
452 finsh_code_dword((long)&(var->value.char_value));
453
454 /* ld_byte 1 */
455 finsh_code_byte(FINSH_OP_LD_BYTE);
456 finsh_code_byte(1);
457
458 /* add_byte */
459 finsh_code_byte(FINSH_OP_SUB_BYTE);
460 /* st_byte */
461 finsh_code_byte(FINSH_OP_ST_BYTE);
462
463 /* load value again */
464 finsh_code_byte(FINSH_OP_LD_VALUE_DWORD_STACK);
465
466 break;
467
468 case FINSH_DATA_TYPE_WORD:
469 /* address */
470 // finsh_code_dword((long)&(var->value.short_value));
471
472 /* ld_value_word &id */
473 finsh_code_byte(FINSH_OP_LD_VALUE_WORD);
474 finsh_code_dword((long)&(var->value.short_value));
475
476 /* ld_word 1 */
477 finsh_code_byte(FINSH_OP_LD_WORD);
478 finsh_code_word(1);
479
480 /* add_word */
481 finsh_code_byte(FINSH_OP_SUB_WORD);
482 /* st_word */
483 finsh_code_byte(FINSH_OP_ST_WORD);
484
485 /* load value again */
486 finsh_code_byte(FINSH_OP_LD_VALUE_DWORD_STACK);
487
488 break;
489
490 case FINSH_DATA_TYPE_DWORD:
491 /* address */
492 // finsh_code_dword((long)&(var->value.long_value));
493
494 /* ld_dword &id */
495 finsh_code_byte(FINSH_OP_LD_VALUE_DWORD);
496 finsh_code_dword((long)&(var->value.long_value));
497
498 /* ld_dword 1 */
499 finsh_code_byte(FINSH_OP_LD_DWORD);
500 finsh_code_dword(1);
501
502 /* add_dword */
503 finsh_code_byte(FINSH_OP_SUB_DWORD);
504 /* st_dword */
505 finsh_code_byte(FINSH_OP_ST_DWORD);
506
507 /* load value again */
508 finsh_code_byte(FINSH_OP_LD_VALUE_DWORD_STACK);
509
510 break;
511 }
512 }
513 break;
514
515 /* increase */
516 case FINSH_NODE_SYS_INC:
517 if (finsh_node_child(node) && finsh_node_child(node)->node_type == FINSH_NODE_ID)
518 {
519 struct finsh_var* var;
520 var = finsh_node_child(node)->id.var;
521
522 switch (node->data_type)
523 {
524 case FINSH_DATA_TYPE_BYTE:
525 /* ld_value_byte &id */
526 // finsh_code_byte(FINSH_OP_LD_VALUE_BYTE);
527 // finsh_code_dword((long)&(var->value.char_value));
528
529 /* ld_dword &id */
530 finsh_code_byte(FINSH_OP_LD_DWORD);
531 finsh_code_dword((long)&(var->value.char_value));
532
533 /* ld_value_byte &id */
534 finsh_code_byte(FINSH_OP_LD_VALUE_BYTE);
535 finsh_code_dword((long)&(var->value.char_value));
536
537 /* ld_byte 1 */
538 finsh_code_byte(FINSH_OP_LD_BYTE);
539 finsh_code_byte(1);
540
541 /* add_byte */
542 finsh_code_byte(FINSH_OP_ADD_BYTE);
543 /* get byte */
544 finsh_code_byte(FINSH_OP_ST_BYTE);
545
546 /* pop */
547 finsh_code_byte(FINSH_OP_POP);
548 break;
549
550 case FINSH_DATA_TYPE_WORD:
551 /* ld_value_word &id */
552 // finsh_code_byte(FINSH_OP_LD_VALUE_WORD);
553 // finsh_code_dword((long)&(var->value.short_value));
554
555 /* ld_dword &id */
556 finsh_code_byte(FINSH_OP_LD_DWORD);
557 finsh_code_dword((long)&(var->value.short_value));
558
559 /* ld_value_word &id */
560 finsh_code_byte(FINSH_OP_LD_VALUE_WORD);
561 finsh_code_dword((long)&(var->value.short_value));
562
563 /* ld_word 1 */
564 finsh_code_byte(FINSH_OP_LD_WORD);
565 finsh_code_word(1);
566
567 /* add_byte */
568 finsh_code_byte(FINSH_OP_ADD_WORD);
569 /* get byte */
570 finsh_code_byte(FINSH_OP_ST_WORD);
571
572 /* pop */
573 finsh_code_byte(FINSH_OP_POP);
574 break;
575
576 case FINSH_DATA_TYPE_DWORD:
577 /* ld_value_dword &id */
578 // finsh_code_byte(FINSH_OP_LD_VALUE_DWORD);
579 // finsh_code_dword((long)&(var->value.long_value));
580
581 /* ld_dword &id */
582 finsh_code_byte(FINSH_OP_LD_DWORD);
583 finsh_code_dword((long)&(var->value.long_value));
584
585 /* ld_value_dword &id */
586 finsh_code_byte(FINSH_OP_LD_VALUE_DWORD);
587 finsh_code_dword((long)&(var->value.long_value));
588
589 /* ld_dword 1 */
590 finsh_code_byte(FINSH_OP_LD_DWORD);
591 finsh_code_dword(1);
592
593 /* add_byte */
594 finsh_code_byte(FINSH_OP_ADD_DWORD);
595 /* get byte */
596 finsh_code_byte(FINSH_OP_ST_DWORD);
597
598 /* pop */
599 finsh_code_byte(FINSH_OP_POP);
600 break;
601 }
602 }
603 break;
604
605 /* decrease */
606 case FINSH_NODE_SYS_DEC:
607 if (finsh_node_child(node) && finsh_node_child(node)->node_type == FINSH_NODE_ID)
608 {
609 struct finsh_var* var;
610 var = finsh_node_child(node)->id.var;
611
612 switch (node->data_type)
613 {
614 case FINSH_DATA_TYPE_BYTE:
615 /* ld_value_byte &id */
616 // finsh_code_byte(FINSH_OP_LD_VALUE_BYTE);
617 // finsh_code_dword((long)&(var->value.char_value));
618
619 /* ld_dword &id */
620 finsh_code_byte(FINSH_OP_LD_DWORD);
621 finsh_code_dword((long)&(var->value.char_value));
622
623 /* ld_value_byte &id */
624 finsh_code_byte(FINSH_OP_LD_VALUE_BYTE);
625 finsh_code_dword((long)&(var->value.char_value));
626
627 /* ld_byte 1 */
628 finsh_code_byte(FINSH_OP_LD_BYTE);
629 finsh_code_byte(1);
630
631 /* add_byte */
632 finsh_code_byte(FINSH_OP_SUB_BYTE);
633 /* get byte */
634 finsh_code_byte(FINSH_OP_ST_BYTE);
635
636 /* pop */
637 finsh_code_byte(FINSH_OP_POP);
638 break;
639
640 case FINSH_DATA_TYPE_WORD:
641 /* ld_value_word &id */
642 // finsh_code_byte(FINSH_OP_LD_VALUE_WORD);
643 // finsh_code_dword((long)&(var->value.short_value));
644
645 /* ld_dword &id */
646 finsh_code_byte(FINSH_OP_LD_DWORD);
647 finsh_code_dword((long)&(var->value.short_value));
648
649 /* ld_value_word &id */
650 finsh_code_byte(FINSH_OP_LD_VALUE_WORD);
651 finsh_code_dword((long)&(var->value.short_value));
652
653 /* ld_word 1 */
654 finsh_code_byte(FINSH_OP_LD_WORD);
655 finsh_code_word(1);
656
657 /* add_byte */
658 finsh_code_byte(FINSH_OP_SUB_WORD);
659 /* get byte */
660 finsh_code_byte(FINSH_OP_ST_WORD);
661
662 /* pop */
663 finsh_code_byte(FINSH_OP_POP);
664 break;
665
666 case FINSH_DATA_TYPE_DWORD:
667 /* ld_value_dword &id */
668 // finsh_code_byte(FINSH_OP_LD_VALUE_DWORD);
669 // finsh_code_dword((long)&(var->value.long_value));
670
671 /* ld_dword &id */
672 finsh_code_byte(FINSH_OP_LD_DWORD);
673 finsh_code_dword((long)&(var->value.long_value));
674
675 /* ld_value_dword &id */
676 finsh_code_byte(FINSH_OP_LD_VALUE_DWORD);
677 finsh_code_dword((long)&(var->value.long_value));
678
679 /* ld_dword 1 */
680 finsh_code_byte(FINSH_OP_LD_DWORD);
681 finsh_code_dword(1);
682
683 /* add_byte */
684 finsh_code_byte(FINSH_OP_SUB_DWORD);
685 /* get byte */
686 finsh_code_byte(FINSH_OP_ST_DWORD);
687
688 /* pop */
689 finsh_code_byte(FINSH_OP_POP);
690 break;
691 }
692 }
693 break;
694
695 case FINSH_NODE_SYS_NULL:
696 finsh_code_dword(0);
697 break;
698
699 case FINSH_NODE_SYS_GETVALUE:
700 if (node->idtype & FINSH_IDTYPE_ADDRESS)
701 {
702 /* nothing will be generated */
703 }
704 else
705 {
706 switch (node->data_type)
707 {
708 case FINSH_DATA_TYPE_BYTE:
709 finsh_code_byte(FINSH_OP_LD_VALUE_BYTE_STACK);
710 break;
711 case FINSH_DATA_TYPE_WORD:
712 finsh_code_byte(FINSH_OP_LD_VALUE_WORD_STACK);
713 break;
714 case FINSH_DATA_TYPE_DWORD:
715 finsh_code_byte(FINSH_OP_LD_VALUE_DWORD_STACK);
716 break;
717 default:
718 break;
719 }
720 }
721 break;
722
723 case FINSH_NODE_SYS_GETADDR:
724 /* nothing will be generated */
725 break;
726
727 default:
728 finsh_error_set(FINSH_ERROR_UNKNOWN_NODE);
729 break;
730 }
731
732 /* compile sibling node */
733 if (finsh_node_sibling(node) != NULL)
734 finsh_compile(finsh_node_sibling(node));
735 }
736
737 return 0;
738 }
739
finsh_type_check(struct finsh_node * node,uint8_t is_addr)740 static int finsh_type_check(struct finsh_node* node, uint8_t is_addr)
741 {
742 if (node != NULL)
743 {
744 /* address & value */
745 if (node->node_type == FINSH_NODE_SYS_ASSIGN ||
746 node->node_type == FINSH_NODE_SYS_PREINC ||
747 node->node_type == FINSH_NODE_SYS_PREDEC ||
748 node->node_type == FINSH_NODE_SYS_GETADDR)
749 {
750 /* address */
751 finsh_type_check(finsh_node_child(node), FINSH_IDTYPE_ADDRESS);
752 }
753 else if (node->node_type == FINSH_NODE_SYS_GETVALUE && is_addr)
754 {
755 /* change the attribute of getvalue in left expr */
756 finsh_type_check(finsh_node_child(node), 0);
757 }
758 else
759 {
760 /* transfer 'av' to child node */
761 finsh_type_check(finsh_node_child(node), is_addr);
762 }
763
764 /* always does not load address in sibling */
765 finsh_type_check(finsh_node_sibling(node), FINSH_NODE_VALUE);
766
767 /** set attribute of current node */
768
769 /* make sure the current node is address or value */
770 if (node->idtype != FINSH_IDTYPE_SYSCALL) node->idtype |= is_addr;
771
772 if (finsh_node_child(node) != NULL)
773 {
774 node->data_type = finsh_node_child(node)->data_type;
775 return 0;
776 }
777
778 if (node->node_type == FINSH_NODE_ID)
779 {
780 if (node->idtype & FINSH_IDTYPE_VAR)
781 {
782 struct finsh_var* var;
783
784 var = node->id.var;
785 if (var != NULL)
786 {
787 switch (var->type)
788 {
789 case finsh_type_void:
790 node->data_type = FINSH_DATA_TYPE_VOID;
791 break;
792
793 case finsh_type_char:
794 case finsh_type_uchar:
795 node->data_type = FINSH_DATA_TYPE_BYTE;
796 break;
797
798 case finsh_type_short:
799 case finsh_type_ushort:
800 node->data_type = FINSH_DATA_TYPE_WORD;
801 break;
802
803 case finsh_type_int:
804 case finsh_type_uint:
805 case finsh_type_long:
806 case finsh_type_ulong:
807 node->data_type = FINSH_DATA_TYPE_DWORD;
808 break;
809
810 case finsh_type_charp:
811 case finsh_type_voidp:
812 case finsh_type_shortp:
813 case finsh_type_intp:
814 case finsh_type_longp:
815 node->data_type = FINSH_DATA_TYPE_DWORD;
816 break;
817
818 default:
819 finsh_error_set(FINSH_ERROR_UNKNOWN_TYPE);
820 break;
821 }
822 }
823 }
824 else if (node->idtype & FINSH_IDTYPE_SYSVAR)
825 {
826 struct finsh_sysvar *sysvar;
827
828 sysvar = node->id.sysvar;
829 if (sysvar != NULL)
830 {
831 switch (sysvar->type)
832 {
833 case finsh_type_void:
834 node->data_type = FINSH_DATA_TYPE_VOID;
835 break;
836
837 case finsh_type_char:
838 case finsh_type_uchar:
839 node->data_type = FINSH_DATA_TYPE_BYTE;
840 break;
841
842 case finsh_type_short:
843 case finsh_type_ushort:
844 node->data_type = FINSH_DATA_TYPE_WORD;
845 break;
846
847 case finsh_type_int:
848 case finsh_type_uint:
849 case finsh_type_long:
850 case finsh_type_ulong:
851 node->data_type = FINSH_DATA_TYPE_DWORD;
852 break;
853
854 case finsh_type_charp:
855 case finsh_type_voidp:
856 case finsh_type_shortp:
857 case finsh_type_intp:
858 case finsh_type_longp:
859 node->data_type = FINSH_DATA_TYPE_DWORD;
860 break;
861
862 default:
863 finsh_error_set(FINSH_ERROR_UNKNOWN_TYPE);
864 break;
865 }
866 }
867 }
868 }
869 else if (node->node_type == FINSH_NODE_VALUE_CHAR)
870 {
871 node->data_type = FINSH_DATA_TYPE_BYTE;
872 }
873 else if (node->node_type == FINSH_NODE_VALUE_INT ||
874 node->node_type == FINSH_NODE_VALUE_LONG ||
875 node->node_type == FINSH_NODE_VALUE_STRING ||
876 node->node_type == FINSH_NODE_VALUE_NULL)
877 {
878 node->data_type = FINSH_DATA_TYPE_DWORD;
879 }
880 }
881 return 0;
882 }
883
finsh_compiler_run(struct finsh_node * node)884 int finsh_compiler_run(struct finsh_node* node)
885 {
886 struct finsh_node* sibling;
887
888 /* type check */
889 finsh_type_check(node, FINSH_NODE_VALUE);
890
891 /* clean text segment and vm stack */
892 memset(&text_segment[0], 0, sizeof(text_segment));
893 memset(&finsh_vm_stack[0], 0, sizeof(finsh_vm_stack[0]));
894
895 /* reset compile stack pointer and pc */
896 finsh_compile_sp = &finsh_vm_stack[0];
897 finsh_compile_pc = &text_segment[0];
898
899 /* compile node */
900 sibling = node;
901 while (sibling != NULL)
902 {
903 struct finsh_node* current_node;
904 current_node = sibling;
905
906 /* get sibling node */
907 sibling = current_node->sibling;
908
909 /* clean sibling node */
910 current_node->sibling = NULL;
911 finsh_compile(current_node);
912
913 /* pop current value */
914 if (sibling != NULL) finsh_code_byte(FINSH_OP_POP);
915 }
916
917 return 0;
918 }
919