Skip to content

Commit d64154c

Browse files
committed
py/emitinlinethumb: Update to work with new small-heap compiler.
Note that the inline assembler only works with the small-heap compiler enabled.
1 parent 4145377 commit d64154c

File tree

5 files changed

+116
-91
lines changed

5 files changed

+116
-91
lines changed

py/compile2.c

Lines changed: 52 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -34,6 +34,7 @@
3434
#include "py/emit.h"
3535
#include "py/compile.h"
3636
#include "py/runtime.h"
37+
#include "py/asmbase.h"
3738

3839
#if MICROPY_ENABLE_COMPILER && MICROPY_USE_SMALL_HEAP_COMPILER
3940

@@ -81,6 +82,19 @@ typedef enum {
8182

8283
#endif
8384

85+
#if MICROPY_EMIT_INLINE_ASM
86+
// define macros for inline assembler
87+
#if MICROPY_EMIT_INLINE_THUMB
88+
#define ASM_DECORATOR_QSTR MP_QSTR_asm_thumb
89+
#define ASM_EMITTER(f) emit_inline_thumb_##f
90+
#elif MICROPY_EMIT_INLINE_XTENSA
91+
#define ASM_DECORATOR_QSTR MP_QSTR_asm_xtensa
92+
#define ASM_EMITTER(f) emit_inline_xtensa_##f
93+
#else
94+
#error "unknown asm emitter"
95+
#endif
96+
#endif
97+
8498
#define EMIT_INLINE_ASM(fun) (comp->emit_inline_asm_method_table->fun(comp->emit_inline_asm))
8599
#define EMIT_INLINE_ASM_ARG(fun, ...) (comp->emit_inline_asm_method_table->fun(comp->emit_inline_asm, __VA_ARGS__))
86100

@@ -117,7 +131,7 @@ typedef struct _compiler_t {
117131
const emit_method_table_t *emit_method_table; // current emit method table
118132
#endif
119133

120-
#if MICROPY_EMIT_INLINE_THUMB
134+
#if MICROPY_EMIT_INLINE_ASM
121135
emit_inline_asm_t *emit_inline_asm; // current emitter for inline asm
122136
const emit_inline_asm_method_table_t *emit_inline_asm_method_table; // current emit method table for inline asm
123137
#endif
@@ -790,10 +804,10 @@ STATIC bool compile_built_in_decorator(compiler_t *comp, const byte *p, const by
790804
} else if (attr == MP_QSTR_viper) {
791805
*emit_options = MP_EMIT_OPT_VIPER;
792806
#endif
793-
#if MICROPY_EMIT_INLINE_THUMB
794-
} else if (attr == MP_QSTR_asm_thumb) {
795-
*emit_options = MP_EMIT_OPT_ASM_THUMB;
796-
#endif
807+
#if MICROPY_EMIT_INLINE_ASM
808+
} else if (attr == ASM_DECORATOR_QSTR) {
809+
*emit_options = MP_EMIT_OPT_ASM;
810+
#endif
797811
} else {
798812
compile_syntax_error(comp, NULL, "invalid micropython decorator");
799813
}
@@ -3016,7 +3030,7 @@ STATIC void compile_scope(compiler_t *comp, scope_t *scope, pass_kind_t pass) {
30163030
assert(comp->cur_except_level == 0);
30173031
}
30183032

3019-
#if MICROPY_EMIT_INLINE_THUMB
3033+
#if MICROPY_EMIT_INLINE_ASM
30203034
// requires 3 passes: SCOPE, CODE_SIZE, EMIT
30213035
STATIC void compile_scope_inline_asm(compiler_t *comp, scope_t *scope, pass_kind_t pass) {
30223036
comp->pass = pass;
@@ -3029,7 +3043,7 @@ STATIC void compile_scope_inline_asm(compiler_t *comp, scope_t *scope, pass_kind
30293043
}
30303044

30313045
if (comp->pass > MP_PASS_SCOPE) {
3032-
EMIT_INLINE_ASM_ARG(start_pass, comp->pass, comp->scope_cur, &comp->compile_error);
3046+
EMIT_INLINE_ASM_ARG(start_pass, comp->pass, &comp->compile_error);
30333047
}
30343048

30353049
// get the function definition parse node
@@ -3134,7 +3148,8 @@ STATIC void compile_scope_inline_asm(compiler_t *comp, scope_t *scope, pass_kind
31343148
return;
31353149
}
31363150
if (pass > MP_PASS_SCOPE) {
3137-
EMIT_INLINE_ASM_ARG(align, pt_small_int_value(p_args));
3151+
mp_asm_base_align((mp_asm_base_t*)comp->emit_inline_asm,
3152+
pt_small_int_value(p_args));
31383153
}
31393154
} else if (op == MP_QSTR_data) {
31403155
if (!(n_args >= 2 && pt_is_small_int(p_args))) {
@@ -3151,7 +3166,8 @@ STATIC void compile_scope_inline_asm(compiler_t *comp, scope_t *scope, pass_kind
31513166
}
31523167
mp_int_t val;
31533168
p_args = pt_get_small_int(p_args, &val);
3154-
EMIT_INLINE_ASM_ARG(data, bytesize, val);
3169+
mp_asm_base_data((mp_asm_base_t*)comp->emit_inline_asm,
3170+
bytesize, val);
31553171
}
31563172
}
31573173
} else {
@@ -3174,6 +3190,13 @@ STATIC void compile_scope_inline_asm(compiler_t *comp, scope_t *scope, pass_kind
31743190

31753191
if (comp->pass > MP_PASS_SCOPE) {
31763192
EMIT_INLINE_ASM_ARG(end_pass, type_sig);
3193+
3194+
if (comp->pass == MP_PASS_EMIT) {
3195+
void *f = mp_asm_base_get_code((mp_asm_base_t*)comp->emit_inline_asm);
3196+
mp_emit_glue_assign_native(comp->scope_cur->raw_code, MP_CODE_NATIVE_ASM,
3197+
f, mp_asm_base_get_code_size((mp_asm_base_t*)comp->emit_inline_asm),
3198+
NULL, comp->scope_cur->num_pos_args, 0, type_sig);
3199+
}
31773200
}
31783201

31793202
if (comp->compile_error != MP_OBJ_NULL) {
@@ -3309,10 +3332,10 @@ mp_raw_code_t *mp_compile_to_raw_code(mp_parse_tree_t *parse_tree, qstr source_f
33093332
keep_going = true;
33103333
s->raw_code = mp_emit_glue_new_raw_code();
33113334
if (false) {
3312-
#if MICROPY_EMIT_INLINE_THUMB
3313-
} else if (s->emit_options == MP_EMIT_OPT_ASM_THUMB) {
3335+
#if MICROPY_EMIT_INLINE_ASM
3336+
} else if (s->emit_options == MP_EMIT_OPT_ASM) {
33143337
compile_scope_inline_asm(comp, s, MP_PASS_SCOPE);
3315-
#endif
3338+
#endif
33163339
} else {
33173340
compile_scope(comp, s, MP_PASS_SCOPE);
33183341
}
@@ -3337,30 +3360,32 @@ mp_raw_code_t *mp_compile_to_raw_code(mp_parse_tree_t *parse_tree, qstr source_f
33373360
// compile pass 2 and 3
33383361
#if MICROPY_EMIT_NATIVE
33393362
emit_t *emit_native = NULL;
3340-
#endif
3341-
#if MICROPY_EMIT_INLINE_THUMB
3342-
emit_inline_asm_t *emit_inline_thumb = NULL;
33433363
#endif
33443364
for (uint i = 0; i < comp->num_scopes && comp->compile_error == MP_OBJ_NULL; ++i) {
33453365
scope_t *s = comp->scopes[i];
33463366
if (s == NULL) { continue; }
33473367
if (false) {
33483368
// dummy
33493369

3350-
#if MICROPY_EMIT_INLINE_THUMB
3351-
} else if (s->emit_options == MP_EMIT_OPT_ASM_THUMB) {
3352-
// inline assembly for thumb
3353-
if (emit_inline_thumb == NULL) {
3354-
emit_inline_thumb = emit_inline_thumb_new(max_num_labels);
3370+
#if MICROPY_EMIT_INLINE_ASM
3371+
} else if (s->emit_options == MP_EMIT_OPT_ASM) {
3372+
// inline assembly
3373+
if (comp->emit_inline_asm == NULL) {
3374+
comp->emit_inline_asm = ASM_EMITTER(new)(comp->co_data, max_num_labels);
33553375
}
33563376
comp->emit = NULL;
3357-
comp->emit_inline_asm = emit_inline_thumb;
3358-
comp->emit_inline_asm_method_table = &emit_inline_thumb_method_table;
3377+
comp->emit_inline_asm_method_table = &ASM_EMITTER(method_table);
3378+
compile_scope_inline_asm(comp, s, MP_PASS_CODE_SIZE);
3379+
#if MICROPY_EMIT_INLINE_XTENSA
3380+
// Xtensa requires an extra pass to compute size of l32r const table
3381+
// TODO this can be improved by calculating it during SCOPE pass
3382+
// but that requires some other structural changes to the asm emitters
33593383
compile_scope_inline_asm(comp, s, MP_PASS_CODE_SIZE);
3384+
#endif
33603385
if (comp->compile_error == MP_OBJ_NULL) {
33613386
compile_scope_inline_asm(comp, s, MP_PASS_EMIT);
33623387
}
3363-
#endif
3388+
#endif
33643389

33653390
} else {
33663391

@@ -3445,11 +3470,11 @@ mp_raw_code_t *mp_compile_to_raw_code(mp_parse_tree_t *parse_tree, qstr source_f
34453470
#endif
34463471
}
34473472
#endif
3448-
#if MICROPY_EMIT_INLINE_THUMB
3449-
if (emit_inline_thumb != NULL) {
3450-
emit_inline_thumb_free(emit_inline_thumb);
3473+
#if MICROPY_EMIT_INLINE_ASM
3474+
if (comp->emit_inline_asm != NULL) {
3475+
ASM_EMITTER(free)(comp->emit_inline_asm);
34513476
}
3452-
#endif
3477+
#endif
34533478

34543479
// free the parse tree
34553480
mp_parse_tree_clear(parse_tree);

py/emit.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -271,7 +271,7 @@ typedef struct _emit_inline_asm_method_table_t {
271271
extern const emit_inline_asm_method_table_t emit_inline_thumb_method_table;
272272
extern const emit_inline_asm_method_table_t emit_inline_xtensa_method_table;
273273

274-
emit_inline_asm_t *emit_inline_thumb_new(mp_uint_t max_num_labels);
274+
emit_inline_asm_t *emit_inline_thumb_new(mp_uint_t *co_data, mp_uint_t max_num_labels);
275275
emit_inline_asm_t *emit_inline_xtensa_new(mp_uint_t max_num_labels);
276276

277277
void emit_inline_thumb_free(emit_inline_asm_t *emit);

0 commit comments

Comments
 (0)
pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy