STM32 project code size problem ( small active load) - Page 1
Forum section: electronics / general

author: Sniper1
author_rank: Regular Contributor
timestamp: October 23, 2022, 08:25:18 am
content: So i had a STM32 , since i ordered the wrong one and i want to use it if possible, and i was also in need of a small active load (5W+ ) on the heat sink and circuit part i am more or less done designing ( since i mostly copy from Dave s vid and the PWM to analog is the part that concerned me more).Tangents aside i just set up the pins and such in stm32cubide and the code size exceeded the 16k of my MCU (without any libraries added). I know my code will be relatively small (100-200lines) and i am very surprised that it is so large (also why would one sell such MCUs if u cant run stuff on them?). So after a bit of research i found out how bloated stm32cubide is.STM32L010K4T6 (https://www.mouser.co.uk/ProductDetail/511-STM32L010K4T6)I want to do this:Read 3-4 buttons (or a rotary encoder) and based on that increase/decrease PWM duty cycle (that gets filtered to analog) and fed into Dave s op amp+FET constant current circuit. And have the most relevant data live on a I2C LCD. And potentially add code for constant power, constant voltage and constant resistance and maybe potentially a SD card for data logger.The thing is i know that in Arduino the code would be relatively small even with a LCD lib so i am very confused onto how to proceed. What would a good tool that would reduce the code bloat ? I it a 1 off so multi MCU compatibility is not a concern.NOTE:1 i did heat dissipation math and i should be fine up to 6.5W without a fan and with a fan i think i am close to 11W2 also power supply will be 12V and i am thinking of potentially adding a negative rail with a 555 timer so i have enough swing for the op amp and FET3 for flashing i have a USB to UART bridge that supports 3v3 logic , a few Arduino and a home made rpi pico (it seems to be working)PS: regarding the PWM filtering and heat math i am not sure if i should post later here or in another post, the thing is i know i can push it to 5W safely but i am not sure how much further i can actually push it + i know that if i use a slower PWM i get a better resolution but i am not sure about how to filter such wide bands ( atm i only simulated in LTTSpice with 1 frequency and a RC low pass filters and buffers)

author: DavidAlfa
author_rank: Super Contributor
timestamp: October 23, 2022, 08:28:52 am
content: How about compiler optimizations?Have you set "optimize for size" (Os) ?Also, try enabling LTO to sabe additional space by adding "-flto" to the compiler and linker arguments.

author: Sniper1
author_rank: Regular Contributor
timestamp: October 23, 2022, 08:30:57 am
content: probably nothow do i do this? i am new to STM32.......

author: capt bullshot
author_rank: Super Contributor
timestamp: October 23, 2022, 08:52:36 am
content: If you're new to STM32, and want to use their tools, I'd recommend you to get a derivative with plenty of Flash and RAM.E.g. one of the smallish Nucleo-32 boards with a STM32L432 (don't go for a low memory derivative with these boards, they all cost the same).Once you're familiar with their workflow and tools, you can start to reduce the memory footprint - e.g. by moving from HAL to LL (a setting for code generation within STM32CubeMX), but this will demand some labour from you as HAL and LL have different approaches, and HAL has more working examples than LL.For the lowest memory footprint, drop that tool at all and write all the low level stuff yourself.

author: Sniper1
author_rank: Regular Contributor
timestamp: October 23, 2022, 08:58:29 am
content: So after looking into the program i ended up here:command: gccAll options :-mcpu=cortex-m0plus -std=gnu11 -g3 -DDEBUG -DUSE_HAL_DRIVER -DSTM32L010x4 -c -I../Core/Inc -I../Drivers/STM32L0xx_HAL_Driver/Inc -I../Drivers/STM32L0xx_HAL_Driver/Inc/Legacy -I../Drivers/CMSIS/Device/ST/STM32L0xx/Include -I../Drivers/CMSIS/Include -O0 -ffunction-sections -fdata-sections -Wall -fstack-usage --specs=nano.specs -mfloat-abi=soft -mthumbSo from what i understand i need to edit command and have it like:gcc -Os -flto??

author: DavidAlfa
author_rank: Super Contributor
timestamp: October 23, 2022, 09:00:31 am
content: First, ensure you're compiling for Release and not for Debug (Click on the "Hammer" building icon, select Release)(Edit: You're clearly not with -O0)Then right click on the project -> Properties -> C/C++ Build -> SettingsEnsure the upper tab "Configuration" is set to Release.Optimization -> choose Optimize for size.Try compiling now.Fitting or not, you might want to try this additional setting:Miscellaneous tab -> Other flags -> Click the adding button (Small icon with green "+") and write "-flto".Repeat this last step with the miscellaneous tab on the Linker.Recompile and check the difference in size!Zip and attach your project if you want it to get checked.

author: Sniper1
author_rank: Regular Contributor
timestamp: October 23, 2022, 09:16:21 am
content: donenow it is this:arm-none-eabi-gcc -o "Active_Load.elf" @"objects.list" -mcpu=cortex-m0plus -T"D:\github-stuff\Progrmable_Active_Loads\Small_load_V1\SW1\STM32L010K4TX_FLASH.ld" --specs=nosys.specs -Wl,-Map="Active_Load.map" -Wl,--gc-sections -static -flto --specs=nano.specs -mfloat-abi=soft -mthumb -Wl,--start-group -lc -lm -Wl,--end-groupe:\st\stm32cubeide_1.8.0\stm32cubeide\plugins\com.st.stm32cube.ide.mcu.externaltools.gnu-tools-for-stm32.10.3-2021.10.win32_1.0.0.202111181127\tools\arm-none-eabi\bin\ld.exe: Active_Load.elf section `._user_heap_stack' will not fit in region `RAM'e:\st\stm32cubeide_1.8.0\stm32cubeide\plugins\com.st.stm32cube.ide.mcu.externaltools.gnu-tools-for-stm32.10.3-2021.10.win32_1.0.0.202111181127\tools\arm-none-eabi\bin\ld.exe: region `RAM' overflowed by 192 bytescollect2.exe: error: ld returned 1 exit statusmake: *** [makefile:64: Active_Load.elf] Error 1"make -j8 all" terminated with exit code 2. Build might be incomplete.so now it is RAM.... Arduino has same amount 2k so again something feels very off here since there is no actual code just pericardial setup

author: wek
author_rank: Frequent Contributor
timestamp: October 23, 2022, 09:22:08 am
content: Post mapfile (Active_Load.map).JW

author: DavidAlfa
author_rank: Super Contributor
timestamp: October 23, 2022, 09:22:59 am
content: You might be alllocating a too large buffer somewhere.Additonally, open CubeMX (Double-click the blue .ioc file), try reducing the heap and stack sizes under "Project Manager".

author: Sniper1
author_rank: Regular Contributor
timestamp: October 23, 2022, 09:33:41 am
content: therehttps://pastebin.com/ivb48bgCAlso ill try to look at those heap files it is 0x200 how much should i put 0x100? Also min stack size is 0x400 (what is that ?)

author: DavidAlfa
author_rank: Super Contributor
timestamp: October 23, 2022, 09:38:50 am
content: Quote from: DavidAlfa on October 23, 2022, 09:22:59 amToday my messages are getting flooded with [ size] tags automatically, what's wrong with the forum?Try to find what's using the ram, temporary edit the linker script (STM23xxxx_FLASH.ld) and modify the RAM size.Code:RAM (xrw) : ORIGIN = 0x20000000, LENGTH = 2KPut 16K for example. Will compile now, and you'll be able to see everything in the Build Analyzer section.Go to Memory Details, RAM and find out what's using so much.(Of course, programming that will simply not work)Once you fix it and get under the 2K limit, put the original size back.To have an idea of the stack size, open The Static Stack Analyzer window.Under Call graph, you'll find the worst case scenario (Where a function allocates stack, calls another function, allocates more stack and so on).Ensure the reserved stack setting in CubeMX meets this, so if you have 400bytes there, you'll be fine with 0x1C0 bytes in CubeMX (448bytes).Of course, that will change as your code grows, so give it some margin, ex. 0x200 (512bytes).As you get close to the final code, you might tighten it down.The heap size is a different thing, that's for the dynamic allocation (malloc and such), often used by some CubeMX functions like the USB library to allocate the buffers.You can find out the allocated memory with this codeCode:#include <malloc.h>uint32_t getHeapUsage(void){return mallinfo().uordblks;}Calling getHeapUsage() would return the Heap usage in bytes.You can call this after HAL initialization.Can't help further without seeing some code, you might be declaring large arrays, or using the wrong word size for them, can't really tell!

author: Sniper1
author_rank: Regular Contributor
timestamp: October 23, 2022, 09:45:43 am
content: not sure but it didn't let me attach files, that is why i used paste binalso a hep of 0x100 is enough ? or rather what does it do and how much can i safely reduce it?

author: pcprogrammer
author_rank: Super Contributor
timestamp: October 23, 2022, 09:53:11 am
content: To attach files here they should be less then 4MB and have one of the listed extensions.To add a binary file just add a ".txt" extension after the ".bin" and you can upload it here, provided it is less then the 4MB size limit.

author: pcprogrammer
author_rank: Super Contributor
timestamp: October 23, 2022, 09:55:21 am
content: Quote from: Sniper1 on October 23, 2022, 09:33:41 amThis reserves 1KB of memory for the call stack used by C. This is where parameters are passed to functions and return addresses are kept.

author: Sniper1
author_rank: Regular Contributor
timestamp: October 23, 2022, 09:55:32 am
content: it was about 150k and i made it stuff.map.txt so it was ok in theory but it didnt want to upload

author: pcprogrammer
author_rank: Super Contributor
timestamp: October 23, 2022, 09:58:58 am
content: That is weird, try to attach a picture to see if it will do it.

author: Sniper1
author_rank: Regular Contributor
timestamp: October 23, 2022, 10:02:17 am
content: update:with a stack of 0x100 it did compile and uses like 96+% of RAM, aparently the largest consumer is user heap stacki have most of the project on github but the stm32 part is not since i am not sure if uploading all is okfolders insidde the folder:.setingscoredebugdriversreleasewhat should i upload? also core release and drivers have sub folders , should i upload them too?

author: DavidAlfa
author_rank: Super Contributor
timestamp: October 23, 2022, 10:07:24 am
content: CubeMX allocates that Stack by default, for a small project it's usually overkill.You can attach zip files fine. Just compress it.There's a very convenient option, Right click ->Export -> Archive file, will create a zip file with the whole project.But first run Right click -> Clean to wipe all the unnecessary built stuff.I forgot something: Stack usage analysis won't work if you enable LTO.

author: cv007
author_rank: Frequent Contributor
timestamp: October 23, 2022, 10:19:18 am
content: Your map file shows a stack size of 0x400, heap size of 0x200, bss used 0x2B4, data use 0x0c-0x400+0x200+0x2B4+0x0C = 0x8C0, 0x8C0 - 0x800 = 0xC0 = the 192 bytes the linker is complaining about.You just need to adjust the stack/heap sizes to something more appropriate. You could also set both to 0 and forego the linker checking for stack/heap space (via overflowing ram allocation). Making up numbers without evidence is kind of useless anyway (unless they are large and you have the ram to not care).edit- obviously you need stack space, but you can also monitor data usage (I'll assume the ide has some way to inform, otherwise the toolchain 'size' program can inform). You can also figure out a good number for stack space size that both allows for your stack size usage + some fudge, then set it as a stack size number for the linker to check at compile time to make sure your data does not get into this area. There are various ways to get an idea of the stack space used for your app (and there are ways to make your app panic if that fudge area is breached).

author: DavidAlfa
author_rank: Super Contributor
timestamp: October 23, 2022, 10:27:15 am
content: Setting stack/heap to 0 won't work.From my previous experiences, you don't get any type of warning.If the stack grows too much, it will overwite other memory regions and start a lot of gremlins and funny stuff going in your code.Suddenly you do Fruits=Apples+Oranges, Eggs turns to -1763, Tomatoes to 0xFFF12 and things like thatUse the heap reported in static stack analuzer call graph!

author: hans
author_rank: Super Contributor
timestamp: October 23, 2022, 10:29:28 am
content: I've used that STM32 before, and the FLASH size is so small that even ST's HAL library is too big too fit.Yes a minimal program will fit, but if you enable all parts of the HAL it won't.I think there is a configuration header file for this purpose to enable/disable drivers. It removes the code from compilation and saves code space. For some reason linker settings won't fix this, probably because driver code is called from interrupt vectors and so the compiler still thinks they need to be linked in.Oh also I recommended to not bother with malloc/heap on that size MCU. Just set heap to 0 and never use malloc. Reduce stack size, which unfortunately is a bit of a 'mystery', but 1kiB seems quite large. You could reduce it till the program doesn't like it anymore. (Note; there are static analysis tools for this, IIRC GCC also has some, but it's not easy to use/access)

author: Sniper1
author_rank: Regular Contributor
timestamp: October 23, 2022, 10:31:23 am
content: https://github.com/immortal-sniper1/Progrmable_Active_Loadsthere

author: DavidAlfa
author_rank: Super Contributor
timestamp: October 23, 2022, 10:34:30 am
content: It's the project atSmall_load_V1/SW1, right?Your current Release config uses 59% flash, 72% ram.Checking the call usage, the highest amount is 252 bytes, so setting the Stack to 0x100 byte (Was 0x200=512bytes) reduces ram to 59%.Then enabling LTO reduces flash to 43% and slightly increases ram to 64%.Seems good to me, you have plenty of resources left.

author: westfw
author_rank: Super Contributor
timestamp: October 23, 2022, 10:38:02 am
content: QuoteProbably it's too small to use most of the standard C functions, too. (even with "newlib nano")While a 16k/2k ARM chip is theoretically as useful as a 16k/2k 8bit microcontroller, pretty much NONE of the libraries are optimized well enough to be useful, unless you're really careful. :-(

author: Sniper1
author_rank: Regular Contributor
timestamp: October 23, 2022, 10:40:17 am
content: yes

author: cv007
author_rank: Frequent Contributor
timestamp: October 23, 2022, 10:40:31 am
content: QuoteIt will work, you just will not get any help from the linker warning you about data sizes. Once you have a good idea of the stack size used for your app you can plug in a number and start getting warnings at compile time about your data size getting too large. Those values which were created in the linker are only used in the linker, and are only used to pad a section to cause a ram overflow as a warning.

author: Sniper1
author_rank: Regular Contributor
timestamp: October 23, 2022, 10:41:46 am
content: well when i bouth this one i went with more or less the specs of an arduino uno since i knew that on it i had way more then enough RAM and FLASH for what i was doing

author: pcprogrammer
author_rank: Super Contributor
timestamp: October 23, 2022, 10:51:41 am
content: For these kind of microcontrollers bare metal programming is a way of reducing code size to a minimum. Sure it takes getting to know the peripherals, but it is not that difficult.Find your self a nice IDE like visual studio or eclipse or even a simple text editor can do. Setup a make script and build your project.For what you intend to use it you won't need any library functions. Making PWM can be done with the timers. The CPU only has to setup the registers for it. Reading a couple of buttons or a rotary encoder is simple. Also controlling a 2 line 16 character display is not that difficult.Some of the things you need can be found in this repository:https://github.com/pecostm32/STM32F303_Sine_Square_Generator

author: cv007
author_rank: Frequent Contributor
timestamp: October 23, 2022, 10:51:52 am
content: QuoteIts not always easy to compare 8bit usage of flash/ram to a 32bit mcu. You can most likely make what you have work- you are currently using ~10k flash and less than 1K of ram, unless you plan on creating a lot more code.

author: DavidAlfa
author_rank: Super Contributor
timestamp: October 23, 2022, 10:54:22 am
content: Quote from: hans on October 23, 2022, 10:29:28 amNot so simple, std lib (printf, etc)and some parts of HAL need to allocate some memory.Just learn how to deal with it, adjusting the heap to the required amount.LTO actually does optimize HAL quite a lot.You'll see how almosy all HAL init code disappears from the call graph, and suddenly your main becomes 3KB in size, but packing everything in a much more efficient way.Quote from: cv007 on October 23, 2022, 10:40:31 amWhat I was trying to say is the objetive of doing that (Getting compiler warning) won't work.The code will compile just fine! But your system might crash or behave in a unpredictable ways if heap/stack grow too much, will overlap other parts of the memory.Try yourself:For a MCU with 16Kb of RAM, create a global array of 15KB, then make a function with a local array also with size of 15KB (this would be allocated into the stack).Initialize the array in main, call the function writing random stuff, then check how the global array contents magically changed.Edit: Updated to CubeIDE 1.10.1. Surprise, as f**ing always it crashed, needing to delete the whole ST folder and reinstalling. St updates are a joke.

author: cv007
author_rank: Frequent Contributor
timestamp: October 23, 2022, 11:05:03 am
content: QuoteThe heap still exists. Those minimum size values just pad out the end of the ram region to cause a region overflow so you get a warning when your data size starts to increase. Its nice to have if the numbers you provide make sense. Until you get those numbers you can skip the check, and monitor data usage like one normally would do. Once you have numbers you know are good, plug them in and you can pay less attention to the data size as the linker is watching it for you.

author: hans
author_rank: Super Contributor
timestamp: October 23, 2022, 11:14:21 am
content: Quote from: DavidAlfa on October 23, 2022, 10:54:22 amYou sure? I've used HALs from many parts (from 8-bit AVRs to Cortex-m7), and in all cases I've never seen malloc being added. I could always set heap to 0 bytes.If you're getting heap usage in your program, consider switching to the nano or newlib stdlib implementation. You don't want to run the full stdlib on an embedded device.

author: DavidAlfa
author_rank: Super Contributor
timestamp: October 23, 2022, 11:28:01 am
content: Let me show an example:Code:void test (void){#define TEST_SZ16384uint32_t data;for (uint32_t i=0;i<TEST_SZ;i++){data = GPIOA->IDR;if(data==12)GPIOB->IDR=data;}for (uint32_t i=0;i<TEST_SZ;i++){GPIOA->ODR = data;}}This does nothing really, but as GPIO registers are volatile, it prevents the compiler from optimizing and removing the large buffer.As you see, my buffer is 16384*4=64KB in size! A lot more than this MCU has.Where's the compiler warning? Nowhere.Code:13:34:38 Build Finished. 0 errors, 0 warnings. (took 2s.9ms)Then if you check the Static Call Analyzer, you'll find out there's a function using that much memory.Code:Function Local costtest 65552Running this would completely destroy the memory and ultimately cause a Hardfault exception when trying to access illegal/no-existing memory adressses.But if you allocate a little less, ex. 1.5KB, it would just overwrite other random variables, causing your program to perform like it had some hard drugs.So it's up to you to watch this and adjust the minimum stack size.The reserved stack size is nothing more than a way to prevent heap and normal memory from overlapping, it basically statically allocates a global variable "heap".So when your allocate too much in other place, you'll get a out of memory error. Otherwise, the heap would grow inadvertently and overwrite random memory areas like in this example.When setting the reserved stack to the largest value reported in stack analyzer call graph (65632 bytes), Boom! Now you get the expected result!Code:region `RAM' overflowed by 64544 bytesSo that's it. Setting the stack to 0 is just silly. Set it to the actual reported usage.Why isn't this being done automatically? I have no idea. But feel lucky, other compilers doesn't report stack or heap usage.How to deal with that in those cases? I have no idea. Global variables everywhere, I guess.

author: Sniper1
author_rank: Regular Contributor
timestamp: October 23, 2022, 11:34:48 am
content: Quote from: pcprogrammer on October 23, 2022, 10:51:41 amYes that would be nice i am atm trying to do that with an RP2040 and failing a lot so i am not that confident if i can pull it off

author: pcprogrammer
author_rank: Super Contributor
timestamp: October 23, 2022, 11:50:03 am
content: Quote from: Sniper1 on October 23, 2022, 11:34:48 amIt takes some practice. I have not played with the RP2040 yet, but the CPU is also an ARM cortex. The peripheral system is different as far as I read about it here. something with a PIO (programmable IO) controller that can do a lot apart from the CPU.The STM is simpler. Starting point is to get the data sheet and reference manual for the one you are using from st.comhttps://www.st.com/en/microcontrollers-microprocessors/stm32l010k4.html#documentationMost of the peripherals are similar between the different ranges like the L0, F1, F3, etc. So look at the startup bit in my code and see if it matches your registers. Clock frequencies most likely need to be adjusted, and you will need the header file for your device, but you can find that in the project you are using now.

author: eutectique
author_rank: Frequent Contributor
timestamp: October 23, 2022, 01:47:08 pm
content: Quote from: DavidAlfa on October 23, 2022, 10:27:15 amPlacing stack at the bottom of RAM would help. Stack growth beyond the limit will cause hard fault rather then trashed variables. This doesn't work for FreeRTOS though (and some other RTOSes, perhaps).

author: Sniper1
author_rank: Regular Contributor
timestamp: October 23, 2022, 02:45:17 pm
content: Quote from: pcprogrammer on October 23, 2022, 11:50:03 amTHXi already built a RP2040 board and it seems to work more or less (SD card problems + RTC problems) but i traced them back to code so not the hard part that is why i am trying to use VS code not Arduinoas for STM32 i am looking atm is there is any MCU with the same footprint and M core available in stock , just in casethen again now i have 5k Flash and 500+ B RAM free , so i think il manage , so just maybe i will get a larger MCU since once i order some PCBs it is hard to redo them and easyer to replace 1 component that is very unlikely to need changesBTW let me ask again just to make sure:So i have a L0 is there a chance a F1 3 etc will be pin compatible with what i have atm ? (there are some L0 but none in stock)

author: pcprogrammer
author_rank: Super Contributor
timestamp: October 23, 2022, 03:10:26 pm
content: A quick scan showed me that yours is 32 pins, and the F1, F3, F4 are at the smallest 48 pins. So I guess not.The L4 states it has pin compatibility with other STM32 lines.And for what I read about it all STM32 devices are hard to get.

author: eutectique
author_rank: Frequent Contributor
timestamp: October 23, 2022, 03:12:41 pm
content: Quote from: DavidAlfa on October 23, 2022, 08:28:52 amA word of caution regarding LTO.Some versions of gcc will remove the vector table from the binary.GNU Arm Embedded Toolchain 9-2020-q2-update (9.3.1)surely does this. The reason is that the vector table is not referenced by any code, so the compiler is free to get rid of "unused" symbol.To avoid this, decorate the vector table with__attribute__((__used__)). Check the map file, anyway.

author: Sniper1
author_rank: Regular Contributor
timestamp: October 23, 2022, 03:51:08 pm
content: sadly yes i only got L0 with 32 pins then again i am in no rush i intend to place the PCB and Mouser orders somewhere in mid late November

author: bson
author_rank: Unknown
timestamp: October 23, 2022, 06:24:58 pm
content: For a device like this dump the ST HAL libraries and work directly with the hardware, creating only exactly the abstraction your project actually needs. Then 'cat' all your sources together into a single file and compile with -fwhole-file. (This intermediate is sometimes called a fat source.)Make sure to compile with -ffunction-sections and link with ld --gc-sections so unused functions (and lambdas, if you use C++) are removed by the linker.Have the linker add a symbol at the end of the stack (through the link script). Then while running enable a hardware watchpoint on that symbol (through the debugger, e.g. with gdb you'd use "awatch endofstack"); this has a good probability of catching a stack overflow.

author: Sniper1
author_rank: Regular Contributor
timestamp: October 23, 2022, 07:35:44 pm
content: Also on a side note what is the best place to find libraries for STM32? atm i find them via YT videos but this is probably not great for more specific ICs

author: westfw
author_rank: Super Contributor
timestamp: October 23, 2022, 10:33:00 pm
content: QuoteST has put their HAL and Cube libraries on github (which is wonderful!)https://github.com/STMicroelectronics/STM32CubeL0/As previously mentioned, these may not be well optimized for size and memory use, but at least you can look at them without having to wade through a full local Cube install.Alsohttps://github.com/libopencm3

author: DavidAlfa
author_rank: Super Contributor
timestamp: October 24, 2022, 12:00:00 am
content: C'mon, you already have the HAL, still 50% free flash, should be enough for your code!

author: Sniper1
author_rank: Regular Contributor
timestamp: October 24, 2022, 12:22:48 pm
content: yea ill manage now the lcd lib was not as large as i thought

author: DavidAlfa
author_rank: Super Contributor
timestamp: October 24, 2022, 12:28:58 pm
content: What LCD and lib are you using?Remember with u8g2 you can strip down fonts and include only the required characters, this greatly reduces space.Mosts libs include a huge font with all ascii chars, then you might need only numbers, but it'll be stored whole into the flash.Definitely, the crappy **_HandleTypeDefs** are using almost half of the ram, woudl be nice to get rid of them.Switching the project to LL (LowLevel) libraries will do it, still provide a library to interface the hardware.I did the test, ram and flash went down to 26%!Only 32 bytes used by the system.Then the stack and heap were using 256bytes each (The reserved sizes in the linker script), could be tracked down and reduced by taking care on the code.If you'll be using stdlib functions (*printf*), then check the allocated heap with the mallinfo function I posted earlier (AFTER using those functions, heap get allocated on first call), assigning just a little more (i.e 32 bytes), and that would be it.Otherwise, as fas as I know only the USB library allocates memory that way, you probably could set the heap to 0 in your code otherwise, but always check first with mallinfo.Same for user stack:Analyze the list / call graph and assign the heap a slightly larger value.That way you'll be protecting the heap and user memory from colliding, yet wasting the minimal resources.If you don't allocate large structures inside your functions (Or avoid long chained calls between functions, each one allocating more data), then stack usage will be minimal.It's this behavior what increases the Stack a lot:Code:void func4(void){uint8_t buffer4; //<-- Another 128bytes on stack (512 now)return; // Now all stack will be freed up}void func3(void){uint8_t buffer3; //<-- Another 128bytes on stack (384 now)func3(); // Another function call, perhabs buffer3 was not required anymore}void func2(void){uint8_t buffer2; //<-- Another 128bytes on stack (256 now)func3(); // Another function call, perhabs buffer2 was not required anymore}void func1(void){uint8_t buffer1; //<-- 128bytes on stackfunc2(); // Stack not freed up, but calling another function, perhabs buffer1 was not required anymore}Which will be greatly minimized if you avoid the call-hierarchy, breaking the functions in a diferent way:Code:int func4(void){uint8_t buffer4; //<-- 128bytes on stackdo_whatever();return result; // stack freed up}int func3(void){uint8_t buffer3; //<-- 128bytes on stackdo_whatever();return result; // stack freed up}int func2(void){uint8_t buffer2; //<-- 128bytes on stackdo_whatever();return result; // stack freed up}int func1(void){uint8_t buffer; //<-- 128bytes on stackdo_whatever();return result; // stack freed up}void handle(void){if( func1()=='do_func2' ){if( func2()=='do_func3' ){if( func3()=='do_func4' ){func4();}}}}Or by many other ways.First example will forcefully need a stack of not less than 512bytes, second will only use 128.Developing in LL will be a bit harder, but still much easier than managing the registers yourself.