How Much Flash and SRAM Does My Project Use?

When developing firmware for an embedded project, it is important to know how much flash and SRAM the program is using. This allows you to make the best decision on whether the chosen MCU has sufficient resources for your needs.

By default, GCC does not give any information regarding program size. However, GCC does include a utility that can help, sensibly it is called “size.exe” (or “arm-none-eabi-size.exe” for the embedded GCC version). If you run the program as follows:

c:\iccv9cortex\gnuarm\bin\arm-none-eabi-size -A -x bin\Debug\Test.elf

The /path/to/ is as installed by ImageCraft’s JumpStart C++ program, but any embedded GCC installation will have this program. The last argument is the input file (in default ELF format). “-A” means to output in SysV format (Berkeley format is the other option), and “-x” is to use hexadecimal output. The above produces something as follows:

bin\Debug\TestDriver.elf  :
section size addr
.text 0x6720 0x8000000
.ARM.extab 0x258 0x8006720
.ARM.exidx 0x2f0 0x8006978
.ARM.attributes 0x2a 0x8006c68
.data 0x804 0x20000000
.bss 0x9c0 0x20000804
._user_heap_stack 0x2804 0x200011c4
.debug_line 0x405a 0x0
.debug_info 0x24c75 0x0
...
.debug_ranges 0x60 0x0
.comment 0x75 0x0
.debug_frame 0x2dd4 0x0
.stab 0x9c 0x0
.stabstr 0x14f 0x0
Total 0x3d8f3

Each line represents a “region” in the output file. If a region has an address of 0x0, it means that it is not using any space in the target MCU and most likely only contains debug information, and will be used for debugging only. The regions’ names and allocations are controlled by the linker script used so your output may look slightly different.

The entries of interest are: .text this is the size of your program, i.e. flash usage. In this example, 0x6720 or 26400 bytes of flash is used, plenty left over from the 512K STM32F411RE that I am using.

.data and .bss are the static SRAM usage. .data has the global/static variables that have initialization, and .bss has the global/static variables that have no initialization (but are initialized to zero per C/C++ definition). In this case, 4548 bytes are needed, also significantly less than the 128K bytes of SRAM available on the F411RE.

Finally, ._user_heap_stack is the area reserved for memory allocated at runtime, heap is for memory used by malloc/free, and C++’s “new” etc., and stack is used for mainly for local variables and function context. As the runtime memory size changes as your program is run, this is only the minimum amount set in the linker script. Your program controls how much dynamic memory it uses. Stack usage depends on the call patterns in your program and how much stack space (e.g. local variables) a function uses. A future blog post will describe one way to determine stack usage of a program.

You can write a simple utility program to process the “size” output to give a simple summary, which is what we have done with the JumpStart C++ tools. A typical post-build message looks like this:

ELF file output size
Code size: 26400 bytes starting at 0x08000000
SRAM data: 4548 bytes starting at 0x20000000
Heap and Stack: 10244 bytes heap starts 0x200011C4 stack starts 0x200039C8

With size.exe and some processing, it is simple to see your program’s flash and SRAM requirements.

Posted in Uncategorized | Leave a comment

Embedded GCC Libraries: newlib vs. nanolib

C/C++ compilers include a set of standard functions to be linked with user programs. They are called libc and libc++ respectively. For GCC, they are also called glibc and glibc++ (in the rest of this post, I would use glibc to mean both glibc and glibc++). Most of the functions are directly callable by the user programs, e.g. printf, but some are internal functions known to the compiler to support operations not directly supported by the target hardware. For example, double precision floating point add.

Traditional glibc is written for “big machines” such as Linux. For embedded use, it’s too bloated as embedded systems may not be running on top of an OS and advanced features such as locale (international language) support may not be needed. Even things like printf with full formatting and floating point support may take too much code for smaller microcontrollers.

Continue reading
Posted in Uncategorized | Leave a comment

2018-Q4 GNU Embedded ARM objcopy “64-bit address… out of range” Error

From time to time, we refresh the GNU Embedded ARM compiler (GCC) in our JumpStart C++ with the latest stable GNU release. Earlier in 2019, we refreshed GCC to the 2018-Q4 release. Surprisingly, our testing showed a failure immediately:

objcopy.exe: 64-bit address 0x4b4fa300000000 out of range 
Continue reading
Posted in Uncategorized | Leave a comment

Removing Bootloader Protection On The AdaFruit Metro / Arduino Zero / SAMD21

