pycryptodome installing for error cannot python pycrypto

python - installing - Firma y verificación de datos usando pycrypto(RSA)



pycrypto python 3.7 windows (3)

A continuación se muestra la clase de ayuda que creé para realizar todas las funciones RSA necesarias (cifrado, descifrado, firma, verificación de firmas y generación de nuevas claves)

rsa.py

from Crypto.PublicKey import RSA from Crypto.Cipher import PKCS1_OAEP from Crypto.Signature import PKCS1_v1_5 from Crypto.Hash import SHA512, SHA384, SHA256, SHA, MD5 from Crypto import Random from base64 import b64encode, b64decode hash = "SHA-256" def newkeys(keysize): random_generator = Random.new().read key = RSA.generate(keysize, random_generator) private, public = key, key.publickey() return public, private def importKey(externKey): return RSA.importKey(externKey) def getpublickey(priv_key): return priv_key.publickey() def encrypt(message, pub_key): #RSA encryption protocol according to PKCS#1 OAEP cipher = PKCS1_OAEP.new(pub_key) return cipher.encrypt(message) def decrypt(ciphertext, priv_key): #RSA encryption protocol according to PKCS#1 OAEP cipher = PKCS1_OAEP.new(priv_key) return cipher.decrypt(ciphertext) def sign(message, priv_key, hashAlg="SHA-256"): global hash hash = hashAlg signer = PKCS1_v1_5.new(priv_key) if (hash == "SHA-512"): digest = SHA512.new() elif (hash == "SHA-384"): digest = SHA384.new() elif (hash == "SHA-256"): digest = SHA256.new() elif (hash == "SHA-1"): digest = SHA.new() else: digest = MD5.new() digest.update(message) return signer.sign(digest) def verify(message, signature, pub_key): signer = PKCS1_v1_5.new(pub_key) if (hash == "SHA-512"): digest = SHA512.new() elif (hash == "SHA-384"): digest = SHA384.new() elif (hash == "SHA-256"): digest = SHA256.new() elif (hash == "SHA-1"): digest = SHA.new() else: digest = MD5.new() digest.update(message) return signer.verify(digest, signature)

Uso de la muestra

import rsa from base64 import b64encode, b64decode msg1 = "Hello Tony, I am Jarvis!" msg2 = "Hello Toni, I am Jarvis!" keysize = 2048 (public, private) = rsa.newkeys(keysize) encrypted = b64encode(rsa.encrypt(msg1, public)) decrypted = rsa.decrypt(b64decode(encrypted), private) signature = b64encode(rsa.sign(msg1, private, "SHA-512")) verify = rsa.verify(msg1, b64decode(signature), public) print(private.exportKey(''PEM'')) print(public.exportKey(''PEM'')) print("Encrypted: " + encrypted) print("Decrypted: ''%s''" % decrypted) print("Signature: " + signature) print("Verify: %s" % verify) rsa.verify(msg2, b64decode(signature), public)

Estoy tratando de familiarizarme con el módulo de pycrypto, pero la falta de documentación clara dificulta las cosas.

Para empezar, me gustaría entender cómo firmar y verificar datos. ¿Podría alguien dar un ejemplo de cómo se escribiría esto?


Esta es una versión completa del ejemplo en la documentación:

import Crypto.Hash.MD5 as MD5 import Crypto.PublicKey.RSA as RSA import Crypto.PublicKey.DSA as DSA import Crypto.PublicKey.ElGamal as ElGamal import Crypto.Util.number as CUN import os plaintext = ''The rain in Spain falls mainly on the Plain'' # Here is a hash of the message hash = MD5.new(plaintext).digest() print(repr(hash)) # ''/xb1./J/xa883/x974/xa4/xac/x1e/x1b!/xc8/x11'' for alg in (RSA, DSA, ElGamal): # Generates a fresh public/private key pair key = alg.generate(384, os.urandom) if alg == DSA: K = CUN.getRandomNumber(128, os.urandom) elif alg == ElGamal: K = CUN.getPrime(128, os.urandom) while CUN.GCD(K, key.p - 1) != 1: print(''K not relatively prime with {n}''.format(n=key.p - 1)) K = CUN.getPrime(128, os.urandom) # print(''GCD({K},{n})=1''.format(K=K,n=key.p-1)) else: K = '''' # You sign the hash signature = key.sign(hash, K) print(len(signature), alg.__name__) # (1, ''Crypto.PublicKey.RSA'') # (2, ''Crypto.PublicKey.DSA'') # (2, ''Crypto.PublicKey.ElGamal'') # You share pubkey with Friend pubkey = key.publickey() # You send message (plaintext) and signature to Friend. # Friend knows how to compute hash. # Friend verifies the message came from you this way: assert pubkey.verify(hash, signature) # A different hash should not pass the test. assert not pubkey.verify(hash[:-1], signature)


Según la documentación en:

https://www.dlitz.net/software/pycrypto/api/current/Crypto.PublicKey.RSA._RSAobj-class.html

no debe usar la función Crypto.PublicKey.RSA.sign de PyCrypto en código real:

Atención: esta función realiza el descifrado RSA simple y primitivo (libro de texto). En aplicaciones reales, siempre debe usar el relleno criptográfico adecuado, y no debe firmar directamente los datos con este método. De lo contrario, se pueden producir vulnerabilidades de seguridad. Se recomienda utilizar los módulos Crypto.Signature.PKCS1_PSS o Crypto.Signature.PKCS1_v1_5 en su lugar.

Terminé usando el módulo RSA que implementa PKCS1_v1_5. La documentación para la firma fue bastante sencilla. Otros han recomendado usar M2Crypto .