php - password - باسورد هاش




كيف تستخدم bcrypt لتجزئة كلمات المرور في PHP؟ (6)

التفكير الحالي: يجب أن تكون التجزئة هي الأبطأ المتاحة ، وليس الأسرع قدر الإمكان. هذا يمنع هجمات طاولة قوس قزح .

ذات صلة أيضًا ، ولكن احترازي: يجب ألا يكون لدى المهاجم مطلقًا إمكانية الوصول غير المحدود إلى شاشة تسجيل الدخول. لمنع ذلك: قم بإعداد جدول تتبع عنوان IP يسجل كل نتيجة مع URI. إذا كان هناك أكثر من 5 محاولات لتسجيل الدخول من عنوان IP نفسه في أي فترة بخمس دقائق ، قم بالحظر مع الشرح. النهج الثانوي هو أن يكون لديك نظام كلمة مرور ذو مستويين ، مثلما تفعل البنوك. يؤدي وضع قفل للأعطال في الممر الثاني إلى زيادة الأمان.

ملخص: إبطاء المهاجم باستخدام دالات هاش مستهلكة للوقت. يمكنك أيضًا حظر الدخول إلى عدد كبير جدًا من معلومات تسجيل الدخول الخاصة بك ، وإضافة طبقة ثانية من كلمة المرور.

بين الحين والآخر سمعت النصيحة "استخدم bcrypt لتخزين كلمات المرور في PHP ، قواعد bcrypt".

ولكن ما هو bcrypt ؟ لا تقدم PHP أي وظائف من هذا القبيل ، و babish Wikipedia حول أداة تشفير الملفات وعمليات البحث على شبكة الإنترنت تكشف فقط عن بعض تطبيقات Blowfish بلغات مختلفة. الآن mcrypt متوفر أيضًا في PHP عبر mcrypt ، ولكن كيف يساعد ذلك في تخزين كلمات المرور؟ Blowfish هو تشفير للأغراض العامة ، وهو يعمل طريقتين. إذا كان يمكن تشفيرها ، يمكن فك تشفيرها. تحتاج كلمات المرور إلى وظيفة تجزئة أحادية الاتجاه.

ما هو التفسير؟


بالنسبة إلى كلمات مرور OAuth 2 :

$bcrypt = new \Zend\Crypt\Password\Bcrypt;
$bcrypt->create("youpasswordhere", 10)

تعديل: 2013.01.15 - إذا كان الخادم الخاص بك يدعمه ، استخدم حل martinstoeckli بدلاً من ذلك.

الجميع يريد أن يجعل الأمر أكثر تعقيدًا مما هو عليه. تقوم الدالة crypt () بمعظم العمل.

function blowfishCrypt($password,$cost)
{
    $chars='./ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789';
    $salt=sprintf('$2y$%02d$',$cost);
//For PHP < PHP 5.3.7 use this instead
//    $salt=sprintf('$2a$%02d$',$cost);
    //Create a 22 character salt -edit- 2013.01.15 - replaced rand with mt_rand
    mt_srand();
    for($i=0;$i<22;$i++) $salt.=$chars[mt_rand(0,63)];
    return crypt($password,$salt);
}

مثال:

$hash=blowfishCrypt('password',10); //This creates the hash
$hash=blowfishCrypt('password',12); //This creates a more secure hash
if(crypt('password',$hash)==$hash){ /*ok*/ } //This checks a password

أعلم أنه يجب أن يكون واضحًا ، ولكن يُرجى عدم استخدام كلمة المرور ككلمة مرورك.


سوف تحصل على الكثير من المعلومات في ما يكفي مع جداول قوس قزح: ما تحتاج إلى معرفته عن مخططات كلمة المرور الآمنة أو إطار عمل PHP لكلمة السر المحمولة .

الهدف هو تجزئة كلمة المرور بشيء بطيء ، لذلك سيموت شخص ما يحصل على قاعدة بيانات كلمة المرور الخاصة بك في محاولة لإجبارها على إجبارها (تأخير 10 مللي ثانية لفحص كلمة المرور لا يمثل شيئًا بالنسبة لك ، والكثير من الأشخاص الذين يحاولون إجبارهم على إجبارهم). Bcrypt بطيء ويمكن استخدامه مع المعلمة لاختيار مدى بطئها.


لذا ، كنت ترغب في استخدام bcrypt؟ رائع! ومع ذلك ، مثل غيرها من مجالات التشفير ، لا ينبغي عليك أن تفعل ذلك بنفسك. إذا كنت بحاجة للقلق بشأن أي شيء مثل إدارة المفاتيح ، أو تخزين الأملاح أو توليد أرقام عشوائية ، فأنت تقوم بذلك بشكل خاطئ.

والسبب بسيط: إنه من السهل جدا أن يفسد bcrypt . في الواقع ، إذا نظرت إلى كل جزء من الشفرة تقريبًا في هذه الصفحة ، فستلاحظ أنه ينتهك واحدة على الأقل من هذه المشكلات الشائعة.

مواجهة ذلك ، تشفير صعب.

