printf()
glibc/stdio-common/printf.cに定義される。
int __printf(const char *format, ...) {
va_list arg;
int done;
va_start(arg, format);
done = vfprintf(stdout, format, arg);
va_end(arg);
return done;
}
ldbl_strong_alias(__printf, printf);
エイリアスの実装は以下である。
#define ldbl_strong_alias(name, aliasname) strong_alias(name, aliasname)
#define strong_alias(name, aliasname) _strong_alias(name, aliasname)
#define _strong_alias(name, aliasname) extern __typeof(name) aliasname __attribute__((alias(#name)));
vfprintf()
vfprintf()は_IO_putc_unlockedでバッファリングを行う。
ファイル構造体は_IO_write_base、_IO_write_ptr、_IO_write_endを持つ。
#define _IO_putc_unlocked(_ch, _fp) _fp->_IO_write_ptr >= _fp->_IO_write_end ? __overflow() : *_fp->_IO_write_ptr++ = _ch
_IO_do_write()は以下の条件で呼ばれ、最終的にwrite()を呼び出す。
- EOFに達した
- _IO_UNBUFFEREDが立っている
- _IO_LINE_BUFが立っており、改行コードが来た
_IO_LINE_BUFはsetvbuf()で_IOLBFを指定するか、出力先がTTYの場合に立つ。
FreeBSD
カーネル、ライブラリ、コマンドをまとめて配布する。
関数末尾の関数呼び出しはジャンプに最適化されていた。
Newlib
浮動小数点数を使用できない組み込みシステムでは、フルセットのprintf()はエラーになる。
configureのオプションでミニマムな実装を選択でき、サイズの削減とビルドの成功率に貢献する。