سؤال

في محاولة لكتابة بضع وظائف تشفير ملف أو فك تشفيرها وستتأستخدم الفئة الموجودة هنا لمحاولة إنجاز هذا:

http://www.itnewb.com/v/php-encryption-edecryption-using-the-mcrypt-library-libmcrypt.

يبدو أن وظيفة التشفير أدناه تعمل، حيث يبدو أنها تشفير الملف ووضعها في الدليل المقصود. أحاول فك تشفير الملف الآن، وتموت فقط مع الرسالة "فشل في إكمال فك التشفير" (والذي يتم ترميزه هناك ...) لا يوجد شيء في سجلات خطأ PHP، لذلك لست متأكدا من سبب عدم الفشل ، ولكن كما Mcrypt جديد تماما بالنسبة لي، فأنا أكثر من ميلا في الاعتقاد أنني أفعل شيئا خاطئا هنا ...

فيما يلي الوظائف:

//ENCRYPT FILE
    function encryptFile() {
        global $cryptastic;
        $pass = PGPPASS;
        $salt = PGPSALT;
        $key = $cryptastic->pbkdf2($pass, $salt, 1000, 32) or die("Failed to generate secret key.");

        if ($handle = opendir(PATH.'/ftpd')) {
            while (false !== ($file = readdir($handle))) {
                if ($file != "." && $file != "..") {
                    $newfile = PATH.'/encrypted/'.$file.'.txt';
                    $msg = file_get_contents(PATH.'/ftpd/'.$file);
                    $encrypted = $cryptastic->encrypt($msg, $key) or die("Failed to complete encryption.");
                    $nfile = fopen($newfile, 'w');
                    fwrite($nfile, $encrypted);
                    fclose($nfile);
                    unlink(PATH.'/ftpd/'.$file);

                }
            }
            closedir($handle);
        }       


//DECRYPT FILE
    function inFTP() {
        global $cryptastic;
        $pass = PGPPASS;
        $salt = PGPSALT;
        $key = $cryptastic->pbkdf2($pass, $salt, 1000, 32) or die("Failed to generate secret key.");

        if ($handle = opendir(PATH.'/encrypted')) {
            while (false !== ($file = readdir($handle))) {
                if ($file != "." && $file != "..") {
                    $newfile = PATH.'/decrypted/'.$file;
                    $msg = PATH.'/encrypted/'.$file;
                    $decrypted = $cryptastic->decrypt($msg, $key) or die("Failed to complete decryption.");
                    $nfile = fopen($newfile, 'w');
                    fwrite($nfile, $decrypted);
                    fclose($nfile);
                    //unlink(PATH.'/encrypted/'.$file);

                }
            }
            closedir($handle);
        }       
        //$crypt->decrypt($file);
    }
هل كانت مفيدة؟

المحلول

جرب فئة PHP5 هذه للتشفير باستخدام MCRYPT. في هذه الحالة، يستخدم تشفير AES. سترغب في تغيير المفتاح لكل موقع تستخدمه عليه. إذا كنت لا تستخدمه على الأقل قد يرشدك في كتابة نسختك الخاصة منه.

<?php

class Encryption
{
    const CIPHER = MCRYPT_RIJNDAEL_128; // Rijndael-128 is AES
    const MODE   = MCRYPT_MODE_CBC;

    /* Cryptographic key of length 16, 24 or 32. NOT a password! */
    private $key;
    public function __construct($key) {
        $this->key = $key;
    }

    public function encrypt($plaintext) {
        $ivSize = mcrypt_get_iv_size(self::CIPHER, self::MODE);
        $iv = mcrypt_create_iv($ivSize, MCRYPT_DEV_URANDOM);
        $ciphertext = mcrypt_encrypt(self::CIPHER, $this->key, $plaintext, self::MODE, $iv);
        return base64_encode($iv.$ciphertext);
    }

    public function decrypt($ciphertext) {
        $ciphertext = base64_decode($ciphertext);
        $ivSize = mcrypt_get_iv_size(self::CIPHER, self::MODE);
        if (strlen($ciphertext) < $ivSize) {
            throw new Exception('Missing initialization vector');
        }

        $iv = substr($ciphertext, 0, $ivSize);
        $ciphertext = substr($ciphertext, $ivSize);
        $plaintext = mcrypt_decrypt(self::CIPHER, $this->key, $ciphertext, self::MODE, $iv);
        return rtrim($plaintext, "\0");
    }
}

الاستعمال:

$key = /* CRYPTOGRAPHIC!!! key */;
$crypt = new Encryption($key);
$encrypted_string = $crypt->encrypt('this is a test');
$decrypted_string = $crypt->decrypt($encrypted_string); // this is a test

ملاحظات:

  • هذه الفئة ليست آمنة للاستخدام مع البيانات الثنائية (التي قد تنتهي في NUL BYTES)
  • لا توفر هذه الفئة تشفير مصادق.

نصائح أخرى

في حين أن Johns Answer هو جيد، فإن استخدام ترميز Base64 لمجرد إصلاح مشكلة السلامة الثنائية هو المبالغة وستجعل الملفات المشفرة 33٪ أكبر من الأصل. فيما يلي تطبيق PHP الخاص بي لتنسيق ملف Crypt AES الذي يحل جميع القضايا المذكورة أعلاه بشفافية.

https://github.com/philios33/php-aes-file-encryption.

إنها آمنة ثنائية وتشمل التشفير المصادق عليه. نظرا لأنه يستخدم تنسيق ملف Crypt Open Source AES (.AES) متوافقا تماما مع برنامج .AES الآخر.

https://www.aescrypt.com/

الواجهة بسيطة جدا سواء كنت تشفير أو فك تشفيرها. أنت فقط تعطيه ملف المصدر وكلمة المرور.

يجب أن لا تستخدم mcrypt لتشفير / فك تشفير البيانات. كما هو موضح في سؤالك، وفي الإجابة المقبولة، لا تتم مصادقة البيانات، مما يعني أنه سيسقط ضحية لمختار الهجمات المشفرين.

علاوة على ذلك، تم إجراء الكثير من الجهود للتأكد من أن المطورين قد جمعوا البدائية التشفير بشكل صحيح. على هذا النحو، بدلا من Mcrypt، يجب أن تستخدم Libsodium لمشاريع PHP الخاصة بك. Libsodium هو شوكة من NACL. تتم كتابة NACL / Libsodium لإزالة الكثير من المزالق التشفير الذي يجده المطورون أنفسهم، مثل هجمات التوقيت مع التحقق من علامات Mac.

تم إهمال MCRYPT في PHP 7.1، و LIBSODIM هو الطريقة المفضلة للتعامل مع التشفير في PHP.

باستخدام Libsodium في مشروع PHP الخاص بك سهل وآمن. كتب Scott Arcisewski كتابا واسع النطاق لاستخدام Libsodium مع PHP https://paragonie.com/book/pecl-libsodium.. وبعد الأمر يستحق القراءة لأي شخص يقوم بتشفير فب.

cakephp. لديه جيدة جدا التنفيذ من rijndael. أنا لا نشر الرمز مباشرة هنا لأنه غير متأكد من التداعيات القانونية.

وهنا مستندات API ل Security::rijndael() طريقة.

إذا تم ترميز ملف، فستحتاج إلى base64_encode() قبل الاتصال بهذه الطريقة مع 'encrypt'، و base64_decode() بعد استدعاء هذه الطريقة مع "decrypt'

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top