ECDSA не подписывает / проверяет правильно

В настоящее время у меня возникают проблемы при подписании / проверке строки с помощью Crypto ++. Я пробовал методы, перечисленные на этом сайте среди других, в течение нескольких месяцев, но безуспешно. Ранее я пробовал решение в стиле C, опубликованное здесь: http://www.cryptopp.com/wiki/Elliptic_Curve_Digital_Signature_Algorithm, но в настоящее время я работаю над реализацией с использованием фильтров.

Моя попытка ниже является модификацией решения, размещенного здесь: Получить подпись ECDSA с Crypto ++.

Следующий код выводит ошибку:
ERROR: VerifierFilter: digital signature not valid

ECDSA<ECP, SHA256>::PrivateKey privateKey;
ECDSA<ECP, SHA256>::PublicKey publicKey;

AutoSeededRandomPool prng, rrng;

privateKey.Initialize(prng, CryptoPP::ASN1::secp256k1());

privateKey.MakePublicKey(publicKey);

string signature;

signature.erase();

string message = "Do or do not. There is no try.";

StringSource(message, true,
new SignerFilter(rrng,
ECDSA<ECP, SHA256>::Signer(privateKey),
new StringSink(signature)));

try
{
StringSource(signature + message, true,
new SignatureVerificationFilter(
ECDSA<ECP, SHA256>::Verifier(publicKey), NULL,
SignatureVerificationFilter::THROW_EXCEPTION
) // SignatureVerificationFilter
); // StringSource
}
catch (CryptoPP::Exception& e)
{
std::cerr << "\n\nERROR: " << e.what() << std::endl;
}

Любая помощь приветствуется, спасибо.

4

Решение

После более длительного просмотра вики я думаю, что, возможно, наткнулся на решение.

http://www.cryptopp.com/wiki/SignatureVerificationFilter#Signature_Generation_and_Verification

В приведенном выше примере фильтр получает конкатенацию
сообщение + подпись. Когда SIGNATURE_AT_BEGIN не указан в
конструктор, SIGNATURE_AT_END подразумевается и подпись будет
проверено должно быть представлено после сообщения. Если подпись
вставленный первым, SIGNATURE_AT_BEGIN должен быть указан как
значение дополнительных флагов, как показано ниже.

Так как THROW_EXCEPTION используется, signature а также message должны поменяться местами или SIGNATURE_AT_BEGIN должен быть добавлен. В этом случае следующий код не вызывает исключение.

StringSource ss(signature + message, true,
new SignatureVerificationFilter(
verifier, NULL,
THROW_EXCEPTION | SIGNATURE_AT_BEGIN
) // SignatureVerificationFilter
); // StringSource
3

Другие решения

StringSource(signature + message, true,
new SignatureVerificationFilter(
ECDSA<ECP, SHA256>::Verifier(publicKey), NULL,
SignatureVerificationFilter::THROW_EXCEPTION
) // SignatureVerificationFilter
); //

Выше выглядит подозрительно. Это выглядит подозрительно по двум причинам. Во-первых, он использует анонимные объявления, и я знаю, что некоторые версии GCC дают с ними плохие результаты. GCC генерирует код так, что деструкторы запускаются слишком рано. Так назови свою декларацию.

Во-вторых, SignatureVerificationFilter берет ссылку, а не временную. Таким образом, вы должны предоставить ссылку на verifierили используйте Ref() функция-член, если она доступна.

Сначала попробуйте просто:

ECDSA<ECP, SHA256>::Verifier verifier(publicKey);

StringSource ss(signature + message, true,
new SignatureVerificationFilter(
verifier, NULL,
SignatureVerificationFilter::THROW_EXCEPTION
) // SignatureVerificationFilter
); // StringSource

Во-вторых, попробуйте с:

StringSource ss(signature + message, true,
new SignatureVerificationFilter(
ECDSA<ECP, SHA256>::Verifier(publicKey).Ref(), NULL,
SignatureVerificationFilter::THROW_EXCEPTION
) // SignatureVerificationFilter
); // StringSource

Но я не уверен, если ECDSA<ECP, SHA256>::Verifier(publicKey).Ref() собирается на работу.

0

По вопросам рекламы [email protected]