2011-08-23 3 views
2

Normalement, si j'ai un mot de passe, je voudrais utiliser ce pseudo-code:Comment l'argument sel et la valeur de retour de la fonction crypt() de PHP fonctionnent-ils?

$password = "this is the user's password"; 
/***/ 
$salt = GenerateSalt(); 
$hash = Hash($password); 
$hash = Hash($hash . $salt); 

Cependant, si je comprends bien, PHP a une fonction crypt() qui prend un sel ainsi que le nombre d'itérations d'un algorithme particulier. Apparemment, vous êtes supposé passer le hachage retourné de cryptencrypt comme le sel. Je ne comprends pas cela.

Quelqu'un peut-il clarifier comment fonctionne la crypte? Est-ce que je dois encore ajouter mon propre sel et ressasser? Dans ce cas, est-ce que j'utiliserais juste un sel fixe pour la crypte, et ensuite générerais une crypte séparée pour chaque utilisateur? Ou le paramètre $salt de crypt s'en occupe-t-il pour moi?

+1

Veuillez noter que vous devriez * PHP's ['crypt'] (http: // us2. php.net/manual/fr/function.crypt.php) ne peut pas être utilisé avant la version 5.3 *. Vous voulez toujours utiliser les préfixes '$ 2a $', '$ 5 $' ou '$ 6 $' pour obtenir respectivement Blowfish, SHA-256 ou SHA-512, et ceux-ci ne sont pas garantis dans les versions antérieures. Veuillez lire la page de manuel pour plus de détails. – Charles

+0

Sachez également que crypt est cassé dans PHP 5.3.7 pour MD5. Ils viennent de sortir le correctif 5.3.8 –

Répondre

5

La sortie de crypt se compose de:

  • (éventuellement un identifiant d'algorithme + charge facteur)
  • le sel pour l'algorithme utilisé
  • le vrai hachage

Lorsque vous passez cette sortie als « sel » retour à crypt, il extraira l'algorithme droite et le sel, et les utiliser pour l'opération. S'il n'y a qu'un algorithme mentionné, il utilise celui-ci et génère du sel aléatoire. Sinon, il choisira un algorithme par défaut et générera du sel aléatoire. La partie hash du paramètre sel passé est ignorée.

Donc, vous pouvez simplement comparer votre stored_hash avec crypt (mot de passe, stored_hash) - s'il est égal, il a probablement été le bon mot de passe.

Voici une explication de pseudo-code (dans la syntaxe comme PHP) comment fonctionne crypte:

function crypt($password, $salt) 
{ 
    if (substr($salt,0 1) == "_") { 
    $count = substr($salt, 1, 4); 
    $real_salt = substr($salt, 5, 4); 
    return "_" . $count . $real_salt . crypt_ext_des($password, $count, $salt); 
    } 
    if(substr($salt, 0, 3) == "$1$") { 
    list($ignored, $real_salt, $ignored) = explode("$", $salt); 
    return "$1$" . $real_salt . "$" . crypt_md5($password, $real_salt); 
    } 
    if(substr($salt, 0, 4) == "$2a$") { 
     $cost = substr($salt, 4, 2); 
     $real_salt = substr($salt, 7, 22); 
     return "$2a$" . $cost . "$" . $real_salt . crypt_brypt($password, $real_salt, $cost); 
    } 
    // ... SHA256 and SHA512 analogons 

    // no match => STD_DES 
    $real_salt = substr($salt, 0, 2); 
    return $real_salt . crypt_std_des($password, $real_salt); 
} 

Les différentes fonctions de crypt_xxx font alors le vrai travail, en fonction de l'algorithme. (En fait, la génération de sel aléatoire est manquante dans cette description.Cela sera fait si le $ real_salt est vide.)

+0

Donc le "hachage" retourné est en fait à la fois un sel et un hachage, et typiquement dans une base de données MySQL par exemple, je voudrais juste stocker cela comme une valeur? –

+0

Tous les identifiants d'algorithme, sel et hachage. Et oui, vous stockez la valeur de retour entière dans la base de données comme une valeur varchar. –

0

crypte est hachage à sens unique, comme MD5

utiliser comme indiqué dans le manuel

<?php 
$password = crypt('mypassword'); // let the salt be automatically generated 

/* You should pass the entire results of crypt() as the salt for comparing a 
    password, to avoid problems when different hashing algorithms are used. (As 
    it says above, standard DES-based password hashing uses a 2-character salt, 
    but MD5-based hashing uses 12.) */ 
if (crypt($user_input, $password) == $password) { 
    echo "Password verified!"; 
} 
?> 
+0

C'était exactement ma question. 'if (crypt ($ user_input, $ password) == $ mot de passe)' n'a pas vraiment de sens pour moi. Pourquoi passez-vous '$ password', qui était le hachage, comme le sel? –

+0

crypt ('mypassword') crée du sel, pas un mot de passe. – genesis

Questions connexes