В настоящее время я конвертирую код одной из наших библиотек Linux в Windows DLL.
В этой библиотеке у меня есть функция, которая принимает последние параметры в формате printf (строка формата, затем многоточие). В этой функции я использую vsnprintf для форматирования предоставленных аргументов. Поскольку я хочу знать, могу ли я втиснуть последнюю строку в небольшой буфер или мне придется выделить памяти для него, меня интересует определение «предполагаемой длины» отформатированной строки.
Для этого я сейчас использую vsnprintf вот так (очевидно, составленный пример кода):
#include
#include
#include
void foo(const char* fmt, ...)
{
int len = 0;
va_list ap;
va_start(ap, fmt);
len = vsnprintf(0, 0, fmt, ap);
printf("len = %d\n", len);
va_end(ap);
}
int main(void)
{
foo("12345%s", "67890");
exit(0);
}
Это использование покрывается Выпуском 6 базовых спецификаций открытых групп :
vsnprintf ( char * restrict s, size_t n, const char * restrict format, va_list ap)
Функции [...] vsnprintf () [...] должны быть эквивалентны [...] snprintf ().
snprintf (char * restrict s, size_t n, const char * restrict format, ...)
Если значение n равно нулю при вызове snprintf (), ничего не должно быть записано, количество байтов который был бы записан, если бы n было достаточно большим, исключая завершающий нуль, должен быть возвращен, а s может быть нулевым указателем.
Проблема возникла, когда я компилировал этот код в системе Windows (Visual Studio 2010) с включенным параметром / analysis. Компилятор / анализатор дал мне следующее:
test.c (11): предупреждение C6309: Аргумент '1' равен нулю: это не соответствует спецификации функции 'vsnprintf'
test.c (11): предупреждение C6387: 'аргумент 1' может быть '0': это не соответствует спецификации функции 'vsnprintf': Строки: 7, 8, 10, 11
Быстрый просмотр записи MSDN для vsnprintf дал мне следующее:
Если буфер или формат равен NULL , или если count меньше или равно нулю, эти функции вызывают обработчик недопустимых параметров, как описано в разделе Проверка параметров. Если выполнение может быть продолжено, эти функции возвращают -1.
Как ни странно, приведенный выше образец тем не менее работает в Windows «как и ожидалось» (т. Е.он возвращает мне количество символов, которые должны были быть написаны).
Но поскольку я не хочу, чтобы это полагалось на что-то неопределенное, я хотел бы знать, есть ли лучший, официальный способ достижения того же, не надеясь, что это не сломается в каком-то будущем выпуске.
Спасибо за уделенное время!