2016-08-08 2 views
0

Я пишу класс C++ для добавления цифровой подписи в PDF, используя OpenSSL для генерации хэша SHA1, который затем распечатать файл:std :: ofstream печатает лишние байты при задании массива unsigned char, но только в режиме Release

unsigned char hash[SHA_DIGEST_LENGTH]; 
SHA1((unsigned char *)temp.c_str(), temp.size(), hash); 

std::ofstream fout("resources/hash.out", std::ios::binary); 
fout << hash; 
fout.close(); 

Этот код работает, как ожидается, в режиме отладки. В режиме выпуска, fout << hash печатает 30 вместо SHA_DIGEST_LENGTH = 20 байт, последние 10 из которых выглядят как мусор (возможно переполнение буфера?)

Мой текущий обходной путь, чтобы напечатать каждый символ вместо потокового:

for (int i=0; i<SHA_DIGEST_LENGTH; ++i) 
    fout.put(hash[i]); 

Что работает в обоих режимах сборки, но мне любопытно, что может заставить оператора потока неправильно считывать длину строки. У кого-нибудь есть мысли?

Для записи я компилирую с MSVC++ 12 (x86_amd64).

+4

ли 'SHA1' нуль-прекратить буфер? – aschepler

+0

Также обратите внимание, что 'temp.size()' не включает нулевой ограничитель. – NathanOliver

+0

Это не C, поэтому не помещайте его C. –

ответ

3

Существует строчка для ввода строк с нулевым символом, которая выбрана.

Но вы пытаетесь вывести массив фиксированной длины, содержащий произвольные байты, что является чем-то совершенно другим, что приводит к UB.

Просто используйте функцию-член write(buffer, size) вместо этого, которая предназначена для этого.

2

Необходимо учитывать, что методы SHA OpenSSL не завершают нулевой вывод вывода. Нормальный operator << требует нулевого окончания, поэтому вы не можете использовать его напрямую.

Чтобы напечатать эту «неиспользуемую» строку с потоками C++, см., Например,

C++ non null terminated char array outputting

для printf например

Using printf with a non-null terminated string

Смежные вопросы