mirror of
https://github.com/postfixadmin/postfixadmin.git
synced 2024-09-19 19:22:14 +02:00
split up pacrypt() into different functions; add some minimal test coverage
This commit is contained in:
parent
6ed1527497
commit
6446f3f6cc
@ -891,43 +891,27 @@ function validate_password($password) {
|
||||
return $result;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Encrypt a password, using the apparopriate hashing mechanism as defined in
|
||||
* config.inc.php ($CONF['encrypt']).
|
||||
* When wanting to compare one pw to another, it's necessary to provide the salt used - hence
|
||||
* the second parameter ($pw_db), which is the existing hash from the DB.
|
||||
*
|
||||
* @param string $pw
|
||||
* @param string $pw_db optional encrypted password
|
||||
* @return string encrypted password.
|
||||
*/
|
||||
function pacrypt($pw, $pw_db="") {
|
||||
global $CONF;
|
||||
$password = "";
|
||||
$salt = "";
|
||||
|
||||
if ($CONF['encrypt'] == 'md5crypt') {
|
||||
function _pacrypt_md5crypt($pw, $pw_db) {
|
||||
$split_salt = preg_split('/\$/', $pw_db);
|
||||
if (isset($split_salt[2])) {
|
||||
$salt = $split_salt[2];
|
||||
}
|
||||
$password = md5crypt($pw, $salt);
|
||||
} elseif ($CONF['encrypt'] == 'md5') {
|
||||
$password = md5($pw);
|
||||
} elseif ($CONF['encrypt'] == 'system') {
|
||||
if ($pw_db) {
|
||||
$password = crypt($pw, $pw_db);
|
||||
} else {
|
||||
$password = crypt($pw);
|
||||
}
|
||||
} elseif ($CONF['encrypt'] == 'cleartext') {
|
||||
$password = $pw;
|
||||
return md5crypt($pw, $salt);
|
||||
}
|
||||
|
||||
return md5crypt($pw);
|
||||
}
|
||||
|
||||
function _pacrypt_crypt($pw, $pw_db) {
|
||||
|
||||
if ($pw_db) {
|
||||
return crypt($pw, $pw_db);
|
||||
}
|
||||
return crypt($pw);
|
||||
}
|
||||
|
||||
function _pacrypt_mysql_encrypt($pw, $pw_db) {
|
||||
// See https://sourceforge.net/tracker/?func=detail&atid=937966&aid=1793352&group_id=191583
|
||||
// this is apparently useful for pam_mysql etc.
|
||||
elseif ($CONF['encrypt'] == 'mysql_encrypt') {
|
||||
$pw = escape_string($pw);
|
||||
if ($pw_db!="") {
|
||||
$salt=escape_string(substr($pw_db, 0, 2));
|
||||
@ -937,7 +921,11 @@ function pacrypt($pw, $pw_db="") {
|
||||
}
|
||||
$l = db_row($res["result"]);
|
||||
$password = $l[0];
|
||||
} elseif ($CONF['encrypt'] == 'authlib') {
|
||||
return $password;
|
||||
}
|
||||
|
||||
function _pacrypt_authlib($pw, $pw_db) {
|
||||
global $CONF;
|
||||
$flavor = $CONF['authlib_default_flavor'];
|
||||
$salt = substr(create_salt(), 0, 2); # courier-authlib supports only two-character salts
|
||||
if (preg_match('/^{.*}/', $pw_db)) {
|
||||
@ -958,7 +946,12 @@ function pacrypt($pw, $pw_db="") {
|
||||
} else {
|
||||
die("authlib_default_flavor '" . $flavor . "' unknown. Valid flavors are 'md5raw', 'md5', 'SHA' and 'crypt'");
|
||||
}
|
||||
} elseif (preg_match("/^dovecot:/", $CONF['encrypt'])) {
|
||||
return $password;
|
||||
}
|
||||
|
||||
function _pacrypt_dovecot($pw, $pw_db) {
|
||||
global $CONF;
|
||||
|
||||
$split_method = preg_split('/:/', $CONF['encrypt']);
|
||||
$method = strtoupper($split_method[1]);
|
||||
# If $pw_db starts with {method}, change $method accordingly
|
||||
@ -967,7 +960,9 @@ function pacrypt($pw, $pw_db="") {
|
||||
}
|
||||
if (! preg_match("/^[A-Z0-9.-]+$/", $method)) {
|
||||
die("invalid dovecot encryption method");
|
||||
} # TODO: check against a fixed list?
|
||||
}
|
||||
|
||||
# TODO: check against a fixed list?
|
||||
# if (strtolower($method) == 'md5-crypt') die("\$CONF['encrypt'] = 'dovecot:md5-crypt' will not work because dovecotpw generates a random salt each time. Please use \$CONF['encrypt'] = 'md5crypt' instead.");
|
||||
# $crypt_method = preg_match ("/.*-CRYPT$/", $method);
|
||||
|
||||
@ -1004,7 +999,8 @@ function pacrypt($pw, $pw_db="") {
|
||||
|
||||
if (!$pipe) {
|
||||
die("can't proc_open $dovecotpw");
|
||||
} else {
|
||||
}
|
||||
|
||||
// use dovecot's stdin, it uses getpass() twice (except when using -t)
|
||||
// Write pass in pipe stdin
|
||||
if (empty($dovepasstest)) {
|
||||
@ -1041,13 +1037,46 @@ function pacrypt($pw, $pw_db="") {
|
||||
$password = str_replace('{' . $method . '}', '', $password);
|
||||
}
|
||||
|
||||
$password = rtrim($password);
|
||||
}
|
||||
} else {
|
||||
die('unknown/invalid $CONF["encrypt"] setting: ' . $CONF['encrypt']);
|
||||
return rtrim($password);
|
||||
}
|
||||
|
||||
return $password;
|
||||
|
||||
/**
|
||||
* Encrypt a password, using the apparopriate hashing mechanism as defined in
|
||||
* config.inc.php ($CONF['encrypt']).
|
||||
* When wanting to compare one pw to another, it's necessary to provide the salt used - hence
|
||||
* the second parameter ($pw_db), which is the existing hash from the DB.
|
||||
*
|
||||
* @param string $pw
|
||||
* @param string $pw_db optional encrypted password
|
||||
* @return string encrypted password.
|
||||
*/
|
||||
function pacrypt($pw, $pw_db="") {
|
||||
global $CONF;
|
||||
$password = "";
|
||||
$salt = "";
|
||||
|
||||
switch ($CONF['encrypt']) {
|
||||
case 'md5crypt':
|
||||
return _pacrypt_md5crypt($pw, $pw_db);
|
||||
case 'md5':
|
||||
return md5($pw);
|
||||
case 'system' :
|
||||
return _pacrypt_crypt($pw, $pw_db);
|
||||
case 'cleartext' :
|
||||
return $pw;
|
||||
case 'mysql_encrypt' :
|
||||
return _pacrypt_mysql_encrypt($pw, $pw_db);
|
||||
case 'authlib':
|
||||
return _pacrypt_authlib($pw, $pw_db);
|
||||
}
|
||||
|
||||
if (preg_match("/^dovecot:/", $CONF['encrypt'])) {
|
||||
return _pacrypt_dovecot($pw, $pw_db);
|
||||
}
|
||||
|
||||
die('unknown/invalid $CONF["encrypt"] setting: ' . $CONF['encrypt']);
|
||||
|
||||
}
|
||||
|
||||
//
|
||||
|
88
tests/PacryptTest.php
Normal file
88
tests/PacryptTest.php
Normal file
@ -0,0 +1,88 @@
|
||||
<?php
|
||||
|
||||
require_once('common.php');
|
||||
|
||||
class PaCryptTest extends PHPUnit_Framework_TestCase {
|
||||
|
||||
public function testMd5Crypt() {
|
||||
$hash = _pacrypt_md5crypt('test', '');
|
||||
|
||||
$this->assertNotEmpty($hash);
|
||||
$this->assertNotEquals('test', $hash);
|
||||
|
||||
$this->assertEquals($hash, _pacrypt_md5crypt('test', $hash));
|
||||
}
|
||||
|
||||
public function testCrypt() {
|
||||
|
||||
// E_NOTICE if we pass in '' for the salt
|
||||
$hash = _pacrypt_crypt('test', 'sa');
|
||||
|
||||
|
||||
$this->assertNotEmpty($hash);
|
||||
$this->assertNotEquals('test', $hash);
|
||||
|
||||
$this->assertEquals($hash, _pacrypt_crypt('test', $hash));
|
||||
|
||||
}
|
||||
|
||||
public function testMySQLEncrypt() {
|
||||
if(!db_mysql()) {
|
||||
$this->markTestSkipped('Not using MySQL');
|
||||
}
|
||||
|
||||
$hash = _pacrypt_mysql_encrypt('test', '');
|
||||
|
||||
$this->assertNotEmpty($hash);
|
||||
$this->assertNotEquals('test', $hash);
|
||||
|
||||
$this->assertEquals($hash, _pacrypt_mysql_encrypt('test', $hash));
|
||||
|
||||
$hash2 = _pacrypt_mysql_encrypt('test', 'salt');
|
||||
|
||||
$this->assertNotEmpty($hash2);
|
||||
$this->assertNotEquals($hash, $hash2);
|
||||
|
||||
$this->assertEquals($hash2, _pacrypt_mysql_encrypt('test', 'salt'));
|
||||
}
|
||||
|
||||
public function testAuthlib() {
|
||||
|
||||
// too many options!
|
||||
foreach(
|
||||
['md5raw' => '098f6bcd4621d373cade4e832627b4f6',
|
||||
'md5' => 'CY9rzUYh03PK3k6DJie09g==',
|
||||
// crypt requires salt ...
|
||||
'SHA' => 'qUqP5cyxm6YcTAhz05Hph5gvu9M='] as $flavour => $hash) {
|
||||
|
||||
$CONF['authlib_default_flavour'] = $flavour;
|
||||
|
||||
$stored = "{" . $flavour . "}$hash";
|
||||
$hash = _pacrypt_authlib('test', $stored);
|
||||
|
||||
$this->assertEquals($hash, $stored, "Hash: $hash vs Stored: $stored" );
|
||||
//var_dump("Hash: $hash from $flavour");
|
||||
}
|
||||
}
|
||||
|
||||
public function testPacryptDovecot() {
|
||||
global $CONF;
|
||||
if(!file_exists('/usr/bin/doveadm')) {
|
||||
$this->markTestSkipped("No /usr/bin/doveadm");
|
||||
}
|
||||
|
||||
|
||||
$CONF['encrypt'] = 'dovecot:SHA1';
|
||||
|
||||
$expected_hash = '{SHA1}qUqP5cyxm6YcTAhz05Hph5gvu9M=';
|
||||
|
||||
$this->assertEquals($expected_hash, _pacrypt_dovecot('test', ''));
|
||||
|
||||
$this->assertEquals($expected_hash, _pacrypt_dovecot('test', $expected_hash));
|
||||
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/* vim: set expandtab softtabstop=4 tabstop=4 shiftwidth=4: */
|
Loading…
Reference in New Issue
Block a user