Reduce stack usage of _vfiprintf_r()

Federico Terraneo
Sat Oct 13 02:13:00 GMT 2012

Hash: SHA1

On 10/11/2012 04:39 PM, Freddie Chopin wrote:
> W dniu 2012-10-11 16:28, Claudio Lanconelli pisze:
>> Hi, I use newlib for ARM Cortex-M3. I agree with Joel, a
>> malloc()/free() call for each printf() is not acceptable for me,
>> this would raise the risk of memory fragmentation.
>> Just my two cents.
> Please - first read, then post!
> Currently EACH entry to _vf[i]printf_r() costs you 1.3kB of stack.
> When you use it with an unbuffered stream it will use twice that
> (2.6kB).
> With the change I suggested EACH entry to _vf[i]printf_r() costs
> you 300B of stack. ALWAYS! There is NO additional memory allocation
> unless you use an unbuffered stream. Malloc() is called ONLY if the
> stream is unbuffered! There risk of memory fragmentation is very
> low, because the buffer is freed before the function returns -
> fragmentation would only happen in multithreaded application when
> another task interrupts the stream processing and allocates
> something more. No fragmentation is possible for a single threaded
> application. Moreover memory fragmentation usually happens if you
> allocate SMALL pieces of memory and free them in random order, not
> a 1kB buffer which is freed right away...
> Just my three cents. It's probably the third or fourth time I'm 
> explaining... Nobody is suggesting to replace unconditional
> allocation on stack with an uncoditional allocation on heap! Not
> that it would be a wrong idea in some places...
> BTW - printf() style functions use malloc all the time, especially
> for floating point, so your disagreement is a bit late...
> 4\/3!!

My two cents are to fix this by making sure __sbprintf() cannot be
inlined. If I understand correctly, this would reduce the stack usage
down to 300bytes for buffered streams, and 1.3KB for unbuffered ones.
People still concerned with that 1.3KB may modify __BUFSIZ__ to a
lower value, or simply avoid using unbuffered streams.

- - it's a simple patch, can either be done by removing the static
  qualifier or, if the compiler is GCC, with __attribute__((noinline))
- - it introduces no performance penalty but the overhead of a function
  call, which I don't think is a concern for any platform newlib
  supports, so there's no need to enable this conditionally only for
  small memory targets
- - it optimizes for stack usage in the common case of buffered streams
- - it does not introduce heap allocations


Version: GnuPG v1.4.11 (GNU/Linux)
Comment: Using GnuPG with Mozilla -


More information about the Newlib mailing list