Безопасный хэш и соль для паролей PHP

В настоящее время говорят, что MD5 частично небезопасен. Принимая это во внимание, я хотел бы знать, какой механизм использовать для защиты паролем.

Этот вопрос, Является ли «двойное хеширование» паролем менее безопасным, чем его однократное хеширование? предполагает, что многократное хеширование может быть хорошей идеей, тогда как Как реализовать парольную защиту для отдельных файлов? предлагает использовать соль.

Я использую PHP. Мне нужна безопасная и быстрая система шифрования паролей. Хеширование пароля в миллион раз может быть безопаснее, но также и медленнее. Как добиться хорошего баланса между скоростью и безопасностью? Кроме того, я бы предпочел, чтобы результат содержал постоянное количество символов.

  1. Механизм хеширования должен быть доступен в PHP.
  2. Это должно быть безопасно
  3. Он может использовать соль (в этом случае все соли одинаково хороши? Есть ли способ получить хорошие соли?)

Кроме того, следует ли хранить в базе данных два поля (например, одно с использованием MD5, а другое с использованием SHA)? Будет ли это безопаснее или опаснее?

На случай, если я не совсем понял, я хочу знать, какую хеш-функцию (-ы) использовать и как выбрать хорошую соль, чтобы иметь безопасный и быстрый механизм защиты паролем.

Связанные вопросы, которые не совсем охватывают мой вопрос:

В чем разница между SHA и MD5 в PHP
Простое шифрование пароля
Безопасные методы хранения ключей, паролей для asp.net
Как бы вы реализовали соленые пароли в Tomcat 5.5

openwall.com/phpass тоже очень хорошая библиотека
Alfred 02.07.2011 05:02

Md5 теперь совершенно небезопасно

JqueryToAddNumbers 06.07.2012 09:14

@NSAwesomeGuy Это зависит от того, для чего вы его используете. Несложные пароли MD5 без солей и грубой силы, конечно, тривиально, но при приличном подсолении все равно чрезвычайно непрактично построить радужную таблицу для быстрого взлома наборов паролей, а грубая сила - бесполезна.

Craig Ringer 24.08.2012 10:54

PHP 5.5+ имеет безопасный хэш пароля, встроенный в php.net/manual/en/function.password-hash.php

Terence Johnson 01.01.2013 20:09
php.net/faq.password
hakre 27.06.2013 04:58

Также см. Openwall Портативный фреймворк для хеширования паролей PHP (PHPass). Он защищен от ряда распространенных атак на пароли пользователей.

jww 12.10.2014 03:26
Стоит ли изучать PHP в 2026-2027 годах?
Стоит ли изучать PHP в 2026-2027 годах?
Привет всем, сегодня я хочу высказать свои соображения по поводу вопроса, который я уже много раз получал в своем сообществе: "Стоит ли изучать PHP в...
Symfony Station Communiqué - 7 июля 2023 г
Symfony Station Communiqué - 7 июля 2023 г
Это коммюнике первоначально появилось на Symfony Station .
Оживление вашего приложения Laravel: Понимание режима обслуживания
Оживление вашего приложения Laravel: Понимание режима обслуживания
Здравствуйте, разработчики! В сегодняшней статье мы рассмотрим важный аспект управления приложениями, который часто упускается из виду в суете...
Установка и настройка Nginx и PHP на Ubuntu-сервере
Установка и настройка Nginx и PHP на Ubuntu-сервере
В этот раз я сделаю руководство по установке и настройке nginx и php на Ubuntu OS.
Коллекции в Laravel более простым способом
Коллекции в Laravel более простым способом
Привет, читатели, сегодня мы узнаем о коллекциях. В Laravel коллекции - это способ манипулировать массивами и играть с массивами данных. Благодаря...
Как установить PHP на Mac
Как установить PHP на Mac
PHP - это популярный язык программирования, который используется для разработки веб-приложений. Если вы используете Mac и хотите разрабатывать...
1 197
7
232 233
12

Ответы 12

Я бы не стал хранить хешированный пароль двумя разными способами, потому что тогда система будет по крайней мере такой же слабой, как самый слабый из используемых алгоритмов хеширования.

