2016-05-14 1 views
1

Je rencontre des problèmes avec mon système de connexion. Si je définis mon mot de passe utilisateur sur 'TestPassword1234', 'TestPassword' sera accepté comme mot de passe. Après avoir testé un peu plus, j'ai découvert que le code suivant entraînerait la création de deux hachages identiques même si la chaîne passée est pas la même.PHP Le hachage du mot de passe retourne la même valeur

Il est important de savoir que tous les sels utilisés sont générés par cette fonction. Un est généré par test et le même est utilisé pour hacher les deux chaînes (comme ce serait le cas lors de la connexion d'un utilisateur).

function GUID() { 
    if (function_exists('com_create_guid') === true) { return trim(com_create_guid(), '{}'); } 

    return sprintf('%04X%04X-%04X-%04X-%04X-%04X%04X%04X', mt_rand(0, 65535), mt_rand(0, 65535), mt_rand(0, 65535), mt_rand(16384, 20479), mt_rand(32768, 49151), mt_rand(0, 65535), mt_rand(0, 65535), mt_rand(0, 65535)); 
} 

La fonction ci-dessus provient d'une question de débordement de pile, je ne sais pas lequel.

Ce n'est pas le cas si le mot de passe est fondamentalement modifié, voir ci-dessous pour les tests.

L'extrait suivant présente deux mots de passe différents résultant du même hachage.

$guid = GUID(); 

echo(crypt("TestPassword1234", $guid)); //455nKS7NToPuY 
echo("<br />"); 
echo(crypt("TestPassword", $guid)); //455nKS7NToPuY (the same!) 

Cet extrait montre deux mots de passe différents qui ne résultent pas dans le même résultat, même si elles suivent un schéma similaire à l'extrait ci-dessus

$guid = GUID(); 

echo(crypt("Test1234", $guid)); //BBWxwWzIXAOQI 
echo("<br />"); 
echo(crypt("Test", $guid)); //BBhe4TjDcO5XA (different...) 

Je suppose que le problème provient de l'utilisation du Fonction GUID. Peut-être est-il défectueux ou prend uniquement en charge un mot de passe d'une longueur maximale de x. Je n'ai aucune idée et ne peux pas traquer la question SO je l'ai trouvé.

L'aide est très appréciée.

+2

Utilisez 'password_hash' à la place.Vous ne devriez pas générer de sel vous-même car 'password_hash' génère automatiquement un sel sûr pour vous. –

+0

Vous avez trouvé cette fonction ici - http://php.net/manual/en/function.com-create-guid.php#99425 – Drakes

+0

Je ne peux pas utiliser 'password_hash', mon hébergeur utilise une version de PHP qui n » t avoir cette fonction. – Harry

Répondre

3

Pour utiliser crypt(), vous devez respecter l'un des formats de sel d'algorithme répertoriés dans le manuel. Vous ne suivez pas l'un des formats et en tant que tel PHP réduit votre sel aux deux premiers caractères, et le calcule en utilisant l'algorithme DES. DES n'utilise que les 8 premiers caractères et en tant que tel, vous ne faites que hacher deux fois "TestPass" avec le même sel.

La meilleure chose à faire est d'utiliser password_hash() à la place. Cependant, comme vous l'avez mentionné, votre hôte ne prend pas en charge password_hash().

Si crypt() est le choix final, vous aurez besoin de formater un sel correctement. Cependant, le meilleur des algorithmes à choisir avec crypt() permet seulement un maximum de 16 caractères pour le sel. En tant que tel, l'utilisation d'un GUID n'est pas le meilleur choix car la plupart des données ne sont pas utilisées.

Voici un exemple en utilisant un générateur aléatoire d'octets sécurisé, Cela ne fonctionnera que sur PHP 5.3.2 et au-delà:

function newSalt() { 
    $salt = bin2hex(openssl_random_pseudo_bytes (8)); 
    return '$5$'.$salt; 
} 


$salt1 = newSalt(); 
$salt2 = newSalt(); 

echo(crypt("TestPassword1234", $salt1)); 
echo("<br />"); 
echo(crypt("TestPassword", $salt2)); 

Vous pouvez stocker le sel pour utiliser plus tard en stockant les valeurs générées à partir newSalt (

Édition: L'installation de PHP d'OP est trop ancienne pour les implémentations correctes. Je suggère fortement de trouver un serveur qui supporte une version supérieure. J'espère que mon exemple vous a aidé, vous ou quelqu'un d'autre, ainsi que le raisonnement dû aux similitudes de mot de passe d'origine.

+0

En essayant d'utiliser ce code, j'obtiens une erreur: 'Appel à la fonction indéfinie random_bytes()' – Harry

+2

@Harry Je n'ai pas remarqué que 5.2 ne supporte ni random_bytes, ni l'algorithme SHA pour crypt() Votre meilleur pari est de choisir un nouvel hôte qui a une version plus à jour ou un hôte local si vous ne faites que déconner. Il y a quelques choses aléatoires différentes que vous pourriez faire pour une telle version ancienne, mais aucune de celles que je suis disposé à afficher en raison de leurs insécurités et de leurs mauvaises pratiques. – BinaryEvolved

+1

Eh bien, il semble que je suis foutu ... Merci quand même. – Harry