Preventing interference WASM stack (Clang/LLVM)
Closed this issue · 2 comments
I'm compiling to WASM with Clang/LLVM, not Emscripten, and was hoping to use tinyalloc. Going off of the information in this article, specifically the image indicating the data, stack, and heap layouts, it is stated that the .data
section comes first, followed by the stack, and then the heap. Notice that the stack grows downwards toward __data_end
.
(I couldn't find documentation describing Emscripten's memory layout, so I'm not sure if this is the same or different than Emscripten).
That leaves me with a few questions:
__data_end
is typically0x400
, which is used forTA_BASE
. If I placeTA_BASE
at0x400
, aren't I at risk of having the tinyalloc blocks clobbered by a stack that grows all the way to__data_end
?- For my specific application, I have a lot of static strings compiled into my program, and therefore my
.data
section is much larger than0x400
, but I don't necessarily know the exact size at compile time (obviously using0x400
forTA_BASE
was overwriting some of my static data). Is it feasible to define aTA_BASE
at runtime as part ofta_init()
, or are there some reasons that it must be defined at compile time that I just don't understand? - If it's feasible to set
TA_BASE
andTA_HEAP_START
at runtime, I was thinking that it might be a good idea to setTA_BASE
to__heap_base
andTA_HEAP_START
to__heap_base + sizeof(Heap)
so that it can grow without interference to the stack and data sections.
If these seem like valuable additions to the project, I'd be happy to take a stab at implementing them in such a way that these things can be configured when calling ta_init()
and submitting a PR.
Hi @winduptoy - the only reason for TA_BASE
currently being a #define
is because of the way I used this project on embedded devices, where I'd simply supply the start address via command line flags (gcc -DTA_BASE=0x1000 ...
)
I'd welcome a PR where you can configure heap start/end, splitting threshold and maybe even the number of max blocks used via args passed to ta_init()
.
Btw. TA_HEAP_START already is currently set to TA_BASE + sizeof(Heap)
, so your logic with __heap_base + sizeof(Heap)
is sound.
Though, if we want to make the number of max blocks runtime configurable, we will need to replace the blocks
array (in the Heap
struct) with a pointer (or get rid of it totally and update the few use sites in the code) and then update the math to: __heap_base + sizeof(Heap) + maxBlocks * sizeof(Block)
and set blocks
to __heap_base + sizeof(Heap)
I think we can close this now, right?!