blob: eb7d41b24dac30e1d491606e7d00983071f26d0a [file] [log] [blame]
Damienf03001f2013-11-17 13:19:33 +00001#include <stdint.h>
2#include <stdlib.h>
3#include <stdio.h>
4#include <string.h>
5#include <assert.h>
6
7#include "misc.h"
Damiend99b0522013-12-21 18:17:45 +00008#include "mpconfig.h"
9#include "bc0.h"
Damienf03001f2013-11-17 13:19:33 +000010
11#define DECODE_UINT do { unum = *ip++; if (unum > 127) { unum = ((unum & 0x3f) << 8) | (*ip++); } } while (0)
12#define DECODE_ULABEL do { unum = (ip[0] | (ip[1] << 8)); ip += 2; } while (0)
13#define DECODE_SLABEL do { unum = (ip[0] | (ip[1] << 8)) - 0x8000; ip += 2; } while (0)
14#define DECODE_QSTR do { qstr = *ip++; if (qstr > 127) { qstr = ((qstr & 0x3f) << 8) | (*ip++); } } while (0)
15
Damiend99b0522013-12-21 18:17:45 +000016void mp_show_byte_code(const byte *ip, int len) {
Damienf03001f2013-11-17 13:19:33 +000017 const byte *ip_start = ip;
Damien George6baf76e2013-12-30 22:32:17 +000018
19 // decode prelude
20 {
21 uint n_local = *ip++;
22 printf("(NUM_LOCAL %u)\n", n_local);
23 for (; n_local > 0; n_local--) {
24 uint local_num = *ip++;
25 printf("(INIT_CELL %u)\n", local_num);
26 }
27 len -= ip - ip_start;
28 ip_start = ip;
29 }
30
Damienf03001f2013-11-17 13:19:33 +000031 machine_uint_t unum;
32 qstr qstr;
33 while (ip - ip_start < len) {
34 printf("%02u ", (uint)(ip - ip_start));
35 int op = *ip++;
36 switch (op) {
Damiend99b0522013-12-21 18:17:45 +000037 case MP_BC_LOAD_CONST_FALSE:
Damienf03001f2013-11-17 13:19:33 +000038 printf("LOAD_CONST_FALSE");
39 break;
40
Damiend99b0522013-12-21 18:17:45 +000041 case MP_BC_LOAD_CONST_NONE:
Damienf03001f2013-11-17 13:19:33 +000042 printf("LOAD_CONST_NONE");
43 break;
44
Damiend99b0522013-12-21 18:17:45 +000045 case MP_BC_LOAD_CONST_TRUE:
Damienf03001f2013-11-17 13:19:33 +000046 printf("LOAD_CONST_TRUE");
47 break;
48
Damien Georgee9906ac2014-01-04 18:44:46 +000049 case MP_BC_LOAD_CONST_ELLIPSIS:
50 printf("LOAD_CONST_ELLIPSIS");
51 break;
52
Damiend99b0522013-12-21 18:17:45 +000053 case MP_BC_LOAD_CONST_SMALL_INT:
Damienf03001f2013-11-17 13:19:33 +000054 unum = (ip[0] | (ip[1] << 8) | (ip[2] << 16)) - 0x800000;
55 ip += 3;
56 printf("LOAD_CONST_SMALL_INT %d", (int)unum);
57 break;
58
59 /*
Damiend99b0522013-12-21 18:17:45 +000060 case MP_BC_LOAD_CONST_DEC:
Damienf03001f2013-11-17 13:19:33 +000061 DECODE_QSTR;
62 PUSH(rt_load_const_dec(qstr));
63 break;
Damienc1075dd2013-11-25 23:39:36 +000064 */
Damienf03001f2013-11-17 13:19:33 +000065
Damiend99b0522013-12-21 18:17:45 +000066 case MP_BC_LOAD_CONST_ID:
Damienf03001f2013-11-17 13:19:33 +000067 DECODE_QSTR;
Damienc1075dd2013-11-25 23:39:36 +000068 printf("LOAD_CONST_ID %s", qstr_str(qstr));
Damienf03001f2013-11-17 13:19:33 +000069 break;
70
Damiend99b0522013-12-21 18:17:45 +000071 case MP_BC_LOAD_CONST_STRING:
Damienf03001f2013-11-17 13:19:33 +000072 DECODE_QSTR;
Damienff099f32013-11-26 15:14:50 +000073 printf("LOAD_CONST_STRING %s", qstr_str(qstr));
Damienf03001f2013-11-17 13:19:33 +000074 break;
Damienf03001f2013-11-17 13:19:33 +000075
Damiend99b0522013-12-21 18:17:45 +000076 case MP_BC_LOAD_FAST_0:
Damienf03001f2013-11-17 13:19:33 +000077 printf("LOAD_FAST_0");
78 break;
79
Damiend99b0522013-12-21 18:17:45 +000080 case MP_BC_LOAD_FAST_1:
Damienf03001f2013-11-17 13:19:33 +000081 printf("LOAD_FAST_1");
82 break;
83
Damiend99b0522013-12-21 18:17:45 +000084 case MP_BC_LOAD_FAST_2:
Damienf03001f2013-11-17 13:19:33 +000085 printf("LOAD_FAST_2");
86 break;
87
Damiend99b0522013-12-21 18:17:45 +000088 case MP_BC_LOAD_FAST_N:
Damienf03001f2013-11-17 13:19:33 +000089 DECODE_UINT;
Paul Sokolovskye85c3892013-12-30 03:38:32 +020090 printf("LOAD_FAST_N " UINT_FMT, unum);
Damienf03001f2013-11-17 13:19:33 +000091 break;
Damienf03001f2013-11-17 13:19:33 +000092
Damien George6baf76e2013-12-30 22:32:17 +000093 case MP_BC_LOAD_DEREF:
94 DECODE_UINT;
95 printf("LOAD_DEREF " UINT_FMT, unum);
96 break;
97
Damiend99b0522013-12-21 18:17:45 +000098 case MP_BC_LOAD_NAME:
Damienf03001f2013-11-17 13:19:33 +000099 DECODE_QSTR;
100 printf("LOAD_NAME %s", qstr_str(qstr));
101 break;
102
Damiend99b0522013-12-21 18:17:45 +0000103 case MP_BC_LOAD_GLOBAL:
Damienf03001f2013-11-17 13:19:33 +0000104 DECODE_QSTR;
105 printf("LOAD_GLOBAL %s", qstr_str(qstr));
106 break;
107
Damiend99b0522013-12-21 18:17:45 +0000108 case MP_BC_LOAD_ATTR:
Damienf03001f2013-11-17 13:19:33 +0000109 DECODE_QSTR;
Damienc1075dd2013-11-25 23:39:36 +0000110 printf("LOAD_ATTR %s", qstr_str(qstr));
Damienf03001f2013-11-17 13:19:33 +0000111 break;
Damienf03001f2013-11-17 13:19:33 +0000112
Damiend99b0522013-12-21 18:17:45 +0000113 case MP_BC_LOAD_METHOD:
Damienf03001f2013-11-17 13:19:33 +0000114 DECODE_QSTR;
115 printf("LOAD_METHOD %s", qstr_str(qstr));
116 break;
117
Damiend99b0522013-12-21 18:17:45 +0000118 case MP_BC_LOAD_BUILD_CLASS:
Damienc1075dd2013-11-25 23:39:36 +0000119 printf("LOAD_BUILD_CLASS");
Damienf03001f2013-11-17 13:19:33 +0000120 break;
Damienf03001f2013-11-17 13:19:33 +0000121
Damiend99b0522013-12-21 18:17:45 +0000122 case MP_BC_STORE_FAST_0:
Damienf03001f2013-11-17 13:19:33 +0000123 printf("STORE_FAST_0");
124 break;
125
Damiend99b0522013-12-21 18:17:45 +0000126 case MP_BC_STORE_FAST_1:
Damienf03001f2013-11-17 13:19:33 +0000127 printf("STORE_FAST_1");
128 break;
129
Damiend99b0522013-12-21 18:17:45 +0000130 case MP_BC_STORE_FAST_2:
Damienf03001f2013-11-17 13:19:33 +0000131 printf("STORE_FAST_2");
132 break;
133
Damiend99b0522013-12-21 18:17:45 +0000134 case MP_BC_STORE_FAST_N:
Damienf03001f2013-11-17 13:19:33 +0000135 DECODE_UINT;
Paul Sokolovskye85c3892013-12-30 03:38:32 +0200136 printf("STORE_FAST_N " UINT_FMT, unum);
Damienf03001f2013-11-17 13:19:33 +0000137 break;
Damienf03001f2013-11-17 13:19:33 +0000138
Damien George6baf76e2013-12-30 22:32:17 +0000139 case MP_BC_STORE_DEREF:
140 DECODE_UINT;
141 printf("STORE_DEREF " UINT_FMT, unum);
142 break;
143
Damiend99b0522013-12-21 18:17:45 +0000144 case MP_BC_STORE_NAME:
Damienf03001f2013-11-17 13:19:33 +0000145 DECODE_QSTR;
146 printf("STORE_NAME %s", qstr_str(qstr));
147 break;
148
Damiend99b0522013-12-21 18:17:45 +0000149 case MP_BC_STORE_GLOBAL:
Damienf03001f2013-11-17 13:19:33 +0000150 DECODE_QSTR;
Damien George66028ab2014-01-03 14:03:48 +0000151 printf("STORE_GLOBAL %s", qstr_str(qstr));
Damienf03001f2013-11-17 13:19:33 +0000152 break;
153
Damiend99b0522013-12-21 18:17:45 +0000154 case MP_BC_STORE_ATTR:
Damienf03001f2013-11-17 13:19:33 +0000155 DECODE_QSTR;
Damienc1075dd2013-11-25 23:39:36 +0000156 printf("STORE_ATTR %s", qstr_str(qstr));
Damienf03001f2013-11-17 13:19:33 +0000157 break;
158
Damiend99b0522013-12-21 18:17:45 +0000159 case MP_BC_STORE_SUBSCR:
Damienff099f32013-11-26 15:14:50 +0000160 printf("STORE_SUBSCR");
Damienf03001f2013-11-17 13:19:33 +0000161 break;
162
Damiend99b0522013-12-21 18:17:45 +0000163 case MP_BC_DUP_TOP:
Damien8f9e2ee2013-12-29 16:54:59 +0000164 printf("DUP_TOP");
Damienf03001f2013-11-17 13:19:33 +0000165 break;
166
Damiend99b0522013-12-21 18:17:45 +0000167 case MP_BC_DUP_TOP_TWO:
Damienff099f32013-11-26 15:14:50 +0000168 printf("DUP_TOP_TWO");
Damienf03001f2013-11-17 13:19:33 +0000169 break;
Damienf03001f2013-11-17 13:19:33 +0000170
Damiend99b0522013-12-21 18:17:45 +0000171 case MP_BC_POP_TOP:
Damienf03001f2013-11-17 13:19:33 +0000172 printf("POP_TOP");
173 break;
174
175 /*
Damiend99b0522013-12-21 18:17:45 +0000176 case MP_BC_ROT_TWO:
Damienf03001f2013-11-17 13:19:33 +0000177 obj1 = sp[0];
178 sp[0] = sp[1];
179 sp[1] = obj1;
180 break;
Damienff099f32013-11-26 15:14:50 +0000181 */
Damienf03001f2013-11-17 13:19:33 +0000182
Damiend99b0522013-12-21 18:17:45 +0000183 case MP_BC_ROT_THREE:
Damienff099f32013-11-26 15:14:50 +0000184 printf("ROT_THREE");
Damienf03001f2013-11-17 13:19:33 +0000185 break;
Damienf03001f2013-11-17 13:19:33 +0000186
Damiend99b0522013-12-21 18:17:45 +0000187 case MP_BC_JUMP:
Damienf03001f2013-11-17 13:19:33 +0000188 DECODE_SLABEL;
Paul Sokolovskye85c3892013-12-30 03:38:32 +0200189 printf("JUMP " UINT_FMT, ip + unum - ip_start);
Damienf03001f2013-11-17 13:19:33 +0000190 break;
191
Damiend99b0522013-12-21 18:17:45 +0000192 case MP_BC_POP_JUMP_IF_TRUE:
Damienf03001f2013-11-17 13:19:33 +0000193 DECODE_SLABEL;
Paul Sokolovskye85c3892013-12-30 03:38:32 +0200194 printf("POP_JUMP_IF_TRUE " UINT_FMT, ip + unum - ip_start);
Damienf03001f2013-11-17 13:19:33 +0000195 break;
196
Damiend99b0522013-12-21 18:17:45 +0000197 case MP_BC_POP_JUMP_IF_FALSE:
Damienf03001f2013-11-17 13:19:33 +0000198 DECODE_SLABEL;
Paul Sokolovskye85c3892013-12-30 03:38:32 +0200199 printf("POP_JUMP_IF_FALSE " UINT_FMT, ip + unum - ip_start);
Damienf03001f2013-11-17 13:19:33 +0000200 break;
201
Damienff099f32013-11-26 15:14:50 +0000202 /*
Damiend99b0522013-12-21 18:17:45 +0000203 case MP_BC_JUMP_IF_TRUE_OR_POP:
Damienf03001f2013-11-17 13:19:33 +0000204 DECODE_SLABEL;
205 if (rt_is_true(*sp)) {
206 ip += unum;
207 } else {
208 sp++;
209 }
210 break;
211
Damiend99b0522013-12-21 18:17:45 +0000212 case MP_BC_JUMP_IF_FALSE_OR_POP:
Damienf03001f2013-11-17 13:19:33 +0000213 DECODE_SLABEL;
214 if (rt_is_true(*sp)) {
215 sp++;
216 } else {
217 ip += unum;
218 }
219 break;
Damien8f9e2ee2013-12-29 16:54:59 +0000220 */
Damienf03001f2013-11-17 13:19:33 +0000221
Damiend99b0522013-12-21 18:17:45 +0000222 case MP_BC_SETUP_EXCEPT:
Damienf03001f2013-11-17 13:19:33 +0000223 DECODE_ULABEL; // except labels are always forward
Paul Sokolovskye85c3892013-12-30 03:38:32 +0200224 printf("SETUP_EXCEPT " UINT_FMT, ip + unum - ip_start);
Damienf03001f2013-11-17 13:19:33 +0000225 break;
226
Damiend99b0522013-12-21 18:17:45 +0000227 case MP_BC_END_FINALLY:
Damienf03001f2013-11-17 13:19:33 +0000228 // if TOS is an exception, reraises the exception (3 values on TOS)
229 // if TOS is an integer, does something else
230 // if TOS is None, just pops it and continues
231 // else error
Damien8f9e2ee2013-12-29 16:54:59 +0000232 printf("END_FINALLY");
Damienf03001f2013-11-17 13:19:33 +0000233 break;
234
Damiend99b0522013-12-21 18:17:45 +0000235 case MP_BC_GET_ITER:
Damienff099f32013-11-26 15:14:50 +0000236 printf("GET_ITER");
Damienf03001f2013-11-17 13:19:33 +0000237 break;
238
Damiend99b0522013-12-21 18:17:45 +0000239 case MP_BC_FOR_ITER:
Damienf03001f2013-11-17 13:19:33 +0000240 DECODE_ULABEL; // the jump offset if iteration finishes; for labels are always forward
Paul Sokolovskye85c3892013-12-30 03:38:32 +0200241 printf("FOR_ITER " UINT_FMT, ip + unum - ip_start);
Damienf03001f2013-11-17 13:19:33 +0000242 break;
243
Damiend99b0522013-12-21 18:17:45 +0000244 case MP_BC_POP_BLOCK:
Damienf03001f2013-11-17 13:19:33 +0000245 // pops block and restores the stack
Damien8f9e2ee2013-12-29 16:54:59 +0000246 printf("POP_BLOCK");
Damienf03001f2013-11-17 13:19:33 +0000247 break;
248
Damiend99b0522013-12-21 18:17:45 +0000249 case MP_BC_POP_EXCEPT:
Damienf03001f2013-11-17 13:19:33 +0000250 // pops block, checks it's an exception block, and restores the stack, saving the 3 exception values to local threadstate
Damien8f9e2ee2013-12-29 16:54:59 +0000251 printf("POP_EXCEPT");
Damienf03001f2013-11-17 13:19:33 +0000252 break;
253
Damien8f9e2ee2013-12-29 16:54:59 +0000254 /*
Damiend99b0522013-12-21 18:17:45 +0000255 case MP_BC_UNARY_OP:
Damienf03001f2013-11-17 13:19:33 +0000256 unum = *ip++;
257 *sp = rt_unary_op(unum, *sp);
258 break;
259 */
260
Damiend99b0522013-12-21 18:17:45 +0000261 case MP_BC_BINARY_OP:
Damienf03001f2013-11-17 13:19:33 +0000262 unum = *ip++;
Paul Sokolovskye85c3892013-12-30 03:38:32 +0200263 printf("BINARY_OP " UINT_FMT, unum);
Damienf03001f2013-11-17 13:19:33 +0000264 break;
265
Damiend99b0522013-12-21 18:17:45 +0000266 case MP_BC_COMPARE_OP:
Damienf03001f2013-11-17 13:19:33 +0000267 unum = *ip++;
Paul Sokolovskye85c3892013-12-30 03:38:32 +0200268 printf("COMPARE_OP " UINT_FMT, unum);
Damienf03001f2013-11-17 13:19:33 +0000269 break;
270
Damiend99b0522013-12-21 18:17:45 +0000271 case MP_BC_BUILD_TUPLE:
Damienf03001f2013-11-17 13:19:33 +0000272 DECODE_UINT;
Paul Sokolovskye85c3892013-12-30 03:38:32 +0200273 printf("BUILD_TUPLE " UINT_FMT, unum);
Damienf03001f2013-11-17 13:19:33 +0000274 break;
275
Damiend99b0522013-12-21 18:17:45 +0000276 case MP_BC_BUILD_LIST:
Damienf03001f2013-11-17 13:19:33 +0000277 DECODE_UINT;
Paul Sokolovskye85c3892013-12-30 03:38:32 +0200278 printf("BUILD_LIST " UINT_FMT, unum);
Damienf03001f2013-11-17 13:19:33 +0000279 break;
280
Damiend99b0522013-12-21 18:17:45 +0000281 case MP_BC_LIST_APPEND:
Damienf03001f2013-11-17 13:19:33 +0000282 DECODE_UINT;
Damien George27bf5b82014-01-02 18:15:33 +0000283 printf("LIST_APPEND " UINT_FMT, unum);
Damienf03001f2013-11-17 13:19:33 +0000284 break;
285
Damiend99b0522013-12-21 18:17:45 +0000286 case MP_BC_BUILD_MAP:
Damienf03001f2013-11-17 13:19:33 +0000287 DECODE_UINT;
Paul Sokolovskye85c3892013-12-30 03:38:32 +0200288 printf("BUILD_MAP " UINT_FMT, unum);
Damienf03001f2013-11-17 13:19:33 +0000289 break;
290
Damien8f9e2ee2013-12-29 16:54:59 +0000291 /*
Damiend99b0522013-12-21 18:17:45 +0000292 case MP_BC_STORE_MAP:
Damienf03001f2013-11-17 13:19:33 +0000293 sp += 2;
294 rt_store_map(sp[0], sp[-2], sp[-1]);
295 break;
296
Damiend99b0522013-12-21 18:17:45 +0000297 case MP_BC_MAP_ADD:
Damienf03001f2013-11-17 13:19:33 +0000298 DECODE_UINT;
299 // I think it's guaranteed by the compiler that sp[unum + 1] is a map
300 rt_store_map(sp[unum + 1], sp[0], sp[1]);
301 sp += 2;
302 break;
Damiendae7eb72013-12-29 22:32:51 +0000303 */
Damienf03001f2013-11-17 13:19:33 +0000304
Damiend99b0522013-12-21 18:17:45 +0000305 case MP_BC_BUILD_SET:
Damienf03001f2013-11-17 13:19:33 +0000306 DECODE_UINT;
Damien George212c2962013-12-30 12:52:32 +0000307 printf("BUILD_SET " UINT_FMT, unum);
Damienf03001f2013-11-17 13:19:33 +0000308 break;
309
Damiend99b0522013-12-21 18:17:45 +0000310 case MP_BC_SET_ADD:
Damienf03001f2013-11-17 13:19:33 +0000311 DECODE_UINT;
Damien George212c2962013-12-30 12:52:32 +0000312 printf("SET_ADD " UINT_FMT, unum);
Damienf03001f2013-11-17 13:19:33 +0000313 break;
Damienf03001f2013-11-17 13:19:33 +0000314
Damiend99b0522013-12-21 18:17:45 +0000315 case MP_BC_UNPACK_SEQUENCE:
Damienff099f32013-11-26 15:14:50 +0000316 DECODE_UINT;
Paul Sokolovskye85c3892013-12-30 03:38:32 +0200317 printf("UNPACK_SEQUENCE " UINT_FMT, unum);
Damienff099f32013-11-26 15:14:50 +0000318 break;
319
Damiend99b0522013-12-21 18:17:45 +0000320 case MP_BC_MAKE_FUNCTION:
Damienf03001f2013-11-17 13:19:33 +0000321 DECODE_UINT;
Paul Sokolovskye85c3892013-12-30 03:38:32 +0200322 printf("MAKE_FUNCTION " UINT_FMT, unum);
Damienf03001f2013-11-17 13:19:33 +0000323 break;
324
Damien George6baf76e2013-12-30 22:32:17 +0000325 case MP_BC_MAKE_CLOSURE:
326 DECODE_UINT;
327 printf("MAKE_CLOSURE " UINT_FMT, unum);
328 break;
329
Damiend99b0522013-12-21 18:17:45 +0000330 case MP_BC_CALL_FUNCTION:
Damienf03001f2013-11-17 13:19:33 +0000331 DECODE_UINT;
Paul Sokolovskye85c3892013-12-30 03:38:32 +0200332 printf("CALL_FUNCTION n=" UINT_FMT " nkw=" UINT_FMT, unum & 0xff, (unum >> 8) & 0xff);
Damienf03001f2013-11-17 13:19:33 +0000333 break;
334
Damiend99b0522013-12-21 18:17:45 +0000335 case MP_BC_CALL_METHOD:
Damienf03001f2013-11-17 13:19:33 +0000336 DECODE_UINT;
Paul Sokolovskye85c3892013-12-30 03:38:32 +0200337 printf("CALL_METHOD n=" UINT_FMT " nkw=" UINT_FMT, unum & 0xff, (unum >> 8) & 0xff);
Damienf03001f2013-11-17 13:19:33 +0000338 break;
339
Damiend99b0522013-12-21 18:17:45 +0000340 case MP_BC_RETURN_VALUE:
Damienf03001f2013-11-17 13:19:33 +0000341 printf("RETURN_VALUE");
342 break;
343
Damiend99b0522013-12-21 18:17:45 +0000344 case MP_BC_YIELD_VALUE:
Damien George27bf5b82014-01-02 18:15:33 +0000345 printf("YIELD_VALUE");
346 break;
Damienf03001f2013-11-17 13:19:33 +0000347
Damien George66028ab2014-01-03 14:03:48 +0000348 case MP_BC_IMPORT_NAME:
349 DECODE_QSTR;
350 printf("IMPORT NAME %s", qstr_str(qstr));
351 break;
352
353 case MP_BC_IMPORT_FROM:
354 DECODE_QSTR;
355 printf("IMPORT NAME %s", qstr_str(qstr));
356 break;
357
Damienf03001f2013-11-17 13:19:33 +0000358 default:
359 printf("code %p, byte code 0x%02x not implemented\n", ip, op);
360 assert(0);
361 return;
362 }
363 printf("\n");
364 }
365}