以下程序在64位系统崩溃。此代码在32位系统中正常工作 我正在使用centOS 32位和centOS 64位系统.. 这是什么原因?
#if 1
if (1)
{
memset(message1, '\0', sizeof(message1));
vsprintf(message1, format, vAList);
}
#endif
if (1)
{
//PROGRAM CRASHES in the following line IF AM PUTTING #if 1 in the above code as i did
val = vfprintf(logFile, format,vAList);
}
程序达到val = vfprintf(logFile,format,vAList);
这里它在64位系统崩溃..
答案 0 :(得分:2)
您不能两次使用可变参数列表。 vfprintf
"耗尽"参数和下一个调用可能会尝试访问列表后的内存。用手册页的话来说:
这些函数[
v*printf
]不会调用va_end
宏。因此,在调用之后,ap的值是未定义的。应用程序之后应该调用va_end(ap)
。
如果您的格式需要取消引用,例如%s
格式,则可能是您的程序崩溃。
您可以通过两种方式解决这个问题:将vfprintf
和va_start
中的va_end
的所有来电包裹起来:
int f(const char *fmt, ...)
{
va_list va;
va_start(va, fmt);
vprintf(fmt, va);
va_end(va);
va_start(va, fmt);
vprintf(fmt, va);
va_end(va);
return 0;
}
或制作可变参数列表的副本:
int f(const char *fmt, ...)
{
va_list va, vb;
va_start(va, fmt);
va_copy(vb, va);
vprintf(fmt, va);
vprintf(fmt, vb);
va_end(va);
va_end(vb);
return 0;
}
(您必须在复制列表之前制作副本。)
修改:忘记清理第二个示例中复制的va lis vb
。现在修好了。