Skip to content

Commit 8216aa4

Browse files
committed
struct stacks
1 parent 133045a commit 8216aa4

File tree

1 file changed

+33
-30
lines changed

1 file changed

+33
-30
lines changed

main.c

Lines changed: 33 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -126,35 +126,47 @@ uint8_t value_out = 0;
126126
#include "shared-module/os/__init__.h"
127127
#endif
128128

129+
typedef struct {
130+
#if MICROPY_ENABLE_PYSTACK
131+
supervisor_allocation *pystack;
132+
#endif
133+
supervisor_allocation *heap;
134+
} stacks;
135+
129136
static void reset_devices(void) {
130137
#if CIRCUITPY_BLEIO_HCI
131138
bleio_reset();
132139
#endif
133140
}
134141

135142
#if MICROPY_ENABLE_PYSTACK
136-
STATIC supervisor_allocation __attribute__ ((noinline)) * alloc_pystack(void) {
143+
STATIC stacks __attribute__ ((noinline)) alloc_stacks(void) {
144+
stacks res;
145+
#if MICROPY_ENABLE_PYSTACK
137146
mp_int_t pystack_size = CIRCUITPY_PYSTACK_SIZE;
138147
#if CIRCUITPY_OS_GETENV
139148
// Fetch value if exists from settings.toml
140149
// Leaves size to build default on any failure
141150
(void)common_hal_os_getenv_int("CIRCUITPY_PYSTACK_SIZE", &pystack_size);
142151
// Check if value is valid
143-
if ((CIRCUITPY_PYSTACK_SIZE != pystack_size) && ((pystack_size < 384) || (pystack_size % sizeof(size_t) != 0))) {
152+
pystack_size = pystack_size - pystack_size % sizeof(size_t); // Round down to multiple of 4.
153+
if ((CIRCUITPY_PYSTACK_SIZE != pystack_size) && (pystack_size < 384)) {
144154
serial_write_compressed(translate("\nWARNING: Invalid CIRCUITPY_PYSTACK_SIZE, defaulting back to build value.\n\n"));
145155
pystack_size = CIRCUITPY_PYSTACK_SIZE; // Reset
146156
}
147157
#endif
148-
supervisor_allocation *pystack = allocate_memory(pystack_size, false, false);
149-
if (pystack == NULL) {
158+
res.pystack = allocate_memory(pystack_size, false, false);
159+
if (res.pystack == NULL) {
150160
serial_write_compressed(translate("\nWARNING: Allocating pystack failed, defaulting back to build value. \n\n"));
151-
pystack = allocate_memory(CIRCUITPY_PYSTACK_SIZE, false, false);
161+
res.pystack = allocate_memory(CIRCUITPY_PYSTACK_SIZE, false, false);
152162
}
153-
return pystack;
163+
#endif
164+
res.heap = allocate_remaining_memory();
165+
return res;
154166
}
155167
#endif
156168

157-
STATIC void start_mp(supervisor_allocation *heap, supervisor_allocation *pystack) {
169+
STATIC void start_mp(stacks combo) {
158170
supervisor_workflow_reset();
159171

160172
// Stack limit should be less than real stack size, so we have a chance
@@ -182,11 +194,11 @@ STATIC void start_mp(supervisor_allocation *heap, supervisor_allocation *pystack
182194
readline_init0();
183195

184196
#if MICROPY_ENABLE_PYSTACK
185-
mp_pystack_init(pystack->ptr, pystack->ptr + (get_allocation_length(pystack) / sizeof(size_t)));
197+
mp_pystack_init(combo.pystack->ptr, combo.pystack->ptr + get_allocation_length(combo.pystack) / sizeof(size_t));
186198
#endif
187199

188200
#if MICROPY_ENABLE_GC
189-
gc_init(heap->ptr, heap->ptr + get_allocation_length(heap) / 4);
201+
gc_init(combo.heap->ptr, combo.heap->ptr + get_allocation_length(combo.heap) / 4);
190202
#endif
191203
mp_init();
192204
mp_obj_list_init((mp_obj_list_t *)mp_sys_path, 0);
@@ -286,7 +298,7 @@ STATIC void count_strn(void *data, const char *str, size_t len) {
286298
*(size_t *)data += len;
287299
}
288300

289-
STATIC void cleanup_after_vm(supervisor_allocation *heap, supervisor_allocation *pystack, mp_obj_t exception) {
301+
STATIC void cleanup_after_vm(stacks combo, mp_obj_t exception) {
290302
// Get the traceback of any exception from this run off the heap.
291303
// MP_OBJ_SENTINEL means "this run does not contribute to traceback storage, don't touch it"
292304
// MP_OBJ_NULL (=0) means "this run completed successfully, clear any stored traceback"
@@ -366,8 +378,8 @@ STATIC void cleanup_after_vm(supervisor_allocation *heap, supervisor_allocation
366378
// Free the heap last because other modules may reference heap memory and need to shut down.
367379
filesystem_flush();
368380
stop_mp();
369-
free_memory(heap);
370-
free_memory(pystack);
381+
free_memory(combo.heap);
382+
free_memory(combo.pystack);
371383
supervisor_move_memory();
372384

373385
// Let the workflows know we've reset in case they want to restart.
@@ -422,11 +434,8 @@ STATIC bool run_code_py(safe_mode_t safe_mode, bool *simulate_reset) {
422434
};
423435
#endif
424436

425-
#if MICROPY_ENABLE_PYSTACK
426-
supervisor_allocation *pystack = alloc_pystack();
427-
#endif
428-
supervisor_allocation *heap = allocate_remaining_memory();
429-
start_mp(heap, pystack);
437+
stacks combo = alloc_stacks();
438+
start_mp(combo);
430439

431440
#if CIRCUITPY_USB
432441
usb_setup_with_vm();
@@ -474,7 +483,7 @@ STATIC bool run_code_py(safe_mode_t safe_mode, bool *simulate_reset) {
474483

475484

476485
// Finished executing python code. Cleanup includes filesystem flush and a board reset.
477-
cleanup_after_vm(heap, pystack, _exec_result.exception);
486+
cleanup_after_vm(combo, _exec_result.exception);
478487
_exec_result.exception = NULL;
479488

480489
// If a new next code file was set, that is a reason to keep it (obviously). Stuff this into
@@ -770,11 +779,8 @@ STATIC void __attribute__ ((noinline)) run_boot_py(safe_mode_t safe_mode) {
770779

771780
// Do USB setup even if boot.py is not run.
772781

773-
#if MICROPY_ENABLE_PYSTACK
774-
supervisor_allocation *pystack = alloc_pystack();
775-
#endif
776-
supervisor_allocation *heap = allocate_remaining_memory();
777-
start_mp(heap, pystack);
782+
stacks combo = alloc_stacks();
783+
start_mp(combo);
778784

779785
#if CIRCUITPY_USB
780786
// Set up default USB values after boot.py VM starts but before running boot.py.
@@ -860,7 +866,7 @@ STATIC void __attribute__ ((noinline)) run_boot_py(safe_mode_t safe_mode) {
860866

861867
port_post_boot_py(true);
862868

863-
cleanup_after_vm(heap, pystack, _exec_result.exception);
869+
cleanup_after_vm(combo, _exec_result.exception);
864870
_exec_result.exception = NULL;
865871

866872
port_post_boot_py(false);
@@ -875,11 +881,8 @@ STATIC int run_repl(void) {
875881
int exit_code = PYEXEC_FORCED_EXIT;
876882
stack_resize();
877883
filesystem_flush();
878-
#if MICROPY_ENABLE_PYSTACK
879-
supervisor_allocation *pystack = alloc_pystack();
880-
#endif
881-
supervisor_allocation *heap = allocate_remaining_memory();
882-
start_mp(heap, pystack);
884+
stacks combo = alloc_stacks();
885+
start_mp(combo);
883886

884887
#if CIRCUITPY_USB
885888
usb_setup_with_vm();
@@ -922,7 +925,7 @@ STATIC int run_repl(void) {
922925
exit_code = PYEXEC_DEEP_SLEEP;
923926
}
924927
#endif
925-
cleanup_after_vm(heap, pystack, MP_OBJ_SENTINEL);
928+
cleanup_after_vm(combo, MP_OBJ_SENTINEL);
926929

927930
// Also reset bleio. The above call omits it in case workflows should continue. In this case,
928931
// we're switching straight to another VM so we want to reset.

0 commit comments

Comments
 (0)