Как на самом деле работает password_hash?

Я пытаюсь полностью понять password_hash, чтобы иметь возможность объяснить это для аудитора.

Основываясь на моих поисках ответа, я понимаю, что функция password_hash() является оболочкой для crypt(). Читая руководство по PHP для предопределенных констант, я вижу, что оно использует PASSWORD_BCRYPT в качестве целочисленное значение по умолчанию (в основном он использует алгоритм CRYPT_BLOWFISH для хеширования пароля).

Что меня смущает, так это то, что переменная $options, если ее не указать, генерирует случайную соль, а стоимость будет установлена ​​на 10. Если я укажу более высокую стоимость (например: 12), будет ли она по-прежнему генерировать случайную соль, поскольку я не указываю значение соли? Причина, по которой я здесь запутался, заключается в том, что я не пропускаю $options, а вместо этого указываю другую стоимость.

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

  • Почему увеличение стоимости увеличивает безопасность?
  • Как, поскольку password_hash() является односторонней хеш-функцией, password_verify() проверяет пароль, поскольку соль является случайной?
  • Является ли CRYPT_SHA512 более сильным, чем CRYPT_BLOWFISH для хеширования?

person Jaylen    schedule 06.08.2014    source источник
comment
Если вы увеличиваете стоимость, проверка занимает больше времени, что замедляет атаки грубой силы.   -  person Mark Baker    schedule 06.08.2014
comment
Варианты отдельные. Если вы укажете любую стоимость, она все равно будет генерировать случайную соль, а если вы укажете только соль, она будет использовать стоимость 10. Нигде не сказано, что это работает по-другому.   -  person GolezTrol    schedule 06.08.2014
comment
Из документации по адресу php.net/manual/en/function.crypt.php Двузначный параметр стоимости представляет собой логарифм по основанию 2 числа итераций для базового алгоритма хеширования на основе Blowfish и должен находиться в диапазоне 04–31, значения за пределами этого диапазона приведут к сбою crypt(). Другими словами, стоимость определяет количество циклов алгоритма.   -  person Jay Blanchard    schedule 06.08.2014
comment
Также обратите внимание, что PASSWORD_DEFAULT на самом деле является значением по умолчанию. Это то же значение, что и PASSWORD_BCRYPT в текущей версии PHP, но оно может измениться в будущих версиях.   -  person GolezTrol    schedule 06.08.2014
comment
вы можете проверить gkombs.blogspot.com/2014/07/password-storage -mistakes.html. содержит полезную информацию   -  person Kxng Kombian    schedule 06.08.2014
comment
Возможно, вас заинтересует мое руководство по безопасному хранению паролей. Там я попытался объяснить идею соли, фактор стоимости и почему BCrypt лучше подходит для хеширования паролей, чем SHA512.   -  person martinstoeckli    schedule 07.08.2014


Ответы (3)


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

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

Да, будет — как говорится в документации, если соль опущена, случайная соль будет сгенерирована функцией password_hash() для каждого хэшированного пароля (это означает, что если вы не укажете значение соли в массиве параметров, она будет сгенерирована функцией password_hash() по умолчанию). Кроме того, опция соли устарела, начиная с php 7.0.

почему увеличение себестоимости увеличивает безопасность?

Это также объясняется в статье выше в разделе Усложнение взлома паролей: медленный хэш Функции. Чем выше установлена ​​стоимость, тем медленнее работает хеш-функция. Идея состоит в том, чтобы сделать хэш-функцию очень медленной, чтобы даже при наличии быстрого графического процессора или специализированного оборудования атаки по словарю и грубой силе были слишком медленными, чтобы приносить пользу. Однако стоимость должна быть разумной. значение (исходя из спецификаций вашего сервера), чтобы не вызывать значительных временных задержек при проверке паролей пользователей.

Более того, CRYPT_SHA512 сильнее CRYPT_BLOWFISH для хеширования?

Прочтите этот пост об их сравнении.

person mbuster    schedule 25.02.2017

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

Лучше не указывать соль и позволить ей создать ее за вас. Если вы используете только одну соль, вам будет легче взломать все ваши пароли, а не только один. Соли могут быть получены независимо от стоимости.

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

person Machavity♦    schedule 06.08.2014
comment
Соль ..... Кроме того, судя по вашему ответу, вы прочитали заголовок, а не сам вопрос, который в значительной степени касается того, как предоставить параметры для password_hash. - person GolezTrol; 06.08.2014
comment
@ Майк - соли должны быть уникальными для каждого пароля, и функция password_hash() будет генерировать такую ​​уникальную соль каждый раз, когда вы вычисляете хэш. Если в параметре options не определена соль, функция сгенерирует безопасную, независимо от того, установлены ли другие параметры. - person martinstoeckli; 07.08.2014

Вообще говоря:

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

Но bcrypt справляется с солением самостоятельно!

Вернемся к исходному вопросу:

Стоимость используется, чтобы сделать взлом пароля «дорогостоящим» с помощью атаки по словарю/грубой силе.

Bcrypt в основном хеширует пароль снова и снова, что требует много времени (= дорогого) для получения пароля к заданному хэшу. Если вы попытаетесь найти пароль для хэша (атака полным перебором), вам придется вычислить миллиарды хэшей паролей. Когда каждое хеширование занимает в «$cost» раз больше времени, атака грубой силы невозможна. Даже если вы можете вычислить хэш для потенциального пароля в миллисекундах.

Проще говоря: если у вас есть хэш пароля для SHA-1 (небезопасный, не используйте его!) с солью (так как она обычно содержится в хэше) и вы хотите его взломать, то вам нужно хешировать все возможные пароли + соль, и когда вы найдете комбинацию с тем же хэшем, вы нашли возможный пароль для этого хеша.

Допустим, вы используете хорошую соль и достаточно длинный пароль, тогда вам нужно что-то вроде 1-5 секунд для хэша пароля. Если вы используете подход blowfish со стоимостью = 10, вам нужно 10-50 секунд для хэша пароля. Для одного пароля это не имеет большого значения. Таким образом, направленная атака на один хэш по-прежнему проста, но обычно люди получают большие списки комбинаций пользователей и паролей и заинтересованы в том, чтобы быстро получить пароли для всех из них. Тогда это гораздо менее выгодно для плохого парня, так как ему требуется в 10 раз больше мощности процессора, чтобы вычислить все это.

person Patrick Cornelissen    schedule 30.08.2014
comment
Вы понимаете, что удаленные ответы на самом деле не удаляются, и их увидит любой, у кого есть репутация 10K. Если вы просто собираетесь внести изменение, отредактируйте ответ, не удаляйте и не создавайте новый ответ только потому, что есть голос против, улучшите ответ, и, если это уместно, должны быть голоса за. - person zaph; 25.02.2017
comment
Вы правы, хотя это делает концепцию удаления ответа устаревшей. - person Patrick Cornelissen; 25.02.2017