The Microchip/Atmel SAMD21G18A is a powerful Cortex M0+ based MCU with 256K flash and 32K of SRAM. It’s used in the Arduino Zero as well as the Adafruit Metro and Feather lines of development boards, and is becoming a popular choice for users looking for a low cost powerful ARM Cortex-M MCU.

The SAMD21G18A used in the Arduino and Adafruit development boards is programmed with a bootloader. The Arduino IDE uses this feature to download programs onto the MCU.

However, instead of the limited Arduino IDE, you can instead use an advanced development environment such as JumpStart C++, Keil, or IAR. Besides getting the full benefit of using C/C++, you also can use visual debuggers that are lacking in the Arduino IDE.

Continue reading
Posted in Uncategorized | Leave a comment

Cortex-M Debug Pods

In this article, we will examine some of the more popular Cortex-M hardware debug pods (also called debug probes), which are hardware devices necessary for debugging firmware on a Cortex-M based MCU.

Overview of Debugging

In the “good old days”, debugging an embedded system often meant the judicious use of printf to output debugging messages to a terminal. Fortunately, modern MCUs now come with hardware debug support that makes it easy to implement the core debugging features such as instruction breakpoints, and memory access. In the Cortex-M core specification, ARM Inc. includes a Coresight Debug Access Port (DAP) for just such purposes. As the DAP is present in all the Cortex-M base MCUs, this means that they all can provide debug support.

Continue reading
Posted in Uncategorized | Leave a comment

Cortex Compiler: Vendor SDK

A strength of Cortex-M based MCUs is that the core CPU is designed by ARM Inc., while silicon vendors license the core design and then put their own I/O peripherals around it. With all major MCU vendors supporting the Cortex MCU, embedded designers have a large number of MCUs to choose from, while able to reuse their existing knowledge of the CPU information.

To make the software a bit more manageable, ARM has published the CMSIS (Cortex Microcontroller Software Interface Standard). CMSIS addresses the issues of portable macro defines and intrinsic functions common to the Cortex-M CPU cores.  As each MCU has its own set of I/O peripherals, silicon vendors provide header files and sometimes C source files which let a user access the peripheral I/O registers and functions.

Continue reading
Posted in Uncategorized | Leave a comment

Happy Holidays and 18% Off Until End of the Year

Hello, in 2018 we saw some exciting developments at ImageCraft. To celebrate, we are offering 18% off until end of the year. Use coupon code BYE2018 when you check out. Follow the instructions here: https://imagecraft.com/buy/how-to-use-coupon-code

Continue reading
Posted in Uncategorized | Leave a comment

REXIS Logo Revealed!

REXIS (Real-time EXecutive for Intelligent Systems) has been released, and now we have a branding logo! RAWRRRR!

Thanks to the awesome graphic designer Kurt, from Fantastic Realities Studio!

Posted in new product, news | Leave a comment

REXIS Sale Specials!

Happy Thanksgiving! The first public release of REXIS is now available, as part of V9.07.00 of JumpStart C++ for Cortex, which you can download by clicking on the link.

ImageCraft creates different REXIS editions to fulfill the different needs of embedded developers. For consulting engineers, you can prototype, test, and work with the REXIS binary release by installing the JumpStart C++ for Cortex compiler. Get a ST-Nucleo F411RE and you can start running the examples immediately. The binary release is free to use for non-commercial use.

Continue reading
Posted in news, Sales | Tagged | Leave a comment

Synchronous Message Passing and REXIS Benchmarking

If you have read the blog on REXIS Examples, or the REXIS documentation, you may have noticed that REXIS supports synchronous message passing API, in addition to the more common asynchronous messaging with mailboxes. Synchronous message passing is not a new idea. Indeed, the inspiration came from QNX Neutrino, the message passing kernel that powered the BlackBerry smartphone devices in the early 2000s.

Synchronous message passing is a great idea. For example, it makes writing a “full-blown” OS (e.g. Linux) based on microkernel simpler. In such a system, OS services such as the file system support, networking etc. are written as regular tasks or processes instead of being part of the kernel code. Of course having a full OS is less important in a microcontroller system, but nevertheless, the use of synchronous message passing can give firmware a cleaner design. (We will see another example in this post below.) As a footnote, REXIS’ functions can be said to reflect those of a microkernel, perhaps pointing to a possible future path for its development.

Some RTOS producers are loathe to benchmark their products, or allow their users to do so. Here at ImageCraft, we welcome it :-). So let’s dive in and look at some numbers for the REXIS message passing API calls.

Continue reading

Posted in new product, techniques | Tagged | 2 Comments