วิธีถอดรหัสสตริงที่เข้ารหัสโดยใช้ openssl_decrypt

Sep 18 2020

ฉันกำลังพยายามพัฒนาโปรแกรม php ที่เข้ารหัสข้อมูลบางอย่างซึ่งสามารถถอดรหัสได้ในภายหลัง อย่างไรก็ตามฉันมีปัญหาในการถอดรหัสข้อมูลด้วย PHP โดยใช้อัลกอริทึม AES-256-CBC โดยใช้เมธอด openssl_decrypt () ใน PHP การเข้ารหัสใช้งานได้ แต่เมื่อฉันพยายามถอดรหัสมันทำให้ฉันเกิดข้อผิดพลาด: -
hash_equals (): คาดว่า known_string เป็นสตริงบูลที่กำหนดในบรรทัด 44

รหัสของฉันด้านล่าง:

<?php

class Encryption{
    
    protected $data, $encryption_type, $key, $iv;

    public function __construct(){
        $mydata = "Is this safe"; $encryption = $this->secured_encryption($mydata);

        // Decrypting data
        $data_to_decrypt = $encryption;
        $this->decrypt_data($data_to_decrypt);
    }

    public function secured_encryption($data){ $this->data = $data; $this->encryption_type = "AES-256-CBC"; // cipher algorithm
        $this->key = ['6d2d823df2e08c0d3cdf70f148998d49', 'fdb3a18c7b0a322fdb3a18c7b0a320d3']; $this->iv = openssl_random_pseudo_bytes(openssl_cipher_iv_length($this->encryption_type)); $encrypted_data = openssl_encrypt($this->data, $this->encryption_type, $this->key[0], OPENSSL_RAW_DATA, $this->iv);
        $final_encryption = hash_hmac('SHA3-512', $encrypted_data, $this->key[1], true); $output = base64_encode($this->iv.$final_encryption.$encrypted_data); if($output):
            print("Encrypted data: {$output}<br/>"); else: print("Error in encrypting data"); endif; } public function decrypt_data($data){
        $this->data = base64_decode($data);
        $this->encryption_type = "AES-256-CBC"; // cipher algorithm $this->key = ['6d2d823df2e08c0d3cdf70f148998d49', 'fdb3a18c7b0a322fdb3a18c7b0a320d3'];
        $ivlen = openssl_cipher_iv_length($this->encryption_type);
        $this->iv = substr($this->data, 0, $ivlen); $hmac = substr($this->data, $ivlen, $sha2len = 32); $decrypt_data = substr($this->data, $ivlen, $sha2len); $final_decryption = openssl_decrypt($decrypt_data, $this->encryption_type, $this->key[0], OPENSSL_RAW_DATA, $this->iv);
        $calcmac = hash_hmac('SHA3-512', $decrypt_data, $this->key[1], true); if(hash_equals($hmac, $calcmac)): print($final_decryption);
        else:
            print("Error in decrypting data");
        endif;
    }
}

$encryption = Encryption();

?> 

ใครก็ได้ที่จะช่วยฉัน

คำตอบ

3 Topaco Sep 18 2020 at 15:19

มีปัญหาเล็กน้อยในโค้ด:

  • มีคำสั่งส่งคืนที่ขาดหายไปในsecured_encryptionเมธอด นี้เป็นทริกเกอร์สำหรับข้อผิดพลาด ( hash_equals (): คาด known_string จะเป็นสตริงบูลที่กำหนด ) เนื่องจาก$hmacไม่ได้มีสตริง falseแต่ ในตอนท้ายsecured_encryptionคุณต้องเพิ่ม:

    return $output;
    

    ด้วยวิธีนี้การเข้ารหัสจึงใช้งานได้ แต่การถอดรหัสยังใช้ไม่ได้

  • เมื่อใช้การแยก HMac decrypt_dataด้วยความยาวที่ไม่ถูกต้อง SHA3-512 ผลลัพธ์เป็น 512 บิตนั่นคือแฮช 64 ไบต์เช่น:

    $hmac = substr($this->data, $ivlen, $sha2len = 32);
    

    จะต้องถูกแทนที่ด้วย:

    $hmac = substr($this->data, $ivlen, $sha2len = 64);   
    
  • เมื่อแยกข้อมูลเริ่มต้นที่ตำแหน่ง$ivlen + $sha2lenและพิจารณาทุกอย่างจนจบเช่น:

    $decrypt_data = substr($this->data, $ivlen, $sha2len); 
    

    จะต้องถูกแทนที่ด้วย:

    $decrypt_data = substr($this->data, $ivlen + $sha2len);
    

ด้วยการเปลี่ยนแปลงเหล่านี้ทุกอย่างใช้งานได้และผลลัพธ์จะมีลักษณะดังนี้:

Encrypted data: uTjcPmLK8jTktJ0oy5AqB40d5YFuAbgXMHfNEM6+JOH+DtyYAhckcv3mkLhdOvUqPlriKqYjHO6cpJI3ZdoTSS4lqDr0eH0MMiUpJMSXcan81irvobcdIV+rvaMPPRj7
Is this safe 

โดยวิธีการที่นอกเหนือจาก ciphertext ยัง IV ควรได้รับการรับรองความถูกต้องดูที่นี่ นอกจากนี้ยังมีโหมดการทำงานที่พิสูจน์ตัวตนได้ซึ่งให้การรักษาความลับเช่นเดียวกับการพิสูจน์ตัวตนเช่นGCM (เช่นaes-256-gcm) s ความคิดเห็นของปีเตอร์ คุณสามารถตรวจสอบได้openssl_get_cipher_methods()ว่าอัลกอริทึม / โหมดใดที่มีอยู่ในสภาพแวดล้อม