не для хеширования паролей. злоумышленнику достаточно взломать один хэш, чтобы получить пароль. в любом случае это спорный вопрос, поскольку ни у MD5, ни у SHA1 нет каких-либо практических разрывов в сценарии паролей.

frankodwyer 31.12.2008 02:05

извините, я неправильно истолковал ваш ответ как рекомендацию использовать два хэша ... вы на самом деле правы. Использование двух хешей ослабляет систему в случае пароля, поскольку им нужно только взломать более слабый хеш.

frankodwyer 31.12.2008 02:37

Я обычно использую SHA1 и соль с идентификатором пользователя (или другой информацией, специфичной для пользователя), а иногда я дополнительно использую постоянную соль (так что у меня есть 2 части соли).

SHA1 теперь также считается несколько скомпрометированным, но в гораздо меньшей степени, чем MD5. Используя соль (любую соль), вы предотвращаете использование универсального радужный стол для атаки на ваши хэши (некоторые люди даже добились успеха, используя Google как своего рода радужную таблицу при поиске хеша). Злоумышленник может сгенерировать радужную таблицу, используя вашу соль, поэтому вам следует включить соль для конкретного пользователя. Таким образом, им придется сгенерировать радужную таблицу для каждой записи в вашей системе, а не только для всей вашей системы! С таким посолом даже MD5 достаточно безопасен.

постоянная соль - не самая лучшая идея ... возможно, не фатальный недостаток, но излишне ослабляет схему.

frankodwyer 31.12.2008 02:08

MD5 и SHA1 работают быстро, так что это плохой вариант.

CodesInChaos 05.03.2014 16:40

Google говорит, что SHA256 доступен для PHP.

Обязательно используйте соль. Я бы рекомендовал использовать случайные байты (и не ограничиваться символами и числами). Как обычно, чем дольше вы выбираете, тем безопаснее и медленнее становится. Думаю, 64 байта должно хватить.

Кому-то хватит 64 бита?

Konerak 21.06.2011 16:32

@Konerak, я вернусь к этому через 20 лет. :) Но да, SHA256 действительно доступен. Если вы хотите узнать, насколько безопасен SHA256, вы можете проверить это: security.stackexchange.com/questions/90064/…

Vincent Edward Gedaria Binua 04.12.2015 01:18

SHA1 и соли должно хватить (в зависимости, естественно, от того, кодируете ли вы что-то для Форт-Нокс или систему входа в систему для вашего списка покупок) в обозримом будущем. Если SHA1 вам не подходит, используйте SHA256.

Идея соли состоит в том, чтобы, так сказать, вывести результаты хеширования из равновесия. Известно, например, что MD5-хеш пустой строки - это d41d8cd98f00b204e9800998ecf8427e. Итак, если кто-то с достаточно хорошей памятью увидит этот хеш и узнает, что это хеш пустой строки. Но если строка «соленая» (скажем, со строкой «MY_PERSONAL_SALT»), хеш для «пустой строки» (например, «MY_PERSONAL_SALT») становится aeac2612626724592271634fb14d3ea6, следовательно, неочевидный для обратной трассировки. Я пытаюсь сказать, что лучше использовать соль любой, чем не использовать. Следовательно, не так важно знать соль который для использования.

На самом деле есть сайты, которые делают именно это - вы можете передать ему хеш (md5), и он выдаст известный открытый текст, который генерирует этот конкретный хеш. Если бы вы получили доступ к базе данных, в которой хранятся простые md5-хэши, вам было бы тривиально ввести хеш для администратора такой службы и войти в систему. Но если бы пароли были солеными, такая служба стала бы неэффективен.

Кроме того, двойное хеширование обычно считается плохим методом, поскольку оно уменьшает пространство результатов. Все популярные хэши имеют фиксированную длину. Таким образом, вы можете иметь только конечные значения этой фиксированной длины, и результаты станут менее разнообразными. Этот мог можно рассматривать как еще одну форму засолки, но я бы не рекомендовал ее.

Целевой сайт не должен содержать ничего слишком важного (это не банк), но все же я бы предпочел, чтобы он был защищен.

luiscubal 31.12.2008 01:24

двойное хеширование не уменьшает пространство результатов. итеративное хеширование является обычным средством защиты от атак по словарю и грубой силы (это замедляет их гораздо больше, чем замедляет проверку пароля).

