c - 在不使用 va_copy 的情况下将 va_list 传递给另一个函数是否安全?

标签 c language-lawyer c99 variadic-functions

This blog post声称将 va_list 传递给另一个函数(如以下代码)是不安全的,并且必须首先使用 va_copy 复制 va_list:

void
foo_ap(const char *fmt, va_list ap)
{
    char buf[128];

    vsnprintf(buf, sizeof(buf), fmt, ap);

    // now, do something with buf ...
}

就像博客文章的评论之一提到的那样,我看不出这有多么不安全,正如 C99 规范 (7.15) 所述:

The object ap may be passed as an argument to another function; if that function invokes the va_arg macro with parameter ap, the value of ap in the calling function is indeterminate and shall be passed to the va_end macro prior to any further reference to ap.

(只要 foo_ap 在传递后不引用 ap ,句子的第二部分无论如何都不适用。)该博客文章在另一条评论中说他可能是错的,但也许有人可以添加一些说明。为了安全起见,我真的必须使用 va_copy 吗?或者是否有任何平台不符合规范并需要使用 va_copy

最佳答案

如果您仍计划在 vsnprintf 返回后使用 ap,则只需要 va_copy。例如,您可能想调用 vsnprintf 两次 - 一次是为了确定所需的缓冲区大小,另一次是为了真正格式化。如果您不需要再次使用 ap(除了可能将其传递给 va_end,如果您是使用 va_start 创建它的人) , 那么你不需要 va_copy 它。

关于c - 在不使用 va_copy 的情况下将 va_list 传递给另一个函数是否安全?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/26953289/

相关文章:

GNU 语句表达式的编译器支持

c - 我在哪里可以找到每个 C99 字符集的所有字符表?

c++ - 清除标准输入缓冲区(内存占用)

c++ - 如果双端队列不够大,为什么通过 std::copy 成功将 std::deque 对象附加到自身?

C - 不确定值是不确定的吗?

c++ - 为什么数组形式参数总是隐式转换为指针而不是被禁止?

c - 在 C99 中,f()+g() 是未定义的还是仅仅是未指定的?

c - 如何获取与给定 KeySym 关联的 KeyCode?

c - libxml2 无法从节点获取内容

c++ - 为什么相同标识符的大小在 C 和 C++ 中不同?