2017-09-21 6 views
2

나는 다음과 같다 PHP 파일이 있습니다변환하려면 openssl AES는

$encryption_encoded_key = 'c7e1wJFz+PBwQix80D1MbIwwOmOceZOzFGoidzDkF5g='; 

function my_encrypt($data, $key) { 
    $encryption_key = base64_decode($key); 
    $iv = openssl_random_pseudo_bytes(openssl_cipher_iv_length('aes-256-cfb')); 

    $encrypted = openssl_encrypt($data, 'aes-256-cfb', $encryption_key, 1, $iv); 

    // The $iv is just as important as the key for decrypting, so save it with encrypted data using a unique separator (::) 
    return base64_encode($encrypted . '::' . $iv); 
} 

function my_decrypt($data, $key) { 
    // Remove the base64 encoding from key 
    $encryption_key = base64_decode($key); 

    // To decrypt, split the encrypted data from IV - unique separator used was "::" 
    list($encrypted_data, $iv) = explode('::', base64_decode($data), 2); 

    return openssl_decrypt($encrypted_data, 'aes-256-cfb', $encryption_key, 1, $iv); 
} 

$data = 'USER_ID||NAME||EMAIL||MOBILE'; 
$data_encrypted = my_encrypt($data, $encryption_encoded_key); 
echo $data_encrypted; 
$data_decrypted = my_decrypt($data_encrypted, $encryption_encoded_key); 
echo "Decrypted string: ". $data_decrypted; 

이 잘 작동, 지금은 또한 파이썬이 암호화 키와 복호화/암호화 할 수 있습니다 파일 : 내가 PHP 파일을 사용하여 암호화하고 파이썬에 출력을 해독 할 내가 파이썬에서 이것을 사용하려고하면 이것은 또한 잘 작동

import hashlib 
import base64 
from Crypto.Cipher import AES 
from Crypto import Random 

encryption_encoded_key = 'c7e1wJFz+PBwQix80D1MbIwwOmOceZOzFGoidzDkF5g=' 

def my_encrypt(data, key): 
    #Remove the base64 encoding from key 
    encryption_key = base64.b64decode(key) 
    #Generate an initialization vector 
    bs = AES.block_size 
    iv = Random.new().read(bs) 

    cipher = AES.new(encryption_key, AES.MODE_CFB, iv) 
    #Encrypt the data using AES 256 encryption in CBC mode using our encryption key and initialization vector. 
    encrypted = cipher.encrypt(data) 

    #The iv is just as important as the key for decrypting, so save it with encrypted data using a unique separator (::) 
    return base64.b64encode(encrypted + '::' + iv) 


def my_decrypt(data, key): 
    #Remove the base64 encoding from key 
    encryption_key = base64.b64decode(key) 

    #To decrypt, split the encrypted data from IV - unique separator used was "::" 
    encrypted_data, iv = base64.b64decode(data).split('::') 

    cipher = AES.new(encryption_key, AES.MODE_CFB, iv) 

    return cipher.decrypt(encrypted_data) 

data = 'USER_ID||NAME||EMAIL||MOBILE' 

print "Actual string: %s" %(data) 
data_encrypted = my_encrypt(data, encryption_encoded_key) 
print data_encrypted 

data_decrypted = my_decrypt(data_encrypted, encryption_encoded_key) 
print "Decrypted string: %s" %(data_decrypted) 

, 그것은 암호화/암호 입력 문자열을 해독 할 수있다, 모두 사용해야합니다 AES 256 암호화 (CFB 모드 사용), 내가 뭘 잘못하고 있니?

+1

어디 과정입니다 브레아 왕 내려? 각 방법에 대해 암호화/복호화 작업을 실행하기 전에 구문 분석 된 키, iv, 데이터 등을 인쇄 할 수 있습니까? 그게 적어도 당신에게 출발점을 줄 것이다 – Kritner

+0

오, 그리고 조심해야 할 한가지 - 참조 유형에 대한 경계에 파이썬이나 PHP에 대해 많이 알지 못한다. 'iv'는 잠재적으로 암호화/해독 동작을 수행 할 때 각 블록을 통해 수정됩니다. 첫 번째 블록 다음에 "... 0001"의 iv로 시작한다면, 그 iv는'... 0002'로 표현 될 것입니다. (잠재적으로) 수정 된 것보다는 두 가지 구현 모두에서 "원본"iv를 추가해야합니다. – Kritner

답변

2

CFB mode을 사용하려면 세그먼트 크기을 지정해야합니다. OpenSSL은 aes-256-cfb (128 비트), aes-256-cfb1 (1 비트) 및 aes-256-cfb8 (8 비트) (및 AES-128 및 192와 유사한 모드)을 사용합니다. 따라서 PHP 코드에서 128 비트 cfb를 사용하고 있습니다.

파이썬 라이브러리는 AES.newsegment_size 인수를 허용하지만, 기본은 , 그래서 당신은 두 가지 버전으로 다른 모드를 사용하고 있습니다.

은 PHP 코드의 출력을 해독 파이썬 코드를 얻을 암호 오브젝트 (128)의 세그먼트 크기를 추가하는 방법 :. NB 이것이 PyCrypto의 PyCryptodome fork 최신을 사용 (

cipher = AES.new(encryption_key, AES.MODE_CFB, iv, segment_size=128) 

PyCrypto가 있습니다 . 여기에 버그가 작동하지 않습니다)

다른 방법으로, 암호를 설정하여 CFB-8을 사용하는 PHP 코드를 얻을 수있다() 분명히, 모두를 변경하지 마십시오 :

$encrypted = openssl_encrypt($data, 'aes-256-cfb8', $encryption_key, 1, $iv); 
+0

완벽하게 작동합니다. 더 좋은 방법이 있습니까? 같은 파이썬에서 모든 openssl 래퍼 내가 암호화 유형을 추측하려고 대신 같은 일을 할 수있는, 내가 암호/해독 방법을 재작 성하지 않을 수 있도록 castes - cbc에 AES에서 PHP 코드 변경 암호를 말할 수 있습니까? –

+0

멋진 답변,이 문제는 segment_size와 관련이 있지만 변경 방법은 없다고 생각합니다. – georgexsh