我需要返回
的函数count_sprintf()
在Win32和Linux上格式化缓冲区所需的字符数(不是包含字节)。
int count_sprintf(const char *format, va_list ap);
当格式化的值超过缓冲区大小时,在vsnprintf的返回值中,Win32与Linux之间存在微妙的差异。这就是我寻求帮助的原因。
你能为这个功能提供便携式代码(#ifdef WIN32)。
这样使用的功能:
int bufsize = 1 + count_snprintf(format, ap);
char *buf = (char*)malloc(bufsize);
vsnprintf(buf, bufsize, format, ap); // on WIN32, _vsnprint, on Linux, vsnprintf.
由于
答案 0 :(得分:3)
VS运行时具有_vscprintf,用于计算所需的字符数。
int count_sprintf(const char *format, va_list ap) {
#ifdef WIN32
return _vscprintf(format, ap);
#else
char c;
return vsnprintf(&c, 1, format, ap);
#endif
}
答案 1 :(得分:1)
我不知道你是否需要C解决方案,C ++或两者兼而有之。
在C ++中,有一种非常简单的方法可以解决这个问题:使用流而不是printf
函数行。
在CI中建议强烈关注使用变量格式字符串的任何情况:如果函数的变量稍微偏离,并且编译器无法帮助它们,则可能会导致问题您。如果格式是在外部生成的,则更糟糕,因为您基本上对任何数量的缓冲区溢出攻击都是开放的。至少如果你有一个固定的格式字符串,你知道它将开始有多长时间,并且一些编译器可以对varargs进行格式化字符串检查。
答案 2 :(得分:0)
在Linux上,您可以使用asprintf
:
The functions asprintf() and vasprintf() are analogs of sprintf(3) and vsprintf(3), except that they allocate a string large enough to hold the output including the terminating null byte, and return a pointer to it via the first argument. This pointer should be passed to free(3) to release the allocated storage when it is no longer needed.
答案 3 :(得分:0)
你可以使用vsnprintf - 如果给它一个0大小的缓冲区,它实际上不会尝试将任何东西放在缓冲区中,但仍会返回它输出的字符数