summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDamien George <damien@micropython.org>2024-02-09 13:25:58 +1100
committerDamien George <damien@micropython.org>2024-02-16 12:48:02 +1100
commit416465d81e911b088836f4e7c37fac2bc0f67917 (patch)
tree2a535c6f751d75287abea15e91f3d11d646633cd
parent39bf055d23be4b0f761af115773c3db1074fc2dd (diff)
py/emitglue: Provide a truncated mp_raw_code_t for non-asm code.
The `asm_n_pos_args` and `asm_type_sig` members of `mp_raw_code_t` are only used for raw codes of type MP_CODE_NATIVE_ASM, which are rare, for example in frozen code. So using a truncated `mp_raw_code_t` in these cases helps to reduce frozen code size on targets that have MICROPY_EMIT_INLINE_ASM enabled. With this, change in firmware size of RPI_PICO builds is -648. Signed-off-by: Damien George <damien@micropython.org>
-rw-r--r--py/dynruntime.h4
-rw-r--r--py/emitglue.h23
-rwxr-xr-xtools/mpy-tool.py17
3 files changed, 35 insertions, 9 deletions
diff --git a/py/dynruntime.h b/py/dynruntime.h
index de9c93c65..435b85622 100644
--- a/py/dynruntime.h
+++ b/py/dynruntime.h
@@ -207,7 +207,7 @@ static inline void *mp_obj_malloc_helper_dyn(size_t num_bytes, const mp_obj_type
#define MP_DYNRUNTIME_INIT_ENTRY \
mp_obj_t old_globals = mp_fun_table.swap_globals(self->context->module.globals); \
- mp_raw_code_t rc; \
+ mp_raw_code_truncated_t rc; \
rc.kind = MP_CODE_NATIVE_VIPER; \
rc.scope_flags = 0; \
(void)rc;
@@ -217,7 +217,7 @@ static inline void *mp_obj_malloc_helper_dyn(size_t num_bytes, const mp_obj_type
return mp_const_none;
#define MP_DYNRUNTIME_MAKE_FUNCTION(f) \
- (mp_make_function_from_raw_code((rc.fun_data = (f), &rc), self->context, NULL))
+ (mp_make_function_from_raw_code((rc.fun_data = (f), (const mp_raw_code_t *)&rc), self->context, NULL))
#define mp_import_name(name, fromlist, level) \
(mp_fun_table.import_name((name), (fromlist), (level)))
diff --git a/py/emitglue.h b/py/emitglue.h
index c9c6c8ba1..b79283541 100644
--- a/py/emitglue.h
+++ b/py/emitglue.h
@@ -84,6 +84,29 @@ typedef struct _mp_raw_code_t {
#endif
} mp_raw_code_t;
+// Version of mp_raw_code_t but without the asm_n_pos_args/asm_type_sig entries, which are
+// only needed when the kind is MP_CODE_NATIVE_ASM. So this struct can be used when the
+// kind is MP_CODE_BYTECODE, MP_CODE_NATIVE_PY or MP_CODE_NATIVE_VIPER, to reduce its size.
+typedef struct _mp_raw_code_truncated_t {
+ uint32_t kind : 3;
+ uint32_t scope_flags : 7;
+ const void *fun_data;
+ struct _mp_raw_code_t **children;
+ #if MICROPY_PERSISTENT_CODE_SAVE || MICROPY_DEBUG_PRINTERS
+ uint32_t fun_data_len;
+ #endif
+ #if MICROPY_PERSISTENT_CODE_SAVE
+ uint16_t n_children;
+ #if MICROPY_EMIT_MACHINE_CODE
+ uint16_t prelude_offset;
+ #endif
+ #if MICROPY_PY_SYS_SETTRACE
+ uint32_t line_of_definition;
+ mp_bytecode_prelude_t prelude;
+ #endif
+ #endif
+} mp_raw_code_truncated_t;
+
mp_raw_code_t *mp_emit_glue_new_raw_code(void);
void mp_emit_glue_assign_bytecode(mp_raw_code_t *rc, const byte *code,
diff --git a/tools/mpy-tool.py b/tools/mpy-tool.py
index 57411c3fb..9b824099e 100755
--- a/tools/mpy-tool.py
+++ b/tools/mpy-tool.py
@@ -683,7 +683,7 @@ class CompiledModule:
else:
print(" .obj_table = NULL,")
print(" },")
- print(" .rc = &raw_code_%s," % self.raw_code.escaped_name)
+ print(" .rc = (const mp_raw_code_t *)&raw_code_%s," % self.raw_code.escaped_name)
print("};")
def freeze_constant_obj(self, obj_name, obj):
@@ -898,7 +898,7 @@ class RawCode(object):
print()
print("static const mp_raw_code_t *const children_%s[] = {" % self.escaped_name)
for rc in self.children:
- print(" &raw_code_%s," % rc.escaped_name)
+ print(" (const mp_raw_code_t *)&raw_code_%s," % rc.escaped_name)
if prelude_ptr:
print(" (void *)%s," % prelude_ptr)
print("};")
@@ -906,7 +906,11 @@ class RawCode(object):
def freeze_raw_code(self, prelude_ptr=None, type_sig=0):
# Generate mp_raw_code_t.
- print("static const mp_raw_code_t raw_code_%s = {" % self.escaped_name)
+ if self.code_kind == MP_CODE_NATIVE_ASM:
+ raw_code_type = "mp_raw_code_t"
+ else:
+ raw_code_type = "mp_raw_code_truncated_t"
+ print("static const %s raw_code_%s = {" % (raw_code_type, self.escaped_name))
print(" .kind = %s," % RawCode.code_kind_str[self.code_kind])
print(" .scope_flags = 0x%02x," % self.scope_flags)
print(" .fun_data = fun_data_%s," % self.escaped_name)
@@ -949,10 +953,9 @@ class RawCode(object):
print(" },")
print(" #endif")
print(" #endif")
- print(" #if MICROPY_EMIT_INLINE_ASM")
- print(" .asm_n_pos_args = %u," % self.n_pos_args)
- print(" .asm_type_sig = %u," % type_sig)
- print(" #endif")
+ if self.code_kind == MP_CODE_NATIVE_ASM:
+ print(" .asm_n_pos_args = %u," % self.n_pos_args)
+ print(" .asm_type_sig = %u," % type_sig)
print("};")
global raw_code_count, raw_code_content