frankodwyer 31.12.2008 02:10

@frankodwyer: да, это плохо. sha1(sha1($foo)) эффективно уменьшает пространство вывода, потому что любое столкновение внутренней функции автоматически становится столкновением внешней. Ухудшение линейно, но это все еще вызывает беспокойство. Методы итеративного хеширования возвращают данные в каждый раунд, например $hash = sha1(sha1($salt . $password) . $salt). Но это все равно нехорошо ... Придерживайтесь PBKDF2 или Bcrypt ...

ircmaxell 13.09.2012 18:40

В конце концов, двойное хеширование с математической точки зрения не дает никакой пользы. Однако на практике это полезно для предотвращения атак на основе радужных таблиц. Другими словами, это не более выгодно, чем хеширование с использованием соли, которое требует гораздо меньше процессорного времени в вашем приложении или на вашем сервере.

Множественное хеширование также защищает от атак по словарю и грубой силы, то есть просто заставляет их вычислять больше времени.

frankodwyer 31.12.2008 02:00

двойное хеширование не даст вам значительного преимущества, но многократные итерации хеширования по-прежнему являются реальной защитой от атак по словарю и брюс-форса. Хэши паролей промышленной надежности используют более 1000 раундов. PBKDF1 PKCS # 5 предлагает минимум 1000 раундов.

Berk D. Demir 02.01.2009 01:17

Хотя на вопрос был дан ответ, я просто хочу повторить, что соли, используемые для хеширования, должны быть случайными, а не похожими на адрес электронной почты, как было предложено в первом ответе.

Дополнительное объяснение доступно на- http://www.pivotalsecurity.com/blog/password-hashing-salt-should-it-be-random/

Recently I had a discussion whether password hashes salted with random bits are more secure than the one salted with guessable or known salts. Let’s see: If the system storing password is compromised as well as the system which stores the random salt, the attacker will have access to hash as well as salt, so whether the salt is random or not, doesn’t matter. The attacker will can generate pre-computed rainbow tables to crack the hash. Here comes the interesting part- it is not so trivial to generate pre-computed tables. Let us take example of WPA security model. Your WPA password is actually never sent to Wireless Access Point. Instead, it is hashed with your SSID (the network name- like Linksys, Dlink etc). A very good explanation of how this works is here. In order to retrieve password from hash, you will need to know the password as well as salt (network name). Church of Wifi has already pre-computed hash tables which has top 1000 SSIDs and about 1 million passwords. The size is of all tables is about 40 GB. As you can read on their site, someone used 15 FGPA arrays for 3 days to generate these tables. Assuming victim is using the SSID as “a387csf3″ and password as “123456″, will it be cracked by those tables? No! .. it cannot. Even if the password is weak, the tables don’t have hashes for SSID a387csf3. This is the beauty of having random salt. It will deter crackers who thrive upon pre-computed tables. Can it stop a determined hacker? Probably not. But using random salts does provide additional layer of defense. While we are on this topic, let us discuss additional advantage of storing random salts on a separate system. Scenario #1 : Password hashes are stored on system X and salt values used for hashing are stored on system Y. These salt values are guessable or known (e.g. username) Scenario#2 : Password hashes are stored on system X and salt values used for hashing are stored on system Y. These salt values are random. In case system X has been compromised, as you can guess, there is a huge advantage of using random salt on a separate system (Scenario #2) . The attacker will need to guess addition values to be able to crack hashes. If a 32 bit salt is used, 2^32= 4,294,967,296 (about 4.2 billion) iterations will can be required for each password guessed.

Даже если злоумышленник получит соль, строка «sitealt: usersalt: password» по-прежнему устойчива к предварительно вычисленным таблицам, поскольку злоумышленнику необходимо сгенерировать таблицы для каждого пользователя (поэтому атака становится намного медленнее), если, конечно, конкретный пользователь подвергается нападению ...

luiscubal 12.02.2010 19:01

