python aes加密 cbc,在Python中实施OpenSSL AES加密

I'm trying to implement the following in Python:

openssl enc -e -aes-256-cbc -base64 -k "Secret Passphrase" -in plaintext.txt -out ciphertext.txt

openssl enc -d -aes-256-cbc -base64 -k "Secret Passphrase" -in ciphertext.txt -out verification.txt

I've tried several different modules, PyCrypto, M2Crypto, etc but can't seem to get the correct combination of changing the password to the right size key and encoding everything correctly. I've found https://github.com/nvie/SimpleAES but that basically runs OpenSSL on the command line, which I'd rather avoid.

解决方案

Base 64 encoding and decoding can be easily handled via the standard base64 module.

AES-256 decryption and encryption in CBC mode are supported by both PyCrypto and M2Crypto.

The only non-standard (and most difficult) part is the derivation of the IV and the key from the password. OpenSSL does it via its own EVP_BytesToKey function, which is described in this man page.

The Python equivalent is:

def EVP_BytesToKey(password, salt, key_len, iv_len):

"""

Derive the key and the IV from the given password and salt.

"""

from hashlib import md5

dtot = md5(password + salt).digest()

d = [ dtot ]

while len(dtot)

d.append( md5(d[-1] + password + salt).digest() )

dtot += d[-1]

return dtot[:key_len], dtot[key_len:key_len+iv_len]

where key_len is 32 and iv_len is 16 for AES-256. The function returns the key and the IV which you can use to decrypt the payload.

OpenSSL puts and expects the salt in the first 8 bytes of the encrypted payload.

Finally, AES in CBC mode can only work with data aligned to the 16 byte boundary. The default padding used is PKCS#7.

The steps for encrypting are therefore:

Generate 8 bytes of random data as salt.

Derive AES key and IV from password using the salt from step 1.

Pad the input data with PKCS#7.

Encrypt the padded using AES-256 in CBC mode with the key and the IV from step 2.

Encode in Base64 and output the salt from step 1.

Encode in Base64 and output the encrypted data from step 4.

The steps from decrypting are the reverse:

Decode the input data from Base64 into a binary string.

Treat the first 8 bytes of the decoded data as salt.

Derive AES key and IV from password using the salt from step 1.

Decrypt the remaining decoded data using the AES key and the IV from step 3.

Verify and remove the PKCS#7 padding from the result.

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值