From 659fa7f23bb28d316ec6c99a538ee74bc7ffc0a3 Mon Sep 17 00:00:00 2001 From: Matthew Grooms Date: Sun, 3 Aug 2008 17:54:35 +0000 Subject: [PATCH] Cleanup authentication code. The basic auth method, the passwd, htpasswd and pam backing functions have been removed. The basic auth method was legacy code and the backing functions were redundant with no added value that I could see. A simplified replacement backing function named local_backed has been added that authenticates to the local configuration info which should be identical to system pwdb credentials. Since the htpassword file is no longer required, sync_webgui_passwords and its wrapper function system_password_configure have been removed. The local account management functions were renamed for consistency. A few minor bugs related to setting local passwords have also been corrected. --- etc/inc/auth.inc | 948 ++++++++---------- etc/inc/authgui.inc | 5 +- etc/inc/config.inc | 4 +- etc/inc/pfsense-utils.inc | 32 +- etc/inc/priv.inc | 6 +- etc/inc/system.inc | 23 +- etc/phpshellsessions/cvssync | 4 +- etc/rc.bootup | 7 +- etc/rc.initial.password | 26 +- etc/sshd | 3 - usr/local/www/pkg_mgr_install.php | 3 - usr/local/www/system.php | 10 - usr/local/www/system_groupmanager.php | 6 +- .../www/system_groupmanager_addprivs.php | 2 +- usr/local/www/system_usermanager.php | 22 +- usr/local/www/system_usermanager_addprivs.php | 2 +- usr/local/www/system_usermanager_settings.php | 4 - usr/local/www/wizards/setup_wizard.xml | 10 +- 18 files changed, 467 insertions(+), 650 deletions(-) diff --git a/etc/inc/auth.inc b/etc/inc/auth.inc index 2d89e5dbbb..3d5b3ac774 100644 --- a/etc/inc/auth.inc +++ b/etc/inc/auth.inc @@ -102,7 +102,18 @@ function & getGroupEntryByGID($gid) { return false; } -function sync_local_accounts() { +function local_backed($username, $passwd) { + + $user = getUserEntry($username); + if (!$user) + return false; + + $passwd = crypt($passwd, $user['password']); + + return ($passwd == $user['password']); +} + +function local_sync_accounts() { global $config; /* remove local users to avoid uid conflicts */ @@ -140,22 +151,20 @@ function sync_local_accounts() { /* make sure the all group exists */ $allgrp = getGroupEntryByGID(1998); - set_local_group($allgrp, true); + local_group_set($allgrp, true); /* sync all local users */ if (is_array($config['system']['user'])) foreach ($config['system']['user'] as $user) - set_local_user($user); + local_user_set($user); /* sync all local groups */ if (is_array($config['system']['group'])) foreach ($config['system']['group'] as $group) - set_local_group($group); - - sync_webgui_passwords(); + local_group_set($group); } -function set_local_user(& $user, $password = false) { +function local_user_set(& $user) { global $g; $home_base = $g['platform'] == "pfSense" ? "/home" : "/var/home"; @@ -168,30 +177,6 @@ function set_local_user(& $user, $password = false) { $user_shell = "/etc/rc.initial"; $user_group = "nobody"; - /* set all password hashes if required */ - if ($password && strlen($password)) { - - $user['password'] = crypt($password); - $user['md5-hash'] = md5($password); - - /* - * NOTE : This section of code id based on the BSD - * licensed CHAP.php courtesy of Michael Retterklieber. - */ - /* Waiting for mhash to settle into the tree - // Converts ascii to unicode. - $astr = (string) $password; - $ustr = ''; - for ($i = 0; $i < strlen($astr); $i++) { - $a = ord($astr{$i}) << 8; - $ustr.= sprintf("%X", $a); - } - - // Generate the NT-HASH from the unicode string - $user['nt-hash'] = bin2hex(mhash(MHASH_MD4, $ustr)); - */ - } - /* configure shell type */ if (!hasPrivilegeShell($user)) { if (!hasPrivilegeCopyFiles($user)) @@ -241,10 +226,10 @@ function set_local_user(& $user, $password = false) { create_authorized_keys($user_name, $user_home); } -function del_local_user($user) { +function local_user_del($user) { /* remove all memberships */ - set_local_user_groups($user); + local_user_get_groups($user); /* delete from pw db */ $cmd = "/usr/sbin/pw userdel {$user['name']}"; @@ -255,7 +240,30 @@ function del_local_user($user) { pclose($fd); } -function get_local_user_groups($user, $all = false) { +function local_user_set_password(& $user, $password) { + + $user['password'] = crypt($password); + $user['md5-hash'] = md5($password); + + /* + * NOTE : This section of code id based on the BSD + * licensed CHAP.php courtesy of Michael Retterklieber. + */ + /* Waiting for mhash to settle into the tree + // Converts ascii to unicode. + $astr = (string) $password; + $ustr = ''; + for ($i = 0; $i < strlen($astr); $i++) { + $a = ord($astr{$i}) << 8; + $ustr.= sprintf("%X", $a); + } + + // Generate the NT-HASH from the unicode string + $user['nt-hash'] = bin2hex(mhash(MHASH_MD4, $ustr)); + */ +} + +function local_user_get_groups($user, $all = false) { global $config; $groups = array(); @@ -273,13 +281,13 @@ function get_local_user_groups($user, $all = false) { return $groups; } -function set_local_user_groups($user, $new_groups = NULL ) { +function local_user_set_groups($user, $new_groups = NULL ) { global $config, $groupindex; if (!is_array($config['system']['group'])) return; - $cur_groups = get_local_user_groups($user); + $cur_groups = local_user_get_groups($user); $mod_groups = array(); if (!is_array($new_groups)) @@ -309,10 +317,10 @@ function set_local_user_groups($user, $new_groups = NULL ) { /* sync all modified groups */ foreach ($mod_groups as $group) - set_local_group($group); + local_group_set($group); } -function set_local_group($group, $reset = false) { +function local_group_set($group, $reset = false) { $group_name = $group['name']; $group_gid = $group['gid']; @@ -340,7 +348,7 @@ function set_local_group($group, $reset = false) { pclose($fd); } -function del_local_group($group) { +function local_group_del($group) { /* delete from group db */ $cmd = "/usr/sbin/pw groupdel {$group['name']}"; @@ -351,24 +359,384 @@ function del_local_group($group) { pclose($fd); } -function basic_auth($backing) { - global $HTTP_SERVER_VARS; +function ldap_test_connection() { + global $config, $g; - /* Check for AUTH_USER */ - if ($HTTP_SERVER_VARS['PHP_AUTH_USER'] <> "") { - $HTTP_SERVER_VARS['AUTH_USER'] = $HTTP_SERVER_VARS['PHP_AUTH_USER']; - $HTTP_SERVER_VARS['AUTH_PW'] = $HTTP_SERVER_VARS['PHP_AUTH_PW']; + $ldapserver = $config['system']['webgui']['ldapserver']; + $ldapbindun = $config['system']['webgui']['ldapbindun']; + $ldapbindpw = $config['system']['webgui']['ldapbindpw']; + + if (!($ldap = ldap_connect($ldapserver))) + return false; + + return true; +} + +function ldap_test_bind() { + global $config, $g; + + $ldapserver = $config['system']['webgui']['ldapserver']; + $ldapbindun = $config['system']['webgui']['ldapbindun']; + $ldapbindpw = $config['system']['webgui']['ldapbindpw']; + + if (!($ldap = ldap_connect($ldapserver))) + return false; + + ldap_set_option($ldap, LDAP_OPT_REFERRALS, 0); + ldap_set_option($ldap, LDAP_OPT_PROTOCOL_VERSION, 3); + + if (!($res = @ldap_bind($ldap, $ldapbindun, $ldapbindpw))) + return false; + + return true; +} + +function ldap_get_user_ous($show_complete_ou=true) { + global $config, $g; + + if(!function_exists("ldap_connect")) + return; + + $ldapserver = $config['system']['webgui']['ldapserver']; + $ldapbindun = $config['system']['webgui']['ldapbindun']; + $ldapbindpw = $config['system']['webgui']['ldapbindpw']; + $ldapsearchbase = "{$config['system']['webgui']['ldapsearchbase']}"; + $ldaptype = $config['system']['webgui']['backend']; + + $ldapfilter = "(ou=*)"; + putenv('LDAPTLS_REQCERT=never'); + if (!($ldap = ldap_connect($ldapserver))) { + log_error("ERROR! ldap_get_groups() could not connect to server {$ldapserver}. Defaulting to built-in local_backed()"); + $status = local_backed($username, $passwd); + return $status; } - if (!isset($HTTP_SERVER_VARS['AUTH_USER'])) { - require_once("authgui.inc"); - header("WWW-Authenticate: Basic realm=\".\""); - header("HTTP/1.0 401 Unauthorized"); - display_error_form("401", gettext("You must enter valid credentials to access this resource.")); - exit; + ldap_set_option($ldap, LDAP_OPT_REFERRALS, 0); + ldap_set_option($ldap, LDAP_OPT_PROTOCOL_VERSION, 3); + + if (!($res = @ldap_bind($ldap, $ldapbindun, $ldapbindpw))) { + log_error("ERROR! ldap_get_groups() could not bind to {$ldapserver} - {$ldapfilter}. Defaulting to built-in local_backed()"); + $status = local_backed($username, $passwd); + return $status; } - return $backing($HTTP_SERVER_VARS['AUTH_USER'],$HTTP_SERVER_VARS['AUTH_PW']); + $search = ldap_search($ldap, $ldapsearchbase, $ldapfilter); + + $info = ldap_get_entries($ldap, $search); + + $ous = array(); + + if (is_array($info)) { + foreach ($info as $inf) { + if (!$show_complete_ou) { + $inf_split = split(",", $inf['dn']); + $ou = $inf_split[0]; + $ou = str_replace("OU=","", $ou); + } else + if($inf['dn']) + $ou = $inf['dn']; + if($ou) + $ous[] = $ou; + } + } + + //Tack on the default Users container for AD since its non-standard + if($ldaptype == 'ldap') + $ous[] = "CN=Users,".$ldapsearchbase; + + return $ous; +} + +function ldap_get_groups($username) { + global $config; + + if(!function_exists("ldap_connect")) + return; + + if(!$username) + return false; + + if(stristr($username, "@")) { + $username_split=split("\@", $username); + $username = $username_split[0]; + } + + if(stristr($username, "\\")) { + $username_split=split("\\", $username); + $username = $username_split[0]; + } + + //log_error("Getting LDAP groups for {$username}."); + + $ldapserver = $config['system']['webgui']['ldapserver']; + $ldapbindun = $config['system']['webgui']['ldapbindun']; + $ldapbindpw = $config['system']['webgui']['ldapbindpw']; + $ldapfilter = $config['system']['webgui']['ldapfilter']; + $ldapfilter = str_replace("\$username", $username, $ldapfilter); + $ldapgroupattribute = $config['system']['webgui']['ldapgroupattribute']; + $ldapdn = $_SESSION['ldapdn']; + + /*Convert attribute to lowercase. php ldap arrays put everything in lowercase */ + $ldapgroupattribute = strtolower($ldapgroupattribute); + + /* connect and see if server is up */ + putenv('LDAPTLS_REQCERT=never'); + if (!($ldap = ldap_connect($ldapserver))) { + log_error("ERROR! ldap_get_groups() could not connect to server {$ldapserver}. Defaulting to built-in local_backed()"); + $status = local_backed($username, $passwd); + return $status; + } + + ldap_set_option($ldap, LDAP_OPT_REFERRALS, 0); + ldap_set_option($ldap, LDAP_OPT_PROTOCOL_VERSION, 3); + + /* bind as user that has rights to read group attributes */ + if (!($res = @ldap_bind($ldap, $ldapbindun, $ldapbindpw))) { + log_error("ERROR! ldap_get_groups() could not bind to {$ldapserver} - {$ldapfilter}. Defaulting to built-in local_backed()"); + $status = local_backed($username, $passwd); + return $status; + } + + /* get groups from DN found */ + /* use ldap_read instead of search so we don't have to do a bunch of extra work */ + /* since we know the DN is in $_SESSION['ldapdn'] */ + //$search = ldap_read($ldap, $ldapdn, "(objectclass=*)", array($ldapgroupattribute)); + $search = ldap_read($ldap, $ldapdn, $ldapfilter, array($ldapgroupattribute)); + $info = ldap_get_entries($ldap, $search); + + $countem = $info["count"]; + $memberof = array(); + + if(is_array($info[0][$ldapgroupattribute])) { + /* Iterate through the groups and throw them into an array */ + foreach ($info[0][$ldapgroupattribute] as $member) { + if (stristr($member, "CN=") !== false) { + $membersplit = split(",", $member); + $memberof[] = preg_replace("/CN=/i", "", $membersplit[0]); + } + } + } + + /* Time to close LDAP connection */ + ldap_close($ldap); + + $groups = print_r($memberof,true); + + //log_error("Returning groups ".$groups." for user $username"); + + return $memberof; +} + +function ldap_backed($username, $passwd) { + global $config; + + if(!$username) + return; + + if(!function_exists("ldap_connect")) + return; + + $adbindas = $username; + + if(stristr($username, "@")) { + $username_split=split("\@", $username); + $username = $username_split[0]; + } + if(stristr($username, "\\")) { + $username_split=split("\\", $username); + $username = $username_split[0]; + } + + $ldapserver = $config['system']['webgui']['ldapserver']; + $ldapbindun = $config['system']['webgui']['ldapbindun']; + $ldapbindpw = $config['system']['webgui']['ldapbindpw']; + $ldapauthcont = $config['system']['webgui']['ldapauthcontainers']; + $ldapnameattribute = $config['system']['webgui']['ldapnameattribute']; + $ldapfilter = $config['system']['webgui']['ldapfilter']; + $ldaptype = $config['system']['webgui']['backend']; + $ldapfilter = str_replace("\$username", $username, $ldapfilter); + + /* first check if there is even an LDAP server populated */ + if(!$ldapserver) { + log_error("ERROR! ldap_backed() backed selected with no LDAP authentication server defined. Defaulting to built-in local_backed(). Visit System -> User Manager -> Settings."); + $status = local_backed($username, $passwd); + return $status; + } + + ldap_set_option($ldap, LDAP_OPT_REFERRALS, 0); + ldap_set_option($ldap, LDAP_OPT_PROTOCOL_VERSION, 3); + + /* Make sure we can connect to LDAP */ + putenv('LDAPTLS_REQCERT=never'); + if (!($ldap = ldap_connect($ldapserver))) { + log_error("ERROR! ldap_backed() could not connect to server {$ldapserver} - {$ldapfilter}. Defaulting to built-in local_backed(). Visit System -> User Manager -> Settings."); + $status = local_backed($username, $passwd); + return $status; + } + /* ok, its up. now, lets bind as the bind user so we can search it */ + if (!($res = ldap_bind($ldap, $ldapbindun, $ldapbindpw))) { + log_error("ERROR! ldap_backed() could not bind to {$ldapserver} - {$ldapfilter}. Defaulting to built-in local_backed()"); + ldap_close($ldap); + $status = local_backed($username, $passwd); + return $status; + } + + /* Get LDAP Authcontainers and split em up. */ + $ldac_split = split(";", $ldapauthcont); + + /* now count how many there are */ + $containers = count($ldac_split); + log_error("Number of Authentication Containers to search for $username is {$containers}"); + + /* setup the usercount so we think we havn't found anyone yet */ + $usercount = 0; + + /******************************/ + /* Currently LDAP Types are */ + /* LDAP = Active Directory */ + /* LDAPOTHER = eDir/Openldap */ + /******************************/ + + /*****************************************************************/ + /* Now Active Directory We keep this seperate for future addons. */ + /*****************************************************************/ + /* Now LDAP other. eDirectory or Netscape or Sunone or OpenLDAP */ + /*****************************************************************/ + /* We First find the user based on username and filter */ + /* Then, once we find the first occurance of that person */ + /* We set seesion variables to ponit to the OU and DN of the */ + /* Person. To later be used by ldap_get_groups. */ + /* that way we don't have to search twice. */ + /*****************************************************************/ + if ($ldaptype == 'ldap'){ + log_error("Now Searching for {$username} in Active directory."); + /* Iterate through the user containers for search */ + for ($i=0;$i<$containers;$i++){ + /* Make sure we just use the first user we find */ + log_error("Now Searching in {$ldac_split[$i]} for {$ldapfilter}."); + $search = ldap_search($ldap,$ldac_split[$i],$ldapfilter); + $info = ldap_get_entries($ldap,$search); + $matches = $info['count']; + log_error("Matches Found = {$matches}"); + if ($matches == 1){ + $_SESSION['ldapdn'] = $info[0]['dn']; + $_SESSION['ldapou'] = $ldac_split[$i]; + $_SESSION['ldapon'] = "true"; + $ldapdn = $_SESSION['ldapdn']; + $userou = $_SESSION['ldapou']; + break; + } + } + + if ($matches == 1){ + $binduser = $adbindas; + log_error("Going to login as {$username} - DN = {$_SESSION['ldapdn']}"); + } + if ($matches != 1){ + log_error("ERROR! Either LDAP search failed, or multiple users were found"); + $status = local_backed($username, $passwd); + $_SESSION['ldapon'] = "false"; + ldap_close($ldap); + return $status; + } + } + + /*****************************************************************/ + /* Now LDAP other. eDirectory or Netscape or Sunone or OpenLDAP */ + /*****************************************************************/ + /* We First find the user based on username and filter */ + /* Then, once we find the first occurance of that person */ + /* We set seesion variables to ponit to the OU and DN of the */ + /* Person. To later be used by ldap_get_groups. */ + /* that way we don't have to search twice. */ + /*****************************************************************/ + if ($ldaptype == 'ldapother'){ + log_error("Now Searching for {$username} in LDAP."); + /* Iterate through the user containers for search */ + for ($i=0;$i<$containers;$i++){ + /* Make sure we just use the first user we find */ + log_error("Now searching in {$ldac_split[$i]} for {$ldapfilter}."); + $search = ldap_search($ldap,$ldac_split[$i],$ldapfilter); + $info = ldap_get_entries($ldap,$search); + $matches = $info['count']; + log_error("Matches Found = {$matches}."); + + if ($matches == 1){ + $_SESSION['ldapdn'] = $info[0]['dn']; + $_SESSION['ldapou'] = $ldac_split[$i]; + $_SESSION['ldapon'] = "true"; + $ldapdn = $_SESSION['ldapdn']; + $userou = $_SESSION['ldapou']; + break; + } + } + if($matches == 1){ + $binduser = $ldapnameattribute."=".$username.",".$userou; + log_error("Going to login as {$username} - DN = {$_SESSION['ldapdn']}"); + } + if($matches != 1){ + log_error("ERROR! Either LDAP search failed, or multiple users were found"); + $status = local_backed($username, $passwd); + ldap_close($ldap); + $_SESSION['ldapon'] = "false"; + return $status; + } + } + + /* Now lets bind as the user we found */ + if (!($res = @ldap_bind($ldap, $binduser, $passwd))) { + log_error("ERROR! ldap_backed() could not bind to {$ldapserver} - {$username} - {$passwd}. Defaulting to built-in local_backed(). Visit System -> User Manager -> Settings."); + $status = local_backed($username, $passwd); + return $status; + } + + log_error("$binduser succesfully logged in via LDAP."); + + /* At this point we are bound to LDAP so the user was auth'd okay. */ + return true; +} + +function radius_backed($username, $passwd){ + global $config, $debug; + $ret = false; + $radiusservers = $config['system']['radius']['servers']; + + $rauth = new Auth_RADIUS_PAP($username, $passwd); + /* Add a new servers to our instance */ + foreach ($radiusservers as $radsrv) + $rauth->addServer($radsrv['ipaddr'], $radsrv['port'], $radsrv['sharedsecret']); + + if (!$rauth->start()) { + $retvalue['auth_val'] = 1; + $retvalue['error'] = $rauth->getError(); + if ($debug) + printf("Radius start: %s
\n", $retvalue['error']); + } + + // XXX - billm - somewhere in here we need to handle securid challenge/response + + /* Send request */ + $result = $rauth->send(); + if (PEAR::isError($result)) { + $retvalue['auth_val'] = 1; + $retvalue['error'] = $result->getMessage(); + if ($debug) + printf("Radius send failed: %s
\n", $retvalue['error']); + } else if ($result === true) { + $retvalue['auth_val'] = 2; + if ($debug) + printf(gettext("Radius Auth succeeded")."
\n"); + $ret = true; + } else { + $retvalue['auth_val'] = 3; + if ($debug) + printf(gettext("Radius Auth rejected")."
\n"); + } + + // close OO RADIUS_AUTHENTICATION + $rauth->close(); + + return $ret; } function session_auth($backing) { @@ -567,480 +935,4 @@ function session_auth($backing) { return true; } -function pam_backed($username = "", $password = "") { - - /* do not allow blank passwords */ - if ($username == "" || password == "") - return false; - - if (!extension_loaded( 'pam_auth')) - if (!@dl('pam_auth.so')) - return false; - - /* no php file no auth, sorry */ - if (!file_exists("/etc/pam.d/php")) { - - if (!file_exists("/etc/pam.d")) - mkdir("/etc/pam.d"); - - $pam_php = << User Manager -> Settings."); - $status = htpasswd_backed($username, $passwd); - return $status; - } - - ldap_set_option($ldap, LDAP_OPT_REFERRALS, 0); - ldap_set_option($ldap, LDAP_OPT_PROTOCOL_VERSION, 3); - - /* Make sure we can connect to LDAP */ - putenv('LDAPTLS_REQCERT=never'); - if (!($ldap = ldap_connect($ldapserver))) { - log_error("ERROR! ldap_backed() could not connect to server {$ldapserver} - {$ldapfilter}. Defaulting to built-in htpasswd_backed(). Visit System -> User Manager -> Settings."); - $status = htpasswd_backed($username, $passwd); - return $status; - } - /* ok, its up. now, lets bind as the bind user so we can search it */ - if (!($res = ldap_bind($ldap, $ldapbindun, $ldapbindpw))) { - log_error("ERROR! ldap_backed() could not bind to {$ldapserver} - {$ldapfilter}. Defaulting to built-in htpasswd_backed()"); - ldap_close($ldap); - $status = htpasswd_backed($username, $passwd); - return $status; - } - - /* Get LDAP Authcontainers and split em up. */ - $ldac_split = split(";", $ldapauthcont); - - /* now count how many there are */ - $containers = count($ldac_split); - log_error("Number of Authentication Containers to search for $username is {$containers}"); - - /* setup the usercount so we think we havn't found anyone yet */ - $usercount = 0; - - /******************************/ - /* Currently LDAP Types are */ - /* LDAP = Active Directory */ - /* LDAPOTHER = eDir/Openldap */ - /******************************/ - - /*****************************************************************/ - /* Now Active Directory We keep this seperate for future addons. */ - /*****************************************************************/ - /* Now LDAP other. eDirectory or Netscape or Sunone or OpenLDAP */ - /*****************************************************************/ - /* We First find the user based on username and filter */ - /* Then, once we find the first occurance of that person */ - /* We set seesion variables to ponit to the OU and DN of the */ - /* Person. To later be used by ldap_get_groups. */ - /* that way we don't have to search twice. */ - /*****************************************************************/ - if ($ldaptype == 'ldap'){ - log_error("Now Searching for {$username} in Active directory."); - /* Iterate through the user containers for search */ - for ($i=0;$i<$containers;$i++){ - /* Make sure we just use the first user we find */ - log_error("Now Searching in {$ldac_split[$i]} for {$ldapfilter}."); - $search = ldap_search($ldap,$ldac_split[$i],$ldapfilter); - $info = ldap_get_entries($ldap,$search); - $matches = $info['count']; - log_error("Matches Found = {$matches}"); - if ($matches == 1){ - $_SESSION['ldapdn'] = $info[0]['dn']; - $_SESSION['ldapou'] = $ldac_split[$i]; - $_SESSION['ldapon'] = "true"; - $ldapdn = $_SESSION['ldapdn']; - $userou = $_SESSION['ldapou']; - break; - } - } - - if ($matches == 1){ - $binduser = $adbindas; - log_error("Going to login as {$username} - DN = {$_SESSION['ldapdn']}"); - } - if ($matches != 1){ - log_error("ERROR! Either LDAP search failed, or multiple users were found"); - $status = htpasswd_backed($username, $passwd); - $_SESSION['ldapon'] = "false"; - ldap_close($ldap); - return $status; - } - } - - /*****************************************************************/ - /* Now LDAP other. eDirectory or Netscape or Sunone or OpenLDAP */ - /*****************************************************************/ - /* We First find the user based on username and filter */ - /* Then, once we find the first occurance of that person */ - /* We set seesion variables to ponit to the OU and DN of the */ - /* Person. To later be used by ldap_get_groups. */ - /* that way we don't have to search twice. */ - /*****************************************************************/ - if ($ldaptype == 'ldapother'){ - log_error("Now Searching for {$username} in LDAP."); - /* Iterate through the user containers for search */ - for ($i=0;$i<$containers;$i++){ - /* Make sure we just use the first user we find */ - log_error("Now searching in {$ldac_split[$i]} for {$ldapfilter}."); - $search = ldap_search($ldap,$ldac_split[$i],$ldapfilter); - $info = ldap_get_entries($ldap,$search); - $matches = $info['count']; - log_error("Matches Found = {$matches}."); - - if ($matches == 1){ - $_SESSION['ldapdn'] = $info[0]['dn']; - $_SESSION['ldapou'] = $ldac_split[$i]; - $_SESSION['ldapon'] = "true"; - $ldapdn = $_SESSION['ldapdn']; - $userou = $_SESSION['ldapou']; - break; - } - } - if($matches == 1){ - $binduser = $ldapnameattribute."=".$username.",".$userou; - log_error("Going to login as {$username} - DN = {$_SESSION['ldapdn']}"); - } - if($matches != 1){ - log_error("ERROR! Either LDAP search failed, or multiple users were found"); - $status = htpasswd_backed($username, $passwd); - ldap_close($ldap); - $_SESSION['ldapon'] = "false"; - return $status; - } - } - - /* Now lets bind as the user we found */ - if (!($res = @ldap_bind($ldap, $binduser, $passwd))) { - log_error("ERROR! ldap_backed() could not bind to {$ldapserver} - {$username} - {$passwd}. Defaulting to built-in htpasswd_backed(). Visit System -> User Manager -> Settings."); - $status = htpasswd_backed($username, $passwd); - return $status; - } - - log_error("$binduser succesfully logged in via LDAP."); - - /* At this point we are bound to LDAP so the user was auth'd okay. */ - return true; -} - -function htpasswd_backed($username, $passwd) { - $authfile = file("/var/run/htpasswd"); - - /* sanity check to ensure that /usr/local/www/.htpasswd doesn't exist */ - unlink_if_exists("/usr/local/www/.htpasswd"); - - $matches=""; - if(!($line = array_shift(preg_grep("/^$username:.*$/", $authfile)))) - return false; - - /* Get crypted password */ - preg_match("/^$username:((\\$1\\$[.\d\w_\/]{8}\\$)[.\d\w_\/]{22})$/", $line, $matches); - $pass = $matches[1]; - $salt = $matches[2]; - - /* Encrypt entered password with salt - * And finally validate password - */ - if ($pass == crypt($passwd, $salt)) - return true; - - return false; -} - -function radius_backed($username, $passwd){ - global $config, $debug; - $ret = false; - $radiusservers = $config['system']['radius']['servers']; - - $rauth = new Auth_RADIUS_PAP($username, $passwd); - /* Add a new servers to our instance */ - foreach ($radiusservers as $radsrv) - $rauth->addServer($radsrv['ipaddr'], $radsrv['port'], $radsrv['sharedsecret']); - - if (!$rauth->start()) { - $retvalue['auth_val'] = 1; - $retvalue['error'] = $rauth->getError(); - if ($debug) - printf("Radius start: %s
\n", $retvalue['error']); - } - - // XXX - billm - somewhere in here we need to handle securid challenge/response - - /* Send request */ - $result = $rauth->send(); - if (PEAR::isError($result)) { - $retvalue['auth_val'] = 1; - $retvalue['error'] = $result->getMessage(); - if ($debug) - printf("Radius send failed: %s
\n", $retvalue['error']); - } else if ($result === true) { - $retvalue['auth_val'] = 2; - if ($debug) - printf(gettext("Radius Auth succeeded")."
\n"); - $ret = true; - } else { - $retvalue['auth_val'] = 3; - if ($debug) - printf(gettext("Radius Auth rejected")."
\n"); - } - - // close OO RADIUS_AUTHENTICATION - $rauth->close(); - - return $ret; -} - ?> diff --git a/etc/inc/authgui.inc b/etc/inc/authgui.inc index 7467ccd7be..e370250c8d 100644 --- a/etc/inc/authgui.inc +++ b/etc/inc/authgui.inc @@ -46,7 +46,6 @@ require_once("functions.inc"); * radius_backed - this will allow you to use a radius server * pam_backed - this uses the system's PAM facility .htpasswd file */ -$auth_method="session_auth"; /* enable correct auth backend, default to htpasswd_backed */ $ldapcase = $config['system']['webgui']['backend']; @@ -59,11 +58,11 @@ switch($ldapcase) $backing_method="ldap_backed"; break; default: - $backing_method="htpasswd_backed"; + $backing_method="local_backed"; } /* Authenticate user - exit if failed */ -if (!$auth_method($backing_method)) +if (!session_auth($backing_method)) exit; /* diff --git a/etc/inc/config.inc b/etc/inc/config.inc index f811b53e74..cd9e13de7e 100644 --- a/etc/inc/config.inc +++ b/etc/inc/config.inc @@ -1592,7 +1592,7 @@ function convert_config() { $groups[] = $all; $groups = array_merge($config['system']['group'],$groups); $config['system']['group'] = $groups; - set_local_group($all); + local_group_set($all); $config['version'] = 4.9; } @@ -1643,7 +1643,7 @@ function convert_config() { } /* sync all local account information */ - sync_local_accounts(); + local_sync_accounts(); $config['version'] = 5.0; } diff --git a/etc/inc/pfsense-utils.inc b/etc/inc/pfsense-utils.inc index 9c71b67ccb..f49943a233 100644 --- a/etc/inc/pfsense-utils.inc +++ b/etc/inc/pfsense-utils.inc @@ -2580,36 +2580,6 @@ function reload_interfaces() { touch("/tmp/reload_interfaces"); } -/****f* pfsense-utils/sync_webgui_passwords - * NAME - * sync_webgui_passwords - syncs all www pwdb entries - * INPUTS - * none - * RESULT - * none - ******/ -function sync_webgui_passwords() { - global $config, $g, $groupindex, $userindex; - - conf_mount_rw(); - $fd = fopen("{$g['varrun_path']}/htpasswd", "w"); - - if (!$fd) { - log_error("Error: cannot open htpasswd in sync_webgui_passwords().\n"); - return 1; - } - - /* loop through custom users and add "virtual" entries */ - if ($config['system']['user']) - foreach ($config['system']['user'] as $user) - fwrite($fd, "{$user['name']}:{$user['password']}\n"); - - fclose($fd); - chmod("{$g['varrun_path']}/htpasswd", 0600); - - conf_mount_ro(); -} - /****f* pfsense-utils/reload_all_sync * NAME * reload_all - reload all settings @@ -2693,7 +2663,7 @@ function reload_all_sync() { system_routing_enable(); /* ensure passwords are sync'd */ - system_password_configure(); +// system_password_configure(); /* start dnsmasq service */ services_dnsmasq_configure(); diff --git a/etc/inc/priv.inc b/etc/inc/priv.inc index 917cc00b32..dfacf55926 100644 --- a/etc/inc/priv.inc +++ b/etc/inc/priv.inc @@ -142,7 +142,7 @@ function get_user_privileges(& $user) { if (!is_array($privs)) $privs = array(); - $names = get_local_user_groups($user, true); + $names = local_user_get_groups($user, true); foreach ($names as $name) { $group = getGroupEntry($name); @@ -162,7 +162,7 @@ function get_user_privdesc(& $user) { if (!is_array($user_privs)) $user_privs = array(); - $names = get_local_user_groups($user, true); + $names = local_user_get_groups($user, true); foreach ($names as $name) { $group = getGroupEntry($name); @@ -244,7 +244,7 @@ function getAllowedPages($username) { // obtain local groups if we have a local user if ($local_user) { - $allowed_groups = get_local_user_groups($local_user); + $allowed_groups = local_user_get_groups($local_user); getPrivPages($local_user, $allowed_pages); } diff --git a/etc/inc/system.inc b/etc/inc/system.inc index 24617c9784..c161e8fc36 100644 --- a/etc/inc/system.inc +++ b/etc/inc/system.inc @@ -494,9 +494,6 @@ function system_webgui_start() { sleep(1); - /* generate password file */ - system_password_configure(); - chdir($g['www_path']); /* non-standard port? */ @@ -592,9 +589,6 @@ function system_webgui_start_old() { /* kill any running mini_httpd */ killbypid("{$g['varrun_path']}/mini_httpd.pid"); - /* generate password file */ - system_password_configure(); - chdir($g['www_path']); /* non-standard port? */ @@ -1000,21 +994,6 @@ EOD; } -function system_password_configure() { - global $config, $g; - if(isset($config['system']['developerspew'])) { - $mt = microtime(); - echo "system_password_configure() being called $mt\n"; - } - - /* sync passwords */ - sync_webgui_passwords(); - - /* !NOTE! conf_mount_ro is done by sync_webgui_passwords() */ - - return 0; -} - function system_timezone_configure() { global $config, $g; if(isset($config['system']['developerspew'])) { @@ -1308,4 +1287,4 @@ function enable_watchdog() { } } -?> \ No newline at end of file +?> diff --git a/etc/phpshellsessions/cvssync b/etc/phpshellsessions/cvssync index fdb7159952..6bc1317d65 100644 --- a/etc/phpshellsessions/cvssync +++ b/etc/phpshellsessions/cvssync @@ -148,9 +148,9 @@ function post_cvssync_commands() { echo "===> Upgrading configuration (if needed)...\n"; convert_config(); - + echo "===> Syncing system passwords...\n"; - sync_webgui_passwords(); + local_sync_accounts(); echo "===> Restarting check_reload_status...\n"; exec("killall check_reload_status"); diff --git a/etc/rc.bootup b/etc/rc.bootup index eb9811855b..ec8066c64a 100755 --- a/etc/rc.bootup +++ b/etc/rc.bootup @@ -106,11 +106,6 @@ system_setup_sysctl(); echo "done.\n"; - /* sync user passwords */ - echo "Syncing user passwords..."; - sync_webgui_passwords(); - echo "done.\n"; - echo "Starting Secure Shell Services..."; mwexec_bg("/etc/sshd"); echo "done.\n"; @@ -216,7 +211,7 @@ system_routing_enable(); /* ensure passwords are sync'd */ - system_password_configure(); +// system_password_configure(); /* configure console menu */ system_console_configure(); diff --git a/etc/rc.initial.password b/etc/rc.initial.password index f92055f2bc..82a3eddeb5 100755 --- a/etc/rc.initial.password +++ b/etc/rc.initial.password @@ -41,17 +41,25 @@ The webConfigurator password will be reset to the default (which is "' . strtolo gettext('Do you want to proceed [y|n]?'); if (strcasecmp(chop(fgets($fp)), "y") == 0) { - - foreach ($config['system']['user'] as & $user) { - if (isset($user['uid']) && !$user['uid']) { - $user['name'] = "admin"; - set_local_user($user, strtolower($g['product_name'])); - write_config(gettext("password changed from console menu")); - system_password_configure(); - break; - } + $admin_user =& getUserEntryByUID(0); + if (!$admin_user) { + echo "Failed to locate the admin user account! Attempting to restore access.\n"; + $admin_user = array(); + $admin_user['uid'] = 0; + $admin_user['priv'] = explode(",", "user-shell-access,page-all"); + if (!is_array($config['system']['user'])) + $config['system']['user'] = array(); + $config['system']['user'][] = $admin_user; } + $admin_user['name'] = "admin"; + $admin_user['scope'] = "system"; + $admin_user['blah'] = "set by console"; + + local_user_set_password($admin_user, strtolower($g['product_name'])); + local_user_set($admin_user); + write_config(gettext("password changed from console menu")); + echo "\n" . gettext(' The password for the webConfigurator has been reset and the default username has been set to "admin".') . "\n" . diff --git a/etc/sshd b/etc/sshd index e2264cd660..f9c0405003 100755 --- a/etc/sshd +++ b/etc/sshd @@ -65,9 +65,6 @@ touch("/var/log/lastlog"); } - /* reset passwords */ - sync_webgui_passwords(); - $sshConfigDir = "/etc/ssh"; if($config['system']['ssh']['port'] <> "") { diff --git a/usr/local/www/pkg_mgr_install.php b/usr/local/www/pkg_mgr_install.php index 359d5755dd..20d2dded08 100755 --- a/usr/local/www/pkg_mgr_install.php +++ b/usr/local/www/pkg_mgr_install.php @@ -119,9 +119,6 @@ ob_flush(); /* mount rw fs */ conf_mount_rw(); -/* resync password database to avoid out of sync issues */ -sync_webgui_passwords(); - switch($_GET['mode']) { case "delete": $id = get_pkg_id($_GET['pkg']); diff --git a/usr/local/www/system.php b/usr/local/www/system.php index b04e9ce2d5..8abaf4d26d 100755 --- a/usr/local/www/system.php +++ b/usr/local/www/system.php @@ -117,9 +117,6 @@ if ($_POST) { ($_POST['webguiport'] < 1) || ($_POST['webguiport'] > 65535))) { $input_errors[] = "A valid TCP/IP port must be specified for the webConfigurator port."; } - if (($_POST['password']) && ($_POST['password'] != $_POST['password2'])) { - $input_errors[] = "The passwords do not match."; - } $t = (int)$_POST['timeupdateinterval']; if (($t < 0) || (($t > 0) && ($t < 6)) || ($t > 1440)) { @@ -163,12 +160,6 @@ if ($_POST) { unset($config['system']['dnsallowoverride']); $config['system']['dnsallowoverride'] = $_POST['dnsallowoverride'] ? true : false; - if ($_POST['password']) { - $config['system']['password'] = crypt($_POST['password']); - update_changedesc("password changed via webConfigurator"); - sync_webgui_passwords(); - } - /* which interface should the dns servers resolve through? */ if($_POST['dns1gwint']) $config['system']['dns1gwint'] = $pconfig['dns1gwint']; @@ -205,7 +196,6 @@ if ($_POST) { $retval = system_hostname_configure(); $retval |= system_hosts_generate(); $retval |= system_resolvconf_generate(); - $retval |= system_password_configure(); $retval |= services_dnsmasq_configure(); $retval |= system_timezone_configure(); $retval |= system_ntp_configure(); diff --git a/usr/local/www/system_groupmanager.php b/usr/local/www/system_groupmanager.php index e79a77ff49..d2ab78e004 100644 --- a/usr/local/www/system_groupmanager.php +++ b/usr/local/www/system_groupmanager.php @@ -63,7 +63,7 @@ if ($_GET['act'] == "delgroup") { exit; } - del_local_group($a_group[$_GET['id']]); + local_group_del($a_group[$_GET['id']]); $groupdeleted = $a_group[$_GET['id']]['name']; unset($a_group[$_GET['id']]); write_config(); @@ -84,7 +84,7 @@ if ($_GET['act'] == "delpriv") { foreach ($a_group[$id]['member'] as $uid) { $user = getUserEntryByUID($uid); if ($user) - set_local_user($user); + local_user_set($user); } write_config(); @@ -146,7 +146,7 @@ if ($_POST) { $a_group[] = $group; } - set_local_group($group); + local_group_set($group); write_config(); header("Location: system_groupmanager.php"); diff --git a/usr/local/www/system_groupmanager_addprivs.php b/usr/local/www/system_groupmanager_addprivs.php index 6c808be6c4..a449b2de28 100644 --- a/usr/local/www/system_groupmanager_addprivs.php +++ b/usr/local/www/system_groupmanager_addprivs.php @@ -85,7 +85,7 @@ if ($_POST) { foreach ($a_group['member'] as $uid) { $user = getUserEntryByUID($uid); if ($user) - set_local_user($user); + local_user_set($user); } $retval = write_config(); diff --git a/usr/local/www/system_usermanager.php b/usr/local/www/system_usermanager.php index 791fae605a..0b8f76e120 100644 --- a/usr/local/www/system_usermanager.php +++ b/usr/local/www/system_usermanager.php @@ -67,11 +67,10 @@ if (isAllowedPage("system_usermanager")) { exit; } - del_local_user($a_user[$_GET['id']]); + local_user_del($a_user[$_GET['id']]); $userdeleted = $a_user[$_GET['id']]['name']; unset($a_user[$_GET['id']]); write_config(); - $retval = system_password_configure(); $savemsg = gettext("User")." {$userdeleted} ". gettext("successfully deleted")."
"; } @@ -96,7 +95,7 @@ if (isAllowedPage("system_usermanager")) { if (isset($id) && $a_user[$id]) { $pconfig['usernamefld'] = $a_user[$id]['name']; $pconfig['fullname'] = $a_user[$id]['fullname']; - $pconfig['groups'] = get_local_user_groups($a_user[$id]); + $pconfig['groups'] = local_user_get_groups($a_user[$id]); $pconfig['utype'] = $a_user[$id]['scope']; $pconfig['uid'] = $a_user[$id]['uid']; $pconfig['authorizedkeys'] = base64_decode($a_user[$id]['authorizedkeys']); @@ -163,10 +162,14 @@ if (isAllowedPage("system_usermanager")) { if (isset($id) && $a_user[$id]) $userent = $a_user[$id]; - /* the user did change his username */ + /* the user name was modified */ if ($_POST['usernamefld'] <> $_POST['oldusername']) $_SERVER['REMOTE_USER'] = $_POST['usernamefld']; + /* the user password was mofified */ + if ($_POST['passwordfld1']) + local_user_set_password($userent, $_POST['passwordfld1']); + $userent['name'] = $_POST['usernamefld']; $userent['fullname'] = $_POST['fullname']; @@ -182,10 +185,9 @@ if (isAllowedPage("system_usermanager")) { $a_user[] = $userent; } - set_local_user($userent, $_POST['passwordfld1']); - set_local_user_groups($userent,$_POST['groups']); + local_user_set($userent); + local_user_set_groups($userent,$_POST['groups']); write_config(); - $retval = system_password_configure(); pfSenseHeader("system_usermanager.php"); } @@ -488,7 +490,7 @@ function presubmit() {   - +   @@ -563,10 +565,6 @@ function presubmit() { $config['system']['user'][$userindex[$HTTP_SERVER_VARS['AUTH_USER']]]['password'] = crypt(trim($_POST['passwordfld1'])); write_config(); - - sync_webgui_passwords(); - - $retval = system_password_configure(); $savemsg = "Password successfully changed
"; } } diff --git a/usr/local/www/system_usermanager_addprivs.php b/usr/local/www/system_usermanager_addprivs.php index 61758b718a..0214d63a52 100644 --- a/usr/local/www/system_usermanager_addprivs.php +++ b/usr/local/www/system_usermanager_addprivs.php @@ -86,7 +86,7 @@ if ($_POST) { else $a_user['priv'] = array_merge($a_user['priv'], $pconfig['sysprivs']); - set_local_user($a_user); + local_user_set($a_user); $retval = write_config(); $savemsg = get_std_save_message($retval); diff --git a/usr/local/www/system_usermanager_settings.php b/usr/local/www/system_usermanager_settings.php index c1d3a71f11..90e6598692 100755 --- a/usr/local/www/system_usermanager_settings.php +++ b/usr/local/www/system_usermanager_settings.php @@ -126,12 +126,8 @@ if ($_POST) { else unset($pconfig['ldapgroupattribute']); - write_config(); - $retval = system_password_configure(); - sync_webgui_passwords(); - } } diff --git a/usr/local/www/wizards/setup_wizard.xml b/usr/local/www/wizards/setup_wizard.xml index e6b46bc5ef..1cf882cb72 100644 --- a/usr/local/www/wizards/setup_wizard.xml +++ b/usr/local/www/wizards/setup_wizard.xml @@ -418,14 +418,10 @@ if($_POST['adminpassword'] != "") { if($_POST['adminpassword'] == $_POST['adminpasswordagain']) { - $fd = popen("/usr/sbin/pw usermod -n root -H 0", "w"); - $salt = md5(time()); - $crypted_pw = crypt($_POST['adminpassword'],$salt); - fwrite($fd, $crypted_pw); - pclose($fd); - $config['system']['password'] = crypt($_POST['adminpassword']); + $admin_user =& getUserEntryByUID(0); + local_user_set_password($admin_user, $_POST['adminpassword']); + local_user_set($admin_user); write_config(); - system_password_configure(); } else { print_info_box_np("Passwords do not match! Please press back in your browser window and correct."); die;