Что касается «Даже если злоумышленник поймет, что строка« sitealt: usersalt: password »по-прежнему устойчива к предварительно вычисленным таблицам», полностью согласен. Я хочу сказать, что sitealt, если он сделан случайным и длинным, сделает систему более безопасной, чем она (sitealt) предсказуема. Я видел, как некоторые люди рекомендовали использовать идентификатор электронной почты и т. д. В качестве соли, и я не одобряю этого.

Gaurav Kumar 13.02.2010 04:20

Вы пропустили то, что я написал изначально. Я сказал использовать случайный одноразовый номер, хранящийся вместе с записью, ПЛЮС адрес электронной почты. Добавление адреса электронной почты увеличивает энтропию для работы хакера. С тех пор я переписал свой ответ в пользу bcrypt.

Robert K 23.03.2012 05:15

Гораздо более короткий и безопасный ответ - вообще не пишите свой собственный механизм паролей, используйте проверенный и проверенный механизм.

  • PHP 5.5 или выше: password_hash () хорошего качества и является частью ядра PHP.
  • PHP 4.x (устаревший): библиотека OpenWall phpass намного лучше, чем большинство пользовательского кода, используемого в WordPress, Drupal и т. д.

У большинства программистов просто нет опыта для безопасного написания кода, связанного с криптографией, без введения уязвимостей.

Быстрая самопроверка: что такое растягивание пароля и сколько итераций следует использовать? Если вы не знаете ответа, вам следует использовать password_hash(), поскольку растяжение паролей теперь является важной функцией механизмов паролей из-за гораздо более быстрых процессоров и использования Графические процессоры и ПЛИС для взлома паролей со скоростью миллиарды догадок в секунду (с графическими процессорами).

Например, вы можете взломать все 8-значные пароли Windows за 6 часов, используя 25 графических процессоров, установленных на 5 настольных ПК. Это перебор, то есть перечисление и проверка каждый 8-значный пароль Windows, включая специальные символы, и не атака по словарю. Это было в 2012 году, а с 2018 года можно было использовать меньше графических процессоров или быстрее взламывать с помощью 25 графических процессоров.

Существует также множество атак с использованием радужных таблиц на пароли Windows, которые выполняются на обычных процессорах и очень быстры. Все это потому, что Windows по-прежнемуне солит и не растягивает ее пароли, даже в Windows 10 - не делайте той же ошибки, что и Microsoft!

Смотрите также:

  • отличный ответ с дополнительной информацией о том, почему password_hash() или phpass - лучший способ.
  • хорошая статья в блоге дает рекомендуемые «рабочие факторы» (количество итераций) для основных алгоритмов, включая bcrypt, scrypt и PBKDF2.

но эти системы более известны и, возможно, уже взломаны. но лучше делать самому, когда не знаешь, что делаешь.

JqueryToAddNumbers 12.02.2012 02:53

Что касается «эти системы более известны и, возможно, уже скомпрометированы» - нет причин, по которым хорошо спроектированная система аутентификации должна стать «уже скомпрометированной» только потому, что она более известна. Библиотеки, такие как phpass, написаны экспертами и подробно проверены многими людьми - тот факт, что они хорошо известны, сопровождается подробным обзором разными людьми и, скорее всего, означает, что они безопасны.

RichVel 16.02.2012 16:24

Учитывая недавние дампы хэшей паролей от LinkedIn, Last.fm и других, это весьма актуально. Вы попали в хорошую компанию, не зная, как написать собственный механизм паролей!

RichVel 05.07.2012 18:11

«вообще не пишите свой собственный механизм паролей» - но истинные параноики захотят написать свой собственный, чтобы свести к минимуму вероятность того, что у АНБ есть бэкдор.

PP. 12.09.2013 19:29

@PP - шансы, что проверенный алгоритм хеширования паролей имеет бэкдор АНБ, на мой взгляд, очень низок. Шансы того, что кто-то, не являющийся настоящим экспертом в области криптографии, напишет новый механизм хеширования паролей без других уязвимостей, намного ниже. И типичное веб-приложение использует только хеширование MD5 или SHA-1, что ужасно - даже в отличной книге Криса Шифлетта Essential PHP Security рекомендуется MD5 ...

RichVel 14.09.2013 14:55

