fprintf是否在引擎盖下使用malloc()?

我想要一个最小的o-damn-malloc-just-failed处理程序,它将一些信息写入文件(可能只是标准错误)。 我更喜欢使用fprintf()而不是write(),但是如果fprintf()本身尝试使用malloc(),这将很难失败。

是否有一些保证,无论是在C标准中,还是只是在glibc中,fprintf都不会这样做?

不,不能保证它不会。 但是,我见过的大多数实现都倾向于使用固定大小的缓冲区来创建格式化的输出字符串(a)

就glibc而言( 这里 源代码 ),在stdio-common/vfprintf.c有对malloc调用,很多printf系列都在较低端使用,所以如果我是你,我就不会依赖它。 甚至字符串缓冲区输出调用像sprintf ,你可能认为不需要它,在设置一些棘手的FILE libio/iovsprintf.c字符串句柄之后似乎解决了那个调用 – 参见libio/iovsprintf.c

我的建议是编写自己的代码来进行输出,以确保没有内存分配(当然,希望write本身不会这样做(比*printf做得更糟))。 既然你可能不会输出大量转换的东西(可能只是"Dang, I done run outta memory!" ),无论如何,对格式化输出的需求应该是值得怀疑的。


(a) C99环境考虑因素表明(至少)某些早期实施具有缓冲限制。 从我对Turbo C的记忆中,我认为4K是关于极限的,事实上,C99状态(在7.19.6.1 fprintf ):

任何单次转换可以产生的字符数应至少为4095。

(C89的任务是编纂现有的做法,而不是创造一种新的语言,这就是为什么这些最小的最大值被置于标准中的一个原因 – 它们被推迟到标准的后续迭代中)。

C标准并不保证fprintf不会在引擎盖下调用malloc 。 实际上,它并不能保证在覆盖malloc时会发生什么。 您应该参考特定C库的文档,或者只是编写自己的fprintf的函数,它可以直接进行系统调用,避免任何堆分配的可能性。

您可以合理确定的唯一不会调用malloc是POSIX标记为async-signal-safe的函数。 由于malloc不需要异步信号安全(并且因为它基本上不可能使其异步信号安全而不会使它效率低效),异步信号安全function通常无法调用它。

话虽如此,我几乎可以肯定glibc的printf函数(包括fprintf甚至snprintf )可以并且将使用malloc来表示某些(所有?)格式的字符串。