initial commit
[mim.git] / gen.c
1 /*
2 Copyright (C) 2017-2018 Keziah Wesley
3
4 You can redistribute and/or modify this file under the terms of the
5 GNU Affero General Public License as published by the Free Software
6 Foundation, either version 3 of the License, or (at your option) any
7 later version.
8
9 This file is distributed in the hope that it will be useful, but
10 WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 Affero General Public License for more details.
13
14 You should have received a copy of the GNU Affero General Public
15 License along with this file. If not, see
16 <http://www.gnu.org/licenses/>.
17 */
18 /* GENERATED FILE. CHANGES WILL BE OVERRIDDEN. 
19 This file is generated by Muddle code; it is included in the distribution for bootstrapping. */
20 enum {I_HALT=4,I_MUL=3,I_SUBB=2,I_SUB=1,I_GRTRB=0,};
21
22 void run (const uint8_t * p0, const uint8_t * p, object * bp, int sp) {
23 for (;;) {
24 TRACE(p0, p);
25 switch (*p) {
26 case I_HALT: {
27 const uint8_t * const oldp = p;
28 p += 1;
29 return;
30 break;
31 }
32 case I_MUL: {
33 int64_t x = GETFIX(bp[p[1]]);
34 int64_t y = GETFIX(bp[p[2]]);
35 object * _res = RESULT(3);
36 const uint8_t * const oldp = p;
37 p += 4;
38 *_res = (NEWFIX( x * y ));
39 break;
40 }
41 case I_SUBB: {
42 int64_t x = GETFIX(bp[p[1]]);
43 uint8_t rhs = p[2];
44 object * _res = RESULT(3);
45 const uint8_t * const oldp = p;
46 p += 4;
47 *_res = (NEWFIX( x - rhs ));
48 break;
49 }
50 case I_SUB: {
51 int64_t x = GETFIX(bp[p[1]]);
52 int64_t y = GETFIX(bp[p[2]]);
53 object * _res = RESULT(3);
54 const uint8_t * const oldp = p;
55 p += 4;
56 *_res = (NEWFIX( x - y ));
57 break;
58 }
59 case I_GRTRB: {
60 int64_t x = GETFIX(bp[p[1]]);
61 uint8_t rhs = p[2];
62 uint8_t invert = p[3];
63 int8_t offs = (int8_t)p[4];
64 const uint8_t * const oldp = p;
65 p += 5;
66 if (invert ^ (x > rhs)) JUMP(offs);
67 break;
68 }
69 default: assert(0 && "bad opcode");
70 }
71 }
72 }
73
74 int snprint_op_disasm(char ** buf, size_t outlen, const uint8_t ** p, size_t inlen)
75 {
76 switch (**p) {
77 case 4: 
78 if (inlen < 0) { return EBADOPARGS; };
79 *buf += snprintf(*buf, outlen, "<%s>\n", "HALT");
80 *p += 0;
81 return 0;
82 case 3: 
83 if (inlen < 3) { return EBADOPARGS; };
84 *buf += snprintf(*buf, outlen, "<%s fix%hhu fix%hhu %hhi>\n", "MUL", (*p)[1], (*p)[2], (*p)[3]);
85 *p += 3;
86 return 0;
87 case 2: 
88 if (inlen < 3) { return EBADOPARGS; };
89 *buf += snprintf(*buf, outlen, "<%s fix%hhu %hhu %hhi>\n", "SUBB", (*p)[1], (*p)[2], (*p)[3]);
90 *p += 3;
91 return 0;
92 case 1: 
93 if (inlen < 3) { return EBADOPARGS; };
94 *buf += snprintf(*buf, outlen, "<%s fix%hhu fix%hhu %hhi>\n", "SUB", (*p)[1], (*p)[2], (*p)[3]);
95 *p += 3;
96 return 0;
97 case 0: 
98 if (inlen < 4) { return EBADOPARGS; };
99 *buf += snprintf(*buf, outlen, "<%s fix%hhu %hhu %hhu %hhi>\n", "GRTRB", (*p)[1], (*p)[2], (*p)[3], (*p)[4]);
100 *p += 4;
101 return 0;
102 }
103 return EBADOPCODE;
104 }
105