2012-02-12 17:41:28 +01:00
< ? php
/* Copyright ( C ) 2008 - 2011 Laurent Destailleur < eldy @ users . sourceforge . net >
2012-12-30 15:11:07 +01:00
* Copyright ( C ) 2008 - 2012 Regis Houssin < regis . houssin @ capnetworks . com >
2012-02-12 17:41:28 +01:00
*
* This program is free software ; you can redistribute it and / or modify
* it under the terms of the GNU General Public License as published by
2013-01-16 15:36:08 +01:00
* the Free Software Foundation ; either version 3 of the License , or
2012-02-12 17:41:28 +01:00
* ( at your option ) any later version .
*
* This program is distributed in the hope that it will be useful ,
* but WITHOUT ANY WARRANTY ; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE . See the
* GNU General Public License for more details .
*
* You should have received a copy of the GNU General Public License
* along with this program . If not , see < http :// www . gnu . org / licenses />.
* or see http :// www . gnu . org /
*/
/**
* \file htdocs / core / lib / security2 . lib . php
* \ingroup core
* \brief Set of function used for dolibarr security ( not common functions ) .
* Warning , this file must not depends on other library files , except function . lib . php
* because it is used at low code level .
*/
2012-02-12 20:34:40 +01:00
/**
* Return user / group account of web server
*
* @ param string $mode 'user' or 'group'
* @ return string Return user or group of web server
*/
function dol_getwebuser ( $mode )
{
$t = '?' ;
if ( $mode == 'user' ) $t = getenv ( 'APACHE_RUN_USER' ); // $_ENV['APACHE_RUN_USER'] is empty
if ( $mode == 'group' ) $t = getenv ( 'APACHE_RUN_GROUP' );
return $t ;
}
2012-02-12 17:41:28 +01:00
/**
* Return a login if login / pass was successfull
*
* @ param string $usertotest Login value to test
* @ param string $passwordtotest Password value to test
* @ param string $entitytotest Instance of data we must check
* @ param array $authmode Array list of selected authentication mode array ( 'http' , 'dolibarr' , 'xxx' ... )
* @ return string Login or ''
*/
function checkLoginPassEntity ( $usertotest , $passwordtotest , $entitytotest , $authmode )
{
global $conf , $langs ;
2012-06-14 14:08:29 +02:00
//global $dolauthmode; // To return authentication finally used
2012-02-12 17:41:28 +01:00
2012-07-07 12:15:43 +02:00
// Check parameters
2012-02-12 17:41:28 +01:00
if ( $entitytotest == '' ) $entitytotest = 1 ;
dol_syslog ( " checkLoginPassEntity usertotest= " . $usertotest . " entitytotest= " . $entitytotest . " authmode= " . join ( ',' , $authmode ));
$login = '' ;
// Validation of login/pass/entity with standard modules
if ( empty ( $login ))
{
$test = true ;
foreach ( $authmode as $mode )
{
if ( $test && $mode && ! $login )
{
2012-06-14 14:08:29 +02:00
// Validation of login/pass/entity for mode $mode
2012-02-12 17:41:28 +01:00
$mode = trim ( $mode );
2012-06-14 14:08:29 +02:00
$authfile = 'functions_' . $mode . '.php' ;
$fullauthfile = '' ;
2012-07-02 19:30:37 +02:00
$dirlogin = array_merge ( array ( " /core/login " ),( array ) $conf -> modules_parts [ 'login' ]);
foreach ( $dirlogin as $reldir )
{
$dir = dol_buildpath ( $reldir , 0 );
$newdir = dol_osencode ( $dir );
// Check if file found (do not use dol_is_file to avoid loading files.lib.php)
2012-06-14 14:08:29 +02:00
if ( is_file ( $newdir . '/' . $authfile )) $fullauthfile = $newdir . '/' . $authfile ;
}
$result = false ;
2012-08-23 02:04:35 +02:00
if ( $fullauthfile ) $result = include_once $fullauthfile ;
2012-06-14 14:08:29 +02:00
if ( $fullauthfile && $result )
2012-02-12 17:41:28 +01:00
{
// Call function to check user/password
$function = 'check_user_password_' . $mode ;
$login = call_user_func ( $function , $usertotest , $passwordtotest , $entitytotest );
if ( $login ) // Login is successfull
{
$test = false ; // To stop once at first login success
$conf -> authmode = $mode ; // This properties is defined only when logged to say what mode was successfully used
2012-07-13 10:15:47 +02:00
$dol_tz = GETPOST ( 'tz' );
$dol_dst = GETPOST ( 'dst' );
$dol_screenwidth = GETPOST ( 'screenwidth' );
$dol_screenheight = GETPOST ( 'screenheight' );
2012-02-12 17:41:28 +01:00
}
}
else
{
dol_syslog ( " Authentification ko - failed to load file ' " . $authfile . " ' " , LOG_ERR );
sleep ( 1 );
$langs -> load ( 'main' );
$langs -> load ( 'other' );
2016-09-02 22:34:37 +02:00
$langs -> load ( 'errors' );
2012-02-12 17:41:28 +01:00
$_SESSION [ " dol_loginmesg " ] = $langs -> trans ( " ErrorFailedToLoadLoginFileForMode " , $mode );
}
}
}
}
return $login ;
}
/**
2012-02-18 17:10:29 +01:00
* Show Dolibarr default login page .
* Part of this code is also duplicated into main . inc . php :: top_htmlhead
2012-02-12 17:41:28 +01:00
*
2012-02-18 17:10:29 +01:00
* @ param Translate $langs Lang object ( must be initialized by a new ) .
* @ param Conf $conf Conf object
* @ param Societe $mysoc Company object
* @ return void
2012-02-12 17:41:28 +01:00
*/
function dol_loginfunction ( $langs , $conf , $mysoc )
{
global $dolibarr_main_demo , $db ;
2012-03-03 20:05:32 +01:00
global $smartphone , $hookmanager ;
2012-04-18 14:27:31 +02:00
2012-07-02 19:30:37 +02:00
// Instantiate hooks of thirdparty module only if not already define
2012-03-03 20:05:32 +01:00
$hookmanager -> initHooks ( array ( 'mainloginpage' ));
2012-02-12 17:41:28 +01:00
$langs -> load ( " main " );
$langs -> load ( " other " );
$langs -> load ( " help " );
$langs -> load ( " admin " );
$main_authentication = $conf -> file -> main_authentication ;
$session_name = session_name ();
$dol_url_root = DOL_URL_ROOT ;
$php_self = $_SERVER [ 'PHP_SELF' ];
$php_self .= $_SERVER [ " QUERY_STRING " ] ? '?' . $_SERVER [ " QUERY_STRING " ] : '' ;
2013-02-24 13:57:17 +01:00
if ( ! preg_match ( '/mainmenu=/' , $php_self )) $php_self .= ( preg_match ( '/\?/' , $php_self ) ? '&' : '?' ) . 'mainmenu=home' ;
2012-02-12 17:41:28 +01:00
// Title
2015-11-13 10:37:51 +01:00
$appli = constant ( 'DOL_APPLICATION_TITLE' );
$title = $appli . ' ' . DOL_VERSION ;
2012-02-12 17:41:28 +01:00
if ( ! empty ( $conf -> global -> MAIN_APPLICATION_TITLE )) $title = $conf -> global -> MAIN_APPLICATION_TITLE ;
2015-11-13 10:37:51 +01:00
$titletruedolibarrversion = DOL_VERSION ; // $title used by login template after the @ to inform of true Dolibarr version
2012-02-12 17:41:28 +01:00
2013-01-08 15:21:56 +01:00
// Note: $conf->css looks like '/theme/eldy/style.css.php'
$conf -> css = " /theme/ " . ( GETPOST ( 'theme' ) ? GETPOST ( 'theme' , 'alpha' ) : $conf -> theme ) . " /style.css.php " ;
2013-08-07 20:56:10 +02:00
//$themepath=dol_buildpath((empty($conf->global->MAIN_FORCETHEMEDIR)?'':$conf->global->MAIN_FORCETHEMEDIR).$conf->css,1);
$themepath = dol_buildpath ( $conf -> css , 1 );
2013-01-10 08:27:12 +01:00
if ( ! empty ( $conf -> modules_parts [ 'theme' ])) // Using this feature slow down application
{
foreach ( $conf -> modules_parts [ 'theme' ] as $reldir )
{
if ( file_exists ( dol_buildpath ( $reldir . $conf -> css , 0 )))
{
$themepath = dol_buildpath ( $reldir . $conf -> css , 1 );
break ;
}
}
2013-01-08 15:21:56 +01:00
}
$conf_css = $themepath . " ?lang= " . $langs -> defaultlang ;
2012-02-12 17:41:28 +01:00
2013-01-10 08:27:12 +01:00
// Select templates
2013-04-03 15:20:56 +02:00
if ( ! empty ( $conf -> modules_parts [ 'tpl' ])) // Using this feature slow down application
2013-01-10 08:27:12 +01:00
{
2013-04-03 15:20:56 +02:00
$dirtpls = array_merge ( $conf -> modules_parts [ 'tpl' ], array ( '/core/tpl/' ));
foreach ( $dirtpls as $reldir )
{
$tmp = dol_buildpath ( $reldir . 'login.tpl.php' );
if ( file_exists ( $tmp )) { $template_dir = preg_replace ( '/login\.tpl\.php$/' , '' , $tmp ); break ; }
}
2013-01-10 08:27:12 +01:00
}
else
2013-01-08 18:30:49 +01:00
{
2013-04-03 15:20:56 +02:00
$template_dir = DOL_DOCUMENT_ROOT . " /core/tpl/ " ;
2013-01-10 08:27:12 +01:00
}
2013-02-24 13:57:17 +01:00
2012-02-12 17:41:28 +01:00
// Set cookie for timeout management
$prefix = dol_getprefix ();
$sessiontimeout = 'DOLSESSTIMEOUT_' . $prefix ;
if ( ! empty ( $conf -> global -> MAIN_SESSION_TIMEOUT )) setcookie ( $sessiontimeout , $conf -> global -> MAIN_SESSION_TIMEOUT , 0 , " / " , '' , 0 );
2012-02-28 19:18:24 +01:00
if ( GETPOST ( 'urlfrom' , 'alpha' )) $_SESSION [ " urlfrom " ] = GETPOST ( 'urlfrom' , 'alpha' );
2012-02-12 17:41:28 +01:00
else unset ( $_SESSION [ " urlfrom " ]);
if ( ! GETPOST ( " username " )) $focus_element = 'username' ;
else $focus_element = 'password' ;
$login_background = DOL_URL_ROOT . '/theme/login_background.png' ;
if ( file_exists ( DOL_DOCUMENT_ROOT . '/theme/' . $conf -> theme . '/img/login_background.png' ))
{
$login_background = DOL_URL_ROOT . '/theme/' . $conf -> theme . '/img/login_background.png' ;
}
$demologin = '' ;
$demopassword = '' ;
if ( ! empty ( $dolibarr_main_demo ))
{
$tab = explode ( ',' , $dolibarr_main_demo );
$demologin = $tab [ 0 ];
$demopassword = $tab [ 1 ];
}
2012-04-18 14:27:31 +02:00
2012-03-03 20:05:32 +01:00
// Execute hook getLoginPageOptions
2012-07-02 19:30:37 +02:00
// Should be an array with differents options in $hookmanager->resArray
2012-07-13 10:15:47 +02:00
$parameters = array ( 'entity' => GETPOST ( 'entity' , 'int' ));
2015-06-27 02:19:46 +02:00
$reshook = $hookmanager -> executeHooks ( 'getLoginPageOptions' , $parameters ); // Note that $action and $object may have been modified by some hooks. resArray is filled by hook.
2012-02-12 17:41:28 +01:00
// Login
2012-09-08 15:18:14 +02:00
$login = ( ! empty ( $hookmanager -> resArray [ 'username' ]) ? $hookmanager -> resArray [ 'username' ] : ( GETPOST ( " username " , " alpha " ) ? GETPOST ( " username " , " alpha " ) : $demologin ));
2012-02-12 17:41:28 +01:00
$password = $demopassword ;
// Show logo (search in order: small company logo, large company logo, theme logo, common logo)
$width = 0 ;
$urllogo = DOL_URL_ROOT . '/theme/login_logo.png' ;
if ( ! empty ( $mysoc -> logo_small ) && is_readable ( $conf -> mycompany -> dir_output . '/logos/thumbs/' . $mysoc -> logo_small ))
{
$urllogo = DOL_URL_ROOT . '/viewimage.php?cache=1&modulepart=companylogo&file=' . urlencode ( 'thumbs/' . $mysoc -> logo_small );
}
elseif ( ! empty ( $mysoc -> logo ) && is_readable ( $conf -> mycompany -> dir_output . '/logos/' . $mysoc -> logo ))
{
$urllogo = DOL_URL_ROOT . '/viewimage.php?cache=1&modulepart=companylogo&file=' . urlencode ( $mysoc -> logo );
$width = 128 ;
}
elseif ( is_readable ( DOL_DOCUMENT_ROOT . '/theme/' . $conf -> theme . '/img/dolibarr_logo.png' ))
{
$urllogo = DOL_URL_ROOT . '/theme/' . $conf -> theme . '/img/dolibarr_logo.png' ;
}
elseif ( is_readable ( DOL_DOCUMENT_ROOT . '/theme/dolibarr_logo.png' ))
{
$urllogo = DOL_URL_ROOT . '/theme/dolibarr_logo.png' ;
}
// Security graphical code
$captcha = 0 ;
$captcha_refresh = '' ;
if ( function_exists ( " imagecreatefrompng " ) && ! empty ( $conf -> global -> MAIN_SECURITY_ENABLECAPTCHA ))
{
$captcha = 1 ;
2012-02-19 13:55:29 +01:00
$captcha_refresh = img_picto ( $langs -> trans ( " Refresh " ), 'refresh' , 'id="captcha_refresh_img"' );
2012-02-12 17:41:28 +01:00
}
// Extra link
$forgetpasslink = 0 ;
$helpcenterlink = 0 ;
if ( empty ( $conf -> global -> MAIN_SECURITY_DISABLEFORGETPASSLINK ) || empty ( $conf -> global -> MAIN_HELPCENTER_DISABLELINK ))
{
if ( empty ( $conf -> global -> MAIN_SECURITY_DISABLEFORGETPASSLINK ))
{
$forgetpasslink = 1 ;
}
if ( empty ( $conf -> global -> MAIN_HELPCENTER_DISABLELINK ))
{
$helpcenterlink = 1 ;
}
}
// Home message
2012-09-27 11:54:51 +02:00
$main_home = '' ;
2012-02-12 17:41:28 +01:00
if ( ! empty ( $conf -> global -> MAIN_HOME ))
{
$i = 0 ;
2013-07-02 21:53:34 +02:00
while ( preg_match ( '/__\(([a-zA-Z|@]+)\)__/i' , $conf -> global -> MAIN_HOME , $reg ) && $i < 100 )
2012-02-12 17:41:28 +01:00
{
2013-07-02 21:53:34 +02:00
$tmp = explode ( '|' , $reg [ 1 ]);
if ( ! empty ( $tmp [ 1 ])) $langs -> load ( $tmp [ 1 ]);
$conf -> global -> MAIN_HOME = preg_replace ( '/__\(' . preg_quote ( $reg [ 1 ]) . '\)__/i' , $langs -> trans ( $tmp [ 0 ]), $conf -> global -> MAIN_HOME );
2012-02-12 17:41:28 +01:00
$i ++ ;
}
2012-09-27 11:54:51 +02:00
$main_home = dol_htmlcleanlastbr ( $conf -> global -> MAIN_HOME );
2012-02-12 17:41:28 +01:00
}
// Google AD
$main_google_ad_client = (( ! empty ( $conf -> global -> MAIN_GOOGLE_AD_CLIENT ) && ! empty ( $conf -> global -> MAIN_GOOGLE_AD_SLOT )) ? 1 : 0 );
2013-02-24 18:16:26 +01:00
// Set jquery theme
2012-07-13 10:15:47 +02:00
$dol_loginmesg = ( ! empty ( $_SESSION [ " dol_loginmesg " ]) ? $_SESSION [ " dol_loginmesg " ] : '' );
2014-05-24 18:21:05 +02:00
$favicon = dol_buildpath ( '/theme/' . $conf -> theme . '/img/favicon.ico' , 1 );
2014-03-05 17:26:59 +01:00
if ( ! empty ( $conf -> global -> MAIN_FAVICON_URL )) $favicon = $conf -> global -> MAIN_FAVICON_URL ;
2012-02-18 17:10:29 +01:00
$jquerytheme = 'smoothness' ;
2012-07-13 10:15:47 +02:00
if ( ! empty ( $conf -> global -> MAIN_USE_JQUERY_THEME )) $jquerytheme = $conf -> global -> MAIN_USE_JQUERY_THEME ;
2012-02-18 17:10:29 +01:00
2013-04-03 15:20:56 +02:00
// Set dol_hide_topmenu, dol_hide_leftmenu, dol_optimize_smallscreen, dol_nomousehover
2014-06-09 12:34:10 +02:00
$dol_hide_topmenu = GETPOST ( 'dol_hide_topmenu' , 'int' );
$dol_hide_leftmenu = GETPOST ( 'dol_hide_leftmenu' , 'int' );
$dol_optimize_smallscreen = GETPOST ( 'dol_optimize_smallscreen' , 'int' );
$dol_no_mouse_hover = GETPOST ( 'dol_no_mouse_hover' , 'int' );
$dol_use_jmobile = GETPOST ( 'dol_use_jmobile' , 'int' );
2012-02-12 17:41:28 +01:00
2013-02-24 18:16:26 +01:00
// Include login page template
include $template_dir . 'login.tpl.php' ;
2012-02-12 17:41:28 +01:00
2012-02-18 17:10:29 +01:00
2012-02-12 17:41:28 +01:00
$_SESSION [ " dol_loginmesg " ] = '' ;
}
/**
* Fonction pour initialiser un salt pour la fonction crypt .
*
* @ param int $type 2 => renvoi un salt pour cryptage DES
* 12 => renvoi un salt pour cryptage MD5
* non defini => renvoi un salt pour cryptage par defaut
* @ return string Salt string
*/
function makesalt ( $type = CRYPT_SALT_LENGTH )
{
dol_syslog ( " makesalt type= " . $type );
switch ( $type )
{
case 12 : // 8 + 4
$saltlen = 8 ; $saltprefix = '$1$' ; $saltsuffix = '$' ; break ;
case 8 : // 8 (Pour compatibilite, ne devrait pas etre utilise)
$saltlen = 8 ; $saltprefix = '$1$' ; $saltsuffix = '$' ; break ;
case 2 : // 2
default : // by default, fall back on Standard DES (should work everywhere)
$saltlen = 2 ; $saltprefix = '' ; $saltsuffix = '' ; break ;
}
$salt = '' ;
while ( dol_strlen ( $salt ) < $saltlen ) $salt .= chr ( mt_rand ( 64 , 126 ));
$result = $saltprefix . $salt . $saltsuffix ;
dol_syslog ( " makesalt return= " . $result );
return $result ;
}
/**
* Encode or decode database password in config file
*
* @ param int $level Encode level : 0 no encoding , 1 encoding
* @ return int < 0 if KO , > 0 if OK
*/
function encodedecode_dbpassconf ( $level = 0 )
{
dol_syslog ( " encodedecode_dbpassconf level= " . $level , LOG_DEBUG );
$config = '' ;
$passwd = '' ;
$passwd_crypted = '' ;
if ( $fp = fopen ( DOL_DOCUMENT_ROOT . '/conf/conf.php' , 'r' ))
{
while ( ! feof ( $fp ))
{
$buffer = fgets ( $fp , 4096 );
$lineofpass = 0 ;
if ( preg_match ( '/^[^#]*dolibarr_main_db_encrypted_pass[\s]*=[\s]*(.*)/i' , $buffer , $reg )) // Old way to save crypted value
{
$val = trim ( $reg [ 1 ]); // This also remove CR/LF
$val = preg_replace ( '/^["\']/' , '' , $val );
$val = preg_replace ( '/["\'][\s;]*$/' , '' , $val );
if ( ! empty ( $val ))
{
$passwd_crypted = $val ;
$val = dol_decode ( $val );
$passwd = $val ;
$lineofpass = 1 ;
}
}
elseif ( preg_match ( '/^[^#]*dolibarr_main_db_pass[\s]*=[\s]*(.*)/i' , $buffer , $reg ))
{
$val = trim ( $reg [ 1 ]); // This also remove CR/LF
$val = preg_replace ( '/^["\']/' , '' , $val );
$val = preg_replace ( '/["\'][\s;]*$/' , '' , $val );
if ( preg_match ( '/crypted:/i' , $buffer ))
{
$val = preg_replace ( '/crypted:/i' , '' , $val );
$passwd_crypted = $val ;
$val = dol_decode ( $val );
$passwd = $val ;
}
else
{
$passwd = $val ;
$val = dol_encode ( $val );
$passwd_crypted = $val ;
}
$lineofpass = 1 ;
}
// Output line
if ( $lineofpass )
{
// Add value at end of file
if ( $level == 0 )
{
$config .= '$dolibarr_main_db_pass=\'' . $passwd . '\';' . " \n " ;
}
if ( $level == 1 )
{
$config .= '$dolibarr_main_db_pass=\'crypted:' . $passwd_crypted . '\';' . " \n " ;
}
//print 'passwd = '.$passwd.' - passwd_crypted = '.$passwd_crypted;
//exit;
}
else
{
$config .= $buffer ;
}
}
fclose ( $fp );
// Write new conf file
$file = DOL_DOCUMENT_ROOT . '/conf/conf.php' ;
if ( $fp = @ fopen ( $file , 'w' ))
{
fputs ( $fp , $config );
2015-09-30 19:15:45 +02:00
fflush ( $fp );
2012-02-12 17:41:28 +01:00
fclose ( $fp );
2015-09-30 19:15:45 +02:00
clearstatcache ();
2012-02-12 17:41:28 +01:00
// It's config file, so we set read permission for creator only.
// Should set permission to web user and groups for users used by batch
//@chmod($file, octdec('0600'));
return 1 ;
}
else
{
dol_syslog ( " encodedecode_dbpassconf Failed to open conf.php file for writing " , LOG_WARNING );
return - 1 ;
}
}
else
{
dol_syslog ( " encodedecode_dbpassconf Failed to read conf.php " , LOG_ERR );
return - 2 ;
}
}
/**
* Return a generated password using default module
*
2015-08-26 11:24:31 +02:00
* @ param boolean $generic true = Create generic password ( use md5 , sha1 depending on setup ), false = Use the configured password generation module
2012-02-12 17:41:28 +01:00
* @ return string New value for password
*/
function getRandomPassword ( $generic = false )
{
global $db , $conf , $langs , $user ;
$generated_password = '' ;
if ( $generic ) $generated_password = dol_hash ( mt_rand ());
2012-09-15 10:01:35 +02:00
else if ( ! empty ( $conf -> global -> USER_PASSWORD_GENERATED ))
2012-02-12 17:41:28 +01:00
{
$nomclass = " modGeneratePass " . ucfirst ( $conf -> global -> USER_PASSWORD_GENERATED );
$nomfichier = $nomclass . " .class.php " ;
//print DOL_DOCUMENT_ROOT."/core/modules/security/generate/".$nomclass;
2012-08-22 23:11:24 +02:00
require_once DOL_DOCUMENT_ROOT . " /core/modules/security/generate/ " . $nomfichier ;
2012-02-12 17:41:28 +01:00
$genhandler = new $nomclass ( $db , $conf , $langs , $user );
$generated_password = $genhandler -> getNewGeneratedPassword ();
unset ( $genhandler );
}
return $generated_password ;
}