aboutsummaryrefslogtreecommitdiff
path: root/py/emitinlinextensa.c
diff options
context:
space:
mode:
authorDamien George <damien.p.george@gmail.com>2016-12-09 20:35:21 +1100
committerDamien George <damien.p.george@gmail.com>2016-12-09 20:35:21 +1100
commita7fd786a1f8a0bd13ec97d9742f8705b90cd1c46 (patch)
tree8643b12fc502c0b47ab3e036907d80e148d355c4 /py/emitinlinextensa.c
parent3a4ebf57685e2ea03deb61276f832108b4ab08b7 (diff)
py/emitinline: Embed entire asm struct instead of a pointer to it.
This reduces fragmentation, and memory use by 1 word. But more importantly it means the emit_inline_asm_t struct now "derives" from mp_asm_base.
Diffstat (limited to 'py/emitinlinextensa.c')
-rw-r--r--py/emitinlinextensa.c49
1 files changed, 24 insertions, 25 deletions
diff --git a/py/emitinlinextensa.c b/py/emitinlinextensa.c
index bd1a7a3ec..284624e45 100644
--- a/py/emitinlinextensa.c
+++ b/py/emitinlinextensa.c
@@ -36,12 +36,12 @@
#if MICROPY_EMIT_INLINE_XTENSA
struct _emit_inline_asm_t {
+ asm_xtensa_t as;
uint16_t pass;
scope_t *scope;
mp_obj_t *error_slot;
mp_uint_t max_num_labels;
qstr *label_lookup;
- asm_xtensa_t *as;
};
STATIC void emit_inline_xtensa_error_msg(emit_inline_asm_t *emit, const char *msg) {
@@ -54,17 +54,16 @@ STATIC void emit_inline_xtensa_error_exc(emit_inline_asm_t *emit, mp_obj_t exc)
emit_inline_asm_t *emit_inline_xtensa_new(mp_uint_t max_num_labels) {
emit_inline_asm_t *emit = m_new_obj(emit_inline_asm_t);
+ memset(&emit->as, 0, sizeof(emit->as));
+ mp_asm_base_init(&emit->as.base, max_num_labels);
emit->max_num_labels = max_num_labels;
emit->label_lookup = m_new(qstr, max_num_labels);
- emit->as = m_new0(asm_xtensa_t, 1);
- mp_asm_base_init(&emit->as->base, max_num_labels);
return emit;
}
void emit_inline_xtensa_free(emit_inline_asm_t *emit) {
m_del(qstr, emit->label_lookup, emit->max_num_labels);
- mp_asm_base_deinit(&emit->as->base, false);
- m_del_obj(asm_xtensa_t, emit->as);
+ mp_asm_base_deinit(&emit->as.base, false);
m_del_obj(emit_inline_asm_t, emit);
}
@@ -75,18 +74,18 @@ STATIC void emit_inline_xtensa_start_pass(emit_inline_asm_t *emit, pass_kind_t p
if (emit->pass == MP_PASS_CODE_SIZE) {
memset(emit->label_lookup, 0, emit->max_num_labels * sizeof(qstr));
}
- mp_asm_base_start_pass(&emit->as->base, pass == MP_PASS_EMIT ? MP_ASM_PASS_EMIT : MP_ASM_PASS_COMPUTE);
- asm_xtensa_entry(emit->as, 0);
+ mp_asm_base_start_pass(&emit->as.base, pass == MP_PASS_EMIT ? MP_ASM_PASS_EMIT : MP_ASM_PASS_COMPUTE);
+ asm_xtensa_entry(&emit->as, 0);
}
STATIC void emit_inline_xtensa_end_pass(emit_inline_asm_t *emit, mp_uint_t type_sig) {
- asm_xtensa_exit(emit->as);
- asm_xtensa_end_pass(emit->as);
+ asm_xtensa_exit(&emit->as);
+ asm_xtensa_end_pass(&emit->as);
if (emit->pass == MP_PASS_EMIT) {
- void *f = mp_asm_base_get_code(&emit->as->base);
+ void *f = mp_asm_base_get_code(&emit->as.base);
mp_emit_glue_assign_native(emit->scope->raw_code, MP_CODE_NATIVE_ASM, f,
- mp_asm_base_get_code_size(&emit->as->base), NULL, emit->scope->num_pos_args, 0, type_sig);
+ mp_asm_base_get_code_size(&emit->as.base), NULL, emit->scope->num_pos_args, 0, type_sig);
}
}
@@ -120,16 +119,16 @@ STATIC bool emit_inline_xtensa_label(emit_inline_asm_t *emit, mp_uint_t label_nu
}
}
emit->label_lookup[label_num] = label_id;
- mp_asm_base_label_assign(&emit->as->base, label_num);
+ mp_asm_base_label_assign(&emit->as.base, label_num);
return true;
}
STATIC void emit_inline_xtensa_align(emit_inline_asm_t *emit, mp_uint_t align) {
- mp_asm_base_align(&emit->as->base, align);
+ mp_asm_base_align(&emit->as.base, align);
}
STATIC void emit_inline_xtensa_data(emit_inline_asm_t *emit, mp_uint_t bytesize, mp_uint_t val) {
- mp_asm_base_data(&emit->as->base, bytesize, val);
+ mp_asm_base_data(&emit->as.base, bytesize, val);
}
typedef struct _reg_name_t { byte reg; byte name[3]; } reg_name_t;
@@ -263,7 +262,7 @@ STATIC void emit_inline_xtensa_op(emit_inline_asm_t *emit, qstr op, mp_uint_t n_
if (n_args == 0) {
if (op == MP_QSTR_ret_n) {
- asm_xtensa_op_ret_n(emit->as);
+ asm_xtensa_op_ret_n(&emit->as);
} else {
goto unknown_op;
}
@@ -271,13 +270,13 @@ STATIC void emit_inline_xtensa_op(emit_inline_asm_t *emit, qstr op, mp_uint_t n_
} else if (n_args == 1) {
if (op == MP_QSTR_callx0) {
uint r0 = get_arg_reg(emit, op_str, pn_args[0]);
- asm_xtensa_op_callx0(emit->as, r0);
+ asm_xtensa_op_callx0(&emit->as, r0);
} else if (op == MP_QSTR_j) {
int label = get_arg_label(emit, op_str, pn_args[0]);
- asm_xtensa_j_label(emit->as, label);
+ asm_xtensa_j_label(&emit->as, label);
} else if (op == MP_QSTR_jx) {
uint r0 = get_arg_reg(emit, op_str, pn_args[0]);
- asm_xtensa_op_jx(emit->as, r0);
+ asm_xtensa_op_jx(&emit->as, r0);
} else {
goto unknown_op;
}
@@ -286,18 +285,18 @@ STATIC void emit_inline_xtensa_op(emit_inline_asm_t *emit, qstr op, mp_uint_t n_
uint r0 = get_arg_reg(emit, op_str, pn_args[0]);
if (op == MP_QSTR_beqz) {
int label = get_arg_label(emit, op_str, pn_args[1]);
- asm_xtensa_bccz_reg_label(emit->as, ASM_XTENSA_CCZ_EQ, r0, label);
+ asm_xtensa_bccz_reg_label(&emit->as, ASM_XTENSA_CCZ_EQ, r0, label);
} else if (op == MP_QSTR_bnez) {
int label = get_arg_label(emit, op_str, pn_args[1]);
- asm_xtensa_bccz_reg_label(emit->as, ASM_XTENSA_CCZ_NE, r0, label);
+ asm_xtensa_bccz_reg_label(&emit->as, ASM_XTENSA_CCZ_NE, r0, label);
} else if (op == MP_QSTR_mov || op == MP_QSTR_mov_n) {
// we emit mov.n for both "mov" and "mov_n" opcodes
uint r1 = get_arg_reg(emit, op_str, pn_args[1]);
- asm_xtensa_op_mov_n(emit->as, r0, r1);
+ asm_xtensa_op_mov_n(&emit->as, r0, r1);
} else if (op == MP_QSTR_movi) {
// for convenience we emit l32r if the integer doesn't fit in movi
uint32_t imm = get_arg_i(emit, op_str, pn_args[1], 0, 0);
- asm_xtensa_mov_reg_i32(emit->as, r0, imm);
+ asm_xtensa_mov_reg_i32(&emit->as, r0, imm);
} else {
goto unknown_op;
}
@@ -311,10 +310,10 @@ STATIC void emit_inline_xtensa_op(emit_inline_asm_t *emit, qstr op, mp_uint_t n_
uint r1 = get_arg_reg(emit, op_str, pn_args[1]);
if (o->type == RRR) {
uint r2 = get_arg_reg(emit, op_str, pn_args[2]);
- asm_xtensa_op24(emit->as, ASM_XTENSA_ENCODE_RRR(0, o->a0, o->a1, r0, r1, r2));
+ asm_xtensa_op24(&emit->as, ASM_XTENSA_ENCODE_RRR(0, o->a0, o->a1, r0, r1, r2));
} else if (o->type == RRI8_B) {
int label = get_arg_label(emit, op_str, pn_args[2]);
- asm_xtensa_bcc_reg_reg_label(emit->as, o->a0, r0, r1, label);
+ asm_xtensa_bcc_reg_reg_label(&emit->as, o->a0, r0, r1, label);
} else {
int shift, min, max;
if ((o->type & 0xf0) == 0) {
@@ -327,7 +326,7 @@ STATIC void emit_inline_xtensa_op(emit_inline_asm_t *emit, qstr op, mp_uint_t n_
max = 0xff << shift;
}
uint32_t imm = get_arg_i(emit, op_str, pn_args[2], min, max);
- asm_xtensa_op24(emit->as, ASM_XTENSA_ENCODE_RRI8(o->a0, o->a1, r1, r0, (imm >> shift) & 0xff));
+ asm_xtensa_op24(&emit->as, ASM_XTENSA_ENCODE_RRI8(o->a0, o->a1, r1, r0, (imm >> shift) & 0xff));
}
return;
}