اتركها للخبراء. اترك الأمر للأشخاص الذين يعملون للحفاظ على هذه المكتبات. إذا كنت بحاجة إلى اتخاذ قرار ، فأنت تفعل ذلك بشكل خاطئ.

بدلا من ذلك ، مجرد استخدام مكتبة. توجد عدة تبعا لمتطلباتك.

المكتبات

في ما يلي تحليل لبعض واجهات برمجة التطبيقات الأكثر شيوعًا.

PHP 5.5 API - (متوفر لـ 5.3.7 فما فوق)

بدءًا من PHP 5.5 ، يتم تقديم واجهة برمجة تطبيقات جديدة لكلمات مرور التجزئة. هناك أيضا مكتبة توافق الرقائق صيانتها (عني) ل 5.3.7 +. هذا له فائدة من كونه استعراض النظراء وبسيطة للاستخدام التنفيذ.

function register($username, $password) {
    $hash = password_hash($password, PASSWORD_BCRYPT);
    save($username, $hash);
}

function login($username, $password) {
    $hash = loadHashByUsername($username);
    if (password_verify($password, $hash)) {
        //login
    } else {
        // failure
    }
}

حقا ، انها تهدف لتكون بسيطة للغاية.

مصادر:

Zend \ Crypt \ Password \ Bcrypt (5.3.2+)

هذه واجهة برمجة تطبيقات أخرى تشبه واجهة برمجة تطبيقات PHP 5.5 ، وتؤدي غرضًا مشابهًا.

function register($username, $password) {
    $bcrypt = new Zend\Crypt\Password\Bcrypt();
    $hash = $bcrypt->create($password);
    save($user, $hash);
}

function login($username, $password) {
    $hash = loadHashByUsername($username);
    $bcrypt = new Zend\Crypt\Password\Bcrypt();
    if ($bcrypt->verify($password, $hash)) {
        //login
    } else {
        // failure
    }
}

مصادر:

PasswordLib

هذا هو نهج مختلف قليلا لتجزئة كلمة المرور. بدلاً من مجرد دعم bcrypt ، يدعم PasswordLib عددًا كبيرًا من خوارزميات التجزئة. وهي مفيدة بشكل أساسي في السياقات حيث تحتاج إلى دعم التوافق مع الأنظمة القديمة والمتفاوتة التي قد تكون خارج نطاق سيطرتك. وهو يدعم عددًا كبيرًا من خوارزميات التجزئة. ويدعم 5.3.2+

function register($username, $password) {
    $lib = new PasswordLib\PasswordLib();
    $hash = $lib->createPasswordHash($password, '$2y$', array('cost' => 12));
    save($user, $hash);
}

function login($username, $password) {
    $hash = loadHashByUsername($username);
    $lib = new PasswordLib\PasswordLib();
    if ($lib->verifyPasswordHash($password, $hash)) {
        //login
    } else {
        // failure
    }
}

المراجع:

  • شفرة المصدر / التوثيق: GitHub

PHPASS

هذه طبقة تدعم bcrypt ، ولكنها تدعم أيضًا خوارزمية قوية إلى حد ما تكون مفيدة إذا لم يكن لديك الوصول إلى PHP> = 5.3.2 ... إنها تدعم بالفعل PHP 3.0+ (وإن لم يكن مع bcrypt).

function register($username, $password) {
    $phpass = new PasswordHash(12, false);
    $hash = $phpass->HashPassword($password);
    save($user, $hash);
}

function login($username, $password) {
    $hash = loadHashByUsername($username);
    $phpass = new PasswordHash(12, false);
    if ($phpass->CheckPassword($password, $hash)) {
        //login
    } else {
        // failure
    }
}

مصادر

ملاحظة: لا تستخدم بدائل PHPASS التي لم يتم استضافتها على openwall ، فهي مشاريع مختلفة !!!

حول BCrypt

إذا لاحظت ، تقوم كل واحدة من هذه المكتبات بإرجاع سلسلة واحدة. هذا بسبب كيفية عمل BCrypt داخليًا. وهناك طن من الإجابات حول ذلك. في ما يلي مجموعة مختارة قمت بكتابتها ، ولن أنسخها / ألصقها هنا ، ولكن ارتبط بـ:

يتم إحتوائه

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

مرة أخرى ، إذا كنت تستخدم crypt() مباشرة ، فمن المحتمل أنك تقوم بشيء خاطئ. إذا كانت شفرتك تستخدم hash() (أو md5() أو sha1() ) مباشرة ، فأنت تقريبًا تفعل شيئًا خاطئًا.

مجرد استخدام مكتبة ...


يمكنك إنشاء تجزئة ذات اتجاه واحد مع bcrypt باستخدام الدالة crypt() في PHP وتمريرها في ملح Blowfish مناسب. أهم معادلة كاملة هي أن أ) الخوارزمية لم يتم اختراقها و B) ملحت كل كلمة مرور بشكل صحيح . لا تستخدم ملحًا على مستوى التطبيق. التي تفتح تطبيقك بالكامل للهجوم من مجموعة واحدة من جداول راينبو.

فب - وظيفة القبو





bcrypt