Python проверяет цифровую подпись с помощью полезной нагрузки и строки открытого ключа

У меня есть часть данных ['payload'], закодированная в Base64. Затем у меня есть «подпись», которая содержит подпись полезной нагрузки. У меня есть открытый ключ. Алгоритм подписи SHA512 с RSA.

Как я могу проверить подлинность данных в Python? Я использую следующий код для проверки, но, похоже, он не работает

import base64
import hashlib
from Crypto.PublicKey import RSA 
from Crypto.Signature import SHA512
from Crypto.Hash import SHA512 
from base64 import b64decode 

# Public Key
key = "MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQDEpFwIarbm48m6ueG+jhpt2vCGaqXZlwR/HPuL4zH1DQ/eWFbgQtVnrta8QhQz3ywLnbX6s7aecxUzzNJsTtS8VxKAYll4E1lJUqrNdWt8CU+TaUQuFm8vzLoPiYKEXl4bX5rzMQUMqA228gWuYmRFQnpduQTgnYIMO8XVUQXl5wIDAQAB"

# Base64 Encoded payload
payload = "some_string_payload"
decoded_payload = base64.b64decode(payload)

signature = "gw5K+WvO43673XBinZOmwgrZ3ttVuZ17/7SBnzqAAD4pgiwzYbZuEwn2lev6FW01f6TL0d9cNH4WtT53bQnTlhLQOZi4mHTTtM64O7MNljSA5zjJTUl77wXK/cJM+/G6R4YgYAnjydXAZjbMKY4Z9kV0qz2spdnS7Je7Q8I1xaU="
signature_algorithm = "SHA512withRSA"
keytype = "RSA"


m = hashlib.sha512()
m.update( key )
m.update( decoded_payload )
print m
m.hexdigest()
print m


keyDER = b64decode(key)
rsakey = RSA.importKey(keyDER)

signer = SHA512.new(rsakey) 

if signer.verify(m, b64decode(signature)):
    print "Verified"
else:
    print "Not Verified"

person Yogesh Singhal    schedule 04.07.2017    source источник
comment
Предоставленная вами подпись имеет длину 1024 бита, но подпись SHA512 должна иметь длину только 512 бит. Это означает, что у вас либо неправильная подпись, либо неправильный алгоритм. Пожалуйста, обновите свой вопрос с новой информацией. Кроме того, можно ли показать код, создавший подпись? Нам не нужен закрытый ключ.   -  person supersam654    schedule 06.07.2017
comment
Это даже отдаленно не похоже на то, как вы проверяете подпись RSA. signer.verify() должно вызывать исключение, потому что подписывающая сторона на самом деле является хэш-объектом и не имеет метода verify.   -  person President James K. Polk    schedule 10.07.2017
comment
Каждый вопрос с текстом вроде «но он не работает» и не содержит полного описания проблемы, должен быть закрыт как не относящийся к теме.   -  person President James K. Polk    schedule 10.07.2017


Ответы (1)


Код в вопросе имеет пару ошибок в порядке появления:

  • импортированы две разные реализации SHA512;
  • полезная нагрузка явно не закодирована по основанию 64, обычное основание 64 не представляет текст и не содержит символов _ (однако base-64-url содержит);
  • переменные signature_algorithm и keytype даже не используются;
  • key не следует хэшировать для реализации обычной схемы подписи PSS;
  • результат m.hexdigest() игнорируется;
  • вы не можете сгенерировать класс генерации подписи с помощью SHA512.new(rsakey);
  • как сказано, ваш код даже не компилируется, потому что класс SHA512 не может подписывать;

Вместо этого вы можете использовать любой другой образец кода PSS. Например, используйте код здесь и обратите внимание, что это проблема, которую я указывая на. Это минимальное изменение документа, но никто не хочет его исправлять в течение полугода.

from Crypto.Signature import PKCS1_PSS
from Crypto.Hash import SHA512
from Crypto.PublicKey import RSA
from Crypto import Random
message = 'To be signed'
key = RSA.importKey(open('privkey.der').read())
h = SHA512.new()
h.update(message)
signer = PKCS1_PSS.new(key)
signature = PKCS1_PSS.sign(h)

Обратите внимание, что PSS также может использовать хэш внутренне. Возможно, вам придется определить свой собственный вызываемый код, если проверка подписи не удалась, дополнительная информация здесь. Вероятно, лучше всего найти реализацию по умолчанию для MGF1 в коде, скопировать ее, а затем изменить хеш...

person Maarten Bodewes    schedule 12.05.2018