Search code examples
pythoncryptographyaespycrypto

AES 128 in Python


I don't know why when I encrypt in AES a text with the PyCrypto (Crypto.Cipher- AES), the result isn't the same as the ciphertext generate by a code in C.

For example, the following code gives me

99756ed0115f676cef45ae25937bfd63247358a80803dde3fc1eae4953ee7277

instead of

CC613A0BDC930DABEA7A26126CE489EA

here is my code:

key = '1F61ECB5ED5D6BAF8D7A7068B28DCC8E'
IV = 16 * '\x00'
mode = AES.MODE_CBC
encryptor = AES.new(key, mode, IV=IV)
text = '020ABC00ABCDEFf8d500000123456789'
ciphertext = encryptor.encrypt(text)
print binascii.hexlify(ciphertext)

Solution

  • You need to unhexlify both the key and text (example in IPython using Python 3);

    In [1]: from Crypto.Cipher import AES
    
    In [2]: import binascii
    
    In [3]: import os
    
    In [4]: key = binascii.unhexlify('1F61ECB5ED5D6BAF8D7A7068B28DCC8E')
    
    In [5]: IV = os.urandom(16)
    
    In [6]: binascii.hexlify(IV).upper()
    Out[6]: b'3C118E12E1677B8F21D4922BE4B2398E'
    
    In [7]: encryptor = AES.new(key, AES.MODE_CBC, IV=IV)
    
    In [8]: text = binascii.unhexlify('020ABC00ABCDEFf8d500000123456789')
    
    In [9]: ciphertext = encryptor.encrypt(text)
    
    In [10]: print(binascii.hexlify(ciphertext).upper())
    b'2133D236609558353F7C501E6EBBB8D9
    

    Edit: As André Caron correctly states in the comments, it is generally a bad idea to use an IV consisting of only zeroes. I've changed the code to use a random IV. Note that the IV should also be communicated to the receiver; it is needed for decryption. Often the IV is prepended to the ciphertext.