1
votes

I'm building an arm-eabi-gcc toolchain with Newlib 2.5.0 as the target C library.

The target embedded system would prefer smaller code size over execution speed. How do I configure newlib to favour smaller code size?

The default build does things like produce a version of strstr that is over 1KB in code size.

2
How are you determining the size of strstr? I'd be surprised if it were truely that large. Size of object file for example is no measure of code size. - Clifford
Note that sometimes compiling with -O2 produces a smaller binary than -Os, just try the different compiler options until you get what you want, and/or realize the uber generic function you might want to use, you could write a specific one that is likely much smaller. - old_timer
@Clifford Looking in the linker map for the final executable - M.M
@M.M : OK, I guess it is that large! It may be useful to specify the version of Newlib in the question.. If you look at the source strstr.c, there are two implementations; a much simpler/smaller one enabled by #if defined(PREFER_SIZE_OVER_SPEED) || defined(__OPTIMIZE_SIZE__). Note that for long strings it is also significantly slower, but if you are that concerned about code size, perhaps long strings too are avoided? - Clifford

2 Answers

2
votes

Configure newlib like this:

CFLAGS_FOR_TARGET="-DPREFER_SIZE_OVER_SPEED=1 -Os" \
../newlib-2.5.0/configure

(where I've omitted the rest of the arguments I used for configure, they don't change based on this issue).

There isn't a configure flag, but the configure script reads certain variables from the environment. CFLAGS_FOR_TARGET means flags used when building for the target system.

Not to be confused with CFLAGS_FOR_BUILD , which are flags that would be used if the build system needed to make any auxiliary executables to execute on the build system to help with the build process.


I couldn't find any official documentation on this, but searching the source code, it contained many instances of testing for PREFER_SIZE_OVER_SPEED or __OPTIMIZE_SIZE__. Based on a quick grep, these two flags are almost identical. The only difference was a case in the printf family that if a null pointer is passed for %s, then the former will translate it to (null) but the latter bulls on ahead , probably causing a crash.

2
votes

There is fat in Newlib that can be addressed with Newlib-nano, which is already part of GCC ARM Embedded, as discussed here (Note the article is from 2014, so the information may be out-dated, but there appears to be Newlib-nano support in the current v6-2017 too).

It removes some features added after C89 that are rarely used in MCU based embedded systems, simplifies complex functions such as formatted I/O, and removes wide character support from non-wide character specific functions. Critically in respect to this question the default build is already size optimised (-Os).