phpass - НЕ лучший способ. Никогда не было и, скорее всего, никогда не будет. Я просмотрел код несколько лет назад, и он НЕ безопасен в Windows или любой платформе, где / dev / urandom недоступен. Когда дело доходит до безопасности, он НЕ следует передовым практикам, используя комбинацию md5 () и microtime (), когда он должен завершать приложение вместо того, чтобы делать ложные заявления о безопасности. Он не видел никаких обновлений с тех пор, как я просмотрел код, несмотря на то, что сам PHP продвигается вперед в области безопасности с bcrypt в ядре. Держитесь подальше от phpass.

CubicleSoft 08.02.2015 15:57

@CubicleSoft - можете ли вы порекомендовать другую библиотеку PHP для хеширования паролей? Если не будет лучшей библиотеки, phpass все равно будет лучше, чем подавляющее большинство пользовательского кода, использующего несоленый и нерастянутый MD5.

RichVel 09.02.2015 13:16

@RichVel - Функция password_hash (). Как упоминалось ранее, он встроен в ядро ​​PHP (также известное как / ext / standard).

CubicleSoft 15.03.2015 15:10

@CubicleSoft - password_hash () по умолчанию имеет значение bcrypt и имеет функцию стоимости для растягивания, поэтому это кажется хорошим для людей с PHP 5.5 или выше - php.net/manual/en/function.password-hash.php. phpass поддерживает более ранние версии PHP, которые, безусловно, лучше, чем собственный код большинство людей, построенный на MD5 и т. д.

RichVel 19.03.2015 11:55

Я использую Phpass, который представляет собой простой однофайловый класс PHP, который можно очень легко реализовать почти в каждом проекте PHP. См. Также H.

По умолчанию он использовал самое надежное шифрование, реализованное в Phpass, то есть bcrypt, и использовало другие способы шифрования вплоть до MD5, чтобы обеспечить обратную совместимость с такими фреймворками, как Wordpress.

Возвращенный хеш может быть сохранен в базе данных как есть. Пример использования для генерации хэша:

$t_hasher = new PasswordHash(8, FALSE);
$hash = $t_hasher->HashPassword($password);

Для проверки пароля можно использовать:

$t_hasher = new PasswordHash(8, FALSE);
$check = $t_hasher->CheckPassword($password, $hash);

Я просто хочу указать, что PHP 5.5 включает API хеширования паролей, который предоставляет оболочку для crypt(). Этот API значительно упрощает задачу хеширования, проверки и повторного хеширования паролей. Автор также выпустил пакет совместимости (в виде одного файла password.php, который вы просто используете require) для тех, кто использует PHP 5.3.7 и новее и хочет использовать его прямо сейчас.

На данный момент он поддерживает только BCRYPT, но нацелен на то, чтобы его можно было легко расширить, включив в него другие методы хеширования паролей, и поскольку метод и стоимость хранятся как часть хеша, изменения в вашем предпочтительном методе / стоимости хеширования не сделают недействительными текущие хеши, фреймворк автоматически будет использовать правильную технику / стоимость при проверке. Он также обрабатывает создание «безопасной» соли, если вы явно не определяете свою собственную.

API предоставляет четыре функции:

  • password_get_info() - возвращает информацию о заданном хэше
  • password_hash() - создает хеш пароля
  • password_needs_rehash() - проверяет, соответствует ли заданный хеш заданным параметрам. Полезно для проверки, соответствует ли хэш вашей текущей методике / схеме затрат, позволяя при необходимости повторно хешировать
  • password_verify() - проверяет соответствие пароля хешу

В настоящий момент эти функции принимают константы паролей PASSWORD_BCRYPT и PASSWORD_DEFAULT, которые на данный момент являются синонимами, с той разницей, что PASSWORD_DEFAULT «может измениться в новых версиях PHP, когда поддерживаются более новые, более сильные алгоритмы хеширования». Использование PASSWORD_DEFAULT и password_needs_rehash () при входе в систему (и повторное хеширование при необходимости) должно гарантировать, что ваши хэши достаточно устойчивы к атакам методом грубой силы, практически не выполняя для вас никакой работы.

Обновлено: Я только что понял, что это кратко упоминается в ответе Роберта К. Я оставлю этот ответ здесь, поскольку я думаю, что он предоставляет немного больше информации о том, как он работает, и о простоте использования, которую он обеспечивает для тех, кто не знает безопасности.

