在Windows上使用Python加密错误

时间:2017-08-26 21:41:02

标签: python python-3.x pyopenssl

我正在运行一个用Python编写的基本加密程序,虽然它在OS X上运行良好,但我无法让它在Windows上运行(当我在设置中检查时安装了VS 2017的3.6 / Anaconda)我希望安装Python,并在独立的3.4二进制安装中。)

就像单独的每个import语句在解释器中一样,但整体而言这个程序不起作用

from hashlib import sha256

from pbkdf2_ctypes import *
import hmac
import hashlib
import binascii
from os import urandom
from cryptography.hazmat.primitives.ciphers import Cipher, algorithms, modes
from cryptography.hazmat.backends import default_backend
import getpass

masterpassword = "thisisamasterpassword"
salt = urandom(16) 
masterpassword = pbkdf2_hex(masterpassword.encode('utf-8'), salt)
password = masterpassword.decode()
salt = binascii.hexlify(salt)
salt = salt.decode()

print(masterpassword)

结果是:

C:\Users\me\Desktop>py -3.4 masterpassword.py
Traceback (most recent call last):
  File "C:\Python34\lib\site-packages\pbkdf2_ctypes.py", line 127, in <module>
    raise OSError('Library not found')
OSError: Library not found

During handling of the above exception, another exception occurred:

Traceback (most recent call last):
  File "masterpassword.py", line 3, in <module>
    from pbkdf2_ctypes import *
  File "C:\Python34\lib\site-packages\pbkdf2_ctypes.py", line 153, in <module>
    raise ImportError('Cannot find a compatible cryptographic library '
ImportError: Cannot find a compatible cryptographic library on your system

我还安装了一个OpenSSL二进制文件(https://slproweb.com/products/Win32OpenSSL.html),并确保它在Anaconda下运行。

1 个答案:

答案 0 :(得分:1)

如果我猜这个代码从未在Windows-64bit机器上运行过。引发的错误来自搜索加密库的逻辑中的pbkdf2_ctypes;我认为这是一个偶然的(虽然明智的)假设,即libeay64.dll将安装在64位系统上,libeay32.dll将安装在32位系统上:

if system == 'Windows':
    if platform.architecture()[0] == '64bit':
        libname = ctypes.util.find_library('libeay64') # <--- This does not exist even on 64bit machines ... :)
        if not libname:
            raise OSError('Library not found')
        crypto = ctypes.CDLL(libname)
    else:
        libname = ctypes.util.find_library('libeay32')
        if not libname:
            raise OSError('Library libeay32 not found.')

你可以尝试联系Glisco的某个人,但我不认为他们已经存在了,因为他们的公共代码库已经存在了几年了。

让你前进

你可以:

  1. 在python中运行ctypes.util.find_library('libeay32')并查看您的库所在。然后将libeay32.dll复制到同一文件夹中的libeay64.dll。这不应该导致任何问题,因为你复制了一个其他程序都不知道的文件。

  2. 删除from pbkdf2_ctypes import *,并将这些函数添加到从pbkdf2_ctypes中删除的代码中。

    导入ctypes import ctypes.util

    libname = ctypes.util.find_library('libeay32') crypto = ctypes.CDLL(libname)

    def _openssl_hashlib_to_crypto_map_get(hashfunc):     hashlib_to_crypto_map = {hashlib.md5:crypto.EVP_md5,                              hashlib.sha1:crypto.EVP_sha1,                              hashlib.sha256:crypto.EVP_sha256,                              hashlib.sha224:crypto.EVP_sha224,                              hashlib.sha384:crypto.EVP_sha384,                              hashlib.sha512:crypto.EVP_sha512}     crypto_hashfunc = hashlib_to_crypto_map.get(hashfunc)     如果crypto_hashfunc为None:         提高ValueError('Unkwnown digest%s'%hashfunc)     crypto_hashfunc.restype = ctypes.c_void_p     return crypto_hashfunc()

    def _openssl_pbkdf2(data,salt,iterations,digest,keylen):     msgstr“”“OpenSSL兼容包装器     “””     c_hashfunc = ctypes.c_void_p(_openssl_hashlib_to_crypto_map_get(digest))

    c_pass = ctypes.c_char_p(data)
    c_passlen = ctypes.c_int(len(data))
    c_salt = ctypes.c_char_p(salt)
    c_saltlen = ctypes.c_int(len(salt))
    c_iter = ctypes.c_int(iterations)
    c_keylen = ctypes.c_int(keylen)
    c_buff = ctypes.create_string_buffer(keylen)
    
    crypto.PKCS5_PBKDF2_HMAC.argtypes = [ctypes.c_char_p, ctypes.c_int,
                                     ctypes.c_char_p, ctypes.c_int,
                                     ctypes.c_int, ctypes.c_void_p,
                                     ctypes.c_int, ctypes.c_char_p]
    
    crypto.PKCS5_PBKDF2_HMAC.restype = ctypes.c_int
    err = crypto.PKCS5_PBKDF2_HMAC(c_pass, c_passlen,
                        c_salt, c_saltlen,
                        c_iter,
                        c_hashfunc,
                        c_keylen,
                        c_buff)
    return (err, c_buff)
    

    def pkcs5_pbkdf2_hmac(data,salt,iterations = 1000,keylen = 24,hashfunc = None):     如果hashfunc为None:         hashfunc = hashlib.sha1     错误,c_buff = _openssl_pbkdf2(数据,盐,迭代,hashfunc,keylen)

    if err == 0:
        raise ValueError('wrong parameters')
    return c_buff.raw[:keylen]
    

    def pbkdf2_hex(data,salt,iterations = 1000,keylen = 24,hashfunc = None):     return binascii.hexlify(pkcs5_pbkdf2_hmac(data,salt,iterations,keylen,hashfunc))