blob: e529e71b99df53ec9aab9b4b5db95c4b023d5f8f [file] [log] [blame]
Damien39cf3282013-10-05 23:18:38 +01001#include <stdlib.h>
2#include <stdint.h>
Damien39cf3282013-10-05 23:18:38 +01003#include <assert.h>
4
5#include "misc.h"
Damiend99b0522013-12-21 18:17:45 +00006#include "mpconfig.h"
Damien George55baff42014-01-21 21:40:13 +00007#include "qstr.h"
Damien39cf3282013-10-05 23:18:38 +01008#include "lexer.h"
Damien39cf3282013-10-05 23:18:38 +01009#include "parse.h"
Damien39cf3282013-10-05 23:18:38 +010010#include "scope.h"
Damiend99b0522013-12-21 18:17:45 +000011#include "runtime0.h"
Damien39cf3282013-10-05 23:18:38 +010012#include "emit.h"
13
14struct _emit_t {
Damien39cf3282013-10-05 23:18:38 +010015 scope_t *scope;
16};
17
Damien George35e2a4e2014-02-05 00:51:47 +000018emit_t *emit_pass1_new(void) {
Damien39cf3282013-10-05 23:18:38 +010019 emit_t *emit = m_new(emit_t, 1);
Damien39cf3282013-10-05 23:18:38 +010020 return emit;
21}
22
23void emit_pass1_free(emit_t *emit) {
Damien732407f2013-12-29 19:33:23 +000024 m_del_obj(emit_t, emit);
Damien39cf3282013-10-05 23:18:38 +010025}
26
Paul Sokolovsky520e2f52014-02-12 18:31:30 +020027STATIC void emit_pass1_dummy(emit_t *emit) {
Damien39cf3282013-10-05 23:18:38 +010028}
29
Paul Sokolovsky520e2f52014-02-12 18:31:30 +020030STATIC void emit_pass1_start_pass(emit_t *emit, pass_kind_t pass, scope_t *scope) {
Damien39cf3282013-10-05 23:18:38 +010031 assert(pass == PASS_1);
32 emit->scope = scope;
33}
34
Paul Sokolovsky520e2f52014-02-12 18:31:30 +020035STATIC void emit_pass1_end_pass(emit_t *emit) {
Damien39cf3282013-10-05 23:18:38 +010036}
37
Damien Georgec90717a2014-04-10 15:40:38 +000038STATIC bool emit_pass1_last_emit_was_return_value(emit_t *emit) {
39 return false;
40}
41
42STATIC int emit_pass1_get_stack_size(emit_t *emit) {
43 return 0;
44}
45
Paul Sokolovsky520e2f52014-02-12 18:31:30 +020046STATIC void emit_pass1_load_id(emit_t *emit, qstr qstr) {
Damien39cf3282013-10-05 23:18:38 +010047 // name adding/lookup
48 bool added;
49 id_info_t *id = scope_find_or_add_id(emit->scope, qstr, &added);
50 if (added) {
Damien George35e2a4e2014-02-05 00:51:47 +000051#if MICROPY_EMIT_CPYTHON
52 if (qstr == MP_QSTR_super && emit->scope->kind == SCOPE_FUNCTION) {
Damien39cf3282013-10-05 23:18:38 +010053 // special case, super is a global, and also counts as use of __class__
54 id->kind = ID_INFO_KIND_GLOBAL_EXPLICIT;
Damien George35e2a4e2014-02-05 00:51:47 +000055 id_info_t *id2 = scope_find_local_in_parent(emit->scope, MP_QSTR___class__);
Damien39cf3282013-10-05 23:18:38 +010056 if (id2 != NULL) {
Damien George35e2a4e2014-02-05 00:51:47 +000057 id2 = scope_find_or_add_id(emit->scope, MP_QSTR___class__, &added);
Damien39cf3282013-10-05 23:18:38 +010058 if (added) {
59 id2->kind = ID_INFO_KIND_FREE;
Damien George35e2a4e2014-02-05 00:51:47 +000060 scope_close_over_in_parents(emit->scope, MP_QSTR___class__);
Damien39cf3282013-10-05 23:18:38 +010061 }
62 }
Damien George35e2a4e2014-02-05 00:51:47 +000063 } else
64#endif
65 {
Damien39cf3282013-10-05 23:18:38 +010066 id_info_t *id2 = scope_find_local_in_parent(emit->scope, qstr);
67 if (id2 != NULL && (id2->kind == ID_INFO_KIND_LOCAL || id2->kind == ID_INFO_KIND_CELL || id2->kind == ID_INFO_KIND_FREE)) {
68 id->kind = ID_INFO_KIND_FREE;
69 scope_close_over_in_parents(emit->scope, qstr);
70 } else {
71 id->kind = ID_INFO_KIND_GLOBAL_IMPLICIT;
72 }
73 }
74 }
75}
76
Paul Sokolovsky520e2f52014-02-12 18:31:30 +020077STATIC id_info_t *get_id_for_modification(scope_t *scope, qstr qstr) {
Damien39cf3282013-10-05 23:18:38 +010078 // name adding/lookup
79 bool added;
80 id_info_t *id = scope_find_or_add_id(scope, qstr, &added);
81 if (added) {
82 if (scope->kind == SCOPE_MODULE || scope->kind == SCOPE_CLASS) {
83 id->kind = ID_INFO_KIND_GLOBAL_IMPLICIT;
84 } else {
85 id->kind = ID_INFO_KIND_LOCAL;
86 }
87 } else if (scope->kind >= SCOPE_FUNCTION && scope->kind <= SCOPE_GEN_EXPR && id->kind == ID_INFO_KIND_GLOBAL_IMPLICIT) {
88 // rebind as a local variable
89 id->kind = ID_INFO_KIND_LOCAL;
90 }
91
92 assert(id != NULL); // TODO can this ever fail?
93
94 return id;
95}
96
Paul Sokolovsky520e2f52014-02-12 18:31:30 +020097STATIC void emit_pass1_store_id(emit_t *emit, qstr qstr) {
Damien39cf3282013-10-05 23:18:38 +010098 get_id_for_modification(emit->scope, qstr);
99}
100
Paul Sokolovsky520e2f52014-02-12 18:31:30 +0200101STATIC void emit_pass1_delete_id(emit_t *emit, qstr qstr) {
Damien George2bf7c092014-04-09 15:26:46 +0100102 id_info_t *id = get_id_for_modification(emit->scope, qstr);
103 id->flags |= ID_FLAG_IS_DELETED;
Damien39cf3282013-10-05 23:18:38 +0100104}
105
106const emit_method_table_t emit_pass1_method_table = {
107 (void*)emit_pass1_dummy,
108 emit_pass1_start_pass,
109 emit_pass1_end_pass,
Damien Georgec90717a2014-04-10 15:40:38 +0000110 emit_pass1_last_emit_was_return_value,
111 emit_pass1_get_stack_size,
Damien39cf3282013-10-05 23:18:38 +0100112 (void*)emit_pass1_dummy,
Damien George08335002014-01-18 23:24:36 +0000113 (void*)emit_pass1_dummy,
Damien39cf3282013-10-05 23:18:38 +0100114
115 emit_pass1_load_id,
116 emit_pass1_store_id,
117 emit_pass1_delete_id,
118
119 (void*)emit_pass1_dummy,
120 (void*)emit_pass1_dummy,
121 (void*)emit_pass1_dummy,
122 (void*)emit_pass1_dummy,
123 (void*)emit_pass1_dummy,
124 (void*)emit_pass1_dummy,
125 (void*)emit_pass1_dummy,
126 (void*)emit_pass1_dummy,
127 (void*)emit_pass1_dummy,
128 (void*)emit_pass1_dummy,
129 (void*)emit_pass1_dummy,
130 (void*)emit_pass1_dummy,
131 (void*)emit_pass1_dummy,
132 (void*)emit_pass1_dummy,
133 (void*)emit_pass1_dummy,
134 (void*)emit_pass1_dummy,
135 (void*)emit_pass1_dummy,
136 (void*)emit_pass1_dummy,
137 (void*)emit_pass1_dummy,
138 (void*)emit_pass1_dummy,
139 (void*)emit_pass1_dummy,
140 (void*)emit_pass1_dummy,
141 (void*)emit_pass1_dummy,
142 (void*)emit_pass1_dummy,
143 (void*)emit_pass1_dummy,
144 (void*)emit_pass1_dummy,
145 (void*)emit_pass1_dummy,
146 (void*)emit_pass1_dummy,
147 (void*)emit_pass1_dummy,
148 (void*)emit_pass1_dummy,
149 (void*)emit_pass1_dummy,
150 (void*)emit_pass1_dummy,
151 (void*)emit_pass1_dummy,
152 (void*)emit_pass1_dummy,
153 (void*)emit_pass1_dummy,
154 (void*)emit_pass1_dummy,
155 (void*)emit_pass1_dummy,
156 (void*)emit_pass1_dummy,
157 (void*)emit_pass1_dummy,
158 (void*)emit_pass1_dummy,
159 (void*)emit_pass1_dummy,
160 (void*)emit_pass1_dummy,
161 (void*)emit_pass1_dummy,
162 (void*)emit_pass1_dummy,
163 (void*)emit_pass1_dummy,
164 (void*)emit_pass1_dummy,
165 (void*)emit_pass1_dummy,
166 (void*)emit_pass1_dummy,
167 (void*)emit_pass1_dummy,
168 (void*)emit_pass1_dummy,
169 (void*)emit_pass1_dummy,
170 (void*)emit_pass1_dummy,
171 (void*)emit_pass1_dummy,
172 (void*)emit_pass1_dummy,
173 (void*)emit_pass1_dummy,
174 (void*)emit_pass1_dummy,
175 (void*)emit_pass1_dummy,
176 (void*)emit_pass1_dummy,
177 (void*)emit_pass1_dummy,
178 (void*)emit_pass1_dummy,
179 (void*)emit_pass1_dummy,
180 (void*)emit_pass1_dummy,
181 (void*)emit_pass1_dummy,
182 (void*)emit_pass1_dummy,
183 (void*)emit_pass1_dummy,
184 (void*)emit_pass1_dummy,
185 (void*)emit_pass1_dummy,
186 (void*)emit_pass1_dummy,
187 (void*)emit_pass1_dummy,
188 (void*)emit_pass1_dummy,
189 (void*)emit_pass1_dummy,
190 (void*)emit_pass1_dummy,
191 (void*)emit_pass1_dummy,
192 (void*)emit_pass1_dummy,
193 (void*)emit_pass1_dummy,
Damien39cf3282013-10-05 23:18:38 +0100194};