Добрый день. Столкнулся с такой проблемой. Ставлю Postfix с авторизацией через Cyrus-SASL. Система - FreeBSD 6.2. В качестве back-end для SASL использую BerkleyDB.
По умолчанию SASL хранит пароли в базе в открытом виде. При этом к файлу базы права заданы на чтение для группы mail, в которую входит и postfix и cyrus. А это совсем не секьюрно!
Для испаравления этого - ставлю патч отсюда: http://frost.ath.cx/software/cyrus-sasl-patches/
И все бы ничего, но теперь, при создания пользователя командой saslpasswd2 пароль необходимо указывать в зашифрованном виде. Патченный SASL понимает зашифрованные пароли следующих видов (со страницы патча):
crypt - passwords are stored as modular crypt hashes (md5 or blowfish crypt)
crypt_trad - passwords are stored as des crypt hashes (2 character salt crypt)
Изначально пароли задаются вводом с клавиатуры в ответ на прглашение команды:saslpasswd2 -c user@domain.ru
или из скрипта:echo "password" | saslpasswd2 -p -c user@domain.ru
Собственно вопрос, как из шела сгенерить зашифрованный пароль, который поймет патченный SASL?
Пытался делатьperl -e 'print crypt(123,"");'
но функции crypt нужен второй аргумент, а где его взять?
Насколько я разобрался, в случае использования mySQL в качестве back-end, там применяется евойная функция encrypt(), которому тоже необходим второй аргумент.
Посмотрел сам патч - там все просто, но в качестве второго аргумента функции crypt, используются первые 12 или 16 символов уже зашифрованого пароля функцией crypt. Заколдованный круг получается!
>Добрый день. Столкнулся с такой проблемой. Ставлю Postfix с авторизацией через Cyrus-SASL.
>Система - FreeBSD 6.2. В качестве back-end для SASL использую BerkleyDB.
>
>По умолчанию SASL хранит пароли в базе в открытом виде. При этом
>к файлу базы права заданы на чтение для группы mail, в
>которую входит и postfix и cyrus. А это совсем не секьюрно!
>Никаких проблем с безопасностью нет. Для безопасной авторизации по МД5 нужно чтобы на стороне сервера был пароль в открытом виде. Читайте документацию, и подключайте мозги для того, чтобы понять что действительно секьюрно, а что нет.
>
>Никаких проблем с безопасностью нет.Если злоумышленник получает доступ к аккаунту mail через взлом postfix или cyrus, то он в состоянии прочитать все пароли пользователей почты. А некоторые пользователи на почту ставят такой же пароль, как на вход в систему и т.д.
> Для безопасной авторизации по МД5 нужно чтобы
>на стороне сервера был пароль в открытом виде.Если мы про авторизацию SMTP AUTH - то в моем случае она идет открытом текстом по SSL/TLS соединению. MD5 там не применяется.
>Заколдованный круг получается!Второй аргумент функции crypt - это SALT так называемый. То есть просто случайная строка символов, которая вместе с паролем используется для создания дайджеста.
>>Заколдованный круг получается!
>
>Второй аргумент функции crypt - это SALT так называемый. То есть просто
>случайная строка символов, которая вместе с паролем используется для создания дайджеста.
>попробуйте другую связку postfix+dovecot
лучшей будет
>Второй аргумент функции crypt - это SALT так называемый. То есть просто
>случайная строка символов, которая вместе с паролем используется для создания дайджеста.
>SASL использует следующий алгоритм для сравнения пришедшего пароля (clear text) с его зашифрованной формой:
Код из патча привожу с сокращениями и в упрощенном виде, полная версия здаеь: http://frost.ath.cx/software/cyrus-sasl-patches/dist/2.1.19/...
password_format может быть:plaintext - passwords are stored in plaintext format - this is default
crypt - passwords are stored as modular crypt hashes (md5 or blowfish crypt)
crypt_trad - passwords are stored as des crypt hashes (2 character salt crypt)
salt = get_salt("зашифрованный пароль из базы",password_format);
// эта функция по сути возвращает первые 2, 16 или 17 символов зашифрованного пароля в качестве salt
// получаем salt из уже сохраненного пароля:
get_salt (src,format) {
int num; /* how many characters is salt long? */
switch (format) {
case PASSWORD_FORMAT_CRYPT:
/* md5 crypt */
if (src[1] == '1')
num = 12;
/* blowfish crypt */
else if (src[1] == '2')
num = (src[1] == '2' && src[2] == 'a') ? 17 : 16;
/* traditional crypt */
else
num = 2;
break;
case PASSWORD_FORMAT_CRYPTTRAD:
num = 2;
break;
default:
return 1; }
return strncpy(dest, src, num);//
// Здесь мы сравниваем зашифрованную версию полученного открытого пароля и зашифрованную версию из базы
// что бы они были равны мы должны использовать одинаковый пароль и одинаковый salt, но salt мы вычисляем от ранее
// зашифрованного пароля, как видно выше!!! закалдованный круг...if (crypt(clear_passwd, salt) == "зашифрованный пароль из базы"))
return SASL_OK;
else
ret = SASL_BADAUTH;
Может я неправильно понимаю функцию crypt ?
>Может я неправильно понимаю функцию crypt ?Неправильно понимаете. Пароли, например в файле shadow выглядят так:
$1$pprKKhp5$t3HJtFmeqJK8ylhW4tNt1/
В мануале сказано, что между первыми двумя знаками $ указывается алгоритм шифрования, между вторыми двумя - незашифрованный сальт, а потом полученый хэш.
Мануал почитайте:
man crypt
man perlfunc с поиском crypt
>В мануале сказано, что между первыми двумя знаками $ указывается алгоритм шифрования,
>между вторыми двумя - незашифрованный сальт, а потом полученый хэш.skgennady, вы лучший! Я понял: в любом случае SALT, использованный при создании хеша, сохраняется в неизменном виде в самом хеше.
Остался вопрос, как средствами шела (или перла) получить строку вида:
$1$pprKKhp5$t3HJtFmeqJK8ylhW4tNt1/ - так, как это делает passwd.
Хотя уже сейчас я понимаю, что можно использоватьperl -e 'print crypt(password,"случаное число из 2-х символов");'