Я нашел идеальную тему по этому поводу здесь: https://crackstation.net/hashing-security.htm, я хотел, чтобы вы извлекли из этого пользу, вот исходный код, который также обеспечивает защиту от атак, основанных на времени.

<?php
/*
 * Password hashing with PBKDF2.
 * Author: havoc AT defuse.ca
 * www: https://defuse.ca/php-pbkdf2.htm
 */

// These constants may be changed without breaking existing hashes.
define("PBKDF2_HASH_ALGORITHM", "sha256");
define("PBKDF2_ITERATIONS", 1000);
define("PBKDF2_SALT_BYTES", 24);
define("PBKDF2_HASH_BYTES", 24);

define("HASH_SECTIONS", 4);
define("HASH_ALGORITHM_INDEX", 0);
define("HASH_ITERATION_INDEX", 1);
define("HASH_SALT_INDEX", 2);
define("HASH_PBKDF2_INDEX", 3);

function create_hash($password)
{
    // format: algorithm:iterations:salt:hash
    $salt = base64_encode(mcrypt_create_iv(PBKDF2_SALT_BYTES, MCRYPT_DEV_URANDOM));
    return PBKDF2_HASH_ALGORITHM . ":" . PBKDF2_ITERATIONS . ":" .  $salt . ":" . 
        base64_encode(pbkdf2(
            PBKDF2_HASH_ALGORITHM,
            $password,
            $salt,
            PBKDF2_ITERATIONS,
            PBKDF2_HASH_BYTES,
            true
        ));
}

function validate_password($password, $good_hash)
{
    $params = explode(":", $good_hash);
    if (count($params) < HASH_SECTIONS)
       return false; 
    $pbkdf2 = base64_decode($params[HASH_PBKDF2_INDEX]);
    return slow_equals(
        $pbkdf2,
        pbkdf2(
            $params[HASH_ALGORITHM_INDEX],
            $password,
            $params[HASH_SALT_INDEX],
            (int)$params[HASH_ITERATION_INDEX],
            strlen($pbkdf2),
            true
        )
    );
}

// Compares two strings $a and $b in length-constant time.
function slow_equals($a, $b)
{
    $diff = strlen($a) ^ strlen($b);
    for($i = 0; $i < strlen($a) && $i < strlen($b); $i++)
    {
        $diff |= ord($a[$i]) ^ ord($b[$i]);
    }
    return $diff === 0; 
}

/*
 * PBKDF2 key derivation function as defined by RSA's PKCS #5: https://www.ietf.org/rfc/rfc2898.txt
 * $algorithm - The hash algorithm to use. Recommended: SHA256
 * $password - The password.
 * $salt - A salt that is unique to the password.
 * $count - Iteration count. Higher is better, but slower. Recommended: At least 1000.
 * $key_length - The length of the derived key in bytes.
 * $raw_output - If true, the key is returned in raw binary format. Hex encoded otherwise.
 * Returns: A $key_length-byte key derived from the password and salt.
 *
 * Test vectors can be found here: https://www.ietf.org/rfc/rfc6070.txt
 *
 * This implementation of PBKDF2 was originally created by https://defuse.ca
 * With improvements by http://www.variations-of-shadow.com
 */
function pbkdf2($algorithm, $password, $salt, $count, $key_length, $raw_output = false)
{
    $algorithm = strtolower($algorithm);
    if (!in_array($algorithm, hash_algos(), true))
        die('PBKDF2 ERROR: Invalid hash algorithm.');
    if ($count <= 0 || $key_length <= 0)
        die('PBKDF2 ERROR: Invalid parameters.');

    $hash_length = strlen(hash($algorithm, "", true));
    $block_count = ceil($key_length / $hash_length);

    $output = "";
    for($i = 1; $i <= $block_count; $i++) {
        // $i encoded as 4 bytes, big endian.
        $last = $salt . pack("N", $i);
        // first iteration
        $last = $xorsum = hash_hmac($algorithm, $last, $password, true);
        // perform the other $count - 1 iterations
        for ($j = 1; $j < $count; $j++) {
            $xorsum ^= ($last = hash_hmac($algorithm, $last, $password, true));
        }
        $output .= $xorsum;
    }

    if ($raw_output)
        return substr($output, 0, $key_length);
    else
        return bin2hex(substr($output, 0, $key_length));
}
?>

Вы даете нам решение без использования, без использования

Michael 05.05.2016 05:55

Начиная с PHP 5.5, PHP имеет простые и безопасные функции для хеширования и проверки паролей, password_hash () и password_verify ().

$password = 'anna';
$hash = password_hash($password, PASSWORD_DEFAULT);
$expensiveHash = password_hash($password, PASSWORD_DEFAULT, array('cost' => 20));

password_verify('anna', $hash); //Returns true
password_verify('anna', $expensiveHash); //Also returns true
password_verify('elsa', $hash); //Returns false

Когда используется password_hash(), он генерирует случайную соль и включает ее в выводимый хэш (вместе со стоимостью и используемым алгоритмом). Затем password_verify() считывает этот хэш и определяет используемый метод соли и шифрования и проверяет его на соответствие предоставленному паролю в виде открытого текста. .

Предоставление PASSWORD_DEFAULT указывает PHP использовать алгоритм хеширования по умолчанию установленной версии PHP. Что именно означает алгоритм, который будет меняться со временем в будущих версиях, чтобы он всегда был одним из самых надежных доступных алгоритмов.

Увеличение стоимости (которая по умолчанию составляет 10) усложняет перебор хешей, но также означает, что создание хешей и проверка паролей по ним будет труднее для ЦП вашего сервера.

Обратите внимание, что даже несмотря на то, что алгоритм хеширования по умолчанию может измениться, старые хеши будут продолжать проверяться нормально, потому что используемый алгоритм хранится в хеш-коде, и password_verify() подхватывает его.

ОК в припадке нам нужна соль соль должна быть уникальной так позволь сгенерировать это

   /**
     * Generating string
     * @param $size
     * @return string
     */
    function Uniwur_string($size){
        $text = md5(uniqid(rand(), TRUE));
        RETURN substr($text, 0, $size);
    }

также нам нужен хеш Я использую sha512 это лучший и он на php

   /**
     * Hashing string
     * @param $string
     * @return string
     */
    function hash($string){
        return hash('sha512', $string);
    }

так что теперь мы можем использовать эти функции для генерации безопасного пароля

// generating unique password
$password = Uniwur_string(20); // or you can add manual password
// generating 32 character salt
$salt = Uniwur_string(32);
// now we can manipulate this informations

// hashin salt for safe
$hash_salt = hash($salt);
// hashing password
$hash_psw = hash($password.$hash_salt);

теперь нам нужно сохранить в базе данных наше значение переменной $ hash_psw и переменную $ salt

и для авторизации мы будем использовать те же шаги ...

это лучший способ защитить пароли наших клиентов ...

P.s. для последних 2 шагов вы можете использовать свой собственный алгоритм ... но убедитесь, что вы сможете сгенерировать этот хешированный пароль в будущем когда вам нужно авторизовать пользователя ...

Этот вопрос касался хешей паролей. 1 выполнение sha512 (даже если оно соленое) широко считается недостаточно хорошим для защиты паролем. (также, что RNG не является криптографически безопасным, поэтому использование его для генерации пароля рискованно).

luiscubal 08.10.2015 16:53

Вы понятия не имеете, что делаете. Прочтите основные ответы в этом посте, и вы поймете, почему ваш код не просто небезопасен, но и не имеет смысла.

cryptic ツ 09.10.2015 21:12

ОК. мой код небезопасен. так дайте мне знать, почему вы используете в своих алгоритмах только sha256 ??? Я знаю что sha512 лучший, почему бы не использовать ???

shalvasoft 10.10.2015 11:59

@shalvasoft sha512 довольно хорош для хеширования общего назначения, но для защиты паролем требуются хеши с очень специфическими свойствами (например, «быть медленным» - это странно хорошая вещь, а sha512 довольно быстро). Некоторые люди использовали sha512 как строительный блок для создания функций хеширования паролей, но в настоящее время рекомендуемый подход - «используйте bcrypt и следите за scrypt».

luiscubal 11.10.2015 21:37

Другие